Swagger provides us a standard to generate API documentation based on the Open API specification. If we use NestJS for building our API providers, we can utilize a tool provided by NestJS in the @nestjs/swagger
module to generate the documentation automatically in the built time. This module also requires the swagger-ui-express
module if we use Express as the NestJS base HTTP handler.
Set Swagger configuration
First, we need to define Swagger options and instantiate the documentation provider on the main.ts
file.
import { DocumentBuilder, SwaggerModule } from '@nestjs/swagger';
// sample application instance
const app = await NestFactory.create(AppModule);
// setup Swagger options
const options = new DocumentBuilder()
.setTitle('Coffee')
.setVersion('1.0')
.setDescription('Learn NestJS with coffee')
.build();
// build the document
const document = SwaggerModule.createDocument(app, options);
// provide an endpoint where the document can be accessed
SwaggerModule.setup('docs', app, document);
Set custom compiler options
NestJS is optimized for us to implement the object validation processes and define the shapes of any objects passed to our API endpoints that are subjected to data transfer objects (DTO). The implementation utilizes Typescript decorators which are not evaluated in the built time if we use the default compiler. To let the Swagger module generates correct definitions of any request payloads, we need to override default compiler options in the nest-cli.json
file by enabling the NestJS Swagger plugin.
{
// ...
"compilerOptions": {
"deleteOutDir": true,
"plugins": ["@nestjs/swagger/plugin"]
}
}
Revision for PartialType
If we declare a DTO that utilizes the PartialType
function for extending the attributes of a parent DTO, we need to implement the definition provided by the @nestjs/swagger
module. Otherwise, the documentation will not render the correct properties of the DTO.
import { PartialType } from '@nestjs/swagger';
import { ParentDto } from './parent.dto';
export class ChildDto extends PartialType(ParentDto) {}
Add details of DTO properties
We can utilize the @ApiProperty()
decorator on each property in a DTO to set details of the property.
import { ApiProperty } from '@nestjs/swagger';
export class SampleDto {
@ApiProperty({ description: 'Name of the product' })
@IsString()
readonly name: string;
@ApiProperty({ example: [] })
@IsString({ each: true })
readonly models: string[];
}
Add details of HTTP responses
By default, the documentation generated by the Swagger module will only show details of success responses based on the evaluated controllers. If we want to provide custom details or additional response definitions, we can utilize some decorators provided by the @nesjs/swagger
module such as @ApiResponse()
, @ApiForbiddenResponse()
, and so on. These decorators can be applied both on a controller method and the class to provide default definitions for its contained methods.
@ApiResponse({ status: 404, description: 'Resource is not found' })
@Controller('product')
export class ProductController {
@ApiResponse({ status: 401, description: 'Invalid query parameters' })
@Get()
findAll() {}
@ApiForbiddenResponse({ description: 'Unauthorized access' })
@Post()
create() {}
}
Grouping the endpoints
To improve the readability of our documentation, sometimes we need to group or categorize our endpoints. We can apply the @ApiTags()
decorator on our controller class.
@ApiTags('inventory')
@Controller('product')
export class ProductController {}
// ...
@ApiTags('inventory')
@Controller('product-category')
export class ProductCategoryController {}
Comments
Post a Comment