Does nestjs/swagger support documentation of query params, if they are not used separately?
Asked Answered
D

4

11

I define a route to get a paginated result of orders in my controller.

@Get()
async find(
  @Query(new ValidationPipe({ whitelist: true }))
  query: OrderQueryDto & PaginatedQueryDto,
) {
  const builder = this.orderRepository
    .createQueryBuilder('order')
    .select('order.id')
    .take(query.take)
    .skip(query.skip)
    .andWhere('order.status != "deleted"');
   if (query.status) {
    builder.andWhere('order.status = :status');
  }
  const [items, count] = await builder.getManyAndCount();
   return { items, count };
}

However I would like to have some documentation about the query params (of type OrderQueryDto & PaginatedQueryDto). I did not find out any decorator, that creates documentation (and test-fields) for the api description that is generated by the nest swagger-module.

I think I am searching for something like @ApiImplicityQueryString({ type: OrderQueryDto & PaginatedQueryDto }).

I know there is a way to document it like so:

@Get()
@ApiImplicitQuery({
  name: 'take',
  required: false,
  type: Number,
})
@ApiImplicitQuery({
  name: 'skip',
  required: false,
  type: Number,
})
// And all the other decorators for the remaining properties on OrderQueryDto [...]
async find(
  @Query(new ValidationPipe({ whitelist: true }))
  query: OrderQueryDto & PaginatedQueryDto,
) {
  const builder = this.orderRepository
    .createQueryBuilder('order')
    .select('order.id')
    .take(query.take)
    .skip(query.skip)
    .andWhere('order.status != "deleted"');
  if (query.status) {
    builder.andWhere('order.status = :status');
  }
  const [items, count] = await builder.getManyAndCount();
  return { items, count };
}

BTW, the DTOs look like this

import { Transform } from 'class-transformer';
import { IsInt, IsOptional } from 'class-validator';

export class PaginatedQueryDto {
  @IsInt()
  @IsOptional()
  @Transform(value => value && parseInt(value, 10))
  take?: number;

  @IsInt()
  @IsOptional()
  @Transform(value => value && parseInt(value, 10))
  skip?: number;
}
import { IsInt, IsOptional, IsEnum } from 'class-validator';
import { Transform } from 'class-transformer';
import { OrderStatus } from './order.entity';

export class OrderQueryDto {
  @IsInt()
  @IsOptional()
  @Transform(value => value && parseInt(value, 10))
  reseller: number;

  @IsInt()
  @IsOptional()
  @Transform(value => value && parseInt(value, 10))
  customer: number;

  @IsEnum(OrderStatus)
  @IsOptional()
  status: OrderStatus;
}
Duisburg answered 5/1, 2020 at 13:32 Comment(0)
D
6

Add @ApiTags('ports') to controller.Bellow the code

controller

import { Body, Controller, Get, Param, Post, Query } from '@nestjs/common';
import { PaginationQuery } from './pagination-query.dto';
import {
    ApiBearerAuth,
    ApiConsumes,
    ApiExtension,
    ApiHeader,
    ApiOperation,
    ApiQuery,
    ApiResponse,
    ApiSecurity,
    ApiTags
  } from '@nestjs/swagger'

@ApiTags('ports')

@Controller('port')
export class PortController {
    @Get()
    findAll(@Query() paginationQuery: PaginationQuery) {}
}

PaginationQuery

import { ApiProperty } from '@nestjs/swagger';

export enum LettersEnum {
  A = 'A',
  B = 'B',
  C = 'C'
}

export class PaginationQuery {
  @ApiProperty({
    minimum: 0,
    maximum: 10000,
    title: 'Page',
    exclusiveMaximum: true,
    exclusiveMinimum: true,
    format: 'int32',
    default: 0
  })
  page: number;

  @ApiProperty({
    name: '_sortBy'
  })
  sortBy: string[];

  @ApiProperty()
  limit: number;

  @ApiProperty({
    enum: LettersEnum,
    enumName: 'LettersEnum'
  })
  enum: LettersEnum;

  @ApiProperty({
    enum: LettersEnum,
    enumName: 'LettersEnum',
    isArray: true
  })
  enumArr: LettersEnum;

  @ApiProperty()
  beforeDate: Date;

  @ApiProperty({
    type: 'object',
    additionalProperties: true
  })
  filter: Record<string, any>;

  static _OPENAPI_METADATA_FACTORY() {
    return {
      sortBy: { type: () => [String] }
    };
  }
}

Deirdre answered 18/3, 2021 at 10:58 Comment(1)
This example is very comprehensive and helpful to my development. Thanks!Amido
B
6

if you want to use query parameter DTO in nest.js you will need to define it in the controller as belove.

 @Get()
 @ApiQuery({ type: YourDTO})
Bise answered 15/5, 2023 at 17:45 Comment(0)
U
2

You need to define the controller like this

@Get()
@ApiQuery({ name: 'page' })
@ApiQuery({ name: 'size' })
findAll(@Query() paginationQuery: PaginationQuery) {

}

Unwatched answered 4/12, 2023 at 15:29 Comment(0)
R
1

nestjs/swagger not documenting the query params so you have to use @ApiQuery() annotation , source

  @Get('search')
  @ApiOperation({ summary: 'Get Products by search ' })
  @ApiQuery({ name:'searchString', required: true, type:'string' })
  @ApiQuery({ name: 'take', required: false, type: 'number' })
  @ApiQuery({ name: 'page', required: false, type: 'number' })
  getPaginatedBySearchString(
    @Query('searchString') searchString: string,
    @Query('take') take = 10,
    @Query('page') page = 0,
  ) {
    take = take > 20 ? 20 : take;
    return this.productsService.findPoductsBySearchString(
      take,
      page,
      searchString,
    );
  }
Riddell answered 24/2 at 13:32 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.