美文网首页
管道与模块

管道与模块

作者: hellomyshadow | 来源:发表于2019-10-20 22:49 被阅读0次

    管道

    1. 管道可以将输入数据转为所需的输出数据,此外还可以处理验证,数据错误时可能抛出异常;
    2. 创建管道
      nest g pipe pipe/news
      
      1. pipe/news.pipe.ts
      import { PipeTransform, Injectable, ArgumentMetadata } from '@nestjs/common'
      
      @Injectable
      export class NewsPipe implements PipeTransform {
          transform(value:any, metadata:ArgumentMetadata) {
              //value 一般就是 GET/POST 传递的数据
              return value
          }
      }
      
      1. 在控制器方法上使用
      import { UsePipes, Controller, Get, Query } from '@nestjs/common'
      import { NewsPipe } from '../pipe/news.pipe'
      
      @Controller('news')
      export class NewsController {
          @Get()
          @UsePipes(new NewsPipe())
          index(@Query() query) {
          }
      }
      
    3. 控制器接收到请求之后,会交给管道验证或处理这些数据,然后再交给控制器方法;
    4. 使用第三方库 joi 处理验证
      npm i @hapi/joi --save
      
      1. news.pipe.ts
          constructor(private readonly schema) {}
          transform(value:any, metadata:ArgumentMetadata) {
              // 根据Schema验证提交数据的合法性
              const { error } = this.schema.validate(value);
              if (error) {  //数据不合法,则抛出异常
                  throw new BadRequestException('Validation failed');
              }
              return value;
          }
      
      1. 控制器
          import * as Joi from 'hapi/joi'
      
          //定义Schema
          let userSchema = Joi.object().keys({ 
              name:Joi.string().required(), 
              age:Joi.number().integer().min(6).max(66).required()
          });
          
          @Controller('news')
          export class NewsController {
              @Get()
              @UsePipes(new NewsPipe(userSchema))
              index(@Query() query) {
              }
          }
      
      1. 发起请求:http://localhost:3000/news?name=Mack&age=20

    模块

    1. 模块是 @Module() 装饰的类,@Module()装饰器提供了元数据,Nest用模块来组织应用程序的结构;
    2. 通过脚手架创建项目时,会生成一个根模块:app.module.ts,根模块中可以挂载不同功能的子模块,而在子模块中挂载相应的控制器和服务;
    3. 创建模块:
      nest g module module/admin
      
      1. 生成admin模块:module/admin/admin.module.ts
      2. 在根模块中自动引入创建的子模块:
      import { AdminModule } from './module/admin/admin.module'
      @Module({
          imports: [AdminModule],
          controllers: [AppController],
          providers: [AppService]
      })
      export class AppModule {}
      
    4. 在子模块admin中创建控制器和服务
      1. 创建控制器
          nest g controller module/admin/controller/user
      
      1. 创建服务
          nest g service module/admin/service/user
      
      1. 因为admin模块已经存在了,所以控制器和服务会被自动挂载到子模块中,而不再挂载到根模块上;
          import { UserController } from './controller/user/user.controller';
          import { UserService } from './service/user/user.service';
          @Module({
              controllers: [UserController],
              providers: [UserService]
          })
          export class AdminModule {}
      
      1. 在控制器user.controller中引入服务,并依赖注入服务对象
          import { UserService } from '../../service/user/user.service';
          @Controller('admin/user')
          export class UserController {
              constructor(private userService:UserService) {}
      
              @Get()
              index() {
                  return this.userService.findAll();
              }
          }
      
    5. 子模块中创建的服务默认是私有的,其他模块的控制器依赖注入时,也必须先挂载到对应的模块上,然后才能注入成功;
      import { NewsService } from '../api/news.service';
      @Module({
          controllers: [UserController],
          providers: [UserService, NewsService]
      })
      export class AdminModule {}
      
      import { NewsService } from '../../../api/news.service';
      @Controller('admin/user')
      export class UserController {
          // 同时注入UserService和NewsService两个服务
          constructor(private userService:UserService, private newsService:NewsService) {}
      
          @Get()
          index() {
              return this.userService.findAll();
          }
      
          @Get('news')
          index() {
              return this.newsService.getNews();
          }
      }
      
    6. 服务可以是公共的,模块也可以是公共的。把公共模块挂载到其他模块上之后,还需要在公共模块中导出服务,否则仍然不能使用!
      1. 公共模块
      import { UploadService } from './service/upload/upload.service';
      
      @Module({
          providers: [UploadService],  // 声明/挂载服务
          exports: [UploadService]  // 导出服务,引入share模块的模块中,可以使用导出服务
      })
      export class ShareModule {}
      
      1. 挂载公共模块
      //引入公共模块中的服务
      import { ShareModule } from '../share/share.module';
      @Module({
          imports: [ShareModule],  // 挂载公共模块
          controllers: [UserController],
          providers: [UserService, NewsService]
      })
      export class AdminModule {}
      
      1. 注入公共模块中的服务
      import { UploadService } from '../../../share/service/upload/upload.service';
      
      @Controller('admin/user')
      export class UserController {
          
          constructor(private userService:UserService, private uploadService:UploadService) {}
      
          @Get()
          index() {
              return this.userService.findAll();
          }
      
          @Get('upload')
          upload() {
              return this.uploadService.upload();
          }
      }
      

    相关文章

      网友评论

          本文标题:管道与模块

          本文链接:https://www.haomeiwen.com/subject/tytkmctx.html