'NestJS microservices error with "No matching message handler"
I'm building an application with microservices communicating through RabbitMQ (request-response pattern).
Everything works fine but still I have a problem with error "There is no matching message handler defined in the remote service." -
When I send POST to my Client app, it should simply send the message with data through client (ClientProxy) and the Consumer app should response. This functionality actually works, but always only for the second time. I know it sounds strange but on my first POST request there is always the error from Client and my every second POST request works. However this problem is everywhere in my whole application, so the particular POST request is just for the example.
Here is the code:
Client:
@Post('devices')
async pushDevices(
@Body(new ParseArrayPipe({ items: DeviceDto }))
devices: DeviceDto[]
) {
this.logger.log('Devices received');
return this.client.send(NEW_DEVICES_RECEIVED, devices)
}
Consumer:
@MessagePattern(NEW_DEVICES_RECEIVED)
async pushDevices(@Payload() devices: any, @Ctx() context: RmqContext) {
console.log('RECEIVED DEVICES');
console.log(devices);
const channel = context.getChannelRef();
const originalMsg = context.getMessage();
channel.ack(originalMsg);
return 'ANSWER';
}
Client has the RMQ settings with queueOptions: {durable: true} and the consumer as well queueOptions: {durable: true} with noAck: false
Please do you have any ideas what may causes the problem? I have tried sending the data with JSON.stringify and changing the message structure to {data: devices} but the error is still there.
Solution 1:[1]
I had this error while NOT using RabbitMQ. I found very little help online around this error message outside of it being related to RabbitMQ.
For me it was an issue where I was importing a DTO from another microservice in my microservice's Controller. I had a new DTO in my microservice that has a similar name to one in another microservice. I accidentally selected the wrong one from the automated list.
Since there wasn't any real indicator that my build was bad, just this error, I wanted to share in case others made the same mistake I did.
Solution 2:[2]
I encountered this same issue today and could not find any solution online and stumbled upon your question. I solved it in a hacky way and am not sure how it will behave when the application scales.
I basically added one @EventPattern (@MessagePattern in your case) in the controller of the producer microservice itself. And I called the client.emit() function twice.
So essentially the first time it gets consumed by the function that is in the producer itself and the second emit actually goes to the actual consumer. This way only one POST call is sufficient.
Producer Controller:
@EventPattern('video-uploaded')
async test() {
return 1;
}
Producer client :
async publishEvent(data: VideosDto) {
this.client.emit('video-uploaded', data);
this.client.emit('video-uploaded', data);
}
Solution 3:[3]
I had same error and finally solve it today.
In my project, there is an api-gateway as a hybrid application to receive requests and pass data to other systems, every second request gives an error like below.
error: There is no matching message handler defined in the remote service.
Then I tried to remove the api-gateway hybrid application scope in the code below, the error is gone, hope this helps you out with this.
// api-gateway main.ts
const app = await NestFactory.create(AppModule);
// run as a hybrid app —? remove it
app.connectMicroservice({
transport: Transport.RMQ,
noACK: false,
options: {
urls: [`amqp://${rmqUser}:${rmqPassword}@127.0.0.1:5672`],
queue: 'main_queue',
queueOptions: {
durable: false,
},
},
});
// run hybrid app
await app.startAllMicroservices(); —? remove it
await app.listen(3000);
Solution 4:[4]
I've experienced the same error in my another project and after some research I've found out that problem is in the way of distributing messages in RabbitMQ - named round-robin. In my first project I've solved the issue by creating a second queue, in my second project I'm using the package @golevelup/nestjs-rabbitmq instead of default NestJS library, as it is much more configurable. I recommend reading this question
Sources
This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.
Source: Stack Overflow
Solution | Source |
---|---|
Solution 1 | molaro |
Solution 2 | Setanjan Roy |
Solution 3 | |
Solution 4 | Georgius17 |