NestJS中的数据传输对象(DTO)的目的是什么?

18

我正在解决一个问题。我正在按照NestJS的文档进行操作。这是NodeJS的后端框架。文档提到了DTO(数据传输对象)。我为创建用户创建了一个DTO:

export class CreateUserDto {
    readonly email: string;
    readonly password: string;
}

结合这个:

@Post('create')
createUser(@Body() userData: CreateUserDto): User {
    return this.usersService.createUser(userData);
}

出于某种原因,我可以使用任何类型的消息体向此路由发起POST请求,而不会出现错误。这个数据传输对象(DTO)的整个意义在于仅允许消息体中的特定信息,对吧?我尝试过使用“export class CreateUserDTO”以及“export interface CreateUserDTO”,但都没有奏效。我对TypeScript和NestJS都很陌生。是否有人能够解释一下为什么它没有按照我的期望工作,或者这样的数据传输对象有什么目的?

2个回答

33
DTO本身更像是一个指南,供开发人员和使用API的人了解请求体期望的形状,它本身并不运行任何验证。但是,使用Typescript,您可以从class-validator库中添加装饰器,并使用内置ValidationPipe对传入的请求进行验证,以便只有预期的请求体可以进入。
简而言之,DTO是请求应该具有的定义,但由于JavaScript是一种动态语言,您可以发送任何内容。这就是为什么存在像class-validatorruntypes这样的库的原因。

2
感谢@Jay McDoniel。我正在我的私人课程中使用您的巢穴存储库,非常好!再次感谢! - Jorge Guerra Pires

6

在运行时,所有类型都会丢失,因此控制器接受来自请求体的任何JSON。如果您想进行类型检查,应启用一个ValidationPipe,该管道利用class-transformerclass-validator库:

app.useGlobalPipes(
    new ValidationPipe({
      transform: true,
      transformOptions: {
        enableImplicitConversion: true,
      },
      validationError: { target: false, value: false },
    })
  ); 

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接