Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
7 changes: 7 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -1102,6 +1102,13 @@ await descopeClient.management.sso.newSettings(tenantID, ssoId, displayName);
// You can delete existing SSO configuration
// You can pass ssoId in case using multi SSO and you want to delete specific SSO configuration
await descopeClient.management.sso.deleteSettings(tenantID);

// You can disable an SSO configuration without deleting it, and enable it again later.
// Its settings, mappings and domains are kept, so re-enabling needs no payload.
// You can pass ssoId in case using multi SSO and you want to disable a specific SSO configuration
await descopeClient.management.sso.configureAuthType(tenantID, 'none', ssoId);
// Enable it again on the protocol it is configured for ('saml' or 'oidc')
await descopeClient.management.sso.configureAuthType(tenantID, 'saml', ssoId);
```

Note: Certificates should have a similar structure to:
Expand Down
1 change: 1 addition & 0 deletions lib/management/paths.ts
Original file line number Diff line number Diff line change
Expand Up @@ -144,6 +144,7 @@ export default {
sso: {
settings: '/v1/mgmt/sso/settings',
settingsNew: '/v1/mgmt/sso/settings/new',
authType: '/v1/mgmt/sso/settings/authtype',
metadata: '/v1/mgmt/sso/metadata',
mapping: '/v1/mgmt/sso/mapping',
settingsv2: '/v2/mgmt/sso/settings',
Expand Down
55 changes: 55 additions & 0 deletions lib/management/sso.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -484,6 +484,61 @@ describe('Management SSO', () => {
});
});

describe('configureAuthType', () => {
it('should disable a specific SSO configuration', async () => {
const httpResponse = {
ok: true,
json: () => {},
clone: () => ({
json: () => Promise.resolve({}),
}),
status: 200,
};
mockHttpClient.post.mockResolvedValue(httpResponse);

const resp = await management.sso.configureAuthType('t1', 'none', 'conf1');

expect(mockHttpClient.post).toHaveBeenCalledWith(apiPaths.sso.authType, {
tenantId: 't1',
authType: 'none',
ssoId: 'conf1',
});

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

it('should target the default configuration when no ssoId is given', async () => {
const httpResponse = {
ok: true,
json: () => {},
clone: () => ({
json: () => Promise.resolve({}),
}),
status: 200,
};
mockHttpClient.post.mockResolvedValue(httpResponse);

const resp = await management.sso.configureAuthType('t1', 'saml');

expect(mockHttpClient.post).toHaveBeenCalledWith(apiPaths.sso.authType, {
tenantId: 't1',
authType: 'saml',
});

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

describe('newSettings', () => {
it('should send the correct request and receive correct response', async () => {
const mockResponse = {
Expand Down
21 changes: 21 additions & 0 deletions lib/management/sso.ts
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@ import {
SSOSAMLSettings,
SSOSAMLByMetadataSettings,
SSOSettings,
SSOAuthType,
XAASettings,
XAASettingsResponse,
} from './types';
Expand Down Expand Up @@ -156,6 +157,26 @@ const withSSOSettings = (httpClient: HttpClient) => ({
}),
);
},
/**
* Set the authentication type of a single SSO configuration, leaving its stored SAML/OIDC
* settings, mappings and domains untouched. `none` disables the configuration without deleting
* it, `saml`/`oidc` enable it on that protocol.
* @param tenantId the tenant the configuration belongs to
* @param authType `none` to disable, `saml` or `oidc` to enable on that protocol
* @param ssoId the SSO configuration to change; omit for the tenant's default configuration
*/
configureAuthType: (
tenantId: string,
authType: SSOAuthType,
ssoId?: string,
): Promise<SdkResponse<never>> =>
transformResponse(
httpClient.post(apiPaths.sso.authType, {
tenantId,
authType,
...(ssoId ? { ssoId } : {}),
}),
),
configureSAMLSettings: (
tenantId: string,
settings: SSOSAMLSettings,
Expand Down
10 changes: 8 additions & 2 deletions lib/management/types.ts
Original file line number Diff line number Diff line change
Expand Up @@ -247,14 +247,20 @@ export type ClientAssertionResponse = {
/** Represents a tenant in a project. It has an id, a name and an array of
* self provisioning domains used to associate users with that tenant.
*/
/** Authentication type of an SSO configuration. `none` means the configuration is disabled: it
* keeps its stored settings, mappings and domains, and serves no logins until it is set back to
* `saml` or `oidc`.
*/
export type SSOAuthType = 'none' | 'saml' | 'oidc';

export type Tenant = {
id: string;
name: string;
selfProvisioningDomains: string[];
createdTime: number;
customAttributes?: Record<string, string | number | boolean | string[]>;
domains?: string[];
authType?: 'none' | 'saml' | 'oidc';
authType?: SSOAuthType;
enforceSSO?: boolean;
disabled?: boolean;
defaultRoles?: string[];
Expand All @@ -280,7 +286,7 @@ export type SSOSetupSuiteSettings = {
export type TenantSettings = {
selfProvisioningDomains: string[];
domains?: string[];
authType?: 'none' | 'saml' | 'oidc';
authType?: SSOAuthType;
enabled?: boolean;
refreshTokenExpiration?: number;
refreshTokenExpirationUnit?: ExpirationUnit;
Expand Down