Checking JSON request string as a query parameter using Joi

I have a JSON validation problem that is passed in the request parameter of a GET request as a serialized string.

What I need to do is parse this serialized string back into JSON and check it with Joi.

Example: Give JSON

{ limit: {size:10, page:0}, filter: {filter_by: 'foo', filter_val: 'foo', from: '1/1/2016',to: '1/1/2016' } } 

And this JSON is converted to the query string:

 limit%5Bsize%5D=10&limit%5Bpage%5D=0&filter%5Bfilter_by%5D=foo&filter%5Bfilter_val%5D=foo&filter%5Bfrom%5D=1%2F1%2F2016&filter%5Bto%5D=1%2F1%2F2016 

I need something like this:

  validate: { query: { limit: Joi.someMethodToGetJsonFromString.object().keys({ size: Joi.number(), page: Joi.number() } filter: Joi.someMethodToGetJsonFromString,.object().keys({ filter_by: Joi.string().valid(['option1', 'option2']), filter_val: Joi.string(), from: Joi.date(), to: Joi.date(), } } 

Is there anything in Joi that can help in this scenario, or do I need to write special validation functions for it.

+5
source share
1 answer

You will want to change the parsing of the query string because hapi does not support this format by default. It simply uses Node's built-in url module to parse a URL that does not support complex query string encodings. You will need to manually analyze it with qs , after which you can check it as usual.

 const Hapi = require('hapi'); const Joi = require('joi'); const Url = require('url'); const Qs = require('qs'); const server = new Hapi.Server(); server.connection({ port: 4000 }); const onRequest = function (request, reply) { const uri = request.raw.req.url; const parsed = Url.parse(uri, false); // skip the querystring parsing parsed.query = Qs.parse(parsed.query); // parse it ourselves with qs request.setUrl(parsed); return reply.continue(); }; server.ext('onRequest', onRequest); server.route({ config: { validate: { query: { limit: Joi.object().keys({ size: Joi.number(), page: Joi.number() }), filter: Joi.object().keys({ filter_by: Joi.string().valid(['option1', 'option2']), filter_val: Joi.string(), from: Joi.date(), to: Joi.date(), }) } } }, method: 'GET', path: '/', handler: function (request, reply) { return reply('ok'); } }); server.start((err) => { if (err) { throw err; } console.log('Started server'); }); 

This is discussed a bit in the API docs under request.setUrl() .

+3
source

Source: https://habr.com/ru/post/1245462/


All Articles