I wonder if anyone uses some library to validate API calls parameters. So far we use Vandium (https://github.com/vandium-io/vandium-node ) but it seems that it does not work with lambda-proxy integration which we need.
When some parameter is wrong, it ends the lambda function with similar output:
{
"errorMessage": "validation error: Parameter email is required and should have format of email address",
"errorType": "Error",
"stackTrace": []
}
And APIG fails with internal error because it must get output like { "statusCode": 400, "body": "..." }
.
Vandium encapsulates code of the lambda function so validation error can’t be simply caught and transformed in it. The code looks like:
module.exports.appsDetail = vandium.createInstance({
validation: {
schema: {
headers: vandium.types.object().keys({
Authorization: vandium.types.string().required(),
}),
pathParameters: vandium.types.object().keys({
appId: vandium.types.string().required(),
version: vandium.types.number().integer(),
}),
},
},
}).handler((event, context, callback) => {
...
buggy
October 20, 2016, 9:53am
2
I’ve been using Validator to handle simple validation.
https://www.npmjs.com/package/validator
I’m using Joi https://github.com/hapijs/joi
something like this:
const Joi = require('joi');
// const {customResponse, customError} = require('responses');
const validation = {
post: {
body: Joi.object().keys({
name: Joi.string().min(1).max(128).required(),
})
},
};
const controller = {
post(event, context, done) {
MyModel
.put({
name: event.parsedData.name,
})
.then(response => done(null, customResponse(response)))
.catch(err => done(null, customError(err)));
},
};
// Export validated functions only
Object.keys(validation).forEach(methodName => {
const validationObj = validation[methodName];
const controllerFn = controller[methodName];
if (validationObj && controllerFn) {
module.exports[methodName] = validate(validationObj, controllerFn);
}
});
function validate(validation, fn) {
let proxy = fn;
if (validation.body) {
proxy = paramsValidation(proxy, 'body', validation.body);
}
if (validation.queryStringParameters) {
proxy = paramsValidation(proxy, 'queryStringParameters', validation.queryStringParameters);
}
return proxy;
}
function paramsValidation(fn, field, schema) {
return function(event, context, done) {
const raw = event[field];
const params = raw ? JSON.parse(event[field]) : {};
Joi.validate(params, schema, (err, value) => {
if (err) {
const firstMessage = ((err.details || [])[0] || {}).message;
return done(null, customError({
errorMessage: firstMessage || err.details,
errorType: 'InvalidParametersException',
statusCode: 400,
}));
} else {
event.parsedData = Object.assign({}, value, event.parsedData);
fn(event, context, done);
}
});
};
};
Ah, it looks good. Vandium internally uses Joi so migration could be quite easy. Thank you guys.