Skip to content

Commit c9f7b53

Browse files
authored
feat: add support for const value (#276)
1 parent 63554c2 commit c9f7b53

File tree

2 files changed

+77
-20
lines changed

2 files changed

+77
-20
lines changed

index.js

Lines changed: 10 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -102,8 +102,6 @@ function build (schema, options) {
102102
schema.type = inferTypeByKeyword(schema)
103103
}
104104

105-
var hasSchemaSomeIf = hasIf(schema)
106-
107105
var main
108106

109107
switch (schema.type) {
@@ -141,7 +139,7 @@ function build (schema, options) {
141139

142140
var dependencies = []
143141
var dependenciesName = []
144-
if (hasOf(schema) || hasSchemaSomeIf) {
142+
if (dependsOnAjv(schema)) {
145143
dependencies.push(new Ajv(options.ajv))
146144
dependenciesName.push('ajv')
147145
}
@@ -212,24 +210,9 @@ function inferTypeByKeyword (schema) {
212210
return schema.type
213211
}
214212

215-
function hasOf (schema) {
216-
if (!schema) { return false }
217-
if ('anyOf' in schema || 'oneOf' in schema) { return true }
218-
219-
var objectKeys = Object.keys(schema)
220-
for (var i = 0; i < objectKeys.length; i++) {
221-
var value = schema[objectKeys[i]]
222-
if (typeof value === 'object') {
223-
if (hasOf(value)) { return true }
224-
}
225-
}
226-
227-
return false
228-
}
229-
230-
function hasIf (schema) {
213+
function dependsOnAjv (schema) {
231214
const str = JSON.stringify(schema)
232-
return /"if":{/.test(str) && /"then":{/.test(str)
215+
return (/"if":{.*"then":{|"(anyOf|oneOf)":\[|"const":/.test(str))
233216
}
234217

235218
const stringSerializerMap = {
@@ -1187,6 +1170,13 @@ function nested (laterCode, name, key, location, subKey, isArray) {
11871170
code += `
11881171
json += JSON.stringify(obj${accessor})
11891172
`
1173+
} else if ('const' in schema) {
1174+
code += `
1175+
if(ajv.validate(${require('util').inspect(schema, { depth: null })}, obj${accessor}))
1176+
json += '${JSON.stringify(schema.const)}'
1177+
else
1178+
throw new Error(\`Item $\{JSON.stringify(obj${accessor})} does not match schema definition.\`)
1179+
`
11901180
} else {
11911181
throw new Error(`${schema.type} unsupported`)
11921182
}

test/const.test.js

Lines changed: 67 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,67 @@
1+
'use strict'
2+
3+
const test = require('tap').test
4+
const validator = require('is-my-json-valid')
5+
const build = require('..')
6+
7+
test('schema with const string', (t) => {
8+
t.plan(2)
9+
10+
const schema = {
11+
type: 'object',
12+
properties: {
13+
foo: { const: 'bar' }
14+
}
15+
}
16+
17+
const validate = validator(schema)
18+
const stringify = build(schema)
19+
const output = stringify({
20+
foo: 'bar'
21+
})
22+
23+
t.equal(output, '{"foo":"bar"}')
24+
t.ok(validate(JSON.parse(output)), 'valid schema')
25+
})
26+
27+
test('schema with const object', (t) => {
28+
t.plan(2)
29+
30+
const schema = {
31+
type: 'object',
32+
properties: {
33+
foo: { const: { bar: 'baz' } }
34+
}
35+
}
36+
37+
const validate = validator(schema)
38+
const stringify = build(schema)
39+
const output = stringify({
40+
foo: { bar: 'baz' }
41+
})
42+
43+
t.equal(output, '{"foo":{"bar":"baz"}}')
44+
t.ok(validate(JSON.parse(output)), 'valid schema')
45+
})
46+
47+
test('schema with const and invalid object', (t) => {
48+
t.plan(2)
49+
50+
const schema = {
51+
type: 'object',
52+
properties: {
53+
foo: { const: { foo: 'bar' } }
54+
},
55+
required: ['foo']
56+
}
57+
58+
const stringify = build(schema)
59+
try {
60+
stringify({
61+
foo: { foo: 'baz' }
62+
})
63+
} catch (err) {
64+
t.match(err.message, /^Item .* does not match schema definition/, 'Given object has invalid const value')
65+
t.ok(err)
66+
}
67+
})

0 commit comments

Comments
 (0)