@api-client/core 0.19.19 → 0.19.20
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/build/src/authorization/Utils.js +3 -3
- package/build/src/authorization/Utils.js.map +1 -1
- package/build/src/modeling/ApiModel.d.ts +16 -5
- package/build/src/modeling/ApiModel.d.ts.map +1 -1
- package/build/src/modeling/ApiModel.js +17 -2
- package/build/src/modeling/ApiModel.js.map +1 -1
- package/build/src/modeling/ApiValidation.d.ts.map +1 -1
- package/build/src/modeling/ApiValidation.js +2 -1
- package/build/src/modeling/ApiValidation.js.map +1 -1
- package/build/src/modeling/DomainProperty.d.ts +12 -0
- package/build/src/modeling/DomainProperty.d.ts.map +1 -1
- package/build/src/modeling/DomainProperty.js +23 -28
- package/build/src/modeling/DomainProperty.js.map +1 -1
- package/build/src/modeling/DomainSerialization.js +1 -1
- package/build/src/modeling/DomainSerialization.js.map +1 -1
- package/build/src/modeling/ExposedEntity.d.ts +15 -1
- package/build/src/modeling/ExposedEntity.d.ts.map +1 -1
- package/build/src/modeling/ExposedEntity.js +42 -4
- package/build/src/modeling/ExposedEntity.js.map +1 -1
- package/build/src/modeling/actions/Action.d.ts.map +1 -1
- package/build/src/modeling/actions/Action.js +1 -0
- package/build/src/modeling/actions/Action.js.map +1 -1
- package/build/src/modeling/actions/ListAction.d.ts +3 -17
- package/build/src/modeling/actions/ListAction.d.ts.map +1 -1
- package/build/src/modeling/actions/ListAction.js +18 -38
- package/build/src/modeling/actions/ListAction.js.map +1 -1
- package/build/src/modeling/actions/SearchAction.d.ts +4 -4
- package/build/src/modeling/actions/SearchAction.d.ts.map +1 -1
- package/build/src/modeling/actions/SearchAction.js +16 -13
- package/build/src/modeling/actions/SearchAction.js.map +1 -1
- package/build/src/modeling/generators/oas_312/OasGenerator.d.ts +32 -0
- package/build/src/modeling/generators/oas_312/OasGenerator.d.ts.map +1 -0
- package/build/src/modeling/generators/oas_312/OasGenerator.js +1452 -0
- package/build/src/modeling/generators/oas_312/OasGenerator.js.map +1 -0
- package/build/src/modeling/generators/oas_312/OasSchemaGenerator.d.ts +27 -0
- package/build/src/modeling/generators/oas_312/OasSchemaGenerator.d.ts.map +1 -0
- package/build/src/modeling/generators/oas_312/OasSchemaGenerator.js +295 -0
- package/build/src/modeling/generators/oas_312/OasSchemaGenerator.js.map +1 -0
- package/build/src/modeling/generators/oas_312/types.d.ts +1010 -0
- package/build/src/modeling/generators/oas_312/types.d.ts.map +1 -0
- package/build/src/modeling/generators/oas_312/types.js +2 -0
- package/build/src/modeling/generators/oas_312/types.js.map +1 -0
- package/build/src/modeling/generators/oas_320/OasGenerator.d.ts +16 -0
- package/build/src/modeling/generators/oas_320/OasGenerator.d.ts.map +1 -0
- package/build/src/modeling/generators/oas_320/OasGenerator.js +306 -0
- package/build/src/modeling/generators/oas_320/OasGenerator.js.map +1 -0
- package/build/src/modeling/generators/oas_320/OasSchemaGenerator.d.ts +25 -0
- package/build/src/modeling/generators/oas_320/OasSchemaGenerator.d.ts.map +1 -0
- package/build/src/modeling/generators/oas_320/OasSchemaGenerator.js +237 -0
- package/build/src/modeling/generators/oas_320/OasSchemaGenerator.js.map +1 -0
- package/build/src/modeling/generators/oas_320/types.d.ts +1219 -0
- package/build/src/modeling/generators/oas_320/types.d.ts.map +1 -0
- package/build/src/modeling/generators/oas_320/types.js +2 -0
- package/build/src/modeling/generators/oas_320/types.js.map +1 -0
- package/build/src/modeling/types.d.ts +50 -13
- package/build/src/modeling/types.d.ts.map +1 -1
- package/build/src/modeling/types.js.map +1 -1
- package/build/src/modeling/validation/api_model_rules.d.ts +1 -0
- package/build/src/modeling/validation/api_model_rules.d.ts.map +1 -1
- package/build/src/modeling/validation/api_model_rules.js +105 -29
- package/build/src/modeling/validation/api_model_rules.js.map +1 -1
- package/build/src/models/ProjectRequest.d.ts.map +1 -1
- package/build/src/models/ProjectRequest.js +0 -4
- package/build/src/models/ProjectRequest.js.map +1 -1
- package/build/src/models/transformers/ArcDexieTransformer.d.ts.map +1 -1
- package/build/src/models/transformers/ArcDexieTransformer.js +0 -4
- package/build/src/models/transformers/ArcDexieTransformer.js.map +1 -1
- package/build/src/models/transformers/ImportUtils.js +1 -1
- package/build/src/models/transformers/ImportUtils.js.map +1 -1
- package/build/src/models/transformers/PostmanBackupTransformer.d.ts.map +1 -1
- package/build/src/models/transformers/PostmanBackupTransformer.js +0 -4
- package/build/src/models/transformers/PostmanBackupTransformer.js.map +1 -1
- package/build/src/runtime/constants.d.ts +7 -0
- package/build/src/runtime/constants.d.ts.map +1 -0
- package/build/src/runtime/constants.js +8 -0
- package/build/src/runtime/constants.js.map +1 -0
- package/build/src/runtime/http-engine/ntlm/Des.d.ts.map +1 -1
- package/build/src/runtime/http-engine/ntlm/Des.js +1 -0
- package/build/src/runtime/http-engine/ntlm/Des.js.map +1 -1
- package/build/src/runtime/variables/EvalFunctions.d.ts.map +1 -1
- package/build/src/runtime/variables/EvalFunctions.js +0 -1
- package/build/src/runtime/variables/EvalFunctions.js.map +1 -1
- package/build/tsconfig.tsbuildinfo +1 -1
- package/eslint.config.js +6 -0
- package/package.json +3 -1
- package/src/authorization/Utils.ts +3 -3
- package/src/modeling/ApiModel.ts +23 -8
- package/src/modeling/ApiValidation.ts +2 -0
- package/src/modeling/DomainProperty.ts +22 -18
- package/src/modeling/DomainSerialization.ts +1 -1
- package/src/modeling/ExposedEntity.ts +44 -4
- package/src/modeling/actions/Action.ts +1 -0
- package/src/modeling/actions/ListAction.ts +12 -30
- package/src/modeling/actions/SearchAction.ts +11 -8
- package/src/modeling/generators/oas_312/OasGenerator.ts +1685 -0
- package/src/modeling/generators/oas_312/OasSchemaGenerator.ts +322 -0
- package/src/modeling/generators/oas_312/types.ts +1052 -0
- package/src/modeling/generators/oas_320/OasGenerator.ts +359 -0
- package/src/modeling/generators/oas_320/OasSchemaGenerator.ts +255 -0
- package/src/modeling/generators/oas_320/types.ts +1259 -0
- package/src/modeling/types.ts +55 -22
- package/src/modeling/validation/api_model_rules.ts +103 -32
- package/src/models/ProjectRequest.ts +0 -4
- package/src/models/transformers/ArcDexieTransformer.ts +0 -4
- package/src/models/transformers/ImportUtils.ts +1 -1
- package/src/models/transformers/PostmanBackupTransformer.ts +0 -5
- package/src/runtime/constants.ts +9 -0
- package/src/runtime/http-engine/ntlm/Des.ts +1 -0
- package/src/runtime/variables/EvalFunctions.ts +0 -1
- package/tests/test-utils.ts +6 -2
- package/tests/unit/decorators/observed.spec.ts +8 -24
- package/tests/unit/decorators/observed_recursive.spec.ts +0 -1
- package/tests/unit/events/EventsTestHelpers.ts +0 -1
- package/tests/unit/events/events_polyfills.ts +0 -1
- package/tests/unit/legacy-transformers/DataTestHelper.ts +0 -2
- package/tests/unit/legacy-transformers/LegacyExportProcessor.spec.ts +0 -1
- package/tests/unit/modeling/actions/ListAction.spec.ts +9 -69
- package/tests/unit/modeling/actions/SearchAction.spec.ts +9 -35
- package/tests/unit/modeling/api_model.spec.ts +28 -0
- package/tests/unit/modeling/definitions/sku.spec.ts +0 -2
- package/tests/unit/modeling/domain_property.spec.ts +20 -1
- package/tests/unit/modeling/exposed_entity.spec.ts +71 -0
- package/tests/unit/modeling/generators/OasGenerator.spec.ts +302 -0
- package/tests/unit/modeling/validation/api_model_rules.spec.ts +113 -15
package/src/modeling/types.ts
CHANGED
|
@@ -223,41 +223,35 @@ export interface ProblemDetails {
|
|
|
223
223
|
}
|
|
224
224
|
|
|
225
225
|
/**
|
|
226
|
-
* The set of supported filter operators for the List action.
|
|
226
|
+
* The set of supported filter operators for the List and search action.
|
|
227
227
|
* These are used in query parameters, e.g., ?price[gte]=100
|
|
228
228
|
*
|
|
229
229
|
* - eq: Equal
|
|
230
|
-
* -
|
|
230
|
+
* - neq: Not Equal
|
|
231
|
+
* - in: Value is one of the elements in the provided array
|
|
232
|
+
* - nin: Value is not one of the elements in the provided array
|
|
231
233
|
* - lt: Less Than
|
|
232
234
|
* - lte: Less Than or Equal
|
|
233
235
|
* - gt: Greater Than
|
|
234
236
|
* - gte: Greater Than or Equal
|
|
235
|
-
* -
|
|
236
|
-
*
|
|
237
|
-
*
|
|
238
|
-
* -
|
|
239
|
-
* -
|
|
240
|
-
* - st: String starts with
|
|
241
|
-
* - end: String ends with
|
|
242
|
-
* - in: Value is one of the elements in the provided array
|
|
243
|
-
* - nin: Value is not one of the elements in the provided array
|
|
237
|
+
* - exists: Checks if the field exists
|
|
238
|
+
*
|
|
239
|
+
* Search filters only:
|
|
240
|
+
* - contains: String contains substring / Array contains element (Substring Match)
|
|
241
|
+
* - match: Lexical Match, multi-word queries against long text.
|
|
244
242
|
*/
|
|
245
243
|
export type ResourceFilterOperator =
|
|
246
244
|
| 'eq' // Equal
|
|
247
|
-
| '
|
|
245
|
+
| 'neq' // Not equal
|
|
246
|
+
| 'in' // Value is one of the elements in the provided array
|
|
247
|
+
| 'nin' // Value is not one of the elements in the provided array
|
|
248
248
|
| 'lt' // Less than
|
|
249
249
|
| 'lte' // Less than or equal
|
|
250
250
|
| 'gt' // Greater than
|
|
251
251
|
| 'gte' // Greater than or equal
|
|
252
|
-
| '
|
|
253
|
-
| '
|
|
254
|
-
| '
|
|
255
|
-
| 'af' // Date after a specific value
|
|
256
|
-
| 'cn' // String contains substring / Array contains element
|
|
257
|
-
| 'st' // String starts with
|
|
258
|
-
| 'end' // String ends with
|
|
259
|
-
| 'in' // Value is one of the elements in the provided array
|
|
260
|
-
| 'nin' // Value is not one of the elements in the provided array
|
|
252
|
+
| 'exists' // Checks if the field exists
|
|
253
|
+
| 'contains' // String contains substring / Array contains element (Substring Match)
|
|
254
|
+
| 'match' // Lexical Match, multi-word queries against long text.
|
|
261
255
|
|
|
262
256
|
/**
|
|
263
257
|
* The session transport configuration interface.
|
|
@@ -384,6 +378,8 @@ export interface RolesBasedAccessControl extends AuthorizationConfiguration {
|
|
|
384
378
|
roleKey: string
|
|
385
379
|
}
|
|
386
380
|
|
|
381
|
+
export type AuthorizationStrategy = RolesBasedAccessControl
|
|
382
|
+
|
|
387
383
|
/**
|
|
388
384
|
* Configures the strategy for authenticating end-users.
|
|
389
385
|
* An API can only support one authentication strategy at a time.
|
|
@@ -412,6 +408,8 @@ export interface UsernamePasswordConfiguration extends AuthenticationConfigurati
|
|
|
412
408
|
passwordKey?: string
|
|
413
409
|
}
|
|
414
410
|
|
|
411
|
+
export type AuthenticationStrategy = UsernamePasswordConfiguration
|
|
412
|
+
|
|
415
413
|
/**
|
|
416
414
|
* Represents a Data Entity from the Data Domain that the API will expose and operate upon.
|
|
417
415
|
*/
|
|
@@ -492,6 +490,10 @@ export interface ExposedEntitySchema {
|
|
|
492
490
|
* When true, generation for this exposure hit configured limits
|
|
493
491
|
*/
|
|
494
492
|
truncated?: boolean
|
|
493
|
+
/**
|
|
494
|
+
* Pagination contract for this exposure.
|
|
495
|
+
*/
|
|
496
|
+
paginationContract?: PaginationContract
|
|
495
497
|
}
|
|
496
498
|
|
|
497
499
|
/**
|
|
@@ -542,7 +544,13 @@ export interface PaginationStrategy {
|
|
|
542
544
|
* The default page size for the pagination strategy.
|
|
543
545
|
* This is the number of items returned per page when no specific page size is requested.
|
|
544
546
|
*/
|
|
545
|
-
|
|
547
|
+
defaultLimit?: number
|
|
548
|
+
/**
|
|
549
|
+
* The maximum page size for the pagination strategy.
|
|
550
|
+
* This is the maximum number of items that can be returned per page.
|
|
551
|
+
* The API runtime defined the upper limit to prevent abuse.
|
|
552
|
+
*/
|
|
553
|
+
maxLimit?: number
|
|
546
554
|
}
|
|
547
555
|
|
|
548
556
|
/**
|
|
@@ -559,6 +567,31 @@ export interface OffsetPaginationStrategy extends PaginationStrategy {
|
|
|
559
567
|
kind: 'offset'
|
|
560
568
|
}
|
|
561
569
|
|
|
570
|
+
/**
|
|
571
|
+
* Represents the contract for pagination. Defines which fields can be used for filtering, sorting,
|
|
572
|
+
* and searching.
|
|
573
|
+
*/
|
|
574
|
+
export interface PaginationContract {
|
|
575
|
+
/**
|
|
576
|
+
* The list of fields (property keys) that can be used for filtering.
|
|
577
|
+
*/
|
|
578
|
+
filterableFields: string[]
|
|
579
|
+
/**
|
|
580
|
+
* The list of fields (property keys) that can be used for sorting.
|
|
581
|
+
*/
|
|
582
|
+
sortableFields: string[]
|
|
583
|
+
/**
|
|
584
|
+
* The list of fields (property keys) that can be used for searching.
|
|
585
|
+
* Note that these properties must be of type string or array of strings.
|
|
586
|
+
*/
|
|
587
|
+
searchableFields: string[]
|
|
588
|
+
/**
|
|
589
|
+
* The default sort order for the pagination strategy.
|
|
590
|
+
* This is the sort order that will be used when no sort order is specified.
|
|
591
|
+
*/
|
|
592
|
+
defaultSort?: { field: string; direction: 'asc' | 'desc' }[]
|
|
593
|
+
}
|
|
594
|
+
|
|
562
595
|
export type DomainImpactKinds =
|
|
563
596
|
| typeof DomainNamespaceKind
|
|
564
597
|
| typeof DomainEntityKind
|
|
@@ -348,49 +348,62 @@ export function validateApiModelMetadata(model: ApiModel): ApiModelValidationIte
|
|
|
348
348
|
return issues
|
|
349
349
|
}
|
|
350
350
|
|
|
351
|
-
export function
|
|
351
|
+
export function validateApiPagination(model: ApiModel): ApiModelValidationItem[] {
|
|
352
352
|
const issues: ApiModelValidationItem[] = []
|
|
353
353
|
const context: ApiModelValidationContext = {
|
|
354
|
-
apiModelKey,
|
|
355
|
-
kind:
|
|
356
|
-
key:
|
|
357
|
-
parentExposedEntityKey: parent.key,
|
|
354
|
+
apiModelKey: model.key,
|
|
355
|
+
kind: ApiModelKind,
|
|
356
|
+
key: model.key,
|
|
358
357
|
}
|
|
359
|
-
|
|
360
|
-
|
|
361
|
-
|
|
358
|
+
// We only need pagination when the API contains at least one List or Search action
|
|
359
|
+
let validate = false
|
|
360
|
+
for (const exposure of model.exposes.values()) {
|
|
361
|
+
if (exposure.actions.some((action) => ListAction.isListAction(action) || SearchAction.isSearchAction(action))) {
|
|
362
|
+
validate = true
|
|
363
|
+
break
|
|
364
|
+
}
|
|
365
|
+
}
|
|
366
|
+
if (!validate) {
|
|
367
|
+
return issues
|
|
368
|
+
}
|
|
369
|
+
if (!model.pagination || !model.pagination.kind) {
|
|
370
|
+
issues.push({
|
|
371
|
+
code: createCode('API', 'MISSING_PAGINATION'),
|
|
372
|
+
message: 'The API must have a defined pagination strategy when it exposes List or Search actions.',
|
|
373
|
+
suggestion: 'Configure how results are loaded (e.g. by page or by a continuous cursor).',
|
|
374
|
+
severity: 'error',
|
|
375
|
+
context: { ...context, property: 'pagination' },
|
|
376
|
+
})
|
|
377
|
+
} else {
|
|
378
|
+
if (model.pagination.defaultLimit === undefined) {
|
|
362
379
|
issues.push({
|
|
363
|
-
code: createCode('
|
|
364
|
-
message:
|
|
365
|
-
suggestion: '
|
|
366
|
-
severity: '
|
|
367
|
-
context: { ...context, property: 'pagination' },
|
|
380
|
+
code: createCode('API', 'MISSING_PAGINATION_DEFAULT_LIMIT'),
|
|
381
|
+
message: "The API doesn't have a defined default page limit when it exposes List or Search actions.",
|
|
382
|
+
suggestion: 'Set a default page limit for the pagination otherwise the API will use its default limit.',
|
|
383
|
+
severity: 'info',
|
|
384
|
+
context: { ...context, property: 'pagination.defaultLimit' },
|
|
368
385
|
})
|
|
369
386
|
}
|
|
370
|
-
if (
|
|
371
|
-
(!action.filterableFields || action.filterableFields.length === 0) &&
|
|
372
|
-
(!action.sortableFields || action.sortableFields.length === 0)
|
|
373
|
-
) {
|
|
387
|
+
if (model.pagination.maxLimit === undefined) {
|
|
374
388
|
issues.push({
|
|
375
|
-
code: createCode('
|
|
376
|
-
message: '
|
|
377
|
-
suggestion: '
|
|
378
|
-
severity: '
|
|
379
|
-
context,
|
|
389
|
+
code: createCode('API', 'MISSING_PAGINATION_MAX_LIMIT'),
|
|
390
|
+
message: "The API doesn't have a defined page size max limit when it exposes List or Search actions.",
|
|
391
|
+
suggestion: 'Set a max page size limit for the pagination otherwise the API will use its default max limit.',
|
|
392
|
+
severity: 'info',
|
|
393
|
+
context: { ...context, property: 'pagination.maxLimit' },
|
|
380
394
|
})
|
|
381
395
|
}
|
|
382
396
|
}
|
|
397
|
+
return issues
|
|
398
|
+
}
|
|
383
399
|
|
|
384
|
-
|
|
385
|
-
|
|
386
|
-
|
|
387
|
-
|
|
388
|
-
|
|
389
|
-
|
|
390
|
-
|
|
391
|
-
context: { ...context, property: 'fields' },
|
|
392
|
-
})
|
|
393
|
-
}
|
|
400
|
+
export function validateAction(action: Action, parent: ExposedEntity, apiModelKey: string): ApiModelValidationItem[] {
|
|
401
|
+
const issues: ApiModelValidationItem[] = []
|
|
402
|
+
const context: ApiModelValidationContext = {
|
|
403
|
+
apiModelKey,
|
|
404
|
+
kind: 'Action',
|
|
405
|
+
key: action.kind, // Actions lack nanoids, kind represents its type
|
|
406
|
+
parentExposedEntityKey: parent.key,
|
|
394
407
|
}
|
|
395
408
|
|
|
396
409
|
if (DeleteAction.isDeleteAction(action)) {
|
|
@@ -573,9 +586,14 @@ export function validateExposedEntity(entity: ExposedEntity, apiModel: ApiModel)
|
|
|
573
586
|
context: { ...context, property: 'actions' },
|
|
574
587
|
})
|
|
575
588
|
} else {
|
|
589
|
+
let hasSearch = false
|
|
590
|
+
let hasList = false
|
|
576
591
|
for (const action of entity.actions) {
|
|
577
592
|
issues.push(...validateAction(action, entity, apiModel.key))
|
|
578
593
|
|
|
594
|
+
if (SearchAction.isSearchAction(action)) hasSearch = true
|
|
595
|
+
if (ListAction.isListAction(action)) hasList = true
|
|
596
|
+
|
|
579
597
|
// Check inheritance of access rules
|
|
580
598
|
// For a rule to exist, it might be on the action, the exposure, any parent, or the apiModel.
|
|
581
599
|
let hasAuth = false
|
|
@@ -605,6 +623,59 @@ export function validateExposedEntity(entity: ExposedEntity, apiModel: ApiModel)
|
|
|
605
623
|
})
|
|
606
624
|
}
|
|
607
625
|
}
|
|
626
|
+
|
|
627
|
+
if (hasList || hasSearch) {
|
|
628
|
+
const contract = entity.paginationContract
|
|
629
|
+
if (!contract) {
|
|
630
|
+
issues.push({
|
|
631
|
+
code: createCode('EXPOSURE', 'MISSING_PAGINATION_CONTRACT'),
|
|
632
|
+
message: 'The List or Search action needs a pagination contract.',
|
|
633
|
+
suggestion: 'Add a pagination contract to the exposed entity.',
|
|
634
|
+
severity: 'error',
|
|
635
|
+
context,
|
|
636
|
+
})
|
|
637
|
+
} else {
|
|
638
|
+
if (hasList) {
|
|
639
|
+
if (!contract.filterableFields || contract.filterableFields.length === 0) {
|
|
640
|
+
issues.push({
|
|
641
|
+
code: createCode('EXPOSURE', 'LIST_MISSING_FILTERS'),
|
|
642
|
+
message: 'Listing all elements without filters could be overwhelming for large tables.',
|
|
643
|
+
suggestion: 'Select a few important fields to allow filtering.',
|
|
644
|
+
severity: 'warning',
|
|
645
|
+
context,
|
|
646
|
+
})
|
|
647
|
+
}
|
|
648
|
+
if (!contract.sortableFields || contract.sortableFields.length === 0) {
|
|
649
|
+
issues.push({
|
|
650
|
+
code: createCode('EXPOSURE', 'LIST_MISSING_SORTING'),
|
|
651
|
+
message: 'Listing all elements without sorting could be overwhelming for large tables.',
|
|
652
|
+
suggestion: 'Select a few important fields to allow sorting.',
|
|
653
|
+
severity: 'warning',
|
|
654
|
+
context,
|
|
655
|
+
})
|
|
656
|
+
}
|
|
657
|
+
}
|
|
658
|
+
if (hasSearch) {
|
|
659
|
+
// Search and technically be used for filtering.
|
|
660
|
+
const all: string[] = []
|
|
661
|
+
if (Array.isArray(contract.searchableFields)) {
|
|
662
|
+
all.push(...contract.searchableFields)
|
|
663
|
+
}
|
|
664
|
+
if (Array.isArray(contract.filterableFields)) {
|
|
665
|
+
all.push(...contract.filterableFields)
|
|
666
|
+
}
|
|
667
|
+
if (!all.length) {
|
|
668
|
+
issues.push({
|
|
669
|
+
code: createCode('EXPOSURE', 'SEARCH_MISSING_FIELDS'),
|
|
670
|
+
message: 'Search action needs to know which fields to look in.',
|
|
671
|
+
suggestion: 'Select a few important fields to allow searching or full-text search.',
|
|
672
|
+
severity: 'warning',
|
|
673
|
+
context,
|
|
674
|
+
})
|
|
675
|
+
}
|
|
676
|
+
}
|
|
677
|
+
}
|
|
678
|
+
}
|
|
608
679
|
}
|
|
609
680
|
|
|
610
681
|
return issues
|
|
@@ -315,10 +315,6 @@ export class ProjectRequest extends Request implements ProjectDefinitionProperty
|
|
|
315
315
|
if (!environment) {
|
|
316
316
|
return undefined
|
|
317
317
|
}
|
|
318
|
-
let parent = this.getParent()
|
|
319
|
-
if (parent === project) {
|
|
320
|
-
parent = undefined
|
|
321
|
-
}
|
|
322
318
|
return project.findEnvironment(environment)
|
|
323
319
|
}
|
|
324
320
|
|
|
@@ -235,10 +235,6 @@ export class ArcDexieTransformer extends BaseTransformer {
|
|
|
235
235
|
|
|
236
236
|
parseSavedItem(item: DexieRequest): RequestProcessItem {
|
|
237
237
|
const requestName = item.name || item._name
|
|
238
|
-
let keyName = requestName
|
|
239
|
-
if (keyName && keyName[0] === '_') {
|
|
240
|
-
keyName = keyName.substr(1)
|
|
241
|
-
}
|
|
242
238
|
const obj: ExportArcSavedRequest = {
|
|
243
239
|
name: requestName || '',
|
|
244
240
|
method: item.method,
|
|
@@ -118,7 +118,7 @@ export function prepareImportObject(data: Record<string, unknown> | string): unk
|
|
|
118
118
|
data = JSON.parse(data)
|
|
119
119
|
} catch (e) {
|
|
120
120
|
const err = e as Error
|
|
121
|
-
throw new Error(`Unable to read the file. Not a JSON: ${err.message}
|
|
121
|
+
throw new Error(`Unable to read the file. Not a JSON: ${err.message}`, { cause: e })
|
|
122
122
|
}
|
|
123
123
|
}
|
|
124
124
|
return data
|
|
@@ -213,11 +213,6 @@ export class PostmanBackupTransformer extends PostmanTransformer {
|
|
|
213
213
|
let headers = request.headers || ''
|
|
214
214
|
headers = this.ensureVariablesSyntax(headers) as string
|
|
215
215
|
|
|
216
|
-
let createdTime = Number(request.time)
|
|
217
|
-
if (Number.isNaN(createdTime)) {
|
|
218
|
-
createdTime = Date.now()
|
|
219
|
-
}
|
|
220
|
-
|
|
221
216
|
const created = current.addRequest(url)
|
|
222
217
|
created.info.name = name
|
|
223
218
|
if (request.description) {
|
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
// This is shared in the web and node.
|
|
2
|
+
|
|
3
|
+
export const OFFSET_PAGINATION_DEFAULT_LIMIT = 20
|
|
4
|
+
export const OFFSET_PAGINATION_MAX_LIMIT = 100
|
|
5
|
+
export const OFFSET_PAGINATION_MIN_LIMIT = 1
|
|
6
|
+
|
|
7
|
+
export const CURSOR_PAGINATION_DEFAULT_LIMIT = 20
|
|
8
|
+
export const CURSOR_PAGINATION_MAX_LIMIT = 100
|
|
9
|
+
export const CURSOR_PAGINATION_MIN_LIMIT = 1
|
|
@@ -128,6 +128,7 @@ export class Des {
|
|
|
128
128
|
cbcleft =
|
|
129
129
|
(iv!.charCodeAt(m++) << 24) | (iv!.charCodeAt(m++) << 16) | (iv!.charCodeAt(m++) << 8) | iv!.charCodeAt(m++)
|
|
130
130
|
cbcright =
|
|
131
|
+
// eslint-disable-next-line no-useless-assignment
|
|
131
132
|
(iv!.charCodeAt(m++) << 24) | (iv!.charCodeAt(m++) << 16) | (iv!.charCodeAt(m++) << 8) | iv!.charCodeAt(m++)
|
|
132
133
|
m = 0
|
|
133
134
|
}
|
package/tests/test-utils.ts
CHANGED
|
@@ -111,11 +111,15 @@ export const TestUtils = {
|
|
|
111
111
|
if (expectedMessage) {
|
|
112
112
|
if (typeof expectedMessage === 'string') {
|
|
113
113
|
if (!typedError.message.includes(expectedMessage)) {
|
|
114
|
-
throw new Error(`Expected error message to include "${expectedMessage}", got "${typedError.message}"
|
|
114
|
+
throw new Error(`Expected error message to include "${expectedMessage}", got "${typedError.message}"`, {
|
|
115
|
+
cause: error,
|
|
116
|
+
})
|
|
115
117
|
}
|
|
116
118
|
} else if (expectedMessage instanceof RegExp) {
|
|
117
119
|
if (!expectedMessage.test(typedError.message)) {
|
|
118
|
-
throw new Error(`Expected error message to match ${expectedMessage}, got "${typedError.message}"
|
|
120
|
+
throw new Error(`Expected error message to match ${expectedMessage}, got "${typedError.message}"`, {
|
|
121
|
+
cause: error,
|
|
122
|
+
})
|
|
119
123
|
}
|
|
120
124
|
}
|
|
121
125
|
}
|
|
@@ -13,7 +13,6 @@ test.group('observed decorator', () => {
|
|
|
13
13
|
class TestClass {
|
|
14
14
|
domain = mockDomain
|
|
15
15
|
|
|
16
|
-
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
17
16
|
@observed() accessor testProperty: any
|
|
18
17
|
}
|
|
19
18
|
|
|
@@ -41,7 +40,6 @@ test.group('observed decorator', () => {
|
|
|
41
40
|
instanceNotifyCallCount++
|
|
42
41
|
}
|
|
43
42
|
|
|
44
|
-
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
45
43
|
@observed() accessor testProperty: any
|
|
46
44
|
}
|
|
47
45
|
|
|
@@ -92,7 +90,6 @@ test.group('observed decorator', () => {
|
|
|
92
90
|
class TestClass {
|
|
93
91
|
domain = mockDomain
|
|
94
92
|
|
|
95
|
-
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
96
93
|
@observed({ deep: true }) accessor nestedData: any
|
|
97
94
|
}
|
|
98
95
|
|
|
@@ -119,7 +116,6 @@ test.group('observed decorator', () => {
|
|
|
119
116
|
class TestClass {
|
|
120
117
|
domain = mockDomain
|
|
121
118
|
|
|
122
|
-
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
123
119
|
@observed({ deep: true }) accessor primitiveValue: any
|
|
124
120
|
}
|
|
125
121
|
|
|
@@ -146,7 +142,6 @@ test.group('observed decorator', () => {
|
|
|
146
142
|
class TestClass {
|
|
147
143
|
domain = mockDomain
|
|
148
144
|
|
|
149
|
-
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
150
145
|
@observed() accessor nullableValue: any
|
|
151
146
|
}
|
|
152
147
|
|
|
@@ -168,7 +163,7 @@ test.group('observed decorator', () => {
|
|
|
168
163
|
test('should throw error for unsupported decorator locations', ({ assert }) => {
|
|
169
164
|
assert.throws(() => {
|
|
170
165
|
const decorator = observed()
|
|
171
|
-
|
|
166
|
+
|
|
172
167
|
decorator({} as any, { kind: 'field' } as any)
|
|
173
168
|
}, 'Unsupported decorator location: field')
|
|
174
169
|
}).tags(['@decorators', '@observed', '@core', '@unit', '@fast'])
|
|
@@ -184,7 +179,6 @@ test.group('observed decorator', () => {
|
|
|
184
179
|
class TestClass {
|
|
185
180
|
domain = mockDomain
|
|
186
181
|
|
|
187
|
-
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
188
182
|
@observed({ deep: true }) accessor complexData: any
|
|
189
183
|
}
|
|
190
184
|
|
|
@@ -205,7 +199,7 @@ test.group('observed decorator', () => {
|
|
|
205
199
|
test('should handle class without domain or notifyChange', ({ assert }) => {
|
|
206
200
|
class TestClass {
|
|
207
201
|
// @ts-expect-error It is for testing purposes
|
|
208
|
-
|
|
202
|
+
|
|
209
203
|
@observed() accessor testProperty: any
|
|
210
204
|
}
|
|
211
205
|
|
|
@@ -229,9 +223,8 @@ test.group('observed decorator', () => {
|
|
|
229
223
|
class TestClass {
|
|
230
224
|
domain = mockDomain
|
|
231
225
|
|
|
232
|
-
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
233
226
|
@observed() accessor prop1: any
|
|
234
|
-
|
|
227
|
+
|
|
235
228
|
@observed() accessor prop2: any
|
|
236
229
|
}
|
|
237
230
|
|
|
@@ -258,12 +251,11 @@ test.group('observed decorator', () => {
|
|
|
258
251
|
class TestClass {
|
|
259
252
|
domain = mockDomain
|
|
260
253
|
|
|
261
|
-
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
262
254
|
@observed({ deep: true }) accessor data: any
|
|
263
255
|
}
|
|
264
256
|
|
|
265
257
|
const instance = new TestClass()
|
|
266
|
-
|
|
258
|
+
|
|
267
259
|
const obj: any = { name: 'test' }
|
|
268
260
|
obj.self = obj // Create circular reference
|
|
269
261
|
|
|
@@ -316,7 +308,6 @@ test.group('retargetChange decorator', () => {
|
|
|
316
308
|
domain = mockDomain
|
|
317
309
|
|
|
318
310
|
@retargetChange()
|
|
319
|
-
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
320
311
|
accessor target: any
|
|
321
312
|
}
|
|
322
313
|
|
|
@@ -344,7 +335,6 @@ test.group('retargetChange decorator', () => {
|
|
|
344
335
|
domain = mockDomain
|
|
345
336
|
|
|
346
337
|
@retargetChange()
|
|
347
|
-
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
348
338
|
accessor target: any
|
|
349
339
|
}
|
|
350
340
|
|
|
@@ -369,17 +359,14 @@ test.group('retargetChange decorator', () => {
|
|
|
369
359
|
}
|
|
370
360
|
|
|
371
361
|
class TestClass {
|
|
372
|
-
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
373
362
|
#target: any
|
|
374
363
|
domain = mockDomain
|
|
375
364
|
|
|
376
365
|
@retargetChange()
|
|
377
|
-
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
378
366
|
set target(value: any) {
|
|
379
367
|
this.#target = value
|
|
380
368
|
}
|
|
381
369
|
|
|
382
|
-
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
383
370
|
get target(): any {
|
|
384
371
|
return this.#target
|
|
385
372
|
}
|
|
@@ -400,7 +387,7 @@ test.group('retargetChange decorator', () => {
|
|
|
400
387
|
test('should throw error for unsupported decorator locations', ({ assert }) => {
|
|
401
388
|
assert.throws(() => {
|
|
402
389
|
const decorator = retargetChange()
|
|
403
|
-
|
|
390
|
+
|
|
404
391
|
decorator({} as any, { kind: 'field' } as any)
|
|
405
392
|
}, 'Unsupported decorator location: field')
|
|
406
393
|
}).tags(['@decorators', '@retargetChange', '@core', '@unit', '@fast'])
|
|
@@ -417,7 +404,6 @@ test.group('toRaw function', () => {
|
|
|
417
404
|
class TestClass {
|
|
418
405
|
domain = mockDomain
|
|
419
406
|
|
|
420
|
-
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
421
407
|
@observed({ deep: true }) accessor data: any
|
|
422
408
|
}
|
|
423
409
|
|
|
@@ -494,7 +480,7 @@ test.group('edge cases and error conditions', () => {
|
|
|
494
480
|
test('should handle class without domain or notifyChange', ({ assert }) => {
|
|
495
481
|
class TestClass {
|
|
496
482
|
// @ts-expect-error It is for testing purposes
|
|
497
|
-
|
|
483
|
+
|
|
498
484
|
@observed() accessor testProperty: any
|
|
499
485
|
}
|
|
500
486
|
|
|
@@ -518,9 +504,8 @@ test.group('edge cases and error conditions', () => {
|
|
|
518
504
|
class TestClass {
|
|
519
505
|
domain = mockDomain
|
|
520
506
|
|
|
521
|
-
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
522
507
|
@observed() accessor prop1: any
|
|
523
|
-
|
|
508
|
+
|
|
524
509
|
@observed() accessor prop2: any
|
|
525
510
|
}
|
|
526
511
|
|
|
@@ -547,12 +532,11 @@ test.group('edge cases and error conditions', () => {
|
|
|
547
532
|
class TestClass {
|
|
548
533
|
domain = mockDomain
|
|
549
534
|
|
|
550
|
-
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
551
535
|
@observed({ deep: true }) accessor data: any
|
|
552
536
|
}
|
|
553
537
|
|
|
554
538
|
const instance = new TestClass()
|
|
555
|
-
|
|
539
|
+
|
|
556
540
|
const obj: any = { name: 'test' }
|
|
557
541
|
obj.self = obj // Create circular reference
|
|
558
542
|
|
|
@@ -1,7 +1,6 @@
|
|
|
1
1
|
// The event names should be unique across all events in all modules.
|
|
2
2
|
const names: string[] = []
|
|
3
3
|
|
|
4
|
-
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
5
4
|
export function ensureUnique(namespace: string, src: any): void {
|
|
6
5
|
for (const [key, value] of Object.entries(src)) {
|
|
7
6
|
const typedValue = value as string
|