@syndew/oluso-plugin-scim 0.0.0-stage → 0.0.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
|
@@ -0,0 +1,735 @@
|
|
|
1
|
+
import { AdminPlugin, NavItem, PaginatedResponse } from '@syndew/oluso-ui-core';
|
|
2
|
+
import { Routes } from '@angular/router';
|
|
3
|
+
import { Observable } from 'rxjs';
|
|
4
|
+
import * as _angular_core from '@angular/core';
|
|
5
|
+
import { OnInit } from '@angular/core';
|
|
6
|
+
import * as _syndew_oluso_plugin_scim from '@syndew/oluso-plugin-scim';
|
|
7
|
+
import { RoleDto, TeamSummary } from '@syndew/oluso-admin-ui';
|
|
8
|
+
|
|
9
|
+
/**
|
|
10
|
+
* SCIM Admin Plugin
|
|
11
|
+
*
|
|
12
|
+
* Provides SCIM provisioning management functionality:
|
|
13
|
+
* - SCIM client management (CRUD): identity providers that push into us
|
|
14
|
+
* - Token management and rotation
|
|
15
|
+
* - Attribute mapping configuration
|
|
16
|
+
* - Provisioning activity logs
|
|
17
|
+
* - SCIM providers: downstream systems we push users and groups to
|
|
18
|
+
*/
|
|
19
|
+
declare const SCIM_PLUGIN: AdminPlugin;
|
|
20
|
+
/**
|
|
21
|
+
* Helper function to get SCIM navigation items
|
|
22
|
+
*/
|
|
23
|
+
declare function getScimNavItems(): NavItem[];
|
|
24
|
+
|
|
25
|
+
declare const SCIM_ROUTES: Routes;
|
|
26
|
+
|
|
27
|
+
/**
|
|
28
|
+
* SCIM Client configuration
|
|
29
|
+
*/
|
|
30
|
+
interface ScimClient {
|
|
31
|
+
id: string;
|
|
32
|
+
name: string;
|
|
33
|
+
description?: string;
|
|
34
|
+
isEnabled: boolean;
|
|
35
|
+
tokenCreatedAt: string;
|
|
36
|
+
tokenExpiresAt?: string;
|
|
37
|
+
allowedIpRanges?: string;
|
|
38
|
+
rateLimitPerMinute: number;
|
|
39
|
+
canCreateUsers: boolean;
|
|
40
|
+
canUpdateUsers: boolean;
|
|
41
|
+
canDeleteUsers: boolean;
|
|
42
|
+
canManageGroups: boolean;
|
|
43
|
+
defaultRoleId?: string;
|
|
44
|
+
/** Optional OAuth client (clientId) linked for client-credentials JWT auth. */
|
|
45
|
+
oauthClientId?: string;
|
|
46
|
+
createdAt: string;
|
|
47
|
+
lastActivityAt?: string;
|
|
48
|
+
successCount: number;
|
|
49
|
+
errorCount: number;
|
|
50
|
+
}
|
|
51
|
+
/**
|
|
52
|
+
* Request to create a new SCIM client
|
|
53
|
+
*/
|
|
54
|
+
interface CreateScimClientRequest {
|
|
55
|
+
name: string;
|
|
56
|
+
description?: string;
|
|
57
|
+
isEnabled?: boolean;
|
|
58
|
+
tokenExpiresAt?: string;
|
|
59
|
+
allowedIpRanges?: string;
|
|
60
|
+
rateLimitPerMinute?: number;
|
|
61
|
+
canCreateUsers?: boolean;
|
|
62
|
+
canUpdateUsers?: boolean;
|
|
63
|
+
canDeleteUsers?: boolean;
|
|
64
|
+
canManageGroups?: boolean;
|
|
65
|
+
defaultRoleId?: string;
|
|
66
|
+
oauthClientId?: string;
|
|
67
|
+
}
|
|
68
|
+
/**
|
|
69
|
+
* Response when creating a SCIM client (includes the token)
|
|
70
|
+
*/
|
|
71
|
+
interface CreateScimClientResponse {
|
|
72
|
+
client: ScimClient;
|
|
73
|
+
token: string;
|
|
74
|
+
}
|
|
75
|
+
/**
|
|
76
|
+
* SCIM provisioning log entry
|
|
77
|
+
*/
|
|
78
|
+
interface ScimProvisioningLog {
|
|
79
|
+
id: string;
|
|
80
|
+
method: string;
|
|
81
|
+
path: string;
|
|
82
|
+
resourceType?: string;
|
|
83
|
+
resourceId?: string;
|
|
84
|
+
operation: string;
|
|
85
|
+
statusCode: number;
|
|
86
|
+
success: boolean;
|
|
87
|
+
errorMessage?: string;
|
|
88
|
+
clientIp?: string;
|
|
89
|
+
durationMs: number;
|
|
90
|
+
timestamp: string;
|
|
91
|
+
}
|
|
92
|
+
/**
|
|
93
|
+
* Inbound attribute mapping: how an attribute of the SCIM resource an
|
|
94
|
+
* identity provider sends is written onto the internal user.
|
|
95
|
+
*/
|
|
96
|
+
interface ScimAttributeMapping {
|
|
97
|
+
id: string;
|
|
98
|
+
scimClientId: string;
|
|
99
|
+
/** The SCIM attribute path (e.g., "userName", "emails[type eq \"work\"].value", "name.familyName") */
|
|
100
|
+
scimAttribute: string;
|
|
101
|
+
/** The internal user property to write (e.g., "Email", "LastName", "custom:department") */
|
|
102
|
+
internalProperty: string;
|
|
103
|
+
/** Scriban template computing the value; read from the attribute path when empty. Model: scim, enterprise, attr, client. */
|
|
104
|
+
expression?: string;
|
|
105
|
+
/** Scriban boolean expression; the mapping is skipped when false */
|
|
106
|
+
condition?: string;
|
|
107
|
+
/** Whether this mapping must resolve when a user is created */
|
|
108
|
+
isRequired: boolean;
|
|
109
|
+
/** Default value if the SCIM attribute is not provided */
|
|
110
|
+
defaultValue?: string;
|
|
111
|
+
/** Optional transformation function name to apply */
|
|
112
|
+
transformation?: string;
|
|
113
|
+
/** Among mappings writing the same property, higher priority is tried first; the first with a value wins */
|
|
114
|
+
priority: number;
|
|
115
|
+
/** Whether this mapping is enabled */
|
|
116
|
+
isEnabled: boolean;
|
|
117
|
+
createdAt: string;
|
|
118
|
+
updatedAt?: string;
|
|
119
|
+
}
|
|
120
|
+
/**
|
|
121
|
+
* Request to create or update a SCIM attribute mapping
|
|
122
|
+
*/
|
|
123
|
+
interface SaveScimAttributeMappingRequest {
|
|
124
|
+
scimAttribute: string;
|
|
125
|
+
internalProperty: string;
|
|
126
|
+
expression?: string;
|
|
127
|
+
condition?: string;
|
|
128
|
+
isRequired?: boolean;
|
|
129
|
+
defaultValue?: string;
|
|
130
|
+
transformation?: string;
|
|
131
|
+
priority?: number;
|
|
132
|
+
isEnabled?: boolean;
|
|
133
|
+
}
|
|
134
|
+
/** @deprecated use SaveScimAttributeMappingRequest */
|
|
135
|
+
type CreateScimAttributeMappingRequest = SaveScimAttributeMappingRequest;
|
|
136
|
+
interface ScimMappingOptions {
|
|
137
|
+
internalProperties: string[];
|
|
138
|
+
transformations: string[];
|
|
139
|
+
presets: string[];
|
|
140
|
+
/** The mappings in force when a client has none configured */
|
|
141
|
+
defaults: ScimAttributeMapping[];
|
|
142
|
+
}
|
|
143
|
+
interface ScimMappingPreview {
|
|
144
|
+
success: boolean;
|
|
145
|
+
error?: string;
|
|
146
|
+
/** Internal property to the value that would be written; null means cleared */
|
|
147
|
+
fields: Record<string, string | null>;
|
|
148
|
+
usingDefaults: boolean;
|
|
149
|
+
}
|
|
150
|
+
/**
|
|
151
|
+
* Predefined SCIM attribute suggestions for common providers
|
|
152
|
+
*/
|
|
153
|
+
interface ScimAttributeSuggestion {
|
|
154
|
+
attribute: string;
|
|
155
|
+
description: string;
|
|
156
|
+
example?: string;
|
|
157
|
+
provider?: 'azure' | 'okta' | 'google' | 'standard';
|
|
158
|
+
}
|
|
159
|
+
/**
|
|
160
|
+
* Internal user property options
|
|
161
|
+
*/
|
|
162
|
+
interface InternalPropertyOption {
|
|
163
|
+
name: string;
|
|
164
|
+
displayName: string;
|
|
165
|
+
}
|
|
166
|
+
/**
|
|
167
|
+
* Transformation option for attribute mapping
|
|
168
|
+
*/
|
|
169
|
+
interface TransformationOption {
|
|
170
|
+
name: string;
|
|
171
|
+
description: string;
|
|
172
|
+
}
|
|
173
|
+
|
|
174
|
+
/**
|
|
175
|
+
* Outbound SCIM provider: a downstream system this tenant pushes users
|
|
176
|
+
* (and optionally groups) to. The counterpart of ScimClient, which is an
|
|
177
|
+
* identity provider that pushes into us.
|
|
178
|
+
*/
|
|
179
|
+
interface ScimProvider {
|
|
180
|
+
id: string;
|
|
181
|
+
name: string;
|
|
182
|
+
description?: string;
|
|
183
|
+
isEnabled: boolean;
|
|
184
|
+
flavor: string;
|
|
185
|
+
baseUrl: string;
|
|
186
|
+
authType: ScimProviderAuthType;
|
|
187
|
+
oauthTokenEndpoint?: string;
|
|
188
|
+
oauthClientId?: string;
|
|
189
|
+
oauthScope?: string;
|
|
190
|
+
/** A secret is stored. The value itself is never returned. */
|
|
191
|
+
hasSecret: boolean;
|
|
192
|
+
secretUpdatedAt?: string;
|
|
193
|
+
syncUsers: boolean;
|
|
194
|
+
syncGroups: boolean;
|
|
195
|
+
/** What a SCIM Group is built from. */
|
|
196
|
+
groupSource: ScimProviderGroupSource;
|
|
197
|
+
scopeRoleIds: string[];
|
|
198
|
+
/** Team membership includes sub-teams. */
|
|
199
|
+
scopeTeamIds: string[];
|
|
200
|
+
userNameSource: ScimProviderUserNameSource;
|
|
201
|
+
/** Scriban template used when userNameSource is 'expression'. */
|
|
202
|
+
userNameExpression?: string;
|
|
203
|
+
deprovisionMode: ScimProviderDeprovisionMode;
|
|
204
|
+
reconcileIntervalMinutes: number;
|
|
205
|
+
/** Inbound SCIM client that is this same system; its changes are not pushed back here. */
|
|
206
|
+
linkedScimClientId?: string;
|
|
207
|
+
createdAt: string;
|
|
208
|
+
updatedAt?: string;
|
|
209
|
+
lastReconcileAt?: string;
|
|
210
|
+
lastReconcileSummary?: string;
|
|
211
|
+
lastSuccessAt?: string;
|
|
212
|
+
lastErrorAt?: string;
|
|
213
|
+
lastError?: string;
|
|
214
|
+
successCount: number;
|
|
215
|
+
errorCount: number;
|
|
216
|
+
}
|
|
217
|
+
type ScimProviderAuthType = 'bearer' | 'oauth_client_credentials';
|
|
218
|
+
type ScimProviderUserNameSource = 'userName' | 'email' | 'expression';
|
|
219
|
+
type ScimProviderDeprovisionMode = 'deactivate' | 'delete';
|
|
220
|
+
type ScimProviderGroupSource = 'roles' | 'teams' | 'both';
|
|
221
|
+
interface CreateScimProviderRequest {
|
|
222
|
+
name: string;
|
|
223
|
+
description?: string;
|
|
224
|
+
isEnabled?: boolean;
|
|
225
|
+
flavor: string;
|
|
226
|
+
baseUrl: string;
|
|
227
|
+
authType: ScimProviderAuthType;
|
|
228
|
+
oauthTokenEndpoint?: string;
|
|
229
|
+
oauthClientId?: string;
|
|
230
|
+
oauthScope?: string;
|
|
231
|
+
secret?: string;
|
|
232
|
+
syncUsers?: boolean;
|
|
233
|
+
syncGroups?: boolean;
|
|
234
|
+
groupSource?: ScimProviderGroupSource;
|
|
235
|
+
scopeRoleIds?: string[];
|
|
236
|
+
scopeTeamIds?: string[];
|
|
237
|
+
userNameSource?: ScimProviderUserNameSource;
|
|
238
|
+
userNameExpression?: string;
|
|
239
|
+
deprovisionMode?: ScimProviderDeprovisionMode;
|
|
240
|
+
reconcileIntervalMinutes?: number;
|
|
241
|
+
linkedScimClientId?: string;
|
|
242
|
+
}
|
|
243
|
+
interface UpdateScimProviderRequest {
|
|
244
|
+
name: string;
|
|
245
|
+
description?: string;
|
|
246
|
+
isEnabled: boolean;
|
|
247
|
+
flavor: string;
|
|
248
|
+
baseUrl: string;
|
|
249
|
+
authType: ScimProviderAuthType;
|
|
250
|
+
oauthTokenEndpoint?: string;
|
|
251
|
+
oauthClientId?: string;
|
|
252
|
+
oauthScope?: string;
|
|
253
|
+
syncUsers: boolean;
|
|
254
|
+
syncGroups: boolean;
|
|
255
|
+
groupSource: ScimProviderGroupSource;
|
|
256
|
+
scopeRoleIds: string[];
|
|
257
|
+
scopeTeamIds: string[];
|
|
258
|
+
userNameSource: ScimProviderUserNameSource;
|
|
259
|
+
userNameExpression?: string;
|
|
260
|
+
deprovisionMode: ScimProviderDeprovisionMode;
|
|
261
|
+
reconcileIntervalMinutes: number;
|
|
262
|
+
linkedScimClientId?: string;
|
|
263
|
+
}
|
|
264
|
+
interface ScimProviderFlavor {
|
|
265
|
+
key: string;
|
|
266
|
+
displayName: string;
|
|
267
|
+
description: string;
|
|
268
|
+
notes?: string;
|
|
269
|
+
defaultUserNameSource: ScimProviderUserNameSource;
|
|
270
|
+
requiresEmailUserName: boolean;
|
|
271
|
+
supportsPhoneNumbers: boolean;
|
|
272
|
+
supportsEnterpriseExtension: boolean;
|
|
273
|
+
supportsGroups: boolean;
|
|
274
|
+
defaultUserMappings: {
|
|
275
|
+
scimAttribute: string;
|
|
276
|
+
internalProperty: string;
|
|
277
|
+
}[];
|
|
278
|
+
}
|
|
279
|
+
interface ScimProviderOptions {
|
|
280
|
+
flavors: ScimProviderFlavor[];
|
|
281
|
+
internalProperties: string[];
|
|
282
|
+
transformations: string[];
|
|
283
|
+
authTypes: ScimProviderAuthType[];
|
|
284
|
+
userNameSources: ScimProviderUserNameSource[];
|
|
285
|
+
deprovisionModes: ScimProviderDeprovisionMode[];
|
|
286
|
+
groupSources: ScimProviderGroupSource[];
|
|
287
|
+
}
|
|
288
|
+
interface ScimProviderAttributeMapping {
|
|
289
|
+
id: string;
|
|
290
|
+
scimProviderId: string;
|
|
291
|
+
scimAttribute: string;
|
|
292
|
+
/** Empty when the value comes from an expression. */
|
|
293
|
+
internalProperty: string;
|
|
294
|
+
/** Scriban template computing the value; takes precedence over internalProperty. */
|
|
295
|
+
expression?: string;
|
|
296
|
+
/** Scriban boolean expression; the attribute is omitted when false. */
|
|
297
|
+
condition?: string;
|
|
298
|
+
transformation?: string;
|
|
299
|
+
defaultValue?: string;
|
|
300
|
+
isEnabled: boolean;
|
|
301
|
+
createdAt: string;
|
|
302
|
+
updatedAt?: string;
|
|
303
|
+
}
|
|
304
|
+
interface SaveScimProviderAttributeMappingRequest {
|
|
305
|
+
scimAttribute: string;
|
|
306
|
+
internalProperty?: string;
|
|
307
|
+
expression?: string;
|
|
308
|
+
condition?: string;
|
|
309
|
+
transformation?: string;
|
|
310
|
+
defaultValue?: string;
|
|
311
|
+
isEnabled: boolean;
|
|
312
|
+
}
|
|
313
|
+
interface ScimProviderPreview {
|
|
314
|
+
userId: string;
|
|
315
|
+
userName?: string;
|
|
316
|
+
inScope: boolean;
|
|
317
|
+
error?: string;
|
|
318
|
+
payload?: Record<string, unknown>;
|
|
319
|
+
}
|
|
320
|
+
interface ScimProviderTestResult {
|
|
321
|
+
success: boolean;
|
|
322
|
+
message: string;
|
|
323
|
+
discoveryReachable: boolean;
|
|
324
|
+
discoveryStatusCode: number;
|
|
325
|
+
authenticationOk: boolean;
|
|
326
|
+
authenticationStatusCode: number;
|
|
327
|
+
authenticationError?: string;
|
|
328
|
+
patchSupported?: boolean;
|
|
329
|
+
bulkSupported?: boolean;
|
|
330
|
+
filterSupported?: boolean;
|
|
331
|
+
filterMaxResults?: number;
|
|
332
|
+
etagSupported?: boolean;
|
|
333
|
+
authenticationSchemes: string[];
|
|
334
|
+
}
|
|
335
|
+
interface ScimProviderReconcileResult {
|
|
336
|
+
usersQueued: number;
|
|
337
|
+
userRemovalsQueued: number;
|
|
338
|
+
groupsQueued: number;
|
|
339
|
+
groupRemovalsQueued: number;
|
|
340
|
+
summary: string;
|
|
341
|
+
}
|
|
342
|
+
type ScimQueueStatus = 'pending' | 'processing' | 'succeeded' | 'failed' | 'dead' | 'superseded';
|
|
343
|
+
interface ScimProviderQueueSummary {
|
|
344
|
+
pending: number;
|
|
345
|
+
processing: number;
|
|
346
|
+
failed: number;
|
|
347
|
+
dead: number;
|
|
348
|
+
succeededLast24h: number;
|
|
349
|
+
oldestPendingAt?: string;
|
|
350
|
+
}
|
|
351
|
+
interface ScimProviderQueueItem {
|
|
352
|
+
id: string;
|
|
353
|
+
resourceType: 'User' | 'Group';
|
|
354
|
+
internalId: string;
|
|
355
|
+
operation: 'upsert' | 'remove';
|
|
356
|
+
status: ScimQueueStatus;
|
|
357
|
+
attempts: number;
|
|
358
|
+
nextAttemptAt: string;
|
|
359
|
+
lastStatusCode?: number;
|
|
360
|
+
lastError?: string;
|
|
361
|
+
reason?: string;
|
|
362
|
+
createdAt: string;
|
|
363
|
+
updatedAt?: string;
|
|
364
|
+
completedAt?: string;
|
|
365
|
+
}
|
|
366
|
+
interface ScimProviderQueueResponse {
|
|
367
|
+
summary: ScimProviderQueueSummary;
|
|
368
|
+
total: number;
|
|
369
|
+
skip: number;
|
|
370
|
+
take: number;
|
|
371
|
+
items: ScimProviderQueueItem[];
|
|
372
|
+
}
|
|
373
|
+
interface ScimProviderLog {
|
|
374
|
+
id: string;
|
|
375
|
+
operation: string;
|
|
376
|
+
resourceType?: string;
|
|
377
|
+
internalId?: string;
|
|
378
|
+
remoteId?: string;
|
|
379
|
+
method: string;
|
|
380
|
+
path: string;
|
|
381
|
+
statusCode: number;
|
|
382
|
+
success: boolean;
|
|
383
|
+
errorMessage?: string;
|
|
384
|
+
durationMs: number;
|
|
385
|
+
timestamp: string;
|
|
386
|
+
}
|
|
387
|
+
interface ScimProviderResource {
|
|
388
|
+
id: string;
|
|
389
|
+
resourceType: 'User' | 'Group';
|
|
390
|
+
internalId: string;
|
|
391
|
+
remoteId: string;
|
|
392
|
+
remoteVersion?: string;
|
|
393
|
+
isDeprovisioned: boolean;
|
|
394
|
+
createdAt: string;
|
|
395
|
+
lastSyncedAt?: string;
|
|
396
|
+
}
|
|
397
|
+
|
|
398
|
+
declare class ScimService {
|
|
399
|
+
private readonly api;
|
|
400
|
+
getClients(): Observable<ScimClient[]>;
|
|
401
|
+
getClient(id: string): Observable<ScimClient>;
|
|
402
|
+
createClient(request: CreateScimClientRequest): Observable<CreateScimClientResponse>;
|
|
403
|
+
updateClient(id: string, request: ScimClient): Observable<ScimClient>;
|
|
404
|
+
deleteClient(id: string): Observable<void>;
|
|
405
|
+
rotateToken(id: string): Observable<{
|
|
406
|
+
token: string;
|
|
407
|
+
}>;
|
|
408
|
+
getLogs(clientId: string, page?: number, pageSize?: number): Observable<PaginatedResponse<ScimProvisioningLog>>;
|
|
409
|
+
getMappings(clientId: string): Observable<ScimAttributeMapping[]>;
|
|
410
|
+
getMapping(clientId: string, mappingId: string): Observable<ScimAttributeMapping>;
|
|
411
|
+
getMappingOptions(): Observable<ScimMappingOptions>;
|
|
412
|
+
previewMappings(clientId: string, resource: Record<string, unknown>, mode?: 'create' | 'replace' | 'patch'): Observable<ScimMappingPreview>;
|
|
413
|
+
createMapping(clientId: string, request: SaveScimAttributeMappingRequest): Observable<ScimAttributeMapping>;
|
|
414
|
+
updateMapping(clientId: string, mappingId: string, request: SaveScimAttributeMappingRequest): Observable<ScimAttributeMapping>;
|
|
415
|
+
deleteMapping(clientId: string, mappingId: string): Observable<void>;
|
|
416
|
+
applyDefaultMappings(clientId: string, provider?: string): Observable<ScimAttributeMapping[]>;
|
|
417
|
+
getProviderOptions(): Observable<ScimProviderOptions>;
|
|
418
|
+
getProviders(): Observable<ScimProvider[]>;
|
|
419
|
+
getProvider(id: string): Observable<ScimProvider>;
|
|
420
|
+
createProvider(request: CreateScimProviderRequest): Observable<ScimProvider>;
|
|
421
|
+
updateProvider(id: string, request: UpdateScimProviderRequest): Observable<ScimProvider>;
|
|
422
|
+
deleteProvider(id: string): Observable<void>;
|
|
423
|
+
setProviderSecret(id: string, secret: string): Observable<ScimProvider>;
|
|
424
|
+
testProvider(id: string): Observable<ScimProviderTestResult>;
|
|
425
|
+
reconcileProvider(id: string): Observable<ScimProviderReconcileResult>;
|
|
426
|
+
previewProvider(id: string, userId: string): Observable<ScimProviderPreview>;
|
|
427
|
+
getProviderQueue(id: string, status?: string, skip?: number, take?: number): Observable<ScimProviderQueueResponse>;
|
|
428
|
+
retryProviderQueue(id: string): Observable<{
|
|
429
|
+
requeued: number;
|
|
430
|
+
}>;
|
|
431
|
+
/** A provider's calls, newest first; `success` false returns only the failed ones. */
|
|
432
|
+
getProviderLogs(id: string, page?: number, pageSize?: number, success?: boolean): Observable<PaginatedResponse<ScimProviderLog>>;
|
|
433
|
+
getProviderResources(id: string, type?: 'User' | 'Group', page?: number, pageSize?: number): Observable<PaginatedResponse<ScimProviderResource>>;
|
|
434
|
+
getProviderMappings(id: string): Observable<ScimProviderAttributeMapping[]>;
|
|
435
|
+
createProviderMapping(id: string, request: SaveScimProviderAttributeMappingRequest): Observable<ScimProviderAttributeMapping>;
|
|
436
|
+
updateProviderMapping(id: string, mappingId: string, request: SaveScimProviderAttributeMappingRequest): Observable<ScimProviderAttributeMapping>;
|
|
437
|
+
deleteProviderMapping(id: string, mappingId: string): Observable<void>;
|
|
438
|
+
applyProviderDefaultMappings(id: string): Observable<ScimProviderAttributeMapping[]>;
|
|
439
|
+
getScimAttributeSuggestions(): ScimAttributeSuggestion[];
|
|
440
|
+
/**
|
|
441
|
+
* The tenant-specific SCIM base URL to configure in an upstream provisioning
|
|
442
|
+
* client. Resolved server-side from the tenant's issuer (custom domain /
|
|
443
|
+
* subdomain), not the admin portal's origin.
|
|
444
|
+
*/
|
|
445
|
+
getScimEndpointUrl(): Observable<{
|
|
446
|
+
url: string;
|
|
447
|
+
}>;
|
|
448
|
+
static ɵfac: _angular_core.ɵɵFactoryDeclaration<ScimService, never>;
|
|
449
|
+
static ɵprov: _angular_core.ɵɵInjectableDeclaration<ScimService>;
|
|
450
|
+
}
|
|
451
|
+
|
|
452
|
+
declare class ScimClientsComponent implements OnInit {
|
|
453
|
+
private readonly scimService;
|
|
454
|
+
clients: _angular_core.WritableSignal<ScimClient[]>;
|
|
455
|
+
loading: _angular_core.WritableSignal<boolean>;
|
|
456
|
+
error: _angular_core.WritableSignal<string | null>;
|
|
457
|
+
showCreateModal: _angular_core.WritableSignal<boolean>;
|
|
458
|
+
newToken: _angular_core.WritableSignal<string | null>;
|
|
459
|
+
copiedToken: _angular_core.WritableSignal<boolean>;
|
|
460
|
+
createForm: {
|
|
461
|
+
name: string;
|
|
462
|
+
description: string;
|
|
463
|
+
};
|
|
464
|
+
scimEndpointUrl: string;
|
|
465
|
+
ngOnInit(): void;
|
|
466
|
+
loadClients(): void;
|
|
467
|
+
handleCreate(): void;
|
|
468
|
+
handleDelete(id: string): void;
|
|
469
|
+
handleRotateToken(id: string): void;
|
|
470
|
+
copyToken(): void;
|
|
471
|
+
formatDate(dateString: string): string;
|
|
472
|
+
static ɵfac: _angular_core.ɵɵFactoryDeclaration<ScimClientsComponent, never>;
|
|
473
|
+
static ɵcmp: _angular_core.ɵɵComponentDeclaration<ScimClientsComponent, "lib-scim-clients", never, {}, {}, never, never, true, never>;
|
|
474
|
+
}
|
|
475
|
+
|
|
476
|
+
declare class ScimClientDetailComponent implements OnInit {
|
|
477
|
+
private readonly scimService;
|
|
478
|
+
private readonly clientService;
|
|
479
|
+
private readonly route;
|
|
480
|
+
private readonly router;
|
|
481
|
+
client: _angular_core.WritableSignal<ScimClient | null>;
|
|
482
|
+
logs: _angular_core.WritableSignal<ScimProvisioningLog[]>;
|
|
483
|
+
mappings: _angular_core.WritableSignal<ScimAttributeMapping[]>;
|
|
484
|
+
oauthClients: _angular_core.WritableSignal<{
|
|
485
|
+
clientId: string;
|
|
486
|
+
clientName: string;
|
|
487
|
+
}[]>;
|
|
488
|
+
loading: _angular_core.WritableSignal<boolean>;
|
|
489
|
+
loadingMappings: _angular_core.WritableSignal<boolean>;
|
|
490
|
+
saving: _angular_core.WritableSignal<boolean>;
|
|
491
|
+
saveError: _angular_core.WritableSignal<string | null>;
|
|
492
|
+
clientId: string;
|
|
493
|
+
formData: {
|
|
494
|
+
name: string;
|
|
495
|
+
description: string;
|
|
496
|
+
isEnabled: boolean;
|
|
497
|
+
allowedIpRanges: string;
|
|
498
|
+
rateLimitPerMinute: number;
|
|
499
|
+
canCreateUsers: boolean;
|
|
500
|
+
canUpdateUsers: boolean;
|
|
501
|
+
canDeleteUsers: boolean;
|
|
502
|
+
canManageGroups: boolean;
|
|
503
|
+
oauthClientId: string;
|
|
504
|
+
};
|
|
505
|
+
ngOnInit(): void;
|
|
506
|
+
loadOAuthClients(): void;
|
|
507
|
+
loadClient(): void;
|
|
508
|
+
loadLogs(): void;
|
|
509
|
+
loadMappings(): void;
|
|
510
|
+
handleSave(): void;
|
|
511
|
+
goBack(): void;
|
|
512
|
+
formatDate(dateString: string): string;
|
|
513
|
+
formatDateShort(dateString: string): string;
|
|
514
|
+
static ɵfac: _angular_core.ɵɵFactoryDeclaration<ScimClientDetailComponent, never>;
|
|
515
|
+
static ɵcmp: _angular_core.ɵɵComponentDeclaration<ScimClientDetailComponent, "lib-scim-client-detail", never, {}, {}, never, never, true, never>;
|
|
516
|
+
}
|
|
517
|
+
|
|
518
|
+
interface MappingFormData {
|
|
519
|
+
scimAttribute: string;
|
|
520
|
+
internalProperty: string;
|
|
521
|
+
source: 'attribute' | 'expression';
|
|
522
|
+
expression: string;
|
|
523
|
+
condition: string;
|
|
524
|
+
isRequired: boolean;
|
|
525
|
+
defaultValue: string;
|
|
526
|
+
transformation: string;
|
|
527
|
+
priority: number;
|
|
528
|
+
isEnabled: boolean;
|
|
529
|
+
}
|
|
530
|
+
declare class ScimMappingsComponent implements OnInit {
|
|
531
|
+
private readonly scimService;
|
|
532
|
+
private readonly route;
|
|
533
|
+
client: _angular_core.WritableSignal<ScimClient | null>;
|
|
534
|
+
mappings: _angular_core.WritableSignal<ScimAttributeMapping[]>;
|
|
535
|
+
options: _angular_core.WritableSignal<ScimMappingOptions | null>;
|
|
536
|
+
loading: _angular_core.WritableSignal<boolean>;
|
|
537
|
+
error: _angular_core.WritableSignal<string | null>;
|
|
538
|
+
formError: _angular_core.WritableSignal<string | null>;
|
|
539
|
+
showForm: _angular_core.WritableSignal<boolean>;
|
|
540
|
+
editingMapping: _angular_core.WritableSignal<ScimAttributeMapping | null>;
|
|
541
|
+
saving: _angular_core.WritableSignal<boolean>;
|
|
542
|
+
showDefaultsModal: _angular_core.WritableSignal<boolean>;
|
|
543
|
+
selectedProvider: string;
|
|
544
|
+
clientId: string;
|
|
545
|
+
previewJson: string;
|
|
546
|
+
previewMode: 'create' | 'replace' | 'patch';
|
|
547
|
+
previewing: _angular_core.WritableSignal<boolean>;
|
|
548
|
+
preview: _angular_core.WritableSignal<ScimMappingPreview | null>;
|
|
549
|
+
previewError: _angular_core.WritableSignal<string | null>;
|
|
550
|
+
previewFields: _angular_core.WritableSignal<{
|
|
551
|
+
key: string;
|
|
552
|
+
value: string | null;
|
|
553
|
+
}[]>;
|
|
554
|
+
formData: MappingFormData;
|
|
555
|
+
scimSuggestions: ScimAttributeSuggestion[];
|
|
556
|
+
/** The server's mapping-options decide which properties and transformations are offered. */
|
|
557
|
+
internalProperties: _angular_core.Signal<_syndew_oluso_plugin_scim.InternalPropertyOption[]>;
|
|
558
|
+
transformations: _angular_core.Signal<_syndew_oluso_plugin_scim.TransformationOption[]>;
|
|
559
|
+
ngOnInit(): void;
|
|
560
|
+
loadData(): void;
|
|
561
|
+
openCreateForm(): void;
|
|
562
|
+
closeForm(): void;
|
|
563
|
+
handleEdit(mapping: ScimAttributeMapping): void;
|
|
564
|
+
handleSubmit(): void;
|
|
565
|
+
handleDelete(mappingId: string): void;
|
|
566
|
+
handleToggleEnabled(mapping: ScimAttributeMapping): void;
|
|
567
|
+
handleApplyDefaults(): void;
|
|
568
|
+
runPreview(): void;
|
|
569
|
+
private toRequest;
|
|
570
|
+
private messageOf;
|
|
571
|
+
static ɵfac: _angular_core.ɵɵFactoryDeclaration<ScimMappingsComponent, never>;
|
|
572
|
+
static ɵcmp: _angular_core.ɵɵComponentDeclaration<ScimMappingsComponent, "lib-scim-mappings", never, {}, {}, never, never, true, never>;
|
|
573
|
+
}
|
|
574
|
+
|
|
575
|
+
declare class ScimProvidersComponent implements OnInit {
|
|
576
|
+
private readonly scimService;
|
|
577
|
+
private readonly router;
|
|
578
|
+
providers: _angular_core.WritableSignal<ScimProvider[]>;
|
|
579
|
+
options: _angular_core.WritableSignal<ScimProviderOptions | null>;
|
|
580
|
+
flavors: _angular_core.Signal<ScimProviderFlavor[]>;
|
|
581
|
+
loading: _angular_core.WritableSignal<boolean>;
|
|
582
|
+
error: _angular_core.WritableSignal<string | null>;
|
|
583
|
+
showCreateModal: _angular_core.WritableSignal<boolean>;
|
|
584
|
+
creating: _angular_core.WritableSignal<boolean>;
|
|
585
|
+
createError: _angular_core.WritableSignal<string | null>;
|
|
586
|
+
showSecret: _angular_core.WritableSignal<boolean>;
|
|
587
|
+
selectedFlavorKey: _angular_core.WritableSignal<string>;
|
|
588
|
+
selectedFlavor: _angular_core.Signal<ScimProviderFlavor | null>;
|
|
589
|
+
createForm: {
|
|
590
|
+
name: string;
|
|
591
|
+
description: string;
|
|
592
|
+
flavor: string;
|
|
593
|
+
baseUrl: string;
|
|
594
|
+
authType: ScimProviderAuthType;
|
|
595
|
+
oauthTokenEndpoint: string;
|
|
596
|
+
oauthClientId: string;
|
|
597
|
+
oauthScope: string;
|
|
598
|
+
secret: string;
|
|
599
|
+
};
|
|
600
|
+
activityProvider: _angular_core.WritableSignal<ScimProvider | null>;
|
|
601
|
+
activityErrorsOnly: _angular_core.WritableSignal<boolean>;
|
|
602
|
+
activityLogs: _angular_core.WritableSignal<ScimProviderLog[]>;
|
|
603
|
+
activityPage: _angular_core.WritableSignal<number>;
|
|
604
|
+
activityTotal: _angular_core.WritableSignal<number>;
|
|
605
|
+
activityTotalPages: _angular_core.WritableSignal<number>;
|
|
606
|
+
activityLoading: _angular_core.WritableSignal<boolean>;
|
|
607
|
+
activityError: _angular_core.WritableSignal<string | null>;
|
|
608
|
+
private readonly activityPageSize;
|
|
609
|
+
private activityRequest?;
|
|
610
|
+
ngOnInit(): void;
|
|
611
|
+
loadProviders(): void;
|
|
612
|
+
openCreate(): void;
|
|
613
|
+
onFlavorChange(key: string): void;
|
|
614
|
+
handleCreate(): void;
|
|
615
|
+
handleDelete(p: ScimProvider): void;
|
|
616
|
+
openActivity(p: ScimProvider, errorsOnly: boolean): void;
|
|
617
|
+
closeActivity(): void;
|
|
618
|
+
setActivityErrorsOnly(errorsOnly: boolean): void;
|
|
619
|
+
goToActivityPage(page: number): void;
|
|
620
|
+
loadActivity(): void;
|
|
621
|
+
flavorName(key: string): string;
|
|
622
|
+
formatDate(dateString: string): string;
|
|
623
|
+
private emptyForm;
|
|
624
|
+
static ɵfac: _angular_core.ɵɵFactoryDeclaration<ScimProvidersComponent, never>;
|
|
625
|
+
static ɵcmp: _angular_core.ɵɵComponentDeclaration<ScimProvidersComponent, "lib-scim-providers", never, {}, {}, never, never, true, never>;
|
|
626
|
+
}
|
|
627
|
+
|
|
628
|
+
interface MappingForm {
|
|
629
|
+
id: string | null;
|
|
630
|
+
scimAttribute: string;
|
|
631
|
+
source: 'property' | 'expression';
|
|
632
|
+
internalProperty: string;
|
|
633
|
+
expression: string;
|
|
634
|
+
condition: string;
|
|
635
|
+
transformation: string;
|
|
636
|
+
defaultValue: string;
|
|
637
|
+
isEnabled: boolean;
|
|
638
|
+
}
|
|
639
|
+
declare class ScimProviderDetailComponent implements OnInit {
|
|
640
|
+
private readonly scimService;
|
|
641
|
+
private readonly roleService;
|
|
642
|
+
private readonly teamService;
|
|
643
|
+
private readonly route;
|
|
644
|
+
private readonly router;
|
|
645
|
+
providerId: string;
|
|
646
|
+
provider: _angular_core.WritableSignal<ScimProvider | null>;
|
|
647
|
+
options: _angular_core.WritableSignal<ScimProviderOptions | null>;
|
|
648
|
+
flavors: _angular_core.Signal<ScimProviderFlavor[]>;
|
|
649
|
+
internalProperties: _angular_core.Signal<string[]>;
|
|
650
|
+
transformations: _angular_core.Signal<string[]>;
|
|
651
|
+
roles: _angular_core.WritableSignal<RoleDto[]>;
|
|
652
|
+
teams: _angular_core.WritableSignal<TeamSummary[]>;
|
|
653
|
+
inboundClients: _angular_core.WritableSignal<ScimClient[]>;
|
|
654
|
+
loading: _angular_core.WritableSignal<boolean>;
|
|
655
|
+
saving: _angular_core.WritableSignal<boolean>;
|
|
656
|
+
saveError: _angular_core.WritableSignal<string | null>;
|
|
657
|
+
selectedFlavorKey: _angular_core.WritableSignal<string>;
|
|
658
|
+
selectedFlavor: _angular_core.Signal<ScimProviderFlavor | null>;
|
|
659
|
+
groupsUnsupported: _angular_core.Signal<boolean>;
|
|
660
|
+
scopeRoleIds: _angular_core.WritableSignal<Set<string>>;
|
|
661
|
+
scopeTeamIds: _angular_core.WritableSignal<Set<string>>;
|
|
662
|
+
mappings: _angular_core.WritableSignal<ScimProviderAttributeMapping[]>;
|
|
663
|
+
loadingMappings: _angular_core.WritableSignal<boolean>;
|
|
664
|
+
mappingForm: _angular_core.WritableSignal<MappingForm | null>;
|
|
665
|
+
mappingError: _angular_core.WritableSignal<string | null>;
|
|
666
|
+
savingMapping: _angular_core.WritableSignal<boolean>;
|
|
667
|
+
previewUserId: string;
|
|
668
|
+
previewing: _angular_core.WritableSignal<boolean>;
|
|
669
|
+
preview: _angular_core.WritableSignal<ScimProviderPreview | null>;
|
|
670
|
+
queue: _angular_core.WritableSignal<ScimProviderQueueResponse | null>;
|
|
671
|
+
queueFilter: string;
|
|
672
|
+
queueMessage: _angular_core.WritableSignal<string | null>;
|
|
673
|
+
reconciling: _angular_core.WritableSignal<boolean>;
|
|
674
|
+
logs: _angular_core.WritableSignal<ScimProviderLog[]>;
|
|
675
|
+
resourceCounts: _angular_core.WritableSignal<{
|
|
676
|
+
users: number;
|
|
677
|
+
groups: number;
|
|
678
|
+
}>;
|
|
679
|
+
newSecret: string;
|
|
680
|
+
showSecret: _angular_core.WritableSignal<boolean>;
|
|
681
|
+
savingSecret: _angular_core.WritableSignal<boolean>;
|
|
682
|
+
secretError: _angular_core.WritableSignal<string | null>;
|
|
683
|
+
testing: _angular_core.WritableSignal<boolean>;
|
|
684
|
+
testResult: _angular_core.WritableSignal<ScimProviderTestResult | null>;
|
|
685
|
+
readonly attributeSuggestions: string[];
|
|
686
|
+
form: {
|
|
687
|
+
name: string;
|
|
688
|
+
description: string;
|
|
689
|
+
isEnabled: boolean;
|
|
690
|
+
flavor: string;
|
|
691
|
+
baseUrl: string;
|
|
692
|
+
authType: ScimProviderAuthType;
|
|
693
|
+
oauthTokenEndpoint: string;
|
|
694
|
+
oauthClientId: string;
|
|
695
|
+
oauthScope: string;
|
|
696
|
+
syncUsers: boolean;
|
|
697
|
+
syncGroups: boolean;
|
|
698
|
+
groupSource: ScimProviderGroupSource;
|
|
699
|
+
userNameSource: ScimProviderUserNameSource;
|
|
700
|
+
userNameExpression: string;
|
|
701
|
+
deprovisionMode: ScimProviderDeprovisionMode;
|
|
702
|
+
reconcileIntervalMinutes: number;
|
|
703
|
+
linkedScimClientId: string;
|
|
704
|
+
};
|
|
705
|
+
ngOnInit(): void;
|
|
706
|
+
loadProvider(): void;
|
|
707
|
+
private applyProvider;
|
|
708
|
+
onFlavorChange(key: string): void;
|
|
709
|
+
toggleScopeRole(id: string): void;
|
|
710
|
+
toggleScopeTeam(id: string): void;
|
|
711
|
+
handleSave(): void;
|
|
712
|
+
saveSecret(): void;
|
|
713
|
+
testConnection(): void;
|
|
714
|
+
loadMappings(): void;
|
|
715
|
+
startNewMapping(): void;
|
|
716
|
+
editMapping(m: ScimProviderAttributeMapping): void;
|
|
717
|
+
saveMapping(): void;
|
|
718
|
+
deleteMapping(m: ScimProviderAttributeMapping): void;
|
|
719
|
+
applyDefaults(): void;
|
|
720
|
+
runPreview(): void;
|
|
721
|
+
loadQueue(): void;
|
|
722
|
+
retryFailed(): void;
|
|
723
|
+
runReconcile(): void;
|
|
724
|
+
loadLogs(): void;
|
|
725
|
+
loadResourceCounts(): void;
|
|
726
|
+
statusClass(status: ScimQueueStatus): string;
|
|
727
|
+
flavorName(key: string): string;
|
|
728
|
+
goBack(): void;
|
|
729
|
+
formatDate(dateString: string): string;
|
|
730
|
+
static ɵfac: _angular_core.ɵɵFactoryDeclaration<ScimProviderDetailComponent, never>;
|
|
731
|
+
static ɵcmp: _angular_core.ɵɵComponentDeclaration<ScimProviderDetailComponent, "lib-scim-provider-detail", never, {}, {}, never, never, true, never>;
|
|
732
|
+
}
|
|
733
|
+
|
|
734
|
+
export { SCIM_PLUGIN, SCIM_ROUTES, ScimClientDetailComponent, ScimClientsComponent, ScimMappingsComponent, ScimProviderDetailComponent, ScimProvidersComponent, ScimService, getScimNavItems };
|
|
735
|
+
export type { CreateScimAttributeMappingRequest, CreateScimClientRequest, CreateScimClientResponse, CreateScimProviderRequest, InternalPropertyOption, SaveScimAttributeMappingRequest, SaveScimProviderAttributeMappingRequest, ScimAttributeMapping, ScimAttributeSuggestion, ScimClient, ScimMappingOptions, ScimMappingPreview, ScimProvider, ScimProviderAttributeMapping, ScimProviderAuthType, ScimProviderDeprovisionMode, ScimProviderFlavor, ScimProviderGroupSource, ScimProviderLog, ScimProviderOptions, ScimProviderPreview, ScimProviderQueueItem, ScimProviderQueueResponse, ScimProviderQueueSummary, ScimProviderReconcileResult, ScimProviderResource, ScimProviderTestResult, ScimProviderUserNameSource, ScimProvisioningLog, ScimQueueStatus, TransformationOption, UpdateScimProviderRequest };
|