Refactor API Schema and validation

- /schema now returns full openapi/swagger schema
- That schema is used to validate incoming requests
- And used as a contract in future integration tests
- Moved route files up one level
- Fixed incorrect 404 reponses when getting objects
- Fixed saving new objects and passing jsonschemavalidation
This commit is contained in:
Jamie Curnow
2024-10-09 18:05:15 +10:00
parent 63d06da8a8
commit dfe2588523
123 changed files with 5363 additions and 2574 deletions

View File

@ -1,6 +1,4 @@
const error = require('../error');
const path = require('path');
const parser = require('json-schema-ref-parser');
const error = require('../error');
const ajv = require('ajv')({
verbose: true,
@ -17,8 +15,14 @@ const ajv = require('ajv')({
*/
function apiValidator (schema, payload/*, description*/) {
return new Promise(function Promise_apiValidator (resolve, reject) {
if (schema === null) {
reject(new error.ValidationError('Schema is undefined'));
return;
}
if (typeof payload === 'undefined') {
reject(new error.ValidationError('Payload is undefined'));
return;
}
let validate = ajv.compile(schema);
@ -35,11 +39,4 @@ function apiValidator (schema, payload/*, description*/) {
});
}
apiValidator.loadSchemas = parser
.dereference(path.resolve('schema/index.json'))
.then((schema) => {
ajv.addSchema(schema);
return schema;
});
module.exports = apiValidator;

View File

@ -1,6 +1,6 @@
const _ = require('lodash');
const error = require('../error');
const definitions = require('../../schema/definitions.json');
const _ = require('lodash');
const error = require('../error');
const commonDefinitions = require('../../schema/common.json');
RegExp.prototype.toJSON = RegExp.prototype.toString;
@ -9,9 +9,7 @@ const ajv = require('ajv')({
allErrors: true,
format: 'full', // strict regexes for format checks
coerceTypes: true,
schemas: [
definitions
]
schemas: [commonDefinitions]
});
/**
@ -27,21 +25,18 @@ function validator (schema, payload) {
} else {
try {
let validate = ajv.compile(schema);
let valid = validate(payload);
let valid = validate(payload);
if (valid && !validate.errors) {
resolve(_.cloneDeep(payload));
} else {
let message = ajv.errorsText(validate.errors);
reject(new error.InternalValidationError(message));
}
} catch (err) {
reject(err);
}
}
});
}