0

Controller

@Get(')
test(
    @Param('accountId') accountId: string,
    @Query('propertyName') propertyNames: string[],
) {
    console.log(propertyNames);
}

Sample Request localhost:8000?propertyName=test2&propertyName=test3

Output:

[ 'test2', 'test3' ]

This works fine when I have multiple values, but when only one parameter is sent, it creates a string instead of an Array

Request: localhost:8000?propertyName=test3 Generates the output: test3 instead of [test3]

My current approach is to use (as per https://stackoverflow.com/a/4775737/5236575)

propertyName = [].concat(propertyName)

to ensure the value is an array.

Is there a way to force Nest.js to parse the query parameters as a string array at all times as this is required in multiple places across controllers.


Note: ValdiationPipe: transform is set to true

app.useGlobalPipes(new ValidationPipe({ whitelist: true, transform: true }));
shoaib30
  • 877
  • 11
  • 24

2 Answers2

1

Off the top of my head, you could use @Transform decorator from class-transformer to achieve that. You could move the logic of transforming a single string parameter to array with help of that decorator.

Ayzrian
  • 2,279
  • 1
  • 7
  • 14
  • Will try it, but would it handle both an array as well as a string? since it is an array when multiple values come in. – shoaib30 Nov 02 '21 at 12:06
  • The implementation is up to you:) The callback will just receive the value, then you can do whatever you want to do. – Ayzrian Nov 02 '21 at 14:21
0

You could use a custom pipe like so:

@Injectable()
export class ParseQueryValuePipe implements PipeTransform<string, string[]> {
  transform(value: string | string[]): string[] {
    if (value) {
      // You could even perform your validation here
      if (some_condition) {
        throw new BadRequestException('your_message');
      }


      return [value].flat();
    }
  }
}

and then you'd use it like this:

@Query('propertyName', new ParseQueryValuePipe()) propertyNames: string[],
mehayoo
  • 9
  • 3