Skip to content

装饰器种类

  • 类装饰器
  • 方法装饰器
  • 属性装饰器
  • 参数装饰器
  • 访问器装饰器

类装饰器

js
// 类装饰器
const doc: ClassDecorator = (module) => {
  return (target: Function) => {
    target.prototype.module = module
  }
}
// 使用
@doc("user")
class App {
  constructor() {}
}
const app: Record<string, any> = new App()

方法装饰器

js
// 方法装饰器
const Log: MethodDecorator = (
  target: Object,
  propertyKey: string | Symbol,
  descriptor: PropertyDescriptor
) => {
}

class User {
  @Log
  getName() {
    return 'hello'
  }
}

@Log装饰器修饰了 getName方法,tar是被“装饰”的类的圆形,即User.prototype。由于此时类还没有被实例化,因此只能装饰原型对象

属性装饰器

js
const prop: PropertyDecorator = (
  target: Object,
  propertyKey: string | Symbol,
) => {
  console.log('属性装饰器')
}

class User {
  @prop
  name: string = "lengran"
}

@prop用于装饰User类的name属性。此时,target是被装饰的类的原型对象,propertyKey是被修饰的属性名

参数装饰器

js
const Param: ParameterDecorator = (
  target: Object,
  propertyKey: string | Symbol,
  index: number
) => {
  console.log('参数装饰器')
}

class User {
  getName(@Param name: string) {
    return name
  }
}

@Param用于装饰类方法getName的参数,其中target是被装饰类的原型,propertyKey是被装饰的类方法,index是装饰方法参数的索引位置

访问器装饰器

js
const Immutable: ParameterDecorator = (
  target: any,
  propertyKey: string | Symbol,
  descriptor: PropertyDescriptor
) => {
  console.log("访问器装饰器")
}
class User {
  pricate _name = "lengran"

  @Immutable
  get name() {
    return this._name
  }
}

访问器装饰器与类方法装饰器类似,唯一的区别在于它们的描述符(descriptor)中某些键(key)不同

nest中的装饰器

  • 类装饰器: @Controller、@Injectable、@Module
    • @Controller():标记控制器类,控制器处理路由请求
    • @Injectable():标记一个类为可注入的服务,表示该类可以被 NestJS 的依赖注入系统管理。
    • @Module():模块装饰器,用于在Nest中划分功能模块并限制依赖注入的范围
  • 方法装饰器: @Get、@Post、@Put、@Delete、
    • 定义路由方法的HTTP请求方式
  • 属性装饰器: @IsNotEmpty、@IsString、@IsNumber
    • 效验http请求的参数是否符合预期
  • 参数装饰器: @Body、@Param、@Query
    • 用于接收HTTP请求发送的数据,不同的请求方式对应不同的参数接收方式

中间件概述

nest中间件等于express中间件,中间件函数可以访问request和response对象

  • 中间件可以执行任何代码
  • 对请求和想要对象进行修改
  • 结束请求-声明周期
  • 调用堆栈中的下一个中间件函数
  • 如果当前中间件函数没有结束请求(响应周期), 他必须调用next,否则请求将挂起
js
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();
  }
}

中间件应用方式

局部

js
import { Module, NestModule, RequestMethod, 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('cats'); // 只针对cats路由
    //   .forRoutes({ path: 'cats', method: RequestMethod.GET }); // 只针对cats路由下的get
    // forRoutes({ path: 'ab*cd', method: RequestMethod.ALL }); 路由通配符
  }
}

多个中间件

js
consumer.apply(cors(), helmet(), logger).forRoutes(CatsController)

全局中间件

js
const app = await NestFactory.create(AppModule)
app.use(logger)
await app.listen(3000)