How to Validate Comma-Separated Query String as an Array in Fastify with Ajv?

201 views Asked by At

I'm working with Fastify and fastify/ajv-compiler in my project to handle and validate HTTP requests. I've encountered a problem when trying to pass arrays through a query string, where they aren't being properly parsed and validated.

For instance, I have an endpoint 127.0.0.1:3000/api/v1/users/, and I want to be able to pass an userNo array via the query string like userNo=1,2. I expect ['1','2'] but get ['1,2'].

I found refer to fastify ajv example. It should automatically parse the query string into an array based on the default configuration.

Here's my current setup for Fastify and Ajv configuration:

// userNoSchema definition
export const userNoSchema = Type.Partial(
  Type.Object({
    userNo: Type.Array(Type.String())
  }),
  { $id: 'userNo' }
);

// getSchema definition
const getSchema = {
  querystring: Type.Ref(userNoSchema),
  response: {
    200: Type.Object({
      data: Type.Record(Type.String(), Type.String())
    })
  }
};

// Fastify plugin configuration
export default fp((instance, options, done) => {
  instance.addSchema(userNoSchema);

  const factory = fstAjvCompiler();
  const schemas = instance.getSchemas() as Parameters<typeof factory>[0];

  const validator = factory(schemas, {
    customOptions: { keywords: ['instanceOf', 'example'] }
  });
  instance.setValidatorCompiler(validator);
  done();
});

When I send a request to 127.0.0.1:3000/api/v1/users/?userNo=1,2, the userNo parameter is not parsed as an array but rather as an array containing a single string "1,2".

How can I configure Fastify and Ajv to correctly parse and validate a query string like userNo=1,2 as an array ['1', '2']?

Any help or guidance would be greatly appreciated!

1

There are 1 answers

0
TBA On

Fastify is using Node.js querystring module to parse the request query string. You can send an array in the request query string in the following format:

http://127.0.0.1:3000/api/v1/users/?userNo=1&userNo=2&userNo=3

// The request query string is parsed as an array (no need for ajv)
// => request.query.userNo = ['1', '2', '3']

If you want, you can also use a custom query string parser like qs which provides additional options for parsing request query string