forked from projectmoon/tenebrous-dicebot
80 lines
2.2 KiB
JavaScript
80 lines
2.2 KiB
JavaScript
|
'use strict';
|
||
|
|
||
|
var util = require('./_util');
|
||
|
|
||
|
module.exports = function defFunc(ajv) {
|
||
|
if (!ajv._opts.$data) {
|
||
|
console.warn('keyword select requires $data option');
|
||
|
return ajv;
|
||
|
}
|
||
|
var metaSchemaRef = util.metaSchemaRef(ajv);
|
||
|
var compiledCaseSchemas = [];
|
||
|
|
||
|
defFunc.definition = {
|
||
|
validate: function v(schema, data, parentSchema) {
|
||
|
if (parentSchema.selectCases === undefined)
|
||
|
throw new Error('keyword "selectCases" is absent');
|
||
|
var compiled = getCompiledSchemas(parentSchema, false);
|
||
|
var validate = compiled.cases[schema];
|
||
|
if (validate === undefined) validate = compiled.default;
|
||
|
if (typeof validate == 'boolean') return validate;
|
||
|
var valid = validate(data);
|
||
|
if (!valid) v.errors = validate.errors;
|
||
|
return valid;
|
||
|
},
|
||
|
$data: true,
|
||
|
metaSchema: { type: ['string', 'number', 'boolean', 'null'] }
|
||
|
};
|
||
|
|
||
|
ajv.addKeyword('select', defFunc.definition);
|
||
|
ajv.addKeyword('selectCases', {
|
||
|
compile: function (schemas, parentSchema) {
|
||
|
var compiled = getCompiledSchemas(parentSchema);
|
||
|
for (var value in schemas)
|
||
|
compiled.cases[value] = compileOrBoolean(schemas[value]);
|
||
|
return function() { return true; };
|
||
|
},
|
||
|
valid: true,
|
||
|
metaSchema: {
|
||
|
type: 'object',
|
||
|
additionalProperties: metaSchemaRef
|
||
|
}
|
||
|
});
|
||
|
ajv.addKeyword('selectDefault', {
|
||
|
compile: function (schema, parentSchema) {
|
||
|
var compiled = getCompiledSchemas(parentSchema);
|
||
|
compiled.default = compileOrBoolean(schema);
|
||
|
return function() { return true; };
|
||
|
},
|
||
|
valid: true,
|
||
|
metaSchema: metaSchemaRef
|
||
|
});
|
||
|
return ajv;
|
||
|
|
||
|
|
||
|
function getCompiledSchemas(parentSchema, create) {
|
||
|
var compiled;
|
||
|
compiledCaseSchemas.some(function (c) {
|
||
|
if (c.parentSchema === parentSchema) {
|
||
|
compiled = c;
|
||
|
return true;
|
||
|
}
|
||
|
});
|
||
|
if (!compiled && create !== false) {
|
||
|
compiled = {
|
||
|
parentSchema: parentSchema,
|
||
|
cases: {},
|
||
|
default: true
|
||
|
};
|
||
|
compiledCaseSchemas.push(compiled);
|
||
|
}
|
||
|
return compiled;
|
||
|
}
|
||
|
|
||
|
function compileOrBoolean(schema) {
|
||
|
return typeof schema == 'boolean'
|
||
|
? schema
|
||
|
: ajv.compile(schema);
|
||
|
}
|
||
|
};
|