-
MiddlewaresNode.js/Nest 2023. 10. 18. 17:22
Nest.js의 Middlewares에 대해 정리하였습니다.< Middlewares >
Middleware is a function which is called before the route handler.
Middleware functions have access to the request and response objects, and the next() middleware function in the application’s request-response cycle. The next middleware function is commonly denoted by a variable named next- You implement custom Nest middleware in either a function, or in a class with an @Injectable( ) decorator. The class should implement the NestMiddleware interface, while the function does not have any special requirements.
Ex) logger.module.ts using class middleware
import { Injectable, NestMiddleware } from '@nestjs/common'; import { Request, Response, NextFunction } from 'express'; @Injectable() export class LoggerMiddleware implements NestMiddleware { use(req: Request, res: Response, next: NextFunction) { console.log('Request...'); next(); } }
< Applying Middlewares >
There is no place for middleware in the @Module( ) decorator. Instead, we set them up using the configure( ) method of the module class.
Modules that include middleware have to implement the NestModule interface.Ex)
import { Module, NestModule, MiddlewareConsumer } from '@nestjs/common'; import { LoggerMiddleware } from './common/middleware/logger.middleware'; import { CatsModule } from './cats/cats.module'; @Module({ imports: [CatsModule], }) export class AppModule implements NestModule { configure(consumer: MiddlewareConsumer) { consumer .apply(LoggerMiddleware) .forRoutes({ path: 'cats', method: RequestMethod.GET }); } }
< Middleware Consumer >
The MiddlewareConsumer is a helper class. It provides several built-in methods to manage middleware. All of them can be simply chained in the fluent style.
The forRoutes( ) method can take a single string, multiple strings, a RouteInfo object, a controller class and even multiple controller classes. In most cases you'll probably just pass a list of controllers separated by commas. Below is an example with a single controller:Ex)
import { Module, NestModule, MiddlewareConsumer } from '@nestjs/common'; import { LoggerMiddleware } from './common/middleware/logger.middleware'; import { CatsModule } from './cats/cats.module'; import { CatsController } from './cats/cats.controller'; @Module({ imports: [CatsModule], }) export class AppModule implements NestModule { configure(consumer: MiddlewareConsumer) { consumer .apply(LoggerMiddleware) .forRoutes(CatsController); } }
: The apply( ) method may either take a single middleware, or multiple arguments to specify multiple middlewares.
< Excluding Routes >
We can easily exclude certain routes with the exclude( ) method.
Ex)
consumer .apply(LoggerMiddleware) .exclude( { path: 'cats', method: RequestMethod.GET }, { path: 'cats', method: RequestMethod.POST }, 'cats/(.*)', ) .forRoutes(CatsController);
< Functional Middlewares >
Why can't we just define it in a simple function instead of a class? In fact, we can. This type of middleware is called functional middleware.
Ex)
logger.middleware.ts
import { Request, Response, NextFunction } from 'express'; export function logger(req: Request, res: Response, next: NextFunction) { console.log(`Request...`); next(); };
app.module.ts
consumer .apply(logger) .forRoutes(CatsController);
< HINT >
Consider using the simpler functional middleware alternative any time your middleware doesn't need any dependencies.
< Multiple Middleware >
in order to bind multiple middleware that are executed sequentially, simply provide a comma separated list inside the apply( ) method
Ex)
consumer.apply(cors(), helmet(), logger).forRoutes(CatsController);
< Global Middleware >
If we want to bind middleware to every registered route at once, we can use the use( ) method that is supplied by the INestApplication instance
Ex)
const app = await NestFactory.create(AppModule); app.use(logger); await app.listen(3000);
< HINT >
Accessing the DI container in a global middleware is not possible. You can use a functional middleware instead when using app.use( ). Alternatively, you can use a class middleware and consume it with .forRoutes('*') within the AppModule (or any other module).
Reference : https://docs.nestjs.com/middleware
Documentation | NestJS - A progressive Node.js framework
Nest is a framework for building efficient, scalable Node.js server-side applications. It uses progressive JavaScript, is built with TypeScript and combines elements of OOP (Object Oriented Programming), FP (Functional Programming), and FRP (Functional Rea
docs.nestjs.com
'Node.js > Nest' 카테고리의 다른 글
Pipes (0) 2023.11.13 Exception Filters (0) 2023.10.30 Modules (0) 2023.09.26 Providers (0) 2023.09.08 Controllers (0) 2023.08.23