Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat: implement app-auth-client endpoint #1607

Merged
merged 9 commits into from
Feb 25, 2024
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
import { renderObject } from '../../../../../helpers/renderer.js';
import AppAuthClient from '../../../../../models/app-auth-client.js';

export default async (request, response) => {
const appAuthClient = await AppAuthClient.query()
.findById(request.params.appAuthClientId)
.throwIfNotFound();

renderObject(response, appAuthClient);
};
Original file line number Diff line number Diff line change
@@ -0,0 +1,35 @@
import { vi, describe, it, expect, beforeEach } from 'vitest';
import request from 'supertest';
import app from '../../../../../app.js';
import createAuthTokenByUserId from '../../../../../helpers/create-auth-token-by-user-id.js';
import { createUser } from '../../../../../../test/factories/user.js';
import getAdminAppAuthClientMock from '../../../../../../test/mocks/rest/api/v1/admin/get-app-auth-client.js';
import { createAppAuthClient } from '../../../../../../test/factories/app-auth-client.js';
import { createRole } from '../../../../../../test/factories/role.js';
import * as license from '../../../../../helpers/license.ee.js';

describe('GET /api/v1/admin/app-auth-clients/:appAuthClientId', () => {
let currentUser, currentUserRole, currentAppAuthClient, token;

describe('with valid license key', () => {
beforeEach(async () => {
vi.spyOn(license, 'hasValidLicense').mockResolvedValue(true);

currentUserRole = await createRole({ key: 'admin' });
currentUser = await createUser({ roleId: currentUserRole.id });
currentAppAuthClient = await createAppAuthClient();

token = createAuthTokenByUserId(currentUser.id);
});

it('should return specified app auth client info', async () => {
const response = await request(app)
.get(`/api/v1/admin/app-auth-clients/${currentAppAuthClient.id}`)
.set('Authorization', token)
.expect(200);

const expectedPayload = getAdminAppAuthClientMock(currentAppAuthClient);
expect(response.body).toEqual(expectedPayload);
});
});
});
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
import { renderObject } from '../../../../helpers/renderer.js';
import AppAuthClient from '../../../../models/app-auth-client.js';

export default async (request, response) => {
const appAuthClient = await AppAuthClient.query()
.findById(request.params.appAuthClientId)
.where({ active: true })
.throwIfNotFound();

renderObject(response, appAuthClient);
};
Original file line number Diff line number Diff line change
@@ -0,0 +1,31 @@
import { vi, describe, it, expect, beforeEach } from 'vitest';
import request from 'supertest';
import app from '../../../../app.js';
import createAuthTokenByUserId from '../../../../helpers/create-auth-token-by-user-id.js';
import { createUser } from '../../../../../test/factories/user.js';
import getAppAuthClientMock from '../../../../../test/mocks/rest/api/v1/admin/get-app-auth-client.js';
import { createAppAuthClient } from '../../../../../test/factories/app-auth-client.js';
import * as license from '../../../../helpers/license.ee.js';

describe('GET /api/v1/app-auth-clients/:id', () => {
let currentUser, currentAppAuthClient, token;

beforeEach(async () => {
vi.spyOn(license, 'hasValidLicense').mockResolvedValue(true);

currentUser = await createUser();
currentAppAuthClient = await createAppAuthClient();

token = createAuthTokenByUserId(currentUser.id);
});

it('should return specified app auth client info', async () => {
const response = await request(app)
.get(`/api/v1/app-auth-clients/${currentAppAuthClient.id}`)
.set('Authorization', token)
.expect(200);

const expectedPayload = getAppAuthClientMock(currentAppAuthClient);
expect(response.body).toEqual(expectedPayload);
});
});
17 changes: 17 additions & 0 deletions packages/backend/src/routes/api/v1/admin/app-auth-clients.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
import { Router } from 'express';
import { authenticateUser } from '../../../../helpers/authentication.js';
import { authorizeAdmin } from '../../../../helpers/authorization.js';
import { checkIsEnterprise } from '../../../../helpers/check-is-enterprise.js';
import getAdminAppAuthClientsAction from '../../../../controllers/api/v1/admin/app-auth-clients/get-app-auth-client.js';

const router = Router();

router.get(
'/:appAuthClientId',
authenticateUser,
authorizeAdmin,
checkIsEnterprise,
getAdminAppAuthClientsAction
);

export default router;
15 changes: 15 additions & 0 deletions packages/backend/src/routes/api/v1/app-auth-clients.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
import { Router } from 'express';
import { authenticateUser } from '../../../helpers/authentication.js';
import { checkIsEnterprise } from '../../../helpers/check-is-enterprise.js';
import getAppAuthClientAction from '../../../controllers/api/v1/app-auth-clients/get-app-auth-client.js';

const router = Router();

router.get(
'/:appAuthClientId',
authenticateUser,
checkIsEnterprise,
getAppAuthClientAction
);

export default router;
4 changes: 4 additions & 0 deletions packages/backend/src/routes/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -6,10 +6,12 @@ import healthcheckRouter from './healthcheck.js';
import automatischRouter from './api/v1/automatisch.js';
import usersRouter from './api/v1/users.js';
import paymentRouter from './api/v1/payment.ee.js';
import appAuthClientsRouter from './api/v1/app-auth-clients.js';
import samlAuthProvidersRouter from './api/v1/admin/saml-auth-providers.ee.js';
import rolesRouter from './api/v1/admin/roles.ee.js';
import permissionsRouter from './api/v1/admin/permissions.ee.js';
import adminUsersRouter from './api/v1/admin/users.ee.js';
import adminAppAuthClientsRouter from './api/v1/admin/app-auth-clients.js';

const router = Router();

Expand All @@ -20,9 +22,11 @@ router.use('/healthcheck', healthcheckRouter);
router.use('/api/v1/automatisch', automatischRouter);
router.use('/api/v1/users', usersRouter);
router.use('/api/v1/payment', paymentRouter);
router.use('/api/v1/app-auth-clients', appAuthClientsRouter);
router.use('/api/v1/admin/saml-auth-providers', samlAuthProvidersRouter);
router.use('/api/v1/admin/roles', rolesRouter);
router.use('/api/v1/admin/permissions', permissionsRouter);
router.use('/api/v1/admin/users', adminUsersRouter);
router.use('/api/v1/admin/app-auth-clients', adminAppAuthClientsRouter);

export default router;
10 changes: 10 additions & 0 deletions packages/backend/src/serializers/app-auth-client.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
const appAuthClientSerializer = (appAuthClient) => {
return {
id: appAuthClient.id,
appConfigId: appAuthClient.appConfigId,
name: appAuthClient.name,
active: appAuthClient.active,
};
};

export default appAuthClientSerializer;
22 changes: 22 additions & 0 deletions packages/backend/src/serializers/app-auth-client.test.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
import { describe, it, expect, beforeEach } from 'vitest';
import { createAppAuthClient } from '../../test/factories/app-auth-client';
import appAuthClientSerializer from './app-auth-client';

describe('appAuthClient serializer', () => {
let appAuthClient;

beforeEach(async () => {
appAuthClient = await createAppAuthClient();
});

it('should return app auth client data', async () => {
const expectedPayload = {
id: appAuthClient.id,
appConfigId: appAuthClient.appConfigId,
name: appAuthClient.name,
active: appAuthClient.active,
};

expect(appAuthClientSerializer(appAuthClient)).toEqual(expectedPayload);
});
});
2 changes: 2 additions & 0 deletions packages/backend/src/serializers/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -2,12 +2,14 @@ import userSerializer from './user.js';
import roleSerializer from './role.js';
import permissionSerializer from './permission.js';
import samlAuthProviderSerializer from './saml-auth-provider.ee.js';
import appAuthClientSerializer from './app-auth-client.js';

const serializers = {
User: userSerializer,
Role: roleSerializer,
Permission: permissionSerializer,
SamlAuthProvider: samlAuthProviderSerializer,
AppAuthClient: appAuthClientSerializer,
};

export default serializers;
25 changes: 25 additions & 0 deletions packages/backend/test/factories/app-auth-client.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@
import { faker } from '@faker-js/faker';
import { createAppConfig } from './app-config.js';
import AppAuthClient from '../../src/models/app-auth-client';

const formattedAuthDefaults = {
oAuthRedirectUrl: faker.internet.url(),
instanceUrl: faker.internet.url(),
clientId: faker.string.uuid(),
clientSecret: faker.string.uuid(),
};

export const createAppAuthClient = async (params = {}) => {
params.name = params?.name || faker.person.fullName();
params.id = params?.id || faker.string.uuid();
params.appConfigId = params?.appConfigId || (await createAppConfig()).id;
params.active = params?.active ?? true;
params.formattedAuthDefaults =
params?.formattedAuthDefaults || formattedAuthDefaults;

const appAuthClient = await AppAuthClient.query()
.insert(params)
.returning('*');

return appAuthClient;
};
13 changes: 13 additions & 0 deletions packages/backend/test/factories/app-config.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
import AppConfig from '../../src/models/app-config.js';

export const createAppConfig = async (params = {}) => {
const appConfigData = {
key: params?.key || 'gitlab',
};

const appConfig = await AppConfig.query()
.insert(appConfigData)
.returning('*');

return appConfig;
};
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
const getAdminAppAuthClientMock = (appAuthClient) => {
return {
data: {
appConfigId: appAuthClient.appConfigId,
name: appAuthClient.name,
id: appAuthClient.id,
active: appAuthClient.active,
},
meta: {
count: 1,
currentPage: null,
isArray: false,
totalPages: null,
type: 'AppAuthClient',
},
};
};

export default getAdminAppAuthClientMock;
19 changes: 19 additions & 0 deletions packages/backend/test/mocks/rest/api/v1/get-app-auth-client.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
const getAppAuthClientMock = (appAuthClient) => {
return {
data: {
name: appAuthClient.name,
id: appAuthClient.id,
appConfigId: appAuthClient.appConfigId,
active: appAuthClient.active,
},
meta: {
count: 1,
currentPage: null,
isArray: false,
totalPages: null,
type: 'AppAuthClient',
},
};
};

export default getAppAuthClientMock;
Loading