Skip to content

Commit

Permalink
added tenant get/set settings (#334)
Browse files Browse the repository at this point in the history
added password tenant get/set settings
added to readme
added tests
  • Loading branch information
Bars92 authored Feb 11, 2024
1 parent afa5735 commit 360c825
Show file tree
Hide file tree
Showing 10 changed files with 343 additions and 24 deletions.
45 changes: 44 additions & 1 deletion README.md
Original file line number Diff line number Diff line change
Expand Up @@ -524,7 +524,7 @@ const descopeClient = DescopeClient({

### Manage Tenants

You can create, update, delete or load tenants:
You can create, update, delete or load tenants, as well as read and update tenant settings:

```typescript
// The self provisioning domains or optional. If given they'll be used to associate
Expand Down Expand Up @@ -563,6 +563,49 @@ const searchRes = await descopeClient.management.tenant.searchAll(['id']);
searchRes.data.forEach((tenant) => {
// do something
});

// Load tenant settings by id
const tenantSettings = await descopeClient.management.tenant.getSettings('my-tenant-id');

// Update will override all fields as is. Use carefully.
await descopeClient.management.tenant.configureSettings('my-tenant-id', {
domains: ['domain1.com'],
selfProvisioningDomains: ['domain1.com'],
sessionSettingsEnabled: true,
refreshTokenExpiration: 12,
refreshTokenExpirationUnit: 'days',
sessionTokenExpiration: 10,
sessionTokenExpirationUnit: 'minutes',
enableInactivity: true,
JITDisabled: false,
InactivityTime: 10,
InactivityTimeUnit: 'minutes',
});
```

### Manage Password

You can read and update any tenant password settings and policy:

```typescript
// Load tenant password settings by id
const passwordSettings = await descopeClient.management.password.getSettings('my-tenant-id');

// Update will override all fields as is. Use carefully.
await descopeClient.management.password.configureSettings('my-tenant-id', {
enabled: true,
minLength: 8,
expiration: true,
expirationWeeks: 4,
lock: true,
lockAttempts: 5,
reuse: true,
reuseAmount: 6,
lowercase: true,
uppercase: false,
number: true,
nonAlphaNumeric: false,
});
```

### Manage SSO applications
Expand Down
42 changes: 21 additions & 21 deletions examples/managementCli/package-lock.json

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

20 changes: 20 additions & 0 deletions examples/managementCli/src/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -296,6 +296,26 @@ program
handleSdkRes(await sdk.management.tenant.loadAll());
});

// tenant-settings
program
.command('tenant-settings')
.description('Load tenant settings by id')
.argument('<id>', 'Tenant ID')
.action(async (id) => {
handleSdkRes(await sdk.management.tenant.getSettings(id));
});

// *** Password commands ***

// password-settings
program
.command('password-settings')
.description('Load password settings by tenant id')
.argument('<tenant-id>', 'Tenant ID')
.action(async (tenantId) => {
handleSdkRes(await sdk.management.password.getSettings(tenantId));
});

// *** SSO application commands ***

// sso-application-create-oidc
Expand Down
2 changes: 2 additions & 0 deletions lib/management/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,7 @@ import WithTheme from './theme';
import WithAudit from './audit';
import WithAuthz from './authz';
import withSSOApplication from './ssoapplication';
import withPassword from './password';

/** Constructs a higher level Management API that wraps the functions from code-js-sdk */
const withManagement = (sdk: CoreSdk, managementKey?: string) => ({
Expand All @@ -24,6 +25,7 @@ const withManagement = (sdk: CoreSdk, managementKey?: string) => ({
sso: withSSOSettings(sdk, managementKey),
jwt: withJWT(sdk, managementKey),
permission: withPermission(sdk, managementKey),
password: withPassword(sdk, managementKey),
role: withRole(sdk, managementKey),
group: withGroup(sdk, managementKey),
flow: WithFlow(sdk, managementKey),
Expand Down
91 changes: 91 additions & 0 deletions lib/management/password.test.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,91 @@
import { SdkResponse } from '@descope/core-js-sdk';
import withManagement from '.';
import apiPaths from './paths';
import { PasswordSettings } from './types';
import { mockCoreSdk, mockHttpClient } from './testutils';

const management = withManagement(mockCoreSdk, 'key');

const mockPasswordSettings: PasswordSettings = {
enabled: true,
minLength: 8,
expiration: true,
expirationWeeks: 4,
lock: true,
lockAttempts: 5,
reuse: true,
reuseAmount: 6,
lowercase: true,
uppercase: false,
number: true,
nonAlphaNumeric: false,
};

describe('Management Password', () => {
afterEach(() => {
jest.clearAllMocks();
mockHttpClient.reset();
});

describe('getSettings', () => {
it('should send the correct request and receive correct response', async () => {
const httpResponse = {
ok: true,
json: () => mockPasswordSettings,
clone: () => ({
json: () => Promise.resolve(mockPasswordSettings),
}),
status: 200,
};
mockHttpClient.get.mockResolvedValue(httpResponse);

const resp: SdkResponse<PasswordSettings> = await management.password.getSettings('test');

expect(mockHttpClient.get).toHaveBeenCalledWith(apiPaths.password.settings, {
queryParams: { tenantId: 'test' },
token: 'key',
});

expect(resp).toEqual({
code: 200,
data: mockPasswordSettings,
ok: true,
response: httpResponse,
});
});
});

describe('configureSettings', () => {
it('should send the correct request and receive correct response', async () => {
const httpResponse = {
ok: true,
json: () => {},
clone: () => ({
json: () => Promise.resolve(),
}),
status: 200,
};
mockHttpClient.post.mockResolvedValue(httpResponse);

const resp: SdkResponse<never> = await management.password.configureSettings(
'test',
mockPasswordSettings,
);

expect(mockHttpClient.post).toHaveBeenCalledWith(
apiPaths.password.settings,
{ ...mockPasswordSettings, tenantId: 'test' },
{
token: 'key',
},
);

expect(resp).toEqual({
code: 200,
data: undefined,
ok: true,
response: httpResponse,
});
});
});
});
27 changes: 27 additions & 0 deletions lib/management/password.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
import { SdkResponse, transformResponse } from '@descope/core-js-sdk';
import { CoreSdk } from '../types';
import apiPaths from './paths';
import { PasswordSettings } from './types';

const withPassword = (sdk: CoreSdk, managementKey?: string) => ({
getSettings: (tenantId: string): Promise<SdkResponse<PasswordSettings>> =>
transformResponse<PasswordSettings, PasswordSettings>(
sdk.httpClient.get(apiPaths.password.settings, {
queryParams: { tenantId },
token: managementKey,
}),
(data) => data,
),
configureSettings: (tenantId: string, settings: PasswordSettings): Promise<SdkResponse<never>> =>
transformResponse(
sdk.httpClient.post(
apiPaths.password.settings,
{ ...settings, tenantId },
{
token: managementKey,
},
),
),
});

export default withPassword;
4 changes: 4 additions & 0 deletions lib/management/paths.ts
Original file line number Diff line number Diff line change
Expand Up @@ -54,6 +54,7 @@ export default {
update: '/v1/mgmt/tenant/update',
delete: '/v1/mgmt/tenant/delete',
load: '/v1/mgmt/tenant',
settings: '/v1/mgmt/tenant/settings',
loadAll: '/v1/mgmt/tenant/all',
searchAll: '/v1/mgmt/tenant/search',
},
Expand Down Expand Up @@ -82,6 +83,9 @@ export default {
jwt: {
update: '/v1/mgmt/jwt/update',
},
password: {
settings: '/v1/mgmt/password/settings',
},
permission: {
create: '/v1/mgmt/permission/create',
update: '/v1/mgmt/permission/update',
Expand Down
Loading

0 comments on commit 360c825

Please sign in to comment.