You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何为基于GRPC的NestJS微服务编写集成/端到端测试?

NestJS gRPC微服务集成测试实现方案

问题背景

我有一个用gRPC实现微服务通信的NestJS应用,需要为部分端点编写集成/端到端测试(仅模拟外部微服务调用、数据库调用等)。但NestJS官方文档只覆盖了REST应用的集成测试,现有代码如下:

Controller文件

import {
  ClassSerializerInterceptor,
  Controller,
  Logger,
  UseFilters,
  UseInterceptors,
} from '@nestjs/common';
import { GrpcMethod } from '@nestjs/microservices';
import { RpcValidationFilter } from '../../common/exception/filters/rpc.filter';

enum GrpcService {
  NAME = 'TestService',
}

export class TestDto {
  userId: string;

  constructor() {
    this.userId = 'userId';
  }
}

@Controller()
@UseFilters(RpcValidationFilter)
@UseInterceptors(ClassSerializerInterceptor)
export class TestController {
  private readonly logger = new Logger(TestController.name);

  constructor() {}

  @GrpcMethod(GrpcService.NAME)
  public testProto(data: TestDto): Promise<TestDto> {
    this.logger.debug(data, 'Testing GRPC method call');
    return Promise.resolve(new TestDto());
  }
}

Proto文件

syntax = "proto3";

package testProto.v1;

service TestService {
  rpc TestProto (RequestDto) returns (ResponseDto);
}

message RequestDto {
  string user_id = 1;
}

message ResponseDto {
  string user_id = 1;
}

需要创建应用实例并发送gRPC请求调用控制器方法,无服务层/数据库层,该如何实现?


实现步骤

1. 安装必要依赖

确保项目已安装测试相关依赖,若未安装执行:

npm install --save-dev @nestjs/testing @grpc/grpc-js @grpc/proto-loader

2. 编写集成测试文件

在test目录下创建test.controller.e2e-spec.ts,代码如下:

import { Test } from '@nestjs/testing';
import { loadPackageDefinition, credentials } from '@grpc/grpc-js';
import { loadSync } from '@grpc/proto-loader';
import { TestController } from '../src/test/test.controller';

describe('TestController (gRPC)', () => {
  let client: any;
  let app: any;

  beforeAll(async () => {
    // 创建测试模块,注入目标控制器
    const moduleRef = await Test.createTestingModule({
      controllers: [TestController],
    }).compile();

    // 启动gRPC微服务,监听随机端口避免冲突
    app = moduleRef.createNestMicroservice({
      transport: 'grpc',
      options: {
        package: 'testProto.v1',
        protoPath: './src/test/test.proto', // 替换为你的proto文件实际路径
        url: 'localhost:0',
      },
    });
    await app.listen();

    // 获取微服务实际地址,创建gRPC客户端
    const serverUrl = app.getUrl();
    const protoDefinition = loadSync('./src/test/test.proto', {
      keepCase: true,
      longs: String,
      enums: String,
      defaults: true,
      oneofs: true,
    });
    const testProto = loadPackageDefinition(protoDefinition).testProto.v1;
    client = new testProto.TestService(serverUrl, credentials.createInsecure());
  });

  afterAll(async () => {
    // 清理资源:关闭客户端和微服务
    client.close();
    await app.close();
  });

  it('should return expected TestDto when calling TestProto', (done) => {
    const request = { user_id: 'test-user-123' };
    // 调用gRPC方法并验证结果
    client.testProto(request, (error: any, response: any) => {
      expect(error).toBeNull();
      expect(response.user_id).toBe('userId');
      done();
    });
  });
});

3. 关键逻辑说明

  • 测试环境搭建:通过Test.createTestingModule模拟应用容器,仅注入需要测试的控制器,保证测试隔离性。
  • 微服务启动:使用createNestMicroservice创建gRPC服务实例,指定url: 'localhost:0'让系统自动分配可用端口,避免端口占用冲突。
  • 客户端初始化:加载proto文件生成客户端定义,连接到测试微服务的实际地址,实现gRPC请求调用。
  • 异步测试处理:gRPC调用为异步操作,使用done回调通知测试框架异步逻辑完成。

4. 运行测试

确保package.json中包含e2e测试命令:

{
  "scripts": {
    "test:e2e": "jest --config ./test/jest-e2e.json"
  }
}

执行测试命令:

npm run test:e2e

内容的提问来源于stack exchange,提问作者Caroline

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.05 05:15:21