@stndrds/schema 0.1.0-alpha.56 → 0.1.0-alpha.58
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.
- package/dist/{chunk-XBF4EUC4.js → chunk-2OS63USQ.js} +1550 -1250
- package/dist/{chunk-LOOGQL6M.mjs → chunk-JRY236AO.mjs} +1307 -1007
- package/dist/chunk-NEVERCM3.js +41 -0
- package/dist/chunk-SV4BCGQU.mjs +617 -0
- package/dist/chunk-U4AB53AM.js +617 -0
- package/dist/chunk-V2RPPE2Y.mjs +41 -0
- package/dist/index.d.mts +942 -55
- package/dist/index.d.ts +942 -55
- package/dist/index.js +922 -69
- package/dist/index.mjs +988 -135
- package/dist/{runtime-D5MuaVQs.d.mts → runtime-C4vB_EcQ.d.ts} +759 -1779
- package/dist/{runtime-D5MuaVQs.d.ts → runtime-SCsDOQi0.d.mts} +759 -1779
- package/dist/runtime.d.mts +3 -1
- package/dist/runtime.d.ts +3 -1
- package/dist/runtime.js +26 -2
- package/dist/runtime.mjs +25 -1
- package/dist/utils.d.mts +154 -0
- package/dist/utils.d.ts +154 -0
- package/dist/utils.js +19 -0
- package/dist/utils.mjs +19 -0
- package/dist/validation/validators.d.mts +4 -0
- package/dist/validation/validators.d.ts +4 -0
- package/dist/validation/validators.js +121 -0
- package/dist/validation/validators.mjs +121 -0
- package/dist/validators-BgmWgr-G.d.mts +1488 -0
- package/dist/validators-miARInAq.d.ts +1488 -0
- package/package.json +12 -2
package/dist/index.mjs
CHANGED
|
@@ -4,6 +4,7 @@ import {
|
|
|
4
4
|
AttributeNotFoundError,
|
|
5
5
|
AuditService,
|
|
6
6
|
AuthMethodSchema,
|
|
7
|
+
BEHAVIOR_PROPERTIES,
|
|
7
8
|
BaseRepository,
|
|
8
9
|
BaseService,
|
|
9
10
|
ConcurrentModificationError,
|
|
@@ -16,8 +17,8 @@ import {
|
|
|
16
17
|
CustomTabConfig,
|
|
17
18
|
DEFAULT_LABEL_FALLBACK,
|
|
18
19
|
DEFAULT_THEME,
|
|
19
|
-
DEFAULT_VALIDATION_MESSAGES,
|
|
20
20
|
DRIVING_LICENSE,
|
|
21
|
+
DetailViewBuilder,
|
|
21
22
|
DirectTableTabConfig,
|
|
22
23
|
DocumentExecutor,
|
|
23
24
|
DocumentGenerationNotConfiguredError,
|
|
@@ -37,6 +38,7 @@ import {
|
|
|
37
38
|
EndNodeSchema,
|
|
38
39
|
ExecutorRegistry,
|
|
39
40
|
FRENCH_ID_CARD,
|
|
41
|
+
FeatureFlagsContextError,
|
|
40
42
|
FileNotFoundError,
|
|
41
43
|
FileService,
|
|
42
44
|
FlowRowFieldSchema,
|
|
@@ -54,12 +56,15 @@ import {
|
|
|
54
56
|
GrantNotFoundError,
|
|
55
57
|
GrantRevokedError,
|
|
56
58
|
GroupBuilder,
|
|
59
|
+
IDENTITY_PROPERTIES,
|
|
57
60
|
InvalidPathError,
|
|
58
61
|
InverseTableTabConfig,
|
|
59
62
|
InvitationAlreadyAcceptedError,
|
|
60
63
|
InvitationExpiredError,
|
|
61
64
|
InvitationNotFoundError,
|
|
62
65
|
InvitationRevokedError,
|
|
66
|
+
ListViewBuilder,
|
|
67
|
+
ListViewTabConfigBuilder,
|
|
63
68
|
MaxDepthExceededError,
|
|
64
69
|
NodePositionSchema,
|
|
65
70
|
NoopCacheAdapter,
|
|
@@ -73,6 +78,7 @@ import {
|
|
|
73
78
|
ObjectReferencedError,
|
|
74
79
|
ObjectSchemaService,
|
|
75
80
|
PASSPORT,
|
|
81
|
+
PRESENTATION_PROPERTIES,
|
|
76
82
|
PROOF_OF_ADDRESS,
|
|
77
83
|
PermissionService,
|
|
78
84
|
PolicyRegistry,
|
|
@@ -144,9 +150,6 @@ import {
|
|
|
144
150
|
addSchemaToContext,
|
|
145
151
|
and,
|
|
146
152
|
applyDefaultValues,
|
|
147
|
-
asTenantId,
|
|
148
|
-
asUserId,
|
|
149
|
-
attributeConfigSchemas,
|
|
150
153
|
buildAuditChanges,
|
|
151
154
|
buildPolicyContext,
|
|
152
155
|
cacheKeys,
|
|
@@ -159,53 +162,25 @@ import {
|
|
|
159
162
|
checkRecordModifyOrThrow,
|
|
160
163
|
checkSharedObjectWriteAccess,
|
|
161
164
|
checkbox,
|
|
162
|
-
checkboxConfigSchema,
|
|
163
165
|
complete,
|
|
164
166
|
computeLabel,
|
|
165
167
|
computeLabelWithRelations,
|
|
166
|
-
computeRecordStatus,
|
|
167
|
-
createAttributeValidator,
|
|
168
|
-
createCheckboxValidator,
|
|
169
168
|
createContextForCreate,
|
|
170
169
|
createContextForDelete,
|
|
171
170
|
createContextForRestore,
|
|
172
171
|
createContextForUpdate,
|
|
173
|
-
createCurrencyValidator,
|
|
174
|
-
createDateValidator,
|
|
175
172
|
createDefaultExecutorRegistry,
|
|
176
173
|
createDefaultState,
|
|
177
|
-
createDraftValidator,
|
|
178
174
|
createEmptyContext,
|
|
179
|
-
createFileValidator,
|
|
180
|
-
createFormAttributeValidator,
|
|
181
|
-
createFormulaValidator,
|
|
182
|
-
createLocationValidator,
|
|
183
175
|
createMockAdapter,
|
|
184
|
-
createMultiRelationValidator,
|
|
185
|
-
createMultiselectValidator,
|
|
186
|
-
createNumberValidator,
|
|
187
|
-
createObjectValidator,
|
|
188
|
-
createPhoneValidator,
|
|
189
176
|
createQueryBuilder,
|
|
190
|
-
createRatingValidator,
|
|
191
|
-
createRelationValidator,
|
|
192
|
-
createRichtextValidator,
|
|
193
|
-
createRollupValidator,
|
|
194
|
-
createSelectValidator,
|
|
195
|
-
createSingleRelationValidator,
|
|
196
177
|
createStartTransition,
|
|
197
|
-
createStatusValidator,
|
|
198
|
-
createTextAreaValidator,
|
|
199
|
-
createTextValidator,
|
|
200
|
-
createUserValidator,
|
|
201
178
|
currency,
|
|
202
|
-
currencyConfigSchema,
|
|
203
179
|
date,
|
|
204
|
-
dateConfigSchema,
|
|
205
180
|
defaultPolicyRegistry,
|
|
206
181
|
defaultTtl,
|
|
182
|
+
detailView,
|
|
207
183
|
document,
|
|
208
|
-
documentConfigSchema,
|
|
209
184
|
enrichRecordsWithFormulas,
|
|
210
185
|
enrichValuesForDisplay,
|
|
211
186
|
enrichValuesWithSelectLabels,
|
|
@@ -226,23 +201,18 @@ import {
|
|
|
226
201
|
extractRelationNames,
|
|
227
202
|
extractRelationReferences,
|
|
228
203
|
file,
|
|
229
|
-
fileConfigSchema,
|
|
230
204
|
flattenRelationsForEval,
|
|
231
205
|
formatAttributeValue,
|
|
232
206
|
formatFormulaResult,
|
|
233
207
|
formatRecord,
|
|
234
208
|
formatRecords,
|
|
235
209
|
formula,
|
|
236
|
-
formulaConfigSchema,
|
|
237
210
|
generateCssVariables,
|
|
238
|
-
generateId,
|
|
239
|
-
generatePrefixedId,
|
|
240
|
-
generateTemplateName,
|
|
241
|
-
getAttributeConfigSchema,
|
|
242
211
|
getContext,
|
|
243
212
|
getContextValue,
|
|
244
213
|
getDefaultExecutorRegistry,
|
|
245
|
-
|
|
214
|
+
getFeatureFlags,
|
|
215
|
+
getFeatureValue,
|
|
246
216
|
getNodeOutputs,
|
|
247
217
|
getPathDepth,
|
|
248
218
|
getPolicy,
|
|
@@ -256,26 +226,31 @@ import {
|
|
|
256
226
|
getTargetAttributeName,
|
|
257
227
|
getTenantId,
|
|
258
228
|
getUserId,
|
|
229
|
+
getViewSeedPreview,
|
|
259
230
|
getViewSyncPreview,
|
|
260
231
|
group,
|
|
261
232
|
hasContext,
|
|
233
|
+
hasFeatureFlagsContext,
|
|
234
|
+
hasProperties,
|
|
262
235
|
hasRelationReferences,
|
|
263
236
|
hasSchemaContext,
|
|
264
237
|
hashOptions,
|
|
265
238
|
inValues,
|
|
266
239
|
isAdvancedFormNode,
|
|
267
|
-
|
|
240
|
+
isBehaviorProperty,
|
|
268
241
|
isConditionGroup,
|
|
269
242
|
isConditionNode,
|
|
270
243
|
isConditionRule,
|
|
271
244
|
isDocumentNode,
|
|
272
245
|
isEmpty,
|
|
273
246
|
isEndNode,
|
|
247
|
+
isFeatureEnabled,
|
|
274
248
|
isForbiddenError,
|
|
275
249
|
isFormNode,
|
|
276
250
|
isGrantExpired,
|
|
277
251
|
isGrantRevoked,
|
|
278
252
|
isGrantValid,
|
|
253
|
+
isIdentityProperty,
|
|
279
254
|
isInstanceEvent,
|
|
280
255
|
isInstanceTerminal,
|
|
281
256
|
isInstanceWaiting,
|
|
@@ -287,8 +262,8 @@ import {
|
|
|
287
262
|
isNodeEvent,
|
|
288
263
|
isNotEmpty,
|
|
289
264
|
isNotFoundError,
|
|
265
|
+
isPresentationProperty,
|
|
290
266
|
isProtectedResourceError,
|
|
291
|
-
isRecordComplete,
|
|
292
267
|
isSchemaError,
|
|
293
268
|
isSimpleFormNode,
|
|
294
269
|
isStartNode,
|
|
@@ -301,72 +276,125 @@ import {
|
|
|
301
276
|
isValidationError,
|
|
302
277
|
isWorkflowDefinition,
|
|
303
278
|
isWorkflowPublished,
|
|
279
|
+
listView,
|
|
304
280
|
location,
|
|
305
|
-
locationConfigSchema,
|
|
306
|
-
mergeFormToSlot,
|
|
307
281
|
mergeWithDefaults,
|
|
308
282
|
multiselect,
|
|
309
|
-
multiselectConfigSchema,
|
|
310
283
|
neq,
|
|
311
284
|
notesPolicy,
|
|
312
285
|
number,
|
|
313
|
-
numberConfigSchema,
|
|
314
286
|
object,
|
|
315
287
|
or,
|
|
316
|
-
parseAttributeConfig,
|
|
317
288
|
parsePath,
|
|
318
289
|
pathHasManyCardinality,
|
|
319
290
|
phone,
|
|
320
|
-
phoneConfigSchema,
|
|
321
291
|
rating,
|
|
322
|
-
ratingConfigSchema,
|
|
323
292
|
recalculateParentRollups,
|
|
324
293
|
registry,
|
|
325
294
|
relation,
|
|
326
|
-
relationConfigSchema,
|
|
327
295
|
renderLabelExpression,
|
|
328
296
|
resolveMultiplePaths,
|
|
329
297
|
resolveSingleValue,
|
|
330
298
|
richtext,
|
|
331
|
-
richtextConfigSchema,
|
|
332
299
|
rollup,
|
|
333
|
-
rollupConfigSchema,
|
|
334
300
|
runWithContext,
|
|
301
|
+
runWithFeatureFlags,
|
|
335
302
|
runWithMergedSchemaContext,
|
|
336
303
|
runWithSchemaContext,
|
|
337
|
-
|
|
304
|
+
seedRegistryViews,
|
|
338
305
|
select,
|
|
339
|
-
selectConfigSchema,
|
|
340
306
|
setContextValue,
|
|
341
|
-
slugify,
|
|
342
307
|
status,
|
|
343
|
-
statusConfigSchema,
|
|
344
308
|
success,
|
|
345
309
|
syncAll,
|
|
346
310
|
syncNativeObjects,
|
|
347
311
|
syncNativeViews,
|
|
348
312
|
text,
|
|
349
|
-
textConfigSchema,
|
|
350
313
|
textarea,
|
|
351
|
-
|
|
314
|
+
toUndefinedIfEmpty,
|
|
352
315
|
traversePath,
|
|
316
|
+
tryGetFeatureValue,
|
|
353
317
|
user,
|
|
354
|
-
userConfigSchema,
|
|
355
|
-
validateAttribute,
|
|
356
|
-
validateAttributeConfig,
|
|
357
|
-
validateDraft,
|
|
358
|
-
validateDraftOrThrow,
|
|
359
318
|
validateFormulaExpression,
|
|
360
|
-
validateObject,
|
|
361
|
-
validateObjectOrThrow,
|
|
362
319
|
validatePath,
|
|
363
320
|
verifyNativeObjectsSync,
|
|
364
321
|
verifyNativeViewsSync,
|
|
322
|
+
verifyRegistryViewsSeeded,
|
|
365
323
|
view,
|
|
366
324
|
wait,
|
|
325
|
+
withFeatureFlags,
|
|
367
326
|
withTenantContext,
|
|
368
327
|
workflow
|
|
369
|
-
} from "./chunk-
|
|
328
|
+
} from "./chunk-JRY236AO.mjs";
|
|
329
|
+
import {
|
|
330
|
+
asTenantId,
|
|
331
|
+
asUserId,
|
|
332
|
+
generateId,
|
|
333
|
+
generatePrefixedId,
|
|
334
|
+
generateTemplateName,
|
|
335
|
+
indexBy,
|
|
336
|
+
slugify
|
|
337
|
+
} from "./chunk-V2RPPE2Y.mjs";
|
|
338
|
+
import {
|
|
339
|
+
DEFAULT_VALIDATION_MESSAGES,
|
|
340
|
+
attributeConfigSchemas,
|
|
341
|
+
checkboxConfigSchema,
|
|
342
|
+
computeRecordStatus,
|
|
343
|
+
createAttributeValidator,
|
|
344
|
+
createCheckboxValidator,
|
|
345
|
+
createCurrencyValidator,
|
|
346
|
+
createDateValidator,
|
|
347
|
+
createDraftValidator,
|
|
348
|
+
createFileValidator,
|
|
349
|
+
createFormAttributeValidator,
|
|
350
|
+
createFormulaValidator,
|
|
351
|
+
createLocationValidator,
|
|
352
|
+
createMultiRelationValidator,
|
|
353
|
+
createMultiselectValidator,
|
|
354
|
+
createNumberValidator,
|
|
355
|
+
createObjectValidator,
|
|
356
|
+
createPhoneValidator,
|
|
357
|
+
createRatingValidator,
|
|
358
|
+
createRelationValidator,
|
|
359
|
+
createRichtextValidator,
|
|
360
|
+
createRollupValidator,
|
|
361
|
+
createSelectValidator,
|
|
362
|
+
createSingleRelationValidator,
|
|
363
|
+
createStatusValidator,
|
|
364
|
+
createTextAreaValidator,
|
|
365
|
+
createTextValidator,
|
|
366
|
+
createUserValidator,
|
|
367
|
+
currencyConfigSchema,
|
|
368
|
+
dateConfigSchema,
|
|
369
|
+
documentConfigSchema,
|
|
370
|
+
fileConfigSchema,
|
|
371
|
+
formatZodErrors,
|
|
372
|
+
formulaConfigSchema,
|
|
373
|
+
getAttributeConfigSchema,
|
|
374
|
+
getMissingRequiredAttributes,
|
|
375
|
+
isRecordComplete,
|
|
376
|
+
locationConfigSchema,
|
|
377
|
+
multiselectConfigSchema,
|
|
378
|
+
numberConfigSchema,
|
|
379
|
+
parseAttributeConfig,
|
|
380
|
+
phoneConfigSchema,
|
|
381
|
+
ratingConfigSchema,
|
|
382
|
+
relationConfigSchema,
|
|
383
|
+
richtextConfigSchema,
|
|
384
|
+
rollupConfigSchema,
|
|
385
|
+
safeParseAttributeConfig,
|
|
386
|
+
selectConfigSchema,
|
|
387
|
+
statusConfigSchema,
|
|
388
|
+
textConfigSchema,
|
|
389
|
+
textareaConfigSchema,
|
|
390
|
+
userConfigSchema,
|
|
391
|
+
validateAttribute,
|
|
392
|
+
validateAttributeConfig,
|
|
393
|
+
validateDraft,
|
|
394
|
+
validateDraftOrThrow,
|
|
395
|
+
validateObject,
|
|
396
|
+
validateObjectOrThrow
|
|
397
|
+
} from "./chunk-SV4BCGQU.mjs";
|
|
370
398
|
import {
|
|
371
399
|
ALL_SYSTEM_RESOURCES,
|
|
372
400
|
DEFAULT_ROLES,
|
|
@@ -379,43 +407,7 @@ import {
|
|
|
379
407
|
} from "./chunk-V5QXU2OK.mjs";
|
|
380
408
|
import "./chunk-Y6FXYEAI.mjs";
|
|
381
409
|
|
|
382
|
-
// src/types/document-generation.ts
|
|
383
|
-
function isPdfTemplateSource(source) {
|
|
384
|
-
return source.type === "pdf";
|
|
385
|
-
}
|
|
386
|
-
function isDocxTemplateSource(source) {
|
|
387
|
-
return source.type === "docx";
|
|
388
|
-
}
|
|
389
|
-
|
|
390
410
|
// src/types/filters.ts
|
|
391
|
-
function isAdvancedFilterState(state) {
|
|
392
|
-
return "groups" in state;
|
|
393
|
-
}
|
|
394
|
-
function toAdvancedFilterState(state) {
|
|
395
|
-
if (state.rules.length === 0) {
|
|
396
|
-
return {
|
|
397
|
-
combinator: state.combinator,
|
|
398
|
-
groups: []
|
|
399
|
-
};
|
|
400
|
-
}
|
|
401
|
-
return {
|
|
402
|
-
combinator: "and",
|
|
403
|
-
groups: [
|
|
404
|
-
{
|
|
405
|
-
id: crypto.randomUUID(),
|
|
406
|
-
combinator: state.combinator,
|
|
407
|
-
rules: state.rules
|
|
408
|
-
}
|
|
409
|
-
]
|
|
410
|
-
};
|
|
411
|
-
}
|
|
412
|
-
function toSimpleFilterState(state) {
|
|
413
|
-
const allRules = state.groups.flatMap((group2) => group2.rules);
|
|
414
|
-
return {
|
|
415
|
-
combinator: state.combinator,
|
|
416
|
-
rules: allRules
|
|
417
|
-
};
|
|
418
|
-
}
|
|
419
411
|
var OPERATORS_BY_TYPE = {
|
|
420
412
|
text: [
|
|
421
413
|
"is",
|
|
@@ -503,6 +495,21 @@ function isSystemFlow(flow) {
|
|
|
503
495
|
}
|
|
504
496
|
|
|
505
497
|
// src/types/views.ts
|
|
498
|
+
function isDetailView(view2) {
|
|
499
|
+
return view2.type === "detail";
|
|
500
|
+
}
|
|
501
|
+
function isListView(view2) {
|
|
502
|
+
return view2.type === "list";
|
|
503
|
+
}
|
|
504
|
+
function isCalendarView(view2) {
|
|
505
|
+
return view2.type === "calendar";
|
|
506
|
+
}
|
|
507
|
+
function isTimelineView(view2) {
|
|
508
|
+
return view2.type === "timeline";
|
|
509
|
+
}
|
|
510
|
+
function isGalleryView(view2) {
|
|
511
|
+
return view2.type === "gallery";
|
|
512
|
+
}
|
|
506
513
|
function isFormTab(tab) {
|
|
507
514
|
return tab.type === "form";
|
|
508
515
|
}
|
|
@@ -531,6 +538,523 @@ function isDocumentsTab(tab) {
|
|
|
531
538
|
return tab.type === "documents";
|
|
532
539
|
}
|
|
533
540
|
|
|
541
|
+
// src/feature-flags/flag-builder.ts
|
|
542
|
+
function validateFlagName(name) {
|
|
543
|
+
if (!/^[a-z][a-z0-9-]*[a-z0-9]$|^[a-z]$/.test(name)) {
|
|
544
|
+
throw new Error(
|
|
545
|
+
`Invalid flag name "${name}". Flag names must be kebab-case (e.g., "architect-mode", "ai-features").`
|
|
546
|
+
);
|
|
547
|
+
}
|
|
548
|
+
}
|
|
549
|
+
var BaseFlagBuilder = class {
|
|
550
|
+
constructor(name, valueType, defaultValue) {
|
|
551
|
+
validateFlagName(name);
|
|
552
|
+
this.flag = {
|
|
553
|
+
name,
|
|
554
|
+
valueType,
|
|
555
|
+
defaultValue,
|
|
556
|
+
allowedLevels: ["global", "tenant", "user"]
|
|
557
|
+
};
|
|
558
|
+
}
|
|
559
|
+
/**
|
|
560
|
+
* Set the human-readable label for the flag.
|
|
561
|
+
* Required - build() will throw if not set.
|
|
562
|
+
*/
|
|
563
|
+
label(value) {
|
|
564
|
+
this.flag.label = value;
|
|
565
|
+
return this;
|
|
566
|
+
}
|
|
567
|
+
/**
|
|
568
|
+
* Set an optional description for the flag.
|
|
569
|
+
*/
|
|
570
|
+
description(value) {
|
|
571
|
+
this.flag.description = value;
|
|
572
|
+
return this;
|
|
573
|
+
}
|
|
574
|
+
/**
|
|
575
|
+
* Set a category for grouping flags in UI.
|
|
576
|
+
*/
|
|
577
|
+
category(value) {
|
|
578
|
+
this.flag.category = value;
|
|
579
|
+
return this;
|
|
580
|
+
}
|
|
581
|
+
/**
|
|
582
|
+
* Mark this flag as a system flag.
|
|
583
|
+
* System flags cannot be modified via API.
|
|
584
|
+
*/
|
|
585
|
+
system() {
|
|
586
|
+
this.flag.system = true;
|
|
587
|
+
return this;
|
|
588
|
+
}
|
|
589
|
+
/**
|
|
590
|
+
* Restrict the flag to global and tenant levels only.
|
|
591
|
+
* Per-user overrides will not be allowed.
|
|
592
|
+
*/
|
|
593
|
+
tenantScoped() {
|
|
594
|
+
this.flag.allowedLevels = ["global", "tenant"];
|
|
595
|
+
return this;
|
|
596
|
+
}
|
|
597
|
+
/**
|
|
598
|
+
* Restrict the flag to global level only.
|
|
599
|
+
* No tenant or user overrides will be allowed.
|
|
600
|
+
*/
|
|
601
|
+
globalOnly() {
|
|
602
|
+
this.flag.allowedLevels = ["global"];
|
|
603
|
+
return this;
|
|
604
|
+
}
|
|
605
|
+
/**
|
|
606
|
+
* Set custom allowed levels.
|
|
607
|
+
*/
|
|
608
|
+
allowedLevels(levels) {
|
|
609
|
+
this.flag.allowedLevels = levels;
|
|
610
|
+
return this;
|
|
611
|
+
}
|
|
612
|
+
/**
|
|
613
|
+
* Build the flag definition.
|
|
614
|
+
* @throws {Error} If label is not set
|
|
615
|
+
*/
|
|
616
|
+
build() {
|
|
617
|
+
if (!this.flag.label) {
|
|
618
|
+
throw new Error(
|
|
619
|
+
`Flag "${this.flag.name}" must have a label. Use .label("Human-readable label").`
|
|
620
|
+
);
|
|
621
|
+
}
|
|
622
|
+
return this.flag;
|
|
623
|
+
}
|
|
624
|
+
};
|
|
625
|
+
var BooleanFlagBuilder = class extends BaseFlagBuilder {
|
|
626
|
+
constructor(name) {
|
|
627
|
+
super(name, "boolean", false);
|
|
628
|
+
}
|
|
629
|
+
/**
|
|
630
|
+
* Set the default value (default: false).
|
|
631
|
+
*/
|
|
632
|
+
defaultValue(value) {
|
|
633
|
+
this.flag.defaultValue = value;
|
|
634
|
+
return this;
|
|
635
|
+
}
|
|
636
|
+
/**
|
|
637
|
+
* Set the default to true.
|
|
638
|
+
* Shorthand for .defaultValue(true).
|
|
639
|
+
*/
|
|
640
|
+
enabledByDefault() {
|
|
641
|
+
this.flag.defaultValue = true;
|
|
642
|
+
return this;
|
|
643
|
+
}
|
|
644
|
+
};
|
|
645
|
+
var StringFlagBuilder = class extends BaseFlagBuilder {
|
|
646
|
+
constructor(name) {
|
|
647
|
+
super(name, "string", "");
|
|
648
|
+
}
|
|
649
|
+
/**
|
|
650
|
+
* Set the default value.
|
|
651
|
+
*/
|
|
652
|
+
defaultValue(value) {
|
|
653
|
+
this.flag.defaultValue = value;
|
|
654
|
+
return this;
|
|
655
|
+
}
|
|
656
|
+
};
|
|
657
|
+
var NumberFlagBuilder = class extends BaseFlagBuilder {
|
|
658
|
+
constructor(name) {
|
|
659
|
+
super(name, "number", 0);
|
|
660
|
+
}
|
|
661
|
+
/**
|
|
662
|
+
* Set the default value.
|
|
663
|
+
*/
|
|
664
|
+
defaultValue(value) {
|
|
665
|
+
this.flag.defaultValue = value;
|
|
666
|
+
return this;
|
|
667
|
+
}
|
|
668
|
+
};
|
|
669
|
+
var JsonFlagBuilder = class extends BaseFlagBuilder {
|
|
670
|
+
constructor(name, defaultValue) {
|
|
671
|
+
super(name, "json", defaultValue);
|
|
672
|
+
}
|
|
673
|
+
/**
|
|
674
|
+
* Set the default value.
|
|
675
|
+
*/
|
|
676
|
+
defaultValue(value) {
|
|
677
|
+
this.flag.defaultValue = value;
|
|
678
|
+
return this;
|
|
679
|
+
}
|
|
680
|
+
};
|
|
681
|
+
function booleanFlag(name) {
|
|
682
|
+
return new BooleanFlagBuilder(name);
|
|
683
|
+
}
|
|
684
|
+
function stringFlag(name) {
|
|
685
|
+
return new StringFlagBuilder(name);
|
|
686
|
+
}
|
|
687
|
+
function numberFlag(name) {
|
|
688
|
+
return new NumberFlagBuilder(name);
|
|
689
|
+
}
|
|
690
|
+
function jsonFlag(name, defaultValue) {
|
|
691
|
+
return new JsonFlagBuilder(name, defaultValue);
|
|
692
|
+
}
|
|
693
|
+
|
|
694
|
+
// src/feature-flags/flag-registry.ts
|
|
695
|
+
var FlagRegistry = class {
|
|
696
|
+
constructor() {
|
|
697
|
+
this.flags = /* @__PURE__ */ new Map();
|
|
698
|
+
}
|
|
699
|
+
/**
|
|
700
|
+
* Register a feature flag definition.
|
|
701
|
+
*
|
|
702
|
+
* @param flag - The flag definition to register
|
|
703
|
+
* @throws {Error} If a flag with the same name is already registered
|
|
704
|
+
*
|
|
705
|
+
* @example
|
|
706
|
+
* ```typescript
|
|
707
|
+
* registry.register(booleanFlag("my-feature")
|
|
708
|
+
* .label("My Feature")
|
|
709
|
+
* .build()
|
|
710
|
+
* );
|
|
711
|
+
* ```
|
|
712
|
+
*/
|
|
713
|
+
register(flag) {
|
|
714
|
+
if (this.flags.has(flag.name)) {
|
|
715
|
+
throw new Error(`Flag "${flag.name}" is already registered. Each flag name must be unique.`);
|
|
716
|
+
}
|
|
717
|
+
this.flags.set(flag.name, flag);
|
|
718
|
+
}
|
|
719
|
+
/**
|
|
720
|
+
* Register multiple flags at once.
|
|
721
|
+
*
|
|
722
|
+
* @param flags - Array of flag definitions to register
|
|
723
|
+
*/
|
|
724
|
+
registerAll(flags) {
|
|
725
|
+
for (const flag of flags) {
|
|
726
|
+
this.register(flag);
|
|
727
|
+
}
|
|
728
|
+
}
|
|
729
|
+
/**
|
|
730
|
+
* Get a flag definition by name.
|
|
731
|
+
*
|
|
732
|
+
* @param name - The flag name
|
|
733
|
+
* @returns The flag definition or undefined if not found
|
|
734
|
+
*/
|
|
735
|
+
get(name) {
|
|
736
|
+
return this.flags.get(name);
|
|
737
|
+
}
|
|
738
|
+
/**
|
|
739
|
+
* Get a flag definition by name, throwing if not found.
|
|
740
|
+
*
|
|
741
|
+
* @param name - The flag name
|
|
742
|
+
* @returns The flag definition
|
|
743
|
+
* @throws {Error} If the flag is not registered
|
|
744
|
+
*/
|
|
745
|
+
getOrThrow(name) {
|
|
746
|
+
const flag = this.get(name);
|
|
747
|
+
if (!flag) {
|
|
748
|
+
throw new Error(
|
|
749
|
+
`Flag "${name}" is not registered. Available flags: ${this.listNames().join(", ")}`
|
|
750
|
+
);
|
|
751
|
+
}
|
|
752
|
+
return flag;
|
|
753
|
+
}
|
|
754
|
+
/**
|
|
755
|
+
* Check if a flag is registered.
|
|
756
|
+
*
|
|
757
|
+
* @param name - The flag name
|
|
758
|
+
* @returns true if the flag is registered
|
|
759
|
+
*/
|
|
760
|
+
has(name) {
|
|
761
|
+
return this.flags.has(name);
|
|
762
|
+
}
|
|
763
|
+
/**
|
|
764
|
+
* List all registered flag definitions.
|
|
765
|
+
*
|
|
766
|
+
* @returns Array of all flag definitions
|
|
767
|
+
*/
|
|
768
|
+
list() {
|
|
769
|
+
return Array.from(this.flags.values());
|
|
770
|
+
}
|
|
771
|
+
/**
|
|
772
|
+
* List all registered flag names.
|
|
773
|
+
*
|
|
774
|
+
* @returns Array of flag names
|
|
775
|
+
*/
|
|
776
|
+
listNames() {
|
|
777
|
+
return Array.from(this.flags.keys());
|
|
778
|
+
}
|
|
779
|
+
/**
|
|
780
|
+
* List flags filtered by category.
|
|
781
|
+
*
|
|
782
|
+
* @param category - The category to filter by
|
|
783
|
+
* @returns Array of flag definitions in the category
|
|
784
|
+
*/
|
|
785
|
+
listByCategory(category) {
|
|
786
|
+
return this.list().filter((flag) => flag.category === category);
|
|
787
|
+
}
|
|
788
|
+
/**
|
|
789
|
+
* Get all unique categories.
|
|
790
|
+
*
|
|
791
|
+
* @returns Array of unique category names
|
|
792
|
+
*/
|
|
793
|
+
getCategories() {
|
|
794
|
+
const categories = /* @__PURE__ */ new Set();
|
|
795
|
+
for (const flag of this.flags.values()) {
|
|
796
|
+
if (flag.category) {
|
|
797
|
+
categories.add(flag.category);
|
|
798
|
+
}
|
|
799
|
+
}
|
|
800
|
+
return Array.from(categories);
|
|
801
|
+
}
|
|
802
|
+
/**
|
|
803
|
+
* Get the default value for a flag.
|
|
804
|
+
*
|
|
805
|
+
* @param name - The flag name
|
|
806
|
+
* @returns The default value or undefined if flag not found
|
|
807
|
+
*/
|
|
808
|
+
getDefaultValue(name) {
|
|
809
|
+
return this.get(name)?.defaultValue;
|
|
810
|
+
}
|
|
811
|
+
/**
|
|
812
|
+
* Get a map of all flag names to their default values.
|
|
813
|
+
*
|
|
814
|
+
* @returns Map of flag names to default values
|
|
815
|
+
*/
|
|
816
|
+
getDefaults() {
|
|
817
|
+
const defaults = /* @__PURE__ */ new Map();
|
|
818
|
+
for (const [name, flag] of this.flags) {
|
|
819
|
+
defaults.set(name, flag.defaultValue);
|
|
820
|
+
}
|
|
821
|
+
return defaults;
|
|
822
|
+
}
|
|
823
|
+
/**
|
|
824
|
+
* Unregister a flag (mainly for testing).
|
|
825
|
+
*
|
|
826
|
+
* @param name - The flag name to unregister
|
|
827
|
+
* @returns true if the flag was removed, false if it didn't exist
|
|
828
|
+
*/
|
|
829
|
+
unregister(name) {
|
|
830
|
+
return this.flags.delete(name);
|
|
831
|
+
}
|
|
832
|
+
/**
|
|
833
|
+
* Clear all registered flags (mainly for testing).
|
|
834
|
+
*/
|
|
835
|
+
clear() {
|
|
836
|
+
this.flags.clear();
|
|
837
|
+
}
|
|
838
|
+
/**
|
|
839
|
+
* Get the number of registered flags.
|
|
840
|
+
*/
|
|
841
|
+
get size() {
|
|
842
|
+
return this.flags.size;
|
|
843
|
+
}
|
|
844
|
+
};
|
|
845
|
+
var flagRegistry = new FlagRegistry();
|
|
846
|
+
function createFlagRegistry() {
|
|
847
|
+
return new FlagRegistry();
|
|
848
|
+
}
|
|
849
|
+
|
|
850
|
+
// src/feature-flags/flag-service.ts
|
|
851
|
+
var FlagService = class {
|
|
852
|
+
constructor(options) {
|
|
853
|
+
this.repository = options.repository;
|
|
854
|
+
this.registry = options.registry;
|
|
855
|
+
this.staticDefaults = new Map(options.staticDefaults?.map((d) => [d.name, d.value]) ?? []);
|
|
856
|
+
}
|
|
857
|
+
/**
|
|
858
|
+
* Resolve all flags for the current context.
|
|
859
|
+
* Returns a Map suitable for runWithFeatureFlags().
|
|
860
|
+
*
|
|
861
|
+
* @param context - Resolution context with tenant/user IDs
|
|
862
|
+
* @returns Map of flag names to resolved values
|
|
863
|
+
*/
|
|
864
|
+
async resolveAll(context = {}) {
|
|
865
|
+
const resolved = /* @__PURE__ */ new Map();
|
|
866
|
+
const flagNames = /* @__PURE__ */ new Set();
|
|
867
|
+
for (const name of this.registry.listNames()) {
|
|
868
|
+
flagNames.add(name);
|
|
869
|
+
}
|
|
870
|
+
for (const name of this.staticDefaults.keys()) {
|
|
871
|
+
flagNames.add(name);
|
|
872
|
+
}
|
|
873
|
+
const overrides = this.repository ? await this.getAllOverrides(context) : { global: [], tenant: [], user: [] };
|
|
874
|
+
for (const name of flagNames) {
|
|
875
|
+
const value = this.resolveValue(name, overrides, context);
|
|
876
|
+
resolved.set(name, value);
|
|
877
|
+
}
|
|
878
|
+
return resolved;
|
|
879
|
+
}
|
|
880
|
+
/**
|
|
881
|
+
* Resolve a single flag with full metadata.
|
|
882
|
+
*
|
|
883
|
+
* @param flagName - The flag to resolve
|
|
884
|
+
* @param context - Resolution context
|
|
885
|
+
* @returns Resolved flag with source information
|
|
886
|
+
*/
|
|
887
|
+
async resolve(flagName, context = {}) {
|
|
888
|
+
const overrides = this.repository ? await this.getAllOverrides(context) : { global: [], tenant: [], user: [] };
|
|
889
|
+
return this.resolveWithSource(flagName, overrides, context);
|
|
890
|
+
}
|
|
891
|
+
/**
|
|
892
|
+
* Quick check if a boolean flag is enabled.
|
|
893
|
+
*
|
|
894
|
+
* @param flagName - The flag to check
|
|
895
|
+
* @param context - Resolution context
|
|
896
|
+
* @returns true if the flag value is exactly true
|
|
897
|
+
*/
|
|
898
|
+
async isEnabled(flagName, context = {}) {
|
|
899
|
+
const resolved = await this.resolve(flagName, context);
|
|
900
|
+
return resolved.value === true;
|
|
901
|
+
}
|
|
902
|
+
/**
|
|
903
|
+
* Get a flag value with type inference.
|
|
904
|
+
*
|
|
905
|
+
* @param flagName - The flag to get
|
|
906
|
+
* @param context - Resolution context
|
|
907
|
+
* @returns The resolved flag value
|
|
908
|
+
*/
|
|
909
|
+
async getValue(flagName, context = {}) {
|
|
910
|
+
const resolved = await this.resolve(flagName, context);
|
|
911
|
+
return resolved.value;
|
|
912
|
+
}
|
|
913
|
+
/**
|
|
914
|
+
* Set an override for a flag.
|
|
915
|
+
*
|
|
916
|
+
* @param flagName - The flag to override
|
|
917
|
+
* @param level - The level of the override
|
|
918
|
+
* @param value - The override value
|
|
919
|
+
* @param options - Additional options
|
|
920
|
+
*/
|
|
921
|
+
async setOverride(flagName, level, value, options = {}) {
|
|
922
|
+
if (!this.repository) {
|
|
923
|
+
throw new Error(
|
|
924
|
+
"Cannot set override: no FeatureFlagsRepository configured. Add featureFlags to your DatabaseAdapter to enable runtime overrides."
|
|
925
|
+
);
|
|
926
|
+
}
|
|
927
|
+
const flag = this.registry.get(flagName);
|
|
928
|
+
if (flag && !flag.allowedLevels.includes(level)) {
|
|
929
|
+
throw new Error(
|
|
930
|
+
`Flag "${flagName}" does not allow ${level}-level overrides. Allowed levels: ${flag.allowedLevels.join(", ")}`
|
|
931
|
+
);
|
|
932
|
+
}
|
|
933
|
+
if (flag?.system) {
|
|
934
|
+
throw new Error(`Flag "${flagName}" is a system flag and cannot be overridden via API.`);
|
|
935
|
+
}
|
|
936
|
+
await this.repository.setOverride({
|
|
937
|
+
flagName,
|
|
938
|
+
level,
|
|
939
|
+
value,
|
|
940
|
+
targetId: options.targetId,
|
|
941
|
+
expiresAt: options.expiresAt,
|
|
942
|
+
createdBy: options.createdBy
|
|
943
|
+
});
|
|
944
|
+
}
|
|
945
|
+
/**
|
|
946
|
+
* Delete an override.
|
|
947
|
+
*
|
|
948
|
+
* @param flagName - The flag name
|
|
949
|
+
* @param level - The level to delete
|
|
950
|
+
* @param targetId - Optional target ID for tenant/user level
|
|
951
|
+
*/
|
|
952
|
+
async deleteOverride(flagName, level, targetId) {
|
|
953
|
+
if (!this.repository) {
|
|
954
|
+
throw new Error("Cannot delete override: no FeatureFlagsRepository configured.");
|
|
955
|
+
}
|
|
956
|
+
await this.repository.deleteOverride(flagName, level, targetId);
|
|
957
|
+
}
|
|
958
|
+
// ============================================================================
|
|
959
|
+
// PRIVATE HELPERS
|
|
960
|
+
// ============================================================================
|
|
961
|
+
/**
|
|
962
|
+
* Get all overrides organized by level.
|
|
963
|
+
*/
|
|
964
|
+
async getAllOverrides(context) {
|
|
965
|
+
if (!this.repository) {
|
|
966
|
+
return { global: [], tenant: [], user: [] };
|
|
967
|
+
}
|
|
968
|
+
const [globalOverrides, tenantOverrides, userOverrides] = await Promise.all([
|
|
969
|
+
this.repository.getOverrides({ level: "global" }),
|
|
970
|
+
context.tenantId ? this.repository.getOverrides({ level: "tenant", targetId: context.tenantId }) : Promise.resolve([]),
|
|
971
|
+
context.userId ? this.repository.getOverrides({ level: "user", targetId: context.userId }) : Promise.resolve([])
|
|
972
|
+
]);
|
|
973
|
+
return {
|
|
974
|
+
global: globalOverrides,
|
|
975
|
+
tenant: tenantOverrides,
|
|
976
|
+
user: userOverrides
|
|
977
|
+
};
|
|
978
|
+
}
|
|
979
|
+
/**
|
|
980
|
+
* Resolve a flag value from overrides and defaults.
|
|
981
|
+
*/
|
|
982
|
+
resolveValue(flagName, overrides, context) {
|
|
983
|
+
const flag = this.registry.get(flagName);
|
|
984
|
+
const allowedLevels = flag?.allowedLevels ?? ["global", "tenant", "user"];
|
|
985
|
+
if (context.userId && allowedLevels.includes("user")) {
|
|
986
|
+
const userOverride = overrides.user.find((o) => o.flagName === flagName);
|
|
987
|
+
if (userOverride) return userOverride.value;
|
|
988
|
+
}
|
|
989
|
+
if (context.tenantId && allowedLevels.includes("tenant")) {
|
|
990
|
+
const tenantOverride = overrides.tenant.find((o) => o.flagName === flagName);
|
|
991
|
+
if (tenantOverride) return tenantOverride.value;
|
|
992
|
+
}
|
|
993
|
+
if (allowedLevels.includes("global")) {
|
|
994
|
+
const globalOverride = overrides.global.find((o) => o.flagName === flagName);
|
|
995
|
+
if (globalOverride) return globalOverride.value;
|
|
996
|
+
}
|
|
997
|
+
if (this.staticDefaults.has(flagName)) {
|
|
998
|
+
return this.staticDefaults.get(flagName);
|
|
999
|
+
}
|
|
1000
|
+
return flag?.defaultValue;
|
|
1001
|
+
}
|
|
1002
|
+
/**
|
|
1003
|
+
* Resolve a flag value with source information.
|
|
1004
|
+
*/
|
|
1005
|
+
resolveWithSource(flagName, overrides, context) {
|
|
1006
|
+
const flag = this.registry.get(flagName);
|
|
1007
|
+
const allowedLevels = flag?.allowedLevels ?? ["global", "tenant", "user"];
|
|
1008
|
+
if (context.userId && allowedLevels.includes("user")) {
|
|
1009
|
+
const userOverride = overrides.user.find((o) => o.flagName === flagName);
|
|
1010
|
+
if (userOverride) {
|
|
1011
|
+
return {
|
|
1012
|
+
name: flagName,
|
|
1013
|
+
value: userOverride.value,
|
|
1014
|
+
source: "user",
|
|
1015
|
+
sourceId: context.userId
|
|
1016
|
+
};
|
|
1017
|
+
}
|
|
1018
|
+
}
|
|
1019
|
+
if (context.tenantId && allowedLevels.includes("tenant")) {
|
|
1020
|
+
const tenantOverride = overrides.tenant.find((o) => o.flagName === flagName);
|
|
1021
|
+
if (tenantOverride) {
|
|
1022
|
+
return {
|
|
1023
|
+
name: flagName,
|
|
1024
|
+
value: tenantOverride.value,
|
|
1025
|
+
source: "tenant",
|
|
1026
|
+
sourceId: context.tenantId
|
|
1027
|
+
};
|
|
1028
|
+
}
|
|
1029
|
+
}
|
|
1030
|
+
if (allowedLevels.includes("global")) {
|
|
1031
|
+
const globalOverride = overrides.global.find((o) => o.flagName === flagName);
|
|
1032
|
+
if (globalOverride) {
|
|
1033
|
+
return {
|
|
1034
|
+
name: flagName,
|
|
1035
|
+
value: globalOverride.value,
|
|
1036
|
+
source: "global"
|
|
1037
|
+
};
|
|
1038
|
+
}
|
|
1039
|
+
}
|
|
1040
|
+
if (this.staticDefaults.has(flagName)) {
|
|
1041
|
+
return {
|
|
1042
|
+
name: flagName,
|
|
1043
|
+
value: this.staticDefaults.get(flagName),
|
|
1044
|
+
source: "default"
|
|
1045
|
+
};
|
|
1046
|
+
}
|
|
1047
|
+
return {
|
|
1048
|
+
name: flagName,
|
|
1049
|
+
value: flag?.defaultValue ?? void 0,
|
|
1050
|
+
source: "default"
|
|
1051
|
+
};
|
|
1052
|
+
}
|
|
1053
|
+
};
|
|
1054
|
+
function createFlagService(options) {
|
|
1055
|
+
return new FlagService(options);
|
|
1056
|
+
}
|
|
1057
|
+
|
|
534
1058
|
// src/native/notes.ts
|
|
535
1059
|
var NOTES = object({ name: "notes", label: "Note" }).pluralLabel("Notes").icon("file-text").description("Notes that can be linked to any record or used globally").system().labelExpression("{{ title }}").attribute(text({ name: "title", label: "Title" }).placeholder("Untitled").required()).attribute(richtext({ name: "content", label: "Content" }).required()).attribute(
|
|
536
1060
|
select({ name: "visibility", label: "Visibility" }).options([
|
|
@@ -545,12 +1069,12 @@ var ViewRegistry = class {
|
|
|
545
1069
|
constructor() {
|
|
546
1070
|
this.views = /* @__PURE__ */ new Map();
|
|
547
1071
|
this.byObject = /* @__PURE__ */ new Map();
|
|
1072
|
+
this.byObjectAndType = /* @__PURE__ */ new Map();
|
|
548
1073
|
}
|
|
549
1074
|
/**
|
|
550
|
-
* Register a
|
|
1075
|
+
* Register a view
|
|
551
1076
|
* @param viewOrViews - Single view or array of views
|
|
552
|
-
* @throws Error if view
|
|
553
|
-
* @throws Error if view with same name already exists for the object
|
|
1077
|
+
* @throws Error if view with same name and type already exists for the object
|
|
554
1078
|
*/
|
|
555
1079
|
register(viewOrViews) {
|
|
556
1080
|
const views = Array.isArray(viewOrViews) ? viewOrViews : [viewOrViews];
|
|
@@ -560,22 +1084,20 @@ var ViewRegistry = class {
|
|
|
560
1084
|
return this;
|
|
561
1085
|
}
|
|
562
1086
|
registerSingle(view2) {
|
|
563
|
-
|
|
564
|
-
throw new Error(
|
|
565
|
-
`[ViewRegistry] View "${view2.name}" for object "${view2.object}" is missing system flag.
|
|
566
|
-
Only system views can be registered. Add .system() to your view builder.`
|
|
567
|
-
);
|
|
568
|
-
}
|
|
569
|
-
const key = this.makeKey(view2.object, view2.name);
|
|
1087
|
+
const key = this.makeKey(view2.object, view2.name, view2.type);
|
|
570
1088
|
if (this.views.has(key)) {
|
|
571
1089
|
throw new Error(
|
|
572
|
-
`[ViewRegistry] Duplicate view
|
|
1090
|
+
`[ViewRegistry] Duplicate view: "${view2.name}" (${view2.type}) for object "${view2.object}"`
|
|
573
1091
|
);
|
|
574
1092
|
}
|
|
575
1093
|
this.views.set(key, view2);
|
|
576
1094
|
const objectViews = this.byObject.get(view2.object) ?? [];
|
|
577
1095
|
objectViews.push(view2);
|
|
578
1096
|
this.byObject.set(view2.object, objectViews);
|
|
1097
|
+
const typeKey = `${view2.object}:${view2.type}`;
|
|
1098
|
+
const typeViews = this.byObjectAndType.get(typeKey) ?? [];
|
|
1099
|
+
typeViews.push(view2);
|
|
1100
|
+
this.byObjectAndType.set(typeKey, typeViews);
|
|
579
1101
|
}
|
|
580
1102
|
/**
|
|
581
1103
|
* Get all views for an object
|
|
@@ -584,19 +1106,29 @@ Only system views can be registered. Add .system() to your view builder.`
|
|
|
584
1106
|
return this.byObject.get(objectName) ?? [];
|
|
585
1107
|
}
|
|
586
1108
|
/**
|
|
587
|
-
* Get
|
|
1109
|
+
* Get views for an object filtered by type
|
|
588
1110
|
*/
|
|
589
|
-
|
|
590
|
-
return this.
|
|
1111
|
+
getByObjectNameAndType(objectName, type) {
|
|
1112
|
+
return this.byObjectAndType.get(`${objectName}:${type}`) ?? [];
|
|
1113
|
+
}
|
|
1114
|
+
/**
|
|
1115
|
+
* Get a specific view by object, name, and type
|
|
1116
|
+
*/
|
|
1117
|
+
get(objectName, viewName, type) {
|
|
1118
|
+
if (type) {
|
|
1119
|
+
return this.views.get(this.makeKey(objectName, viewName, type));
|
|
1120
|
+
}
|
|
1121
|
+
const objectViews = this.getByObjectName(objectName);
|
|
1122
|
+
return objectViews.find((v) => v.name === viewName);
|
|
591
1123
|
}
|
|
592
1124
|
/**
|
|
593
1125
|
* Get a view or throw if not found
|
|
594
1126
|
*/
|
|
595
|
-
getOrThrow(objectName, viewName) {
|
|
596
|
-
const view2 = this.get(objectName, viewName);
|
|
1127
|
+
getOrThrow(objectName, viewName, type) {
|
|
1128
|
+
const view2 = this.get(objectName, viewName, type);
|
|
597
1129
|
if (!view2) {
|
|
598
1130
|
const available = this.getByObjectName(objectName);
|
|
599
|
-
const availableNames = available.map((v) => v.name).join(", ") || "(none)";
|
|
1131
|
+
const availableNames = available.map((v) => `${v.name} (${v.type})`).join(", ") || "(none)";
|
|
600
1132
|
throw new Error(
|
|
601
1133
|
`[ViewRegistry] View "${viewName}" not found for object "${objectName}".
|
|
602
1134
|
Available views: ${availableNames}`
|
|
@@ -613,8 +1145,12 @@ Available views: ${availableNames}`
|
|
|
613
1145
|
/**
|
|
614
1146
|
* Check if a view exists
|
|
615
1147
|
*/
|
|
616
|
-
has(objectName, viewName) {
|
|
617
|
-
|
|
1148
|
+
has(objectName, viewName, type) {
|
|
1149
|
+
if (type) {
|
|
1150
|
+
return this.views.has(this.makeKey(objectName, viewName, type));
|
|
1151
|
+
}
|
|
1152
|
+
const objectViews = this.getByObjectName(objectName);
|
|
1153
|
+
return objectViews.some((v) => v.name === viewName);
|
|
618
1154
|
}
|
|
619
1155
|
/**
|
|
620
1156
|
* Check if any views exist for an object
|
|
@@ -635,10 +1171,10 @@ Available views: ${availableNames}`
|
|
|
635
1171
|
return Array.from(this.byObject.keys());
|
|
636
1172
|
}
|
|
637
1173
|
/**
|
|
638
|
-
* Get default view for an object
|
|
1174
|
+
* Get default view for an object and type
|
|
639
1175
|
*/
|
|
640
|
-
getDefault(objectName) {
|
|
641
|
-
const views = this.
|
|
1176
|
+
getDefault(objectName, type) {
|
|
1177
|
+
const views = this.getByObjectNameAndType(objectName, type);
|
|
642
1178
|
return views.find((v) => v.default) ?? views[0];
|
|
643
1179
|
}
|
|
644
1180
|
/**
|
|
@@ -647,20 +1183,21 @@ Available views: ${availableNames}`
|
|
|
647
1183
|
clear() {
|
|
648
1184
|
this.views.clear();
|
|
649
1185
|
this.byObject.clear();
|
|
1186
|
+
this.byObjectAndType.clear();
|
|
650
1187
|
}
|
|
651
1188
|
/**
|
|
652
1189
|
* Generate summary string for debugging
|
|
653
1190
|
*/
|
|
654
1191
|
summary() {
|
|
655
1192
|
const lines = [];
|
|
656
|
-
lines.push(`[ViewRegistry] ${this.size}
|
|
1193
|
+
lines.push(`[ViewRegistry] ${this.size} view(s) registered:`);
|
|
657
1194
|
for (const objectName of this.listObjectNames()) {
|
|
658
1195
|
const views = this.getByObjectName(objectName);
|
|
659
1196
|
const viewNames = views.map((v) => {
|
|
660
1197
|
const flags = [];
|
|
661
1198
|
if (v.default) flags.push("default");
|
|
662
1199
|
const flagStr = flags.length > 0 ? ` (${flags.join(", ")})` : "";
|
|
663
|
-
return `${v.name}${flagStr}`;
|
|
1200
|
+
return `${v.name}:${v.type}${flagStr}`;
|
|
664
1201
|
});
|
|
665
1202
|
lines.push(` ${objectName}: ${viewNames.join(", ")}`);
|
|
666
1203
|
}
|
|
@@ -672,11 +1209,289 @@ Available views: ${availableNames}`
|
|
|
672
1209
|
debug() {
|
|
673
1210
|
console.info(this.summary());
|
|
674
1211
|
}
|
|
675
|
-
makeKey(objectName, viewName) {
|
|
676
|
-
return `${objectName}:${viewName}`;
|
|
1212
|
+
makeKey(objectName, viewName, type) {
|
|
1213
|
+
return `${objectName}:${viewName}:${type}`;
|
|
677
1214
|
}
|
|
678
1215
|
};
|
|
679
1216
|
var viewRegistry = new ViewRegistry();
|
|
1217
|
+
|
|
1218
|
+
// src/views/auto-generator.ts
|
|
1219
|
+
function getVisibleAttributes(attributes, excludeNames = []) {
|
|
1220
|
+
return attributes.filter(
|
|
1221
|
+
(attr) => !(attr.hidden || attr.archived || attr.system || excludeNames.includes(attr.name))
|
|
1222
|
+
);
|
|
1223
|
+
}
|
|
1224
|
+
function sortAttributes(attributes) {
|
|
1225
|
+
return [...attributes].sort((a, b) => {
|
|
1226
|
+
const orderA = a.order ?? 999;
|
|
1227
|
+
const orderB = b.order ?? 999;
|
|
1228
|
+
if (orderA !== orderB) return orderA - orderB;
|
|
1229
|
+
return a.name.localeCompare(b.name);
|
|
1230
|
+
});
|
|
1231
|
+
}
|
|
1232
|
+
function getDefaultFieldSpan(type) {
|
|
1233
|
+
switch (type) {
|
|
1234
|
+
case "textarea":
|
|
1235
|
+
case "richtext":
|
|
1236
|
+
case "location":
|
|
1237
|
+
return 12;
|
|
1238
|
+
case "checkbox":
|
|
1239
|
+
return 4;
|
|
1240
|
+
default:
|
|
1241
|
+
return 6;
|
|
1242
|
+
}
|
|
1243
|
+
}
|
|
1244
|
+
function attributeToField(attr) {
|
|
1245
|
+
return {
|
|
1246
|
+
attribute: attr.name,
|
|
1247
|
+
span: getDefaultFieldSpan(attr.type)
|
|
1248
|
+
};
|
|
1249
|
+
}
|
|
1250
|
+
function generateDefaultDetailView(object2, options = {}) {
|
|
1251
|
+
const {
|
|
1252
|
+
includeActivityTab = true,
|
|
1253
|
+
includeNotesTab = true,
|
|
1254
|
+
includeDocumentsTab = true,
|
|
1255
|
+
includeFlowsTab = false,
|
|
1256
|
+
excludeAttributes = []
|
|
1257
|
+
} = options;
|
|
1258
|
+
const visibleAttrs = getVisibleAttributes(object2.attributes, excludeAttributes);
|
|
1259
|
+
const sortedAttrs = sortAttributes(visibleAttrs);
|
|
1260
|
+
const formTab = {
|
|
1261
|
+
id: "form",
|
|
1262
|
+
name: "form",
|
|
1263
|
+
label: "Details",
|
|
1264
|
+
type: "form",
|
|
1265
|
+
groups: [
|
|
1266
|
+
{
|
|
1267
|
+
id: "general",
|
|
1268
|
+
label: "General",
|
|
1269
|
+
fields: sortedAttrs.map(attributeToField),
|
|
1270
|
+
order: 0
|
|
1271
|
+
}
|
|
1272
|
+
],
|
|
1273
|
+
order: 0
|
|
1274
|
+
};
|
|
1275
|
+
const tabs = [formTab];
|
|
1276
|
+
let tabOrder = 1;
|
|
1277
|
+
const hasDocuments = object2.attributes.some((attr) => attr.type === "document");
|
|
1278
|
+
if (includeDocumentsTab && hasDocuments) {
|
|
1279
|
+
tabs.push({
|
|
1280
|
+
id: "documents",
|
|
1281
|
+
name: "documents",
|
|
1282
|
+
label: "Documents",
|
|
1283
|
+
type: "documents",
|
|
1284
|
+
order: tabOrder++,
|
|
1285
|
+
allowUpload: true,
|
|
1286
|
+
allowRemove: true,
|
|
1287
|
+
showProcessing: true
|
|
1288
|
+
});
|
|
1289
|
+
}
|
|
1290
|
+
if (includeActivityTab) {
|
|
1291
|
+
tabs.push({
|
|
1292
|
+
id: "activity",
|
|
1293
|
+
name: "activity",
|
|
1294
|
+
label: "Activity",
|
|
1295
|
+
type: "activity",
|
|
1296
|
+
order: tabOrder++
|
|
1297
|
+
});
|
|
1298
|
+
}
|
|
1299
|
+
if (includeNotesTab) {
|
|
1300
|
+
tabs.push({
|
|
1301
|
+
id: "notes",
|
|
1302
|
+
name: "notes",
|
|
1303
|
+
label: "Notes",
|
|
1304
|
+
type: "notes",
|
|
1305
|
+
order: tabOrder++,
|
|
1306
|
+
allowCreate: true
|
|
1307
|
+
});
|
|
1308
|
+
}
|
|
1309
|
+
if (includeFlowsTab) {
|
|
1310
|
+
tabs.push({
|
|
1311
|
+
id: "flows",
|
|
1312
|
+
name: "flows",
|
|
1313
|
+
label: "Workflows",
|
|
1314
|
+
type: "flows",
|
|
1315
|
+
order: tabOrder++,
|
|
1316
|
+
allowStart: true,
|
|
1317
|
+
allowCancel: true
|
|
1318
|
+
});
|
|
1319
|
+
}
|
|
1320
|
+
const config = {
|
|
1321
|
+
layout: "page",
|
|
1322
|
+
tabs
|
|
1323
|
+
};
|
|
1324
|
+
return {
|
|
1325
|
+
name: "default",
|
|
1326
|
+
label: "Default View",
|
|
1327
|
+
object: object2.name,
|
|
1328
|
+
type: "detail",
|
|
1329
|
+
config,
|
|
1330
|
+
default: true
|
|
1331
|
+
};
|
|
1332
|
+
}
|
|
1333
|
+
function generateDefaultListView(object2, options = {}) {
|
|
1334
|
+
const { excludeAttributes = [], maxListColumns = 5 } = options;
|
|
1335
|
+
const visibleAttrs = getVisibleAttributes(object2.attributes, excludeAttributes);
|
|
1336
|
+
const sortedAttrs = sortAttributes(visibleAttrs);
|
|
1337
|
+
const columns = sortedAttrs.slice(0, maxListColumns).map((attr) => attr.name);
|
|
1338
|
+
const config = {
|
|
1339
|
+
layout: "table",
|
|
1340
|
+
columns
|
|
1341
|
+
};
|
|
1342
|
+
return {
|
|
1343
|
+
name: "default",
|
|
1344
|
+
label: "All Records",
|
|
1345
|
+
object: object2.name,
|
|
1346
|
+
type: "list",
|
|
1347
|
+
config,
|
|
1348
|
+
default: true
|
|
1349
|
+
};
|
|
1350
|
+
}
|
|
1351
|
+
function generateFallbackView(object2, type, options = {}) {
|
|
1352
|
+
switch (type) {
|
|
1353
|
+
case "detail":
|
|
1354
|
+
return generateDefaultDetailView(object2, options);
|
|
1355
|
+
case "list":
|
|
1356
|
+
return generateDefaultListView(object2, options);
|
|
1357
|
+
default:
|
|
1358
|
+
throw new Error(`Fallback generation not supported for view type: ${type}`);
|
|
1359
|
+
}
|
|
1360
|
+
}
|
|
1361
|
+
|
|
1362
|
+
// src/views/view-reset.ts
|
|
1363
|
+
function getPreservedDetailTabs(view2, options) {
|
|
1364
|
+
const { preserveCustomTabs = true, preserveTableTabs = true } = options;
|
|
1365
|
+
const preserved = [];
|
|
1366
|
+
for (const tab of view2.config.tabs) {
|
|
1367
|
+
if (preserveCustomTabs && tab.type === "custom") {
|
|
1368
|
+
preserved.push(tab);
|
|
1369
|
+
}
|
|
1370
|
+
if (preserveTableTabs && tab.type === "table") {
|
|
1371
|
+
preserved.push(tab);
|
|
1372
|
+
}
|
|
1373
|
+
}
|
|
1374
|
+
return preserved;
|
|
1375
|
+
}
|
|
1376
|
+
function mergeDetailTabs(generatedTabs, preservedTabs) {
|
|
1377
|
+
if (preservedTabs.length === 0) {
|
|
1378
|
+
return generatedTabs;
|
|
1379
|
+
}
|
|
1380
|
+
const formTab = generatedTabs.find((t) => t.type === "form");
|
|
1381
|
+
const otherTabs = generatedTabs.filter((t) => t.type !== "form");
|
|
1382
|
+
const result = [];
|
|
1383
|
+
if (formTab) {
|
|
1384
|
+
result.push(formTab);
|
|
1385
|
+
}
|
|
1386
|
+
let order = 1;
|
|
1387
|
+
for (const tab of preservedTabs) {
|
|
1388
|
+
result.push({ ...tab, order: order++ });
|
|
1389
|
+
}
|
|
1390
|
+
for (const tab of otherTabs) {
|
|
1391
|
+
result.push({ ...tab, order: order++ });
|
|
1392
|
+
}
|
|
1393
|
+
return result;
|
|
1394
|
+
}
|
|
1395
|
+
function resetDetailViewToDefault(view2, object2, options) {
|
|
1396
|
+
const { preserveMetadata = true, ...generateOptions } = options;
|
|
1397
|
+
const defaultView = generateDefaultDetailView(object2, generateOptions);
|
|
1398
|
+
const preservedTabs = getPreservedDetailTabs(view2, options);
|
|
1399
|
+
const mergedTabs = mergeDetailTabs(defaultView.config.tabs, preservedTabs);
|
|
1400
|
+
const config = {
|
|
1401
|
+
...defaultView.config,
|
|
1402
|
+
tabs: mergedTabs
|
|
1403
|
+
};
|
|
1404
|
+
const resetView = {
|
|
1405
|
+
...defaultView,
|
|
1406
|
+
config
|
|
1407
|
+
};
|
|
1408
|
+
if (preserveMetadata) {
|
|
1409
|
+
resetView.id = view2.id;
|
|
1410
|
+
resetView.name = view2.name;
|
|
1411
|
+
resetView.label = view2.label;
|
|
1412
|
+
resetView.description = view2.description;
|
|
1413
|
+
resetView.icon = view2.icon;
|
|
1414
|
+
}
|
|
1415
|
+
return resetView;
|
|
1416
|
+
}
|
|
1417
|
+
function resetListViewToDefault(view2, object2, options) {
|
|
1418
|
+
const { preserveMetadata = true, ...generateOptions } = options;
|
|
1419
|
+
const defaultView = generateDefaultListView(object2, generateOptions);
|
|
1420
|
+
const resetView = {
|
|
1421
|
+
...defaultView
|
|
1422
|
+
};
|
|
1423
|
+
if (preserveMetadata) {
|
|
1424
|
+
resetView.id = view2.id;
|
|
1425
|
+
resetView.name = view2.name;
|
|
1426
|
+
resetView.label = view2.label;
|
|
1427
|
+
resetView.description = view2.description;
|
|
1428
|
+
resetView.icon = view2.icon;
|
|
1429
|
+
}
|
|
1430
|
+
return resetView;
|
|
1431
|
+
}
|
|
1432
|
+
function resetViewToDefault(currentView, object2, options = {}) {
|
|
1433
|
+
if (isDetailView(currentView)) {
|
|
1434
|
+
return resetDetailViewToDefault(currentView, object2, options);
|
|
1435
|
+
}
|
|
1436
|
+
if (isListView(currentView)) {
|
|
1437
|
+
return resetListViewToDefault(currentView, object2, options);
|
|
1438
|
+
}
|
|
1439
|
+
throw new Error(`Reset not supported for view type: ${currentView.type}`);
|
|
1440
|
+
}
|
|
1441
|
+
function isDetailViewCustomized(view2, object2) {
|
|
1442
|
+
const defaultView = generateDefaultDetailView(object2);
|
|
1443
|
+
const viewFormTab = view2.config.tabs.find((t) => t.type === "form");
|
|
1444
|
+
const defaultFormTab = defaultView.config.tabs.find((t) => t.type === "form");
|
|
1445
|
+
if (!(viewFormTab && defaultFormTab)) {
|
|
1446
|
+
return true;
|
|
1447
|
+
}
|
|
1448
|
+
if (viewFormTab.type !== "form" || defaultFormTab.type !== "form") {
|
|
1449
|
+
return true;
|
|
1450
|
+
}
|
|
1451
|
+
if (viewFormTab.groups.length !== defaultFormTab.groups.length) {
|
|
1452
|
+
return true;
|
|
1453
|
+
}
|
|
1454
|
+
for (let i = 0; i < viewFormTab.groups.length; i++) {
|
|
1455
|
+
const viewGroup = viewFormTab.groups[i];
|
|
1456
|
+
const defaultGroup = defaultFormTab.groups[i];
|
|
1457
|
+
if (viewGroup.id !== defaultGroup.id) {
|
|
1458
|
+
return true;
|
|
1459
|
+
}
|
|
1460
|
+
if (viewGroup.fields.length !== defaultGroup.fields.length) {
|
|
1461
|
+
return true;
|
|
1462
|
+
}
|
|
1463
|
+
for (let j = 0; j < viewGroup.fields.length; j++) {
|
|
1464
|
+
if (viewGroup.fields[j].attribute !== defaultGroup.fields[j].attribute) {
|
|
1465
|
+
return true;
|
|
1466
|
+
}
|
|
1467
|
+
}
|
|
1468
|
+
}
|
|
1469
|
+
return false;
|
|
1470
|
+
}
|
|
1471
|
+
function isListViewCustomized(view2, object2) {
|
|
1472
|
+
const defaultView = generateDefaultListView(object2);
|
|
1473
|
+
if (view2.config.columns.length !== defaultView.config.columns.length) {
|
|
1474
|
+
return true;
|
|
1475
|
+
}
|
|
1476
|
+
for (let i = 0; i < view2.config.columns.length; i++) {
|
|
1477
|
+
if (view2.config.columns[i] !== defaultView.config.columns[i]) {
|
|
1478
|
+
return true;
|
|
1479
|
+
}
|
|
1480
|
+
}
|
|
1481
|
+
if (view2.config.layout !== defaultView.config.layout) {
|
|
1482
|
+
return true;
|
|
1483
|
+
}
|
|
1484
|
+
return false;
|
|
1485
|
+
}
|
|
1486
|
+
function isViewCustomized(view2, object2) {
|
|
1487
|
+
if (isDetailView(view2)) {
|
|
1488
|
+
return isDetailViewCustomized(view2, object2);
|
|
1489
|
+
}
|
|
1490
|
+
if (isListView(view2)) {
|
|
1491
|
+
return isListViewCustomized(view2, object2);
|
|
1492
|
+
}
|
|
1493
|
+
return true;
|
|
1494
|
+
}
|
|
680
1495
|
export {
|
|
681
1496
|
ALL_SYSTEM_RESOURCES,
|
|
682
1497
|
ActivityTabConfig,
|
|
@@ -684,6 +1499,7 @@ export {
|
|
|
684
1499
|
AttributeNotFoundError,
|
|
685
1500
|
AuditService,
|
|
686
1501
|
AuthMethodSchema,
|
|
1502
|
+
BEHAVIOR_PROPERTIES,
|
|
687
1503
|
BaseRepository,
|
|
688
1504
|
BaseService,
|
|
689
1505
|
ConcurrentModificationError,
|
|
@@ -702,6 +1518,7 @@ export {
|
|
|
702
1518
|
DEFAULT_THEME,
|
|
703
1519
|
DEFAULT_VALIDATION_MESSAGES,
|
|
704
1520
|
DRIVING_LICENSE,
|
|
1521
|
+
DetailViewBuilder,
|
|
705
1522
|
DirectTableTabConfig,
|
|
706
1523
|
DocumentExecutor,
|
|
707
1524
|
DocumentGenerationNotConfiguredError,
|
|
@@ -721,8 +1538,11 @@ export {
|
|
|
721
1538
|
EndNodeSchema,
|
|
722
1539
|
ExecutorRegistry,
|
|
723
1540
|
FRENCH_ID_CARD,
|
|
1541
|
+
FeatureFlagsContextError,
|
|
724
1542
|
FileNotFoundError,
|
|
725
1543
|
FileService,
|
|
1544
|
+
FlagRegistry,
|
|
1545
|
+
FlagService,
|
|
726
1546
|
FlowRowFieldSchema,
|
|
727
1547
|
FlowRowSchema,
|
|
728
1548
|
FlowsTabConfig,
|
|
@@ -738,12 +1558,15 @@ export {
|
|
|
738
1558
|
GrantNotFoundError,
|
|
739
1559
|
GrantRevokedError,
|
|
740
1560
|
GroupBuilder,
|
|
1561
|
+
IDENTITY_PROPERTIES,
|
|
741
1562
|
InvalidPathError,
|
|
742
1563
|
InverseTableTabConfig,
|
|
743
1564
|
InvitationAlreadyAcceptedError,
|
|
744
1565
|
InvitationExpiredError,
|
|
745
1566
|
InvitationNotFoundError,
|
|
746
1567
|
InvitationRevokedError,
|
|
1568
|
+
ListViewBuilder,
|
|
1569
|
+
ListViewTabConfigBuilder,
|
|
747
1570
|
MaxDepthExceededError,
|
|
748
1571
|
NOTES,
|
|
749
1572
|
NO_VALUE_OPERATORS,
|
|
@@ -760,6 +1583,7 @@ export {
|
|
|
760
1583
|
ObjectReferencedError,
|
|
761
1584
|
ObjectSchemaService,
|
|
762
1585
|
PASSPORT,
|
|
1586
|
+
PRESENTATION_PROPERTIES,
|
|
763
1587
|
PROOF_OF_ADDRESS,
|
|
764
1588
|
PermissionService,
|
|
765
1589
|
PolicyRegistry,
|
|
@@ -836,6 +1660,7 @@ export {
|
|
|
836
1660
|
asTenantId,
|
|
837
1661
|
asUserId,
|
|
838
1662
|
attributeConfigSchemas,
|
|
1663
|
+
booleanFlag,
|
|
839
1664
|
buildAuditChanges,
|
|
840
1665
|
buildPolicyContext,
|
|
841
1666
|
cacheKeys,
|
|
@@ -866,6 +1691,8 @@ export {
|
|
|
866
1691
|
createDraftValidator,
|
|
867
1692
|
createEmptyContext,
|
|
868
1693
|
createFileValidator,
|
|
1694
|
+
createFlagRegistry,
|
|
1695
|
+
createFlagService,
|
|
869
1696
|
createFormAttributeValidator,
|
|
870
1697
|
createFormulaValidator,
|
|
871
1698
|
createLocationValidator,
|
|
@@ -893,6 +1720,7 @@ export {
|
|
|
893
1720
|
dateConfigSchema,
|
|
894
1721
|
defaultPolicyRegistry,
|
|
895
1722
|
defaultTtl,
|
|
1723
|
+
detailView,
|
|
896
1724
|
document,
|
|
897
1725
|
documentConfigSchema,
|
|
898
1726
|
enrichRecordsWithFormulas,
|
|
@@ -916,14 +1744,19 @@ export {
|
|
|
916
1744
|
extractRelationReferences,
|
|
917
1745
|
file,
|
|
918
1746
|
fileConfigSchema,
|
|
1747
|
+
flagRegistry,
|
|
919
1748
|
flattenRelationsForEval,
|
|
920
1749
|
formatAttributeValue,
|
|
921
1750
|
formatFormulaResult,
|
|
922
1751
|
formatRecord,
|
|
923
1752
|
formatRecords,
|
|
1753
|
+
formatZodErrors,
|
|
924
1754
|
formula,
|
|
925
1755
|
formulaConfigSchema,
|
|
926
1756
|
generateCssVariables,
|
|
1757
|
+
generateDefaultDetailView,
|
|
1758
|
+
generateDefaultListView,
|
|
1759
|
+
generateFallbackView,
|
|
927
1760
|
generateId,
|
|
928
1761
|
generatePrefixedId,
|
|
929
1762
|
generateTemplateName,
|
|
@@ -931,6 +1764,8 @@ export {
|
|
|
931
1764
|
getContext,
|
|
932
1765
|
getContextValue,
|
|
933
1766
|
getDefaultExecutorRegistry,
|
|
1767
|
+
getFeatureFlags,
|
|
1768
|
+
getFeatureValue,
|
|
934
1769
|
getMissingRequiredAttributes,
|
|
935
1770
|
getNodeOutputs,
|
|
936
1771
|
getPathDepth,
|
|
@@ -945,37 +1780,44 @@ export {
|
|
|
945
1780
|
getTargetAttributeName,
|
|
946
1781
|
getTenantId,
|
|
947
1782
|
getUserId,
|
|
1783
|
+
getViewSeedPreview,
|
|
948
1784
|
getViewSyncPreview,
|
|
949
1785
|
group,
|
|
950
1786
|
hasContext,
|
|
1787
|
+
hasFeatureFlagsContext,
|
|
1788
|
+
hasProperties,
|
|
951
1789
|
hasRelationReferences,
|
|
952
1790
|
hasSchemaContext,
|
|
953
1791
|
hashOptions,
|
|
954
1792
|
inValues,
|
|
1793
|
+
indexBy,
|
|
955
1794
|
isActivityTab,
|
|
956
|
-
isAdvancedFilterState,
|
|
957
1795
|
isAdvancedFormNode,
|
|
958
|
-
|
|
1796
|
+
isBehaviorProperty,
|
|
1797
|
+
isCalendarView,
|
|
959
1798
|
isConditionGroup,
|
|
960
1799
|
isConditionNode,
|
|
961
1800
|
isConditionRule,
|
|
962
1801
|
isCustomTab,
|
|
963
1802
|
isDefaultRole,
|
|
1803
|
+
isDetailView,
|
|
964
1804
|
isDirectTableTab,
|
|
965
1805
|
isDocumentNode,
|
|
966
1806
|
isDocumentsTab,
|
|
967
|
-
isDocxTemplateSource,
|
|
968
1807
|
isEmpty,
|
|
969
1808
|
isEndNode,
|
|
1809
|
+
isFeatureEnabled,
|
|
970
1810
|
isFlowDefinition,
|
|
971
1811
|
isFlowPublished,
|
|
972
1812
|
isFlowsTab,
|
|
973
1813
|
isForbiddenError,
|
|
974
1814
|
isFormNode,
|
|
975
1815
|
isFormTab,
|
|
1816
|
+
isGalleryView,
|
|
976
1817
|
isGrantExpired,
|
|
977
1818
|
isGrantRevoked,
|
|
978
1819
|
isGrantValid,
|
|
1820
|
+
isIdentityProperty,
|
|
979
1821
|
isInstanceEvent,
|
|
980
1822
|
isInstanceTerminal,
|
|
981
1823
|
isInstanceWaiting,
|
|
@@ -985,12 +1827,13 @@ export {
|
|
|
985
1827
|
isInvitationOrGrantEvent,
|
|
986
1828
|
isInvitationValid,
|
|
987
1829
|
isLabelExpression,
|
|
1830
|
+
isListView,
|
|
988
1831
|
isNoValueOperator,
|
|
989
1832
|
isNodeEvent,
|
|
990
1833
|
isNotEmpty,
|
|
991
1834
|
isNotFoundError,
|
|
992
1835
|
isNotesTab,
|
|
993
|
-
|
|
1836
|
+
isPresentationProperty,
|
|
994
1837
|
isProtectedResourceError,
|
|
995
1838
|
isRecordComplete,
|
|
996
1839
|
isSchemaError,
|
|
@@ -1002,14 +1845,17 @@ export {
|
|
|
1002
1845
|
isSystemTemplate,
|
|
1003
1846
|
isSystemWorkflow,
|
|
1004
1847
|
isTableTab,
|
|
1848
|
+
isTimelineView,
|
|
1005
1849
|
isTokenRevoked,
|
|
1006
1850
|
isUniversalRelation,
|
|
1007
1851
|
isValidationError,
|
|
1852
|
+
isViewCustomized,
|
|
1008
1853
|
isWorkflowDefinition,
|
|
1009
1854
|
isWorkflowPublished,
|
|
1855
|
+
jsonFlag,
|
|
1856
|
+
listView,
|
|
1010
1857
|
location,
|
|
1011
1858
|
locationConfigSchema,
|
|
1012
|
-
mergeFormToSlot,
|
|
1013
1859
|
mergeWithDefaults,
|
|
1014
1860
|
multiselect,
|
|
1015
1861
|
multiselectConfigSchema,
|
|
@@ -1017,6 +1863,7 @@ export {
|
|
|
1017
1863
|
notesPolicy,
|
|
1018
1864
|
number,
|
|
1019
1865
|
numberConfigSchema,
|
|
1866
|
+
numberFlag,
|
|
1020
1867
|
object,
|
|
1021
1868
|
or,
|
|
1022
1869
|
parseAttributeConfig,
|
|
@@ -1031,6 +1878,7 @@ export {
|
|
|
1031
1878
|
relation,
|
|
1032
1879
|
relationConfigSchema,
|
|
1033
1880
|
renderLabelExpression,
|
|
1881
|
+
resetViewToDefault,
|
|
1034
1882
|
resolveMultiplePaths,
|
|
1035
1883
|
resolveSingleValue,
|
|
1036
1884
|
richtext,
|
|
@@ -1038,15 +1886,18 @@ export {
|
|
|
1038
1886
|
rollup,
|
|
1039
1887
|
rollupConfigSchema,
|
|
1040
1888
|
runWithContext,
|
|
1889
|
+
runWithFeatureFlags,
|
|
1041
1890
|
runWithMergedSchemaContext,
|
|
1042
1891
|
runWithSchemaContext,
|
|
1043
1892
|
safeParseAttributeConfig,
|
|
1893
|
+
seedRegistryViews,
|
|
1044
1894
|
select,
|
|
1045
1895
|
selectConfigSchema,
|
|
1046
1896
|
setContextValue,
|
|
1047
1897
|
slugify,
|
|
1048
1898
|
status,
|
|
1049
1899
|
statusConfigSchema,
|
|
1900
|
+
stringFlag,
|
|
1050
1901
|
success,
|
|
1051
1902
|
syncAll,
|
|
1052
1903
|
syncNativeObjects,
|
|
@@ -1055,9 +1906,9 @@ export {
|
|
|
1055
1906
|
textConfigSchema,
|
|
1056
1907
|
textarea,
|
|
1057
1908
|
textareaConfigSchema,
|
|
1058
|
-
|
|
1059
|
-
toSimpleFilterState,
|
|
1909
|
+
toUndefinedIfEmpty,
|
|
1060
1910
|
traversePath,
|
|
1911
|
+
tryGetFeatureValue,
|
|
1061
1912
|
user,
|
|
1062
1913
|
userConfigSchema,
|
|
1063
1914
|
validateAttribute,
|
|
@@ -1070,9 +1921,11 @@ export {
|
|
|
1070
1921
|
validatePath,
|
|
1071
1922
|
verifyNativeObjectsSync,
|
|
1072
1923
|
verifyNativeViewsSync,
|
|
1924
|
+
verifyRegistryViewsSeeded,
|
|
1073
1925
|
view,
|
|
1074
1926
|
viewRegistry,
|
|
1075
1927
|
wait,
|
|
1928
|
+
withFeatureFlags,
|
|
1076
1929
|
withTenantContext,
|
|
1077
1930
|
workflow
|
|
1078
1931
|
};
|