@squiz/dx-json-schema-lib 1.21.1-alpha.13 → 1.21.1-alpha.16

Sign up to get free protection for your applications and to get access to all the features.
Files changed (67) hide show
  1. package/.npm/_logs/2023-03-15T00_26_26_642Z-debug-0.log +37 -0
  2. package/lib/JsonValidationService.d.ts +1 -1
  3. package/lib/JsonValidationService.js +15 -5
  4. package/lib/JsonValidationService.js.map +1 -1
  5. package/lib/JsonValidationService.spec.js +444 -445
  6. package/lib/JsonValidationService.spec.js.map +1 -1
  7. package/lib/index.d.ts +5 -1
  8. package/lib/index.js +5 -1
  9. package/lib/index.js.map +1 -1
  10. package/lib/jsonTypeResolution/{arbitraryTypeResolution.d.ts → TypeResolver.d.ts} +7 -12
  11. package/lib/jsonTypeResolution/{arbitraryTypeResolution.js → TypeResolver.js} +17 -17
  12. package/lib/jsonTypeResolution/TypeResolver.js.map +1 -0
  13. package/lib/jsonTypeResolution/{arbitraryTypeResolution.spec.js → TypeResolver.spec.js} +12 -39
  14. package/lib/jsonTypeResolution/TypeResolver.spec.js.map +1 -0
  15. package/lib/jsonTypeResolution/TypeResolverBuilder.d.ts +12 -0
  16. package/lib/jsonTypeResolution/TypeResolverBuilder.js +32 -0
  17. package/lib/jsonTypeResolution/TypeResolverBuilder.js.map +1 -0
  18. package/lib/manifest/v1/DxContentMetaSchema.json +1 -1
  19. package/lib/manifest/v1/MatrixAssetSchema.json +28 -8
  20. package/lib/manifest/v1/v1.d.ts +10 -7
  21. package/lib/primitiveTypes/FormattedText.d.ts +8 -0
  22. package/lib/primitiveTypes/FormattedText.js +21 -0
  23. package/lib/primitiveTypes/FormattedText.js.map +1 -0
  24. package/lib/primitiveTypes/SquizImage.d.ts +26 -0
  25. package/lib/primitiveTypes/SquizImage.js +105 -0
  26. package/lib/primitiveTypes/SquizImage.js.map +1 -0
  27. package/lib/primitiveTypes/index.d.ts +2 -0
  28. package/lib/primitiveTypes/index.js +19 -0
  29. package/lib/primitiveTypes/index.js.map +1 -0
  30. package/lib/resolvableTypes/MatrixAsset.d.ts +9 -0
  31. package/lib/resolvableTypes/MatrixAsset.js +21 -0
  32. package/lib/resolvableTypes/MatrixAsset.js.map +1 -0
  33. package/lib/resolvableTypes/index.d.ts +1 -0
  34. package/lib/resolvableTypes/index.js +18 -0
  35. package/lib/resolvableTypes/index.js.map +1 -0
  36. package/package.json +5 -4
  37. package/src/JsonValidationService.spec.ts +585 -584
  38. package/src/JsonValidationService.ts +19 -9
  39. package/src/index.ts +6 -1
  40. package/src/jsonTypeResolution/{arbitraryTypeResolution.spec.ts → TypeResolver.spec.ts} +23 -70
  41. package/src/jsonTypeResolution/{arbitraryTypeResolution.ts → TypeResolver.ts} +27 -23
  42. package/src/jsonTypeResolution/TypeResolverBuilder.ts +43 -0
  43. package/src/manifest/v1/DxContentMetaSchema.json +1 -1
  44. package/src/manifest/v1/MatrixAssetSchema.json +28 -8
  45. package/src/manifest/v1/v1.ts +22 -9
  46. package/src/primitiveTypes/FormattedText.ts +24 -0
  47. package/src/primitiveTypes/SquizImage.ts +128 -0
  48. package/src/primitiveTypes/index.ts +2 -0
  49. package/src/resolvableTypes/MatrixAsset.ts +24 -0
  50. package/src/resolvableTypes/index.ts +1 -0
  51. package/tsconfig.tsbuildinfo +1 -1
  52. package/.npm/_logs/2023-03-14T06_15_33_115Z-debug-0.log +0 -39
  53. package/lib/jsonTypeResolution/arbitraryTypeResolution.js.map +0 -1
  54. package/lib/jsonTypeResolution/arbitraryTypeResolution.spec.js.map +0 -1
  55. package/lib/jsonTypeResolution/index.d.ts +0 -76
  56. package/lib/jsonTypeResolution/index.js +0 -35
  57. package/lib/jsonTypeResolution/index.js.map +0 -1
  58. package/lib/jsonTypeResolution/primitiveTypes.d.ts +0 -10
  59. package/lib/jsonTypeResolution/primitiveTypes.js +0 -27
  60. package/lib/jsonTypeResolution/primitiveTypes.js.map +0 -1
  61. package/lib/jsonTypeResolution/resolvableTypes.d.ts +0 -12
  62. package/lib/jsonTypeResolution/resolvableTypes.js +0 -30
  63. package/lib/jsonTypeResolution/resolvableTypes.js.map +0 -1
  64. package/src/jsonTypeResolution/index.ts +0 -16
  65. package/src/jsonTypeResolution/primitiveTypes.ts +0 -32
  66. package/src/jsonTypeResolution/resolvableTypes.ts +0 -37
  67. /package/lib/jsonTypeResolution/{arbitraryTypeResolution.spec.d.ts → TypeResolver.spec.d.ts} +0 -0
@@ -6,7 +6,14 @@ import validManifestJson from './manifest/v1/__test__/schemas/validComponentJson
6
6
  import { FormattedText } from './formatted-text/v1/formattedText';
7
7
  import inputStringWithFormat from './manifest/v1/__test__/schemas/inputStringWithFormat.json';
8
8
  import { JSONSchema } from 'json-schema-library';
9
- import { PrimitiveType, ResolvableType, TypeResolver } from './jsonTypeResolution/arbitraryTypeResolution';
9
+ import {
10
+ AnyPrimitiveType,
11
+ AnyResolvableType,
12
+ PrimitiveType,
13
+ ResolvableType,
14
+ TypeResolver,
15
+ } from './jsonTypeResolution/TypeResolver';
16
+ import { FormattedTextType } from './primitiveTypes';
10
17
 
11
18
  // eslint-disable-next-line @typescript-eslint/ban-types
12
19
  function expectToThrowErrorMatchingTypeAndMessage(received: Function, errorType: Function, message: string) {
@@ -67,6 +74,175 @@ describe('JsonValidationService', () => {
67
74
  });
68
75
  });
69
76
 
77
+ describe('validateRenderInput', () => {
78
+ describe('matrix-asset-uri input', () => {
79
+ const functionInputSchema = {
80
+ type: 'object',
81
+
82
+ properties: {
83
+ 'matrix-asset': { type: 'string', format: 'matrix-asset-uri', matrixAssetTypes: ['image'] },
84
+ },
85
+
86
+ required: ['matrix-asset'],
87
+ };
88
+ it('should return true for valid a string with matrix-asset-uri format', () => {
89
+ const validMatrixAssetUri = 'matrix-asset://canary.uat.matrix.squiz.cloud/abc123';
90
+ expect(
91
+ jsonValidationService.validateRenderInput(functionInputSchema, {
92
+ 'matrix-asset': validMatrixAssetUri,
93
+ }),
94
+ ).toEqual(true);
95
+ });
96
+ it('should throw error for invalid matrix-asset-uri format', () => {
97
+ const invalidMatrixAssetUri = 'not-valid://canary.uat.matrix.squiz.cloud//abc123';
98
+ expectToThrowErrorMatchingTypeAndMessage(
99
+ () => {
100
+ jsonValidationService.validateRenderInput(functionInputSchema, {
101
+ 'matrix-asset': invalidMatrixAssetUri,
102
+ });
103
+ },
104
+ SchemaValidationError,
105
+ `failed validation: value "not-valid://canary.uat.matrix.squiz.cloud//abc123" isn't a valid matrix asset uri`,
106
+ );
107
+ });
108
+ it('should throw error for invalid matrix-asset-uri type number', () => {
109
+ const invalidMatrixAssetUri = 1234;
110
+ expectToThrowErrorMatchingTypeAndMessage(
111
+ () => {
112
+ jsonValidationService.validateRenderInput(functionInputSchema, {
113
+ 'matrix-asset': invalidMatrixAssetUri,
114
+ });
115
+ },
116
+ SchemaValidationError,
117
+ 'failed validation: Expected `1234` (number) in `#/matrix-asset` to be of type `string`',
118
+ );
119
+ });
120
+ it('should throw error for invalid matrix-asset-uri which does not contain correct number of parts', () => {
121
+ const invalidMatrixAssetUri = 'matrix://';
122
+ expectToThrowErrorMatchingTypeAndMessage(
123
+ () => {
124
+ jsonValidationService.validateRenderInput(functionInputSchema, {
125
+ 'matrix-asset': invalidMatrixAssetUri,
126
+ });
127
+ },
128
+ SchemaValidationError,
129
+ `failed validation: value "matrix://" isn't a valid matrix asset uri`,
130
+ );
131
+ });
132
+ });
133
+
134
+ it('should validate a property with type FormattedText as string', () => {
135
+ const schema = {
136
+ type: 'object',
137
+ properties: {
138
+ 'my-input': { type: 'FormattedText' },
139
+ },
140
+ required: ['my-input'],
141
+ };
142
+ const value = {
143
+ 'my-input': 'hello',
144
+ };
145
+
146
+ expect(jsonValidationService.validateRenderInput(schema, value)).toEqual(true);
147
+ });
148
+
149
+ it('should error when a property with type FormattedText is provided a valid FormattedText value', () => {
150
+ const schema = {
151
+ type: 'object',
152
+ properties: {
153
+ 'my-input': { type: 'FormattedText' },
154
+ },
155
+ required: ['my-input'],
156
+ };
157
+ const value = {
158
+ 'my-input': [{ type: 'text', value: 'hello' }],
159
+ };
160
+
161
+ expectToThrowErrorMatchingTypeAndMessage(
162
+ () => {
163
+ jsonValidationService.validateRenderInput(schema, value);
164
+ },
165
+ SchemaValidationError,
166
+ 'failed validation: Expected `[object Object]` (array) in `#/my-input` to be of type `string`',
167
+ );
168
+ });
169
+
170
+ it('should validate a property with type FormattedText within an if/then/else as string', () => {
171
+ const schema = {
172
+ type: 'object',
173
+ properties: {
174
+ 'my-input': {
175
+ type: 'object',
176
+ properties: {
177
+ prop: { type: 'string' },
178
+ },
179
+ required: ['prop'],
180
+ if: { properties: { prop: { const: 'a' } } },
181
+ then: {
182
+ properties: {
183
+ text: { type: 'FormattedText' },
184
+ },
185
+ required: ['text'],
186
+ },
187
+ else: {
188
+ properties: {
189
+ text: { type: 'array', items: { type: 'FormattedText' } },
190
+ },
191
+ required: ['text'],
192
+ },
193
+ },
194
+ },
195
+ required: ['my-input'],
196
+ };
197
+ const value = {
198
+ 'my-input': {
199
+ prop: 'a',
200
+ text: 'hello',
201
+ },
202
+ };
203
+
204
+ expect(jsonValidationService.validateRenderInput(schema, value)).toEqual(true);
205
+
206
+ const otherValue = {
207
+ 'my-input': {
208
+ prop: 'b',
209
+ text: ['my', 'formatted', 'text'],
210
+ },
211
+ };
212
+ expect(jsonValidationService.validateRenderInput(schema, otherValue)).toEqual(true);
213
+ });
214
+ });
215
+ });
216
+
217
+ const defaultSchema: JSONSchema = {
218
+ type: 'object',
219
+ properties: {
220
+ myProperty: {
221
+ type: 'string',
222
+ },
223
+ },
224
+ required: ['myProperty'],
225
+ };
226
+ function primitiveTypeFixture<T extends string>(title: T, schema: JSONSchema = defaultSchema) {
227
+ return PrimitiveType({
228
+ ...schema,
229
+ title,
230
+ });
231
+ }
232
+
233
+ function resolvableTypeFixture<T extends string>(title: T, schema: JSONSchema = defaultSchema) {
234
+ return ResolvableType({
235
+ ...schema,
236
+ title,
237
+ });
238
+ }
239
+
240
+ describe('JsonSchemaService', () => {
241
+ let jsonSchemaService: JSONSchemaService<AnyPrimitiveType, AnyResolvableType>;
242
+ beforeAll(() => {
243
+ const typeResolver = new TypeResolver([FormattedTextType]);
244
+ jsonSchemaService = new JSONSchemaService(typeResolver, ComponentInputMetaSchema);
245
+ });
70
246
  describe('validateContentSchema', () => {
71
247
  it('should return true for a valid content schema', () => {
72
248
  const contentSchema = {
@@ -78,7 +254,7 @@ describe('JsonValidationService', () => {
78
254
 
79
255
  required: ['my-input'],
80
256
  };
81
- const result = jsonValidationService.validateContentSchema(contentSchema);
257
+ const result = jsonSchemaService.validateInput(contentSchema);
82
258
  expect(result).toBe(true);
83
259
  });
84
260
 
@@ -100,7 +276,7 @@ describe('JsonValidationService', () => {
100
276
  };
101
277
  expectToThrowErrorMatchingTypeAndMessage(
102
278
  () => {
103
- jsonValidationService.validateContentSchema(contentSchema);
279
+ jsonSchemaService.validateInput(contentSchema);
104
280
  },
105
281
  SchemaValidationError,
106
282
  'failed validation: The required property `required` is missing at `#/properties/my-input`',
@@ -121,7 +297,7 @@ describe('JsonValidationService', () => {
121
297
  };
122
298
  expectToThrowErrorMatchingTypeAndMessage(
123
299
  () => {
124
- jsonValidationService.validateContentSchema(contentSchema);
300
+ jsonSchemaService.validateInput(contentSchema);
125
301
  },
126
302
  SchemaValidationError,
127
303
  `failed validation: Expected value at \`#/type\` to be \`object\`, but value given is \`array\``,
@@ -138,7 +314,7 @@ describe('JsonValidationService', () => {
138
314
  };
139
315
  expectToThrowErrorMatchingTypeAndMessage(
140
316
  () => {
141
- jsonValidationService.validateContentSchema(contentSchema);
317
+ jsonSchemaService.validateInput(contentSchema);
142
318
  },
143
319
  SchemaValidationError,
144
320
  'failed validation: The required property `required` is missing at `#`',
@@ -146,626 +322,467 @@ describe('JsonValidationService', () => {
146
322
  });
147
323
  });
148
324
 
149
- describe('validateComponentInput', () => {
150
- describe('matrix-asset-uri input', () => {
325
+ describe('FormattedText input', () => {
326
+ it('should handle type as an array', () => {
151
327
  const functionInputSchema = {
152
328
  type: 'object',
153
329
 
154
330
  properties: {
155
- 'matrix-asset': { type: 'string', format: 'matrix-asset-uri', matrixAssetTypes: ['image'] },
331
+ 'my-input': { type: ['number', 'string'] },
156
332
  },
157
333
 
158
- required: ['matrix-asset'],
334
+ required: ['my-input'],
159
335
  };
160
- it('should return true for valid a string with matrix-asset-uri format', () => {
161
- const validMatrixAssetUri = 'matrix-asset://canary.uat.matrix.squiz.cloud/abc123';
162
- expect(
163
- jsonValidationService.validateComponentInput(functionInputSchema, {
164
- 'matrix-asset': validMatrixAssetUri,
165
- }),
166
- ).toEqual(true);
167
- });
168
- it('should throw error for invalid matrix-asset-uri format', () => {
169
- const invalidMatrixAssetUri = 'not-valid://canary.uat.matrix.squiz.cloud//abc123';
170
- expectToThrowErrorMatchingTypeAndMessage(
171
- () => {
172
- jsonValidationService.validateComponentInput(functionInputSchema, {
173
- 'matrix-asset': invalidMatrixAssetUri,
174
- });
175
- },
176
- SchemaValidationError,
177
- `failed validation: value "not-valid://canary.uat.matrix.squiz.cloud//abc123" isn't a valid matrix asset uri`,
178
- );
179
- });
180
- it('should throw error for invalid matrix-asset-uri type number', () => {
181
- const invalidMatrixAssetUri = 1234;
182
- expectToThrowErrorMatchingTypeAndMessage(
183
- () => {
184
- jsonValidationService.validateComponentInput(functionInputSchema, {
185
- 'matrix-asset': invalidMatrixAssetUri,
186
- });
187
- },
188
- SchemaValidationError,
189
- 'failed validation: Expected `1234` (number) in `#/matrix-asset` to be of type `string`',
190
- );
191
- });
192
- it('should throw error for invalid matrix-asset-uri which does not contain correct number of parts', () => {
193
- const invalidMatrixAssetUri = 'matrix://';
194
- expectToThrowErrorMatchingTypeAndMessage(
195
- () => {
196
- jsonValidationService.validateComponentInput(functionInputSchema, {
197
- 'matrix-asset': invalidMatrixAssetUri,
198
- });
199
- },
200
- SchemaValidationError,
201
- `failed validation: value "matrix://" isn't a valid matrix asset uri`,
202
- );
203
- });
204
- });
205
-
206
- describe('FormattedText input', () => {
207
- it('should handle type as an array', () => {
208
- const functionInputSchema = {
209
- type: 'object',
210
-
211
- properties: {
212
- 'my-input': { type: ['number', 'string'] },
213
- },
214
336
 
215
- required: ['my-input'],
216
- };
217
-
218
- expect(
219
- jsonValidationService.validateComponentInput(functionInputSchema, {
220
- 'my-input': 'formattedText',
221
- }),
222
- ).toEqual(true);
223
-
224
- expect(
225
- jsonValidationService.validateComponentInput(functionInputSchema, {
226
- 'my-input': 123,
227
- }),
228
- ).toEqual(true);
229
- });
230
-
231
- it('should handle type is an array of both string and FormattedText', () => {
232
- const formattedText: FormattedText = [
337
+ expect(
338
+ jsonSchemaService.validateInput(
233
339
  {
234
- tag: 'p',
235
- type: 'tag',
236
- children: [
237
- { type: 'text', value: 'This is some ' },
238
- { type: 'text', value: 'Link to asset 12345' },
239
- { type: 'text', value: ' with an image ' },
240
- { type: 'text', value: '.' },
241
- ],
242
- },
243
- ];
244
- const functionInputSchema = {
245
- type: 'object',
246
-
247
- properties: {
248
- 'my-input': { type: ['FormattedText', 'string'] },
249
- },
250
-
251
- required: ['my-input'],
252
- };
253
-
254
- expect(
255
- jsonValidationService.validateComponentInput(functionInputSchema, {
256
- 'my-input': formattedText,
257
- }),
258
- ).toEqual(true);
259
-
260
- expect(
261
- jsonValidationService.validateComponentInput(functionInputSchema, {
262
- 'my-input': 'hello',
263
- }),
264
- ).toEqual(true);
265
- });
266
-
267
- it('should return true if input is formatted text', () => {
268
- const functionInputSchema = {
269
- type: 'object',
270
-
271
- properties: {
272
- 'my-input': { type: 'FormattedText' },
340
+ 'my-input': 'formattedText',
273
341
  },
342
+ functionInputSchema,
343
+ ),
344
+ ).toEqual(true);
274
345
 
275
- required: ['my-input'],
276
- };
277
-
278
- const formattedText: FormattedText = [
346
+ expect(
347
+ jsonSchemaService.validateInput(
279
348
  {
280
- tag: 'p',
281
- type: 'tag',
282
- children: [
283
- { type: 'text', value: 'This is some ' },
284
- { type: 'text', value: 'Link to asset 12345' },
285
- { type: 'text', value: ' with an image ' },
286
- { type: 'text', value: '.' },
287
- ],
288
- },
289
- ];
290
- const inputValue = {
291
- 'my-input': formattedText,
292
- };
293
-
294
- expect(jsonValidationService.validateComponentInput(functionInputSchema, inputValue)).toEqual(true);
295
- });
296
-
297
- it('should throw an error if the FormattedText input is not formatted text', () => {
298
- const functionInputSchema = {
299
- type: 'object',
300
-
301
- properties: {
302
- 'my-input': { type: 'FormattedText' },
303
- },
304
-
305
- required: ['my-input'],
306
- };
307
- const inputValue = {
308
- 'my-input': 123,
309
- };
310
- expectToThrowErrorMatchingTypeAndMessage(
311
- () => {
312
- jsonValidationService.validateComponentInput(functionInputSchema, inputValue);
313
- },
314
- SchemaValidationError,
315
- `failed validation: Expected \`123\` (number) in \`#/my-input\` to be of type \`array\``,
316
- );
317
- });
318
-
319
- it('should throw an error if the FormattedText input is invalid formatted text', () => {
320
- const functionInputSchema = {
321
- type: 'object',
322
-
323
- properties: {
324
- 'my-input': { type: 'FormattedText' },
325
- },
326
-
327
- required: ['my-input'],
328
- };
329
- const inputValue = {
330
- 'my-input': {
331
- something: 'aa',
332
- },
333
- };
334
- expectToThrowErrorMatchingTypeAndMessage(
335
- () => {
336
- jsonValidationService.validateComponentInput(functionInputSchema, inputValue);
349
+ 'my-input': 123,
337
350
  },
338
- SchemaValidationError,
339
- `failed validation: Expected \`[object Object]\` (object) in \`#/my-input\` to be of type \`array\``,
340
- );
341
- });
342
-
343
- it('should throw an error if the FormattedText input is invalid formatted text (deeply nested)', () => {
344
- const functionInputSchema = {
345
- type: 'object',
351
+ functionInputSchema,
352
+ ),
353
+ ).toEqual(true);
354
+ });
346
355
 
347
- properties: {
348
- 'my-input': { type: 'FormattedText' },
349
- },
356
+ it.failing('should handle type is an array of both string and FormattedText', () => {
357
+ const formattedText: FormattedText = [
358
+ {
359
+ tag: 'p',
360
+ type: 'tag',
361
+ children: [
362
+ { type: 'text', value: 'This is some ' },
363
+ { type: 'text', value: 'Link to asset 12345' },
364
+ { type: 'text', value: ' with an image ' },
365
+ { type: 'text', value: '.' },
366
+ ],
367
+ },
368
+ ];
369
+ const functionInputSchema = {
370
+ type: 'object',
350
371
 
351
- required: ['my-input'],
352
- };
353
- const formattedText: FormattedText = [
354
- {
355
- tag: 'p',
356
- type: 'tag',
357
- children: [
358
- { type: 'text', value: 'This is some ' },
359
- { type: 'text', value: 'Link to asset 12345' },
360
- { type: 'text', value: ' with an image ' },
361
- { type: 'text', value: 123 as any }, // see here
362
- { type: 'text', value: '.' },
363
- ],
364
- },
365
- ];
372
+ properties: {
373
+ 'my-input': { type: ['FormattedText', 'string'] },
374
+ },
366
375
 
367
- const inputValue = {
368
- 'my-input': formattedText,
369
- };
370
- expectToThrowErrorMatchingTypeAndMessage(
371
- () => {
372
- jsonValidationService.validateComponentInput(functionInputSchema, inputValue);
373
- },
374
- SchemaValidationError,
375
- 'failed validation: Object at `#/my-input/0` does not match any schema',
376
- );
377
- });
376
+ required: ['my-input'],
377
+ };
378
378
 
379
- it('should validate an array of formatted texts', () => {
380
- const formattedText: FormattedText = [
379
+ expect(
380
+ jsonSchemaService.validateInput(
381
381
  {
382
- tag: 'p',
383
- type: 'tag',
384
- children: [{ type: 'text', value: 'hello' }],
385
- },
386
- ];
387
-
388
- const schema = {
389
- type: 'object',
390
- properties: {
391
- arr: {
392
- type: 'array',
393
- items: { type: 'FormattedText' },
394
- },
382
+ 'my-input': formattedText,
395
383
  },
396
- };
397
- const value = {
398
- arr: [formattedText],
399
- };
400
-
401
- expect(jsonValidationService.validateComponentInput(schema, value)).toEqual(true);
402
- });
384
+ functionInputSchema,
385
+ ),
386
+ ).toEqual(true);
403
387
 
404
- it('should throw an error if the FormattedText input is invalid formatted text (deeply, deeply nested)', () => {
405
- const formattedText: FormattedText = [
388
+ expect(
389
+ jsonSchemaService.validateInput(
406
390
  {
407
- tag: 'p',
408
- type: 'tag',
409
- children: [{ type: 'text', value: 'hello' }],
410
- },
411
- ];
412
-
413
- const inputValue: any = {
414
- 'my-input': formattedText,
415
- deep: {
416
- arr: [
417
- {
418
- prop: formattedText,
419
- formattedTextArray: [formattedText, formattedText, { bad: 'data' }],
420
- },
421
- ],
422
- },
423
- };
424
-
425
- const functionInputSchema = {
426
- type: 'object',
427
-
428
- properties: {
429
- 'my-input': { type: 'FormattedText' },
430
- deep: {
431
- type: 'object',
432
- properties: {
433
- arr: {
434
- type: 'array',
435
- items: {
436
- type: 'object',
437
- required: ['prop', 'formattedTextArray'],
438
- properties: {
439
- prop: 'FormattedText',
440
- formattedTextArray: {
441
- type: 'array',
442
- items: {
443
- type: 'FormattedText',
444
- },
445
- },
446
- },
447
- },
448
- },
449
- },
450
- required: ['arr'],
451
- },
452
- },
453
-
454
- required: ['my-input', 'deep'],
455
- };
456
-
457
- expectToThrowErrorMatchingTypeAndMessage(
458
- () => {
459
- jsonValidationService.validateComponentInput(functionInputSchema, inputValue);
391
+ 'my-input': 'hello',
460
392
  },
461
- SchemaValidationError,
462
- 'failed validation: Expected `[object Object]` (object) in `#/deep/arr/0/formattedTextArray/2` to be of type `array`',
463
- );
464
- });
393
+ functionInputSchema,
394
+ ),
395
+ ).toEqual(true);
396
+ });
465
397
 
466
- it('should validate a FormattedText value when the schema is a $ref', async () => {
467
- const formattedText: FormattedText = [
468
- {
469
- tag: 'p',
470
- type: 'tag',
471
- children: [{ type: 'text', value: 'hello' }],
472
- },
473
- ];
398
+ it('should return true if input is formatted text', () => {
399
+ const functionInputSchema = {
400
+ type: 'object',
474
401
 
475
- const schema = {
476
- type: 'object',
477
- properties: {
478
- 'my-input': { $ref: '#/definitions/FormattedText' },
479
- },
480
- definitions: {
481
- FormattedText: { type: 'FormattedText' },
482
- },
483
- required: ['my-input'],
484
- };
485
- const value = {
486
- 'my-input': formattedText,
487
- };
402
+ properties: {
403
+ 'my-input': { type: 'FormattedText' },
404
+ },
488
405
 
489
- expect(jsonValidationService.validateComponentInput(schema, value)).toEqual(true);
490
- });
406
+ required: ['my-input'],
407
+ };
491
408
 
492
- it('should error when a FormattedText value is invalid when the schema is a $ref', async () => {
493
- const schema = {
494
- type: 'object',
495
- properties: {
496
- 'my-input': { $ref: '#/definitions/FormattedText' },
497
- },
498
- definitions: {
499
- FormattedText: { type: 'FormattedText' },
500
- },
501
- required: ['my-input'],
502
- };
503
- const value = {
504
- 'my-input': { bad: 'data' },
505
- };
409
+ const formattedText: FormattedText = [
410
+ {
411
+ tag: 'p',
412
+ type: 'tag',
413
+ children: [
414
+ { type: 'text', value: 'This is some ' },
415
+ { type: 'text', value: 'Link to asset 12345' },
416
+ { type: 'text', value: ' with an image ' },
417
+ { type: 'text', value: '.' },
418
+ ],
419
+ },
420
+ ];
421
+ const inputValue = {
422
+ 'my-input': formattedText,
423
+ };
506
424
 
507
- expectToThrowErrorMatchingTypeAndMessage(
508
- () => {
509
- jsonValidationService.validateComponentInput(schema, value);
510
- },
511
- SchemaValidationError,
512
- 'failed validation: Expected `[object Object]` (object) in `#/my-input` to be of type `array`',
513
- );
514
- });
425
+ expect(() => jsonSchemaService.validateInput(inputValue, functionInputSchema)).not.toThrow();
426
+ });
515
427
 
516
- it('should validate a FormattedText value when the schema is a $ref to a $ref', async () => {
517
- const formattedText: FormattedText = [
518
- {
519
- tag: 'p',
520
- type: 'tag',
521
- children: [{ type: 'text', value: 'hello' }],
522
- },
523
- ];
428
+ it('should throw an error if the FormattedText input is not formatted text', () => {
429
+ const functionInputSchema = {
430
+ type: 'object',
524
431
 
525
- const schema = {
526
- type: 'object',
527
- properties: {
528
- 'my-input': { $ref: '#/definitions/FormattedText' },
529
- },
530
- definitions: {
531
- FormattedText: { $ref: '#/definitions/FormattedText2' },
532
- FormattedText2: { type: 'FormattedText' },
533
- },
534
- required: ['my-input'],
535
- };
536
- const value = {
537
- 'my-input': formattedText,
538
- };
432
+ properties: {
433
+ 'my-input': { type: 'FormattedText' },
434
+ },
539
435
 
540
- expect(jsonValidationService.validateComponentInput(schema, value)).toEqual(true);
541
- });
436
+ required: ['my-input'],
437
+ };
438
+ const inputValue = {
439
+ 'my-input': 123,
440
+ };
441
+ expectToThrowErrorMatchingTypeAndMessage(
442
+ () => {
443
+ jsonSchemaService.validateInput(inputValue, functionInputSchema);
444
+ },
445
+ SchemaValidationError,
446
+ 'failed validation: Value `123` in `#/my-input` does not match any given oneof schema',
447
+ );
448
+ });
542
449
 
543
- it('should validate a FormattedText value when the schema is in an if/then/else', async () => {
544
- const formattedText: FormattedText = [
545
- {
546
- tag: 'p',
547
- type: 'tag',
548
- children: [{ type: 'text', value: 'hello' }],
549
- },
550
- ];
450
+ it('should throw an error if the FormattedText input is invalid formatted text', () => {
451
+ const functionInputSchema = {
452
+ type: 'object',
551
453
 
552
- const schema = {
553
- type: 'object',
554
- properties: {
555
- 'my-input': {
556
- if: { type: 'string' },
557
- then: { type: 'string' },
558
- else: { type: 'FormattedText' },
559
- },
560
- },
561
- required: ['my-input'],
562
- };
563
- const value = {
564
- 'my-input': formattedText,
565
- };
454
+ properties: {
455
+ 'my-input': { type: 'FormattedText' },
456
+ },
566
457
 
567
- expect(jsonValidationService.validateComponentInput(schema, value)).toEqual(true);
568
- });
458
+ required: ['my-input'],
459
+ };
460
+ const inputValue = {
461
+ 'my-input': {
462
+ something: 'aa',
463
+ },
464
+ };
465
+ expectToThrowErrorMatchingTypeAndMessage(
466
+ () => {
467
+ jsonSchemaService.validateInput(inputValue, functionInputSchema);
468
+ },
469
+ SchemaValidationError,
470
+ 'failed validation: Value `{"something":"aa"}` in `#/my-input` does not match any given oneof schema',
471
+ );
569
472
  });
570
473
 
571
- describe('standard inputs', () => {
474
+ it('should throw an error if the FormattedText input is invalid formatted text (deeply nested)', () => {
572
475
  const functionInputSchema = {
573
476
  type: 'object',
574
477
 
575
478
  properties: {
576
- 'my-input': { type: 'number' },
479
+ 'my-input': { type: 'FormattedText' },
577
480
  },
578
481
 
579
482
  required: ['my-input'],
580
483
  };
484
+ const formattedText: FormattedText = [
485
+ {
486
+ tag: 'p',
487
+ type: 'tag',
488
+ children: [
489
+ { type: 'text', value: 'This is some ' },
490
+ { type: 'text', value: 'Link to asset 12345' },
491
+ { type: 'text', value: ' with an image ' },
492
+ { type: 'text', value: 123 as any }, // see here
493
+ { type: 'text', value: '.' },
494
+ ],
495
+ },
496
+ ];
581
497
 
582
- it('should return true for valid input values', () => {
583
- const inputValue = {
584
- 'my-input': 123,
585
- };
586
- const result = jsonValidationService.validateComponentInput(functionInputSchema, inputValue);
587
- expect(result).toBe(true);
588
- });
498
+ const inputValue = {
499
+ 'my-input': formattedText,
500
+ };
501
+ expectToThrowErrorMatchingTypeAndMessage(
502
+ () => {
503
+ jsonSchemaService.validateInput(inputValue, functionInputSchema);
504
+ },
505
+ SchemaValidationError,
506
+ 'failed validation: Value `[{"tag":"p","type":"tag","children":[{"type":"text","value":"This is some "},{"type":"text","value":"Link to asset 12345"},{"type":"text","value":" with an image "},{"type":"text","value":123},{"type":"text","value":"."}]}]` in `#/my-input` does not match any given oneof schema',
507
+ );
508
+ });
589
509
 
590
- it('should throw a SchemaValidationError for invalid input type', () => {
591
- const inputValue = {
592
- 'my-input': '123',
593
- };
594
- expectToThrowErrorMatchingTypeAndMessage(
595
- () => {
596
- jsonValidationService.validateComponentInput(functionInputSchema, inputValue);
597
- },
598
- SchemaValidationError,
599
- `failed validation: Expected \`123\` (string) in \`#/my-input\` to be of type \`number\``,
600
- );
601
- });
510
+ it('should validate an array of formatted texts', () => {
511
+ const formattedText: FormattedText = [
512
+ {
513
+ tag: 'p',
514
+ type: 'tag',
515
+ children: [{ type: 'text', value: 'hello' }],
516
+ },
517
+ ];
602
518
 
603
- it('should throw a SchemaValidationError for invalid input missing properties', () => {
604
- const inputValue = {};
605
- expectToThrowErrorMatchingTypeAndMessage(
606
- () => {
607
- jsonValidationService.validateComponentInput(functionInputSchema, inputValue);
519
+ const schema = {
520
+ type: 'object',
521
+ properties: {
522
+ arr: {
523
+ type: 'array',
524
+ items: { type: 'FormattedText' },
608
525
  },
609
- SchemaValidationError,
610
- `failed validation: The required property \`my-input\` is missing at \`#\``,
611
- );
612
- });
526
+ },
527
+ };
528
+ const value = {
529
+ arr: [formattedText],
530
+ };
613
531
 
614
- it('should throw a SchemaValidationError with a truncated enum value list if there are more than 5 enum options', () => {
615
- expectToThrowErrorMatchingTypeAndMessage(
616
- () => {
617
- jsonValidationService.validateComponentInput(
618
- { type: 'object', properties: { enum: { type: 'string', enum: ['a', 'b', 'c', 'd', 'e', 'f', 'g'] } } },
619
- { enum: 'z' },
620
- );
532
+ expect(jsonSchemaService.validateInput(value, schema)).toEqual(true);
533
+ });
534
+
535
+ it('should throw an error if the FormattedText input is invalid formatted text (deeply, deeply nested)', () => {
536
+ const formattedText: FormattedText = [
537
+ {
538
+ tag: 'p',
539
+ type: 'tag',
540
+ children: [{ type: 'text', value: 'hello' }],
541
+ },
542
+ ];
543
+
544
+ const inputValue: any = {
545
+ 'my-input': formattedText,
546
+ deep: {
547
+ arr: [
548
+ {
549
+ prop: formattedText,
550
+ formattedTextArray: [formattedText, formattedText, { bad: 'data' }],
551
+ },
552
+ ],
553
+ },
554
+ };
555
+
556
+ const functionInputSchema = {
557
+ type: 'object',
558
+
559
+ properties: {
560
+ 'my-input': { type: 'FormattedText' },
561
+ deep: {
562
+ type: 'object',
563
+ properties: {
564
+ arr: {
565
+ type: 'array',
566
+ items: {
567
+ type: 'object',
568
+ required: ['prop', 'formattedTextArray'],
569
+ properties: {
570
+ prop: 'FormattedText',
571
+ formattedTextArray: {
572
+ type: 'array',
573
+ items: {
574
+ type: 'FormattedText',
575
+ },
576
+ },
577
+ },
578
+ },
579
+ },
580
+ },
581
+ required: ['arr'],
621
582
  },
622
- SchemaValidationError,
623
- 'failed validation: Expected given value `z` in #/enum` to be one of `[a, b, c, d, e, ... 2 more]`',
624
- );
625
- });
583
+ },
626
584
 
627
- // TODO DEVX-658
628
- it.skip('should throw a SchemaValidationError for invalid input additional properties', () => {
629
- const inputValue = {
630
- 'my-input': 123,
631
- 'my-input-2': 123,
632
- };
633
- expect(() => {
634
- jsonValidationService.validateComponentInput(functionInputSchema, inputValue);
635
- }).toThrowErrorMatchingInlineSnapshot();
636
- });
585
+ required: ['my-input', 'deep'],
586
+ };
587
+
588
+ expectToThrowErrorMatchingTypeAndMessage(
589
+ () => {
590
+ jsonSchemaService.validateInput(inputValue, functionInputSchema);
591
+ },
592
+ SchemaValidationError,
593
+ 'failed validation: Value `{"bad":"data"}` in `#/deep/arr/0/formattedTextArray/2` does not match any given oneof schema',
594
+ );
637
595
  });
638
- });
639
596
 
640
- describe('validateRenderInput', () => {
641
- it('should validate a property with type FormattedText as string', () => {
597
+ it('should validate a FormattedText value when the schema is a $ref', async () => {
598
+ const formattedText: FormattedText = [
599
+ {
600
+ tag: 'p',
601
+ type: 'tag',
602
+ children: [{ type: 'text', value: 'hello' }],
603
+ },
604
+ ];
605
+
642
606
  const schema = {
643
607
  type: 'object',
644
608
  properties: {
645
- 'my-input': { type: 'FormattedText' },
609
+ 'my-input': { $ref: '#/definitions/FormattedText' },
610
+ },
611
+ definitions: {
612
+ FormattedText: { type: 'FormattedText' },
646
613
  },
647
614
  required: ['my-input'],
648
615
  };
649
616
  const value = {
650
- 'my-input': 'hello',
617
+ 'my-input': formattedText,
651
618
  };
652
619
 
653
- expect(jsonValidationService.validateRenderInput(schema, value)).toEqual(true);
620
+ expect(jsonSchemaService.validateInput(value, schema)).toEqual(true);
654
621
  });
655
622
 
656
- it('should error when a property with type FormattedText is provided a valid FormattedText value', () => {
623
+ it('should error when a FormattedText value is invalid when the schema is a $ref', async () => {
657
624
  const schema = {
658
625
  type: 'object',
659
626
  properties: {
660
- 'my-input': { type: 'FormattedText' },
627
+ 'my-input': { $ref: '#/definitions/FormattedText' },
628
+ },
629
+ definitions: {
630
+ FormattedText: { type: 'FormattedText' },
661
631
  },
662
632
  required: ['my-input'],
663
633
  };
664
634
  const value = {
665
- 'my-input': [{ type: 'text', value: 'hello' }],
635
+ 'my-input': { bad: 'data' },
666
636
  };
667
637
 
668
638
  expectToThrowErrorMatchingTypeAndMessage(
669
639
  () => {
670
- jsonValidationService.validateRenderInput(schema, value);
640
+ jsonSchemaService.validateInput(value, schema);
671
641
  },
672
642
  SchemaValidationError,
673
- 'failed validation: Expected `[object Object]` (array) in `#/my-input` to be of type `string`',
643
+ 'failed validation: Value `{"bad":"data"}` in `#/my-input` does not match any given oneof schema',
674
644
  );
675
645
  });
676
646
 
677
- it('should validate a property with type FormattedText within an if/then/else as string', () => {
647
+ it('should validate a FormattedText value when the schema is a $ref to a $ref', async () => {
648
+ const formattedText: FormattedText = [
649
+ {
650
+ tag: 'p',
651
+ type: 'tag',
652
+ children: [{ type: 'text', value: 'hello' }],
653
+ },
654
+ ];
655
+
678
656
  const schema = {
679
657
  type: 'object',
680
658
  properties: {
681
- 'my-input': {
682
- type: 'object',
683
- properties: {
684
- prop: { type: 'string' },
685
- },
686
- required: ['prop'],
687
- if: { properties: { prop: { const: 'a' } } },
688
- then: {
689
- properties: {
690
- text: { type: 'FormattedText' },
691
- },
692
- required: ['text'],
693
- },
694
- else: {
695
- properties: {
696
- text: { type: 'array', items: { type: 'FormattedText' } },
697
- },
698
- required: ['text'],
699
- },
700
- },
659
+ 'my-input': { $ref: '#/definitions/FormattedText' },
660
+ },
661
+ definitions: {
662
+ FormattedText: { $ref: '#/definitions/FormattedText2' },
663
+ FormattedText2: { type: 'FormattedText' },
701
664
  },
702
665
  required: ['my-input'],
703
666
  };
704
667
  const value = {
705
- 'my-input': {
706
- prop: 'a',
707
- text: 'hello',
708
- },
668
+ 'my-input': formattedText,
709
669
  };
710
670
 
711
- expect(jsonValidationService.validateRenderInput(schema, value)).toEqual(true);
671
+ expect(jsonSchemaService.validateInput(value, schema)).toEqual(true);
672
+ });
712
673
 
713
- const otherValue = {
714
- 'my-input': {
715
- prop: 'b',
716
- text: ['my', 'formatted', 'text'],
674
+ it('should validate a FormattedText value when the schema is in an if/then/else', async () => {
675
+ const formattedText: FormattedText = [
676
+ {
677
+ tag: 'p',
678
+ type: 'tag',
679
+ children: [{ type: 'text', value: 'hello' }],
680
+ },
681
+ ];
682
+
683
+ const schema = {
684
+ type: 'object',
685
+ properties: {
686
+ 'my-input': {
687
+ if: { type: 'string' },
688
+ then: { type: 'string' },
689
+ else: { type: 'FormattedText' },
690
+ },
717
691
  },
692
+ required: ['my-input'],
718
693
  };
719
- expect(jsonValidationService.validateRenderInput(schema, otherValue)).toEqual(true);
694
+ const value = {
695
+ 'my-input': formattedText,
696
+ };
697
+
698
+ expect(jsonSchemaService.validateInput(value, schema)).toEqual(true);
720
699
  });
721
700
  });
722
- });
723
701
 
724
- const defaultSchema: JSONSchema = {
725
- type: 'object',
726
- properties: {
727
- myProperty: {
728
- type: 'string',
729
- },
730
- },
731
- required: ['myProperty'],
732
- };
733
- function primitiveTypeFixture<T extends string>(title: T, schema: JSONSchema = defaultSchema) {
734
- return PrimitiveType({
735
- ...schema,
736
- title,
737
- });
738
- }
702
+ describe('standard inputs', () => {
703
+ const functionInputSchema = {
704
+ type: 'object',
739
705
 
740
- function resolvableTypeFixture<T extends string>(title: T, schema: JSONSchema = defaultSchema) {
741
- return ResolvableType({
742
- ...schema,
743
- title,
706
+ properties: {
707
+ 'my-input': { type: 'number' },
708
+ },
709
+
710
+ required: ['my-input'],
711
+ };
712
+
713
+ it('should return true for valid input values', () => {
714
+ const inputValue = {
715
+ 'my-input': 123,
716
+ };
717
+ const result = jsonSchemaService.validateInput(inputValue, functionInputSchema);
718
+ expect(result).toBe(true);
719
+ });
720
+
721
+ it('should throw a SchemaValidationError for invalid input type', () => {
722
+ const inputValue = {
723
+ 'my-input': '123',
724
+ };
725
+ expectToThrowErrorMatchingTypeAndMessage(
726
+ () => {
727
+ jsonSchemaService.validateInput(inputValue, functionInputSchema);
728
+ },
729
+ SchemaValidationError,
730
+ `failed validation: Expected \`123\` (string) in \`#/my-input\` to be of type \`number\``,
731
+ );
732
+ });
733
+
734
+ it('should throw a SchemaValidationError for invalid input missing properties', () => {
735
+ const inputValue = {};
736
+ expectToThrowErrorMatchingTypeAndMessage(
737
+ () => {
738
+ jsonSchemaService.validateInput(inputValue, functionInputSchema);
739
+ },
740
+ SchemaValidationError,
741
+ `failed validation: The required property \`my-input\` is missing at \`#\``,
742
+ );
743
+ });
744
+
745
+ it('should throw a SchemaValidationError with a truncated enum value list if there are more than 5 enum options', () => {
746
+ expectToThrowErrorMatchingTypeAndMessage(
747
+ () => {
748
+ jsonSchemaService.validateInput(
749
+ { enum: 'z' },
750
+ { type: 'object', properties: { enum: { type: 'string', enum: ['a', 'b', 'c', 'd', 'e', 'f', 'g'] } } },
751
+ );
752
+ },
753
+ SchemaValidationError,
754
+ 'failed validation: Expected given value `z` in #/enum` to be one of `[a, b, c, d, e, ... 2 more]`',
755
+ );
756
+ });
757
+
758
+ // TODO DEVX-658
759
+ it.skip('should throw a SchemaValidationError for invalid input additional properties', () => {
760
+ const inputValue = {
761
+ 'my-input': 123,
762
+ 'my-input-2': 123,
763
+ };
764
+ expect(() => {
765
+ jsonSchemaService.validateInput(inputValue, functionInputSchema);
766
+ }).toThrowErrorMatchingInlineSnapshot();
767
+ });
744
768
  });
745
- }
746
769
 
747
- describe('JsonSchemaService', () => {
748
770
  describe('validateInput', () => {
749
771
  it.each([String('123'), Number(123), [123]])(
750
772
  'should validate any primitive type with its resolvable type %s',
751
773
  (propertyValue) => {
752
774
  const primitiveSchema = primitiveTypeFixture('MyPrimitive', { type: 'string' });
775
+ const MyResolvableNumber = resolvableTypeFixture('MyResolvableNumber', { type: 'number' });
776
+ const MyResolvableArray = resolvableTypeFixture('MyResolvableArray', { type: 'array' });
753
777
  const jsonSchemaService = new JSONSchemaService(
754
- new TypeResolver(
755
- {
756
- MyPrimitive: primitiveSchema,
757
- },
758
- {
759
- MyResolvableNumber: resolvableTypeFixture('MyResolvableNumber', { type: 'number' }),
760
- MyResolvableArray: resolvableTypeFixture('MyResolvableArray', { type: 'array' }),
761
- },
762
- {
763
- MyPrimitive: {
764
- MyResolvableNumber: (value: number) => value.toString(),
765
- MyResolvableArray: (value: any[]) => value.join(''),
766
- },
778
+ new TypeResolver([primitiveSchema], [MyResolvableNumber, MyResolvableArray], {
779
+ MyPrimitive: {
780
+ // @ts-expect-error - fixture is unknown but we know the actual shape
781
+ MyResolvableNumber: (value: number) => value.toString(),
782
+ // @ts-expect-error - fixture is unknown but we know the actual shape
783
+ MyResolvableArray: (value: any[]) => value.join(''),
767
784
  },
768
- ),
785
+ }),
769
786
  ComponentInputMetaSchema,
770
787
  );
771
788
 
@@ -780,22 +797,17 @@ describe('JsonSchemaService', () => {
780
797
 
781
798
  it('should error when a primitive type is provided a value that cannot be resolved by its resolvable types', () => {
782
799
  const primitiveSchema = primitiveTypeFixture('MyPrimitive', { type: 'string' });
800
+ const MyResolvableNumber = resolvableTypeFixture('MyResolvableNumber', { type: 'number' });
801
+ const MyResolvableArray = resolvableTypeFixture('MyResolvableArray', { type: 'array' });
783
802
  const jsonSchemaService = new JSONSchemaService(
784
- new TypeResolver(
785
- {
786
- MyPrimitive: primitiveSchema,
787
- },
788
- {
789
- MyResolvableNumber: resolvableTypeFixture('MyResolvableNumber', { type: 'number' }),
790
- MyResolvableArray: resolvableTypeFixture('MyResolvableArray', { type: 'array' }),
791
- },
792
- {
793
- MyPrimitive: {
794
- MyResolvableNumber: (value: number) => value.toString(),
795
- MyResolvableArray: (value: any[]) => value.join(''),
796
- },
797
- },
798
- ),
803
+ new TypeResolver([primitiveSchema], [MyResolvableNumber, MyResolvableArray], {
804
+ MyPrimitive: {
805
+ // @ts-expect-error - fixture is unknown but we know the actual shape
806
+ MyResolvableNumber: (value: number) => value.toString(),
807
+ // @ts-expect-error - fixture is unknown but we know the actual shape
808
+ MyResolvableArray: (value: any[]) => value.join(''),
809
+ },
810
+ }),
799
811
  ComponentInputMetaSchema,
800
812
  );
801
813
 
@@ -811,22 +823,17 @@ describe('JsonSchemaService', () => {
811
823
  'should validate a primitive type when defined as a ref with resolvable value %s',
812
824
  (propertyValue) => {
813
825
  const primitiveSchema = primitiveTypeFixture('MyPrimitive', { type: 'string' });
826
+ const MyResolvableNumber = resolvableTypeFixture('MyResolvableNumber', { type: 'number' });
827
+ const MyResolvableArray = resolvableTypeFixture('MyResolvableArray', { type: 'array' });
814
828
  const jsonSchemaService = new JSONSchemaService(
815
- new TypeResolver(
816
- {
817
- MyPrimitive: primitiveSchema,
818
- },
819
- {
820
- MyResolvableNumber: resolvableTypeFixture('MyResolvableNumber', { type: 'number' }),
821
- MyResolvableArray: resolvableTypeFixture('MyResolvableArray', { type: 'array' }),
822
- },
823
- {
824
- MyPrimitive: {
825
- MyResolvableNumber: (value: number) => value.toString(),
826
- MyResolvableArray: (value: any[]) => value.join(''),
827
- },
829
+ new TypeResolver([primitiveSchema], [MyResolvableNumber, MyResolvableArray], {
830
+ MyPrimitive: {
831
+ // @ts-expect-error - fixture is unknown but we know the actual shape
832
+ MyResolvableNumber: (value: number) => value.toString(),
833
+ // @ts-expect-error - fixture is unknown but we know the actual shape
834
+ MyResolvableArray: (value: any[]) => value.join(''),
828
835
  },
829
- ),
836
+ }),
830
837
  ComponentInputMetaSchema,
831
838
  );
832
839
 
@@ -845,21 +852,15 @@ describe('JsonSchemaService', () => {
845
852
 
846
853
  it('should not validate on a primitive type against a resolvable type when a resolver is not defined', () => {
847
854
  const primitiveSchema = primitiveTypeFixture('MyPrimitive', { type: 'string' });
855
+ const MyResolvableNumber = resolvableTypeFixture('MyResolvableNumber', { type: 'number' });
856
+ const MyResolvableArray = resolvableTypeFixture('MyResolvableArray', { type: 'array' });
848
857
  const jsonSchemaService = new JSONSchemaService(
849
- new TypeResolver(
850
- {
851
- MyPrimitive: primitiveSchema,
852
- },
853
- {
854
- MyResolvableNumber: resolvableTypeFixture('MyResolvableNumber', { type: 'number' }),
855
- MyResolvableArray: resolvableTypeFixture('MyResolvableArray', { type: 'array' }),
856
- },
857
- {
858
- MyPrimitive: {
859
- MyResolvableNumber: (value: number) => value.toString(),
860
- },
858
+ new TypeResolver([primitiveSchema], [MyResolvableNumber, MyResolvableArray], {
859
+ MyPrimitive: {
860
+ // @ts-expect-error - fixture is unknown but we know the actual shape
861
+ MyResolvableNumber: (value: number) => value.toString(),
861
862
  },
862
- ),
863
+ }),
863
864
  ComponentInputMetaSchema,
864
865
  );
865
866
 
@@ -875,26 +876,26 @@ describe('JsonSchemaService', () => {
875
876
  const primitiveSchema = primitiveTypeFixture('MyPrimitive', { type: 'string' });
876
877
  const jsonSchemaService = new JSONSchemaService(
877
878
  new TypeResolver(
878
- {
879
- MyPrimitive: primitiveSchema,
880
- },
881
- {
882
- MyResolvableSrcNumber: resolvableTypeFixture('MyResolvableSrcNumber', {
879
+ [primitiveSchema],
880
+ [
881
+ resolvableTypeFixture('MyResolvableSrcNumber', {
883
882
  type: 'object',
884
883
  properties: {
885
884
  src: { type: 'number' },
886
885
  },
887
886
  }),
888
- MyResolvableSrcString: resolvableTypeFixture('MyResolvableSrcString', {
887
+ resolvableTypeFixture('MyResolvableSrcString', {
889
888
  type: 'object',
890
889
  properties: {
891
890
  src: { type: 'string' },
892
891
  },
893
892
  }),
894
- },
893
+ ],
895
894
  {
896
895
  MyPrimitive: {
896
+ // @ts-expect-error - fixture is unknown but we know the actual shape
897
897
  MyResolvableSrcNumber: (value: { src: number }) => value.src.toString(),
898
+ // @ts-expect-error - fixture is unknown but we know the actual shape
898
899
  MyResolvableSrcString: (value: { src: string }) => value.src,
899
900
  },
900
901
  },
@@ -932,16 +933,16 @@ describe('JsonSchemaService', () => {
932
933
  const primitiveSchema = primitiveTypeFixture('MyPrimitive', { type: 'string' });
933
934
  const jsonSchemaService = new JSONSchemaService(
934
935
  new TypeResolver(
935
- {
936
- MyPrimitive: primitiveSchema,
937
- },
938
- {
939
- MyResolvableNumber: resolvableTypeFixture('MyResolvableNumber', { type: 'number' }),
940
- MyResolvableArray: resolvableTypeFixture('MyResolvableArray', { type: 'array' }),
941
- },
936
+ [primitiveSchema],
937
+ [
938
+ resolvableTypeFixture('MyResolvableNumber', { type: 'number' }),
939
+ resolvableTypeFixture('MyResolvableArray', { type: 'array' }),
940
+ ],
942
941
  {
943
942
  MyPrimitive: {
943
+ // @ts-expect-error - fixture is unknown but we know the actual shape
944
944
  MyResolvableNumber: (value: number) => value.toString(),
945
+ // @ts-expect-error - fixture is unknown but we know the actual shape
945
946
  MyResolvableArray: (value: any[]) => value.join(''),
946
947
  },
947
948
  },
@@ -965,22 +966,22 @@ describe('JsonSchemaService', () => {
965
966
  const primitiveSchema = primitiveTypeFixture('MyPrimitive', { type: 'string' });
966
967
  const jsonSchemaService = new JSONSchemaService(
967
968
  new TypeResolver(
968
- {
969
- MyPrimitive: primitiveSchema,
970
- },
971
- {
972
- MyResolvableSrcString: resolvableTypeFixture('MyResolvableSrcString', {
969
+ [primitiveSchema],
970
+ [
971
+ resolvableTypeFixture('MyResolvableSrcString', {
973
972
  type: 'object',
974
973
  properties: { src: { type: 'string' } },
975
974
  }),
976
- MyResolvableSrcNumber: resolvableTypeFixture('MyResolvableSrcNumber', {
975
+ resolvableTypeFixture('MyResolvableSrcNumber', {
977
976
  type: 'object',
978
977
  properties: { src: { type: 'number' } },
979
978
  }),
980
- },
979
+ ],
981
980
  {
982
981
  MyPrimitive: {
982
+ // @ts-expect-error - fixture is unknown but we know the actual shape
983
983
  MyResolvableSrcNumber: (value: { src: number }) => value.src.toString(),
984
+ // @ts-expect-error - fixture is unknown but we know the actual shape
984
985
  MyResolvableSrcString: (value: { src: string }) => value.src,
985
986
  },
986
987
  },