NestJS+MQTT通过NodeJS/PM2运行时触发TypeError问题
NestJS MQTT微服务生产运行时报TypeError: Cannot read properties of undefined (reading 'resubscribe')
问题详情
- 环境:NX monorepo + NestJS MQTT微服务
- 异常表现:
- 开发环境执行
yarn nx serve api时功能正常 - 生产编译
yarn nx run-many --t=build --configuration=production无报错 - 直接运行编译后的文件
node ./dist/apps/api/main.js时触发TypeError:
- 开发环境执行
/home/user/Desktop/project/node_modules/mqtt/lib/client.js:701 const resubscribe = obj.resubscribe ^ TypeError: Cannot read properties of undefined (reading 'resubscribe') at MqttClient.subscribe (/home/user/Desktop/project/node_modules/mqtt/lib/client.js:701:27) at /home/user/Desktop/project/node_modules/@nestjs/microservices/server/server-mqtt.js:40:24 at Array.forEach (<anonymous>) at ServerMqtt.bindEvents (/home/user/Desktop/project/node_modules/@nestjs/microservices/server/server-mqtt.js:38:28) at ServerMqtt.start (/home/user/Desktop/project/node_modules/@nestjs/microservices/server/server-mqtt.js:32:14) at ServerMqtt.listen (/home/user/Desktop/project/node_modules/@nestjs/microservices/server/server-mqtt.js:24:18) at /home/user/Desktop/project/node_modules/@nestjs/microservices/nest-microservice.js:107:25 at new Promise (<anonymous>) at NestMicroservice.listen (/home/user/Desktop/project/node_modules/@nestjs/microservices/nest-microservice.js:106:16)
- 核心代码片段(main.ts):
const mqtt_app = await NestFactory.createMicroservice(AppModule, { transport: Transport.MQTT, options: { url: process.env.MQTT_URL, username: process.env.MQTT_USERNAME, password: process.env.MQTT_PASSWORD, }, }); mqtt_app.listen();
- 验证点:不调用
mqtt_app.listen()则无报错;注释@MessagePattern装饰器及对应处理函数后运行正常。
解决方案
1. 确保生产环境变量加载
NX开发环境会自动加载.env文件,但直接运行编译后的Node文件时不会,需手动处理:
- 安装dotenv依赖:
yarn add dotenv - 在main.ts顶部添加环境变量加载逻辑:
import * as dotenv from 'dotenv'; // 根据实际文件路径调整,例如生产环境用.env.production dotenv.config({ path: './apps/api/.env.production' });
或运行时通过命令直接传入环境变量:MQTT_URL=mqtt://your-broker node ./dist/apps/api/main.js
2. 等待微服务启动完成
mqtt_app.listen()返回Promise,未等待完成时可能导致MQTT客户端未就绪就执行订阅操作,修改为:
await mqtt_app.listen(); console.log('MQTT微服务已成功启动');
3. 显式配置MQTT客户端选项
给MQTT options添加默认值和显式的重订阅配置,避免客户端初始化参数异常:
const mqtt_app = await NestFactory.createMicroservice(AppModule, { transport: Transport.MQTT, options: { url: process.env.MQTT_URL || 'mqtt://localhost:1883', username: process.env.MQTT_USERNAME, password: process.env.MQTT_PASSWORD, resubscribe: true, // 显式设置重订阅选项 }, });
4. 检查编译元数据配置
确保NX编译时保留装饰器元数据,修改apps/api/tsconfig.app.json:
{ "compilerOptions": { "emitDecoratorMetadata": true, "experimentalDecorators": true } }
修改后重新编译生产包:yarn nx run-many --t=build --configuration=production
内容的提问来源于stack exchange,提问作者Stefan
相关产品推荐
相关产品推荐

