@squiz/dx-json-schema-lib 1.21.1-alpha.9 → 1.22.1-alpha.0
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/.npm/_logs/2023-03-30T09_50_45_736Z-debug-0.log +37 -0
- package/lib/JsonValidationService.d.ts +1 -1
- package/lib/JsonValidationService.js +15 -5
- package/lib/JsonValidationService.js.map +1 -1
- package/lib/JsonValidationService.spec.js +444 -445
- package/lib/JsonValidationService.spec.js.map +1 -1
- package/lib/index.d.ts +6 -1
- package/lib/index.js +6 -1
- package/lib/index.js.map +1 -1
- package/lib/jsonTypeResolution/{arbitraryTypeResolution.d.ts → TypeResolver.d.ts} +7 -12
- package/lib/jsonTypeResolution/{arbitraryTypeResolution.js → TypeResolver.js} +17 -17
- package/lib/jsonTypeResolution/TypeResolver.js.map +1 -0
- package/lib/jsonTypeResolution/{arbitraryTypeResolution.spec.js → TypeResolver.spec.js} +12 -39
- package/lib/jsonTypeResolution/TypeResolver.spec.js.map +1 -0
- package/lib/jsonTypeResolution/TypeResolverBuilder.d.ts +12 -0
- package/lib/jsonTypeResolution/TypeResolverBuilder.js +32 -0
- package/lib/jsonTypeResolution/TypeResolverBuilder.js.map +1 -0
- package/lib/manifest/v1/DxContentMetaSchema.json +1 -1
- package/lib/manifest/v1/MatrixAssetSchema.json +28 -8
- package/lib/manifest/v1/v1.d.ts +10 -7
- package/lib/primitiveTypes/FormattedText.d.ts +8 -0
- package/lib/primitiveTypes/FormattedText.js +21 -0
- package/lib/primitiveTypes/FormattedText.js.map +1 -0
- package/lib/primitiveTypes/SquizImage.d.ts +26 -0
- package/lib/primitiveTypes/SquizImage.js +105 -0
- package/lib/primitiveTypes/SquizImage.js.map +1 -0
- package/lib/primitiveTypes/index.d.ts +2 -0
- package/lib/primitiveTypes/index.js +19 -0
- package/lib/primitiveTypes/index.js.map +1 -0
- package/lib/resolvableTypes/MatrixAsset.d.ts +9 -0
- package/lib/resolvableTypes/MatrixAsset.js +21 -0
- package/lib/resolvableTypes/MatrixAsset.js.map +1 -0
- package/lib/resolvableTypes/index.d.ts +1 -0
- package/lib/resolvableTypes/index.js +18 -0
- package/lib/resolvableTypes/index.js.map +1 -0
- package/package.json +5 -4
- package/src/JsonValidationService.spec.ts +585 -584
- package/src/JsonValidationService.ts +19 -9
- package/src/index.ts +8 -1
- package/src/jsonTypeResolution/{arbitraryTypeResolution.spec.ts → TypeResolver.spec.ts} +23 -70
- package/src/jsonTypeResolution/{arbitraryTypeResolution.ts → TypeResolver.ts} +27 -23
- package/src/jsonTypeResolution/TypeResolverBuilder.ts +43 -0
- package/src/manifest/v1/DxContentMetaSchema.json +1 -1
- package/src/manifest/v1/MatrixAssetSchema.json +28 -8
- package/src/manifest/v1/v1.ts +22 -9
- package/src/primitiveTypes/FormattedText.ts +24 -0
- package/src/primitiveTypes/SquizImage.ts +128 -0
- package/src/primitiveTypes/index.ts +2 -0
- package/src/resolvableTypes/MatrixAsset.ts +24 -0
- package/src/resolvableTypes/index.ts +1 -0
- package/tsconfig.tsbuildinfo +1 -1
- package/.npm/_logs/2023-03-08T03_21_11_525Z-debug-0.log +0 -39
- package/lib/jsonTypeResolution/arbitraryTypeResolution.js.map +0 -1
- package/lib/jsonTypeResolution/arbitraryTypeResolution.spec.js.map +0 -1
- package/lib/jsonTypeResolution/index.d.ts +0 -76
- package/lib/jsonTypeResolution/index.js +0 -35
- package/lib/jsonTypeResolution/index.js.map +0 -1
- package/lib/jsonTypeResolution/primitiveTypes.d.ts +0 -10
- package/lib/jsonTypeResolution/primitiveTypes.js +0 -27
- package/lib/jsonTypeResolution/primitiveTypes.js.map +0 -1
- package/lib/jsonTypeResolution/resolvableTypes.d.ts +0 -12
- package/lib/jsonTypeResolution/resolvableTypes.js +0 -30
- package/lib/jsonTypeResolution/resolvableTypes.js.map +0 -1
- package/src/jsonTypeResolution/index.ts +0 -16
- package/src/jsonTypeResolution/primitiveTypes.ts +0 -32
- package/src/jsonTypeResolution/resolvableTypes.ts +0 -37
- /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 {
|
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 =
|
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
|
-
|
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
|
-
|
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
|
-
|
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('
|
150
|
-
|
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
|
-
'
|
331
|
+
'my-input': { type: ['number', 'string'] },
|
156
332
|
},
|
157
333
|
|
158
|
-
required: ['
|
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
|
-
|
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
|
-
|
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
|
-
|
276
|
-
|
277
|
-
|
278
|
-
const formattedText: FormattedText = [
|
346
|
+
expect(
|
347
|
+
jsonSchemaService.validateInput(
|
279
348
|
{
|
280
|
-
|
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
|
-
|
339
|
-
|
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
|
-
|
348
|
-
|
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
|
-
|
352
|
-
|
353
|
-
|
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
|
-
|
368
|
-
|
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
|
-
|
380
|
-
|
379
|
+
expect(
|
380
|
+
jsonSchemaService.validateInput(
|
381
381
|
{
|
382
|
-
|
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
|
-
|
398
|
-
|
399
|
-
};
|
400
|
-
|
401
|
-
expect(jsonValidationService.validateComponentInput(schema, value)).toEqual(true);
|
402
|
-
});
|
384
|
+
functionInputSchema,
|
385
|
+
),
|
386
|
+
).toEqual(true);
|
403
387
|
|
404
|
-
|
405
|
-
|
388
|
+
expect(
|
389
|
+
jsonSchemaService.validateInput(
|
406
390
|
{
|
407
|
-
|
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
|
-
|
462
|
-
|
463
|
-
|
464
|
-
|
393
|
+
functionInputSchema,
|
394
|
+
),
|
395
|
+
).toEqual(true);
|
396
|
+
});
|
465
397
|
|
466
|
-
|
467
|
-
|
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
|
-
|
476
|
-
type: '
|
477
|
-
|
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
|
-
|
490
|
-
}
|
406
|
+
required: ['my-input'],
|
407
|
+
};
|
491
408
|
|
492
|
-
|
493
|
-
|
494
|
-
|
495
|
-
|
496
|
-
|
497
|
-
|
498
|
-
|
499
|
-
|
500
|
-
|
501
|
-
|
502
|
-
}
|
503
|
-
|
504
|
-
|
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
|
-
|
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
|
-
|
517
|
-
|
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
|
-
|
526
|
-
type: '
|
527
|
-
|
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
|
-
|
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
|
-
|
544
|
-
|
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
|
-
|
553
|
-
type: '
|
554
|
-
|
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
|
-
|
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
|
-
|
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: '
|
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
|
-
|
583
|
-
|
584
|
-
|
585
|
-
|
586
|
-
|
587
|
-
|
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
|
-
|
591
|
-
|
592
|
-
|
593
|
-
|
594
|
-
|
595
|
-
|
596
|
-
|
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
|
-
|
604
|
-
|
605
|
-
|
606
|
-
|
607
|
-
|
519
|
+
const schema = {
|
520
|
+
type: 'object',
|
521
|
+
properties: {
|
522
|
+
arr: {
|
523
|
+
type: 'array',
|
524
|
+
items: { type: 'FormattedText' },
|
608
525
|
},
|
609
|
-
|
610
|
-
|
611
|
-
|
612
|
-
|
526
|
+
},
|
527
|
+
};
|
528
|
+
const value = {
|
529
|
+
arr: [formattedText],
|
530
|
+
};
|
613
531
|
|
614
|
-
|
615
|
-
|
616
|
-
|
617
|
-
|
618
|
-
|
619
|
-
|
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
|
-
|
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
|
-
|
628
|
-
|
629
|
-
|
630
|
-
|
631
|
-
|
632
|
-
|
633
|
-
|
634
|
-
|
635
|
-
}
|
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
|
-
|
641
|
-
|
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': {
|
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':
|
617
|
+
'my-input': formattedText,
|
651
618
|
};
|
652
619
|
|
653
|
-
expect(
|
620
|
+
expect(jsonSchemaService.validateInput(value, schema)).toEqual(true);
|
654
621
|
});
|
655
622
|
|
656
|
-
it('should error when a
|
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': {
|
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':
|
635
|
+
'my-input': { bad: 'data' },
|
666
636
|
};
|
667
637
|
|
668
638
|
expectToThrowErrorMatchingTypeAndMessage(
|
669
639
|
() => {
|
670
|
-
|
640
|
+
jsonSchemaService.validateInput(value, schema);
|
671
641
|
},
|
672
642
|
SchemaValidationError,
|
673
|
-
'failed validation:
|
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
|
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
|
-
|
683
|
-
|
684
|
-
|
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(
|
671
|
+
expect(jsonSchemaService.validateInput(value, schema)).toEqual(true);
|
672
|
+
});
|
712
673
|
|
713
|
-
|
714
|
-
|
715
|
-
|
716
|
-
|
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
|
-
|
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
|
-
|
725
|
-
|
726
|
-
|
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
|
-
|
741
|
-
|
742
|
-
|
743
|
-
|
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
|
-
|
757
|
-
|
758
|
-
|
759
|
-
|
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
|
-
|
787
|
-
|
788
|
-
|
789
|
-
|
790
|
-
|
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
|
-
|
818
|
-
|
819
|
-
|
820
|
-
|
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
|
-
|
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
|
-
|
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
|
-
|
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
|
-
|
937
|
-
|
938
|
-
|
939
|
-
|
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
|
-
|
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
|
-
|
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
|
},
|