How to Use Queue in NestJS: Simple Guide with Examples
@nestjs/bull package which wraps BullMQ, a popular Redis-based queue library. Define queues with @Processor and @Process decorators to handle jobs asynchronously, enabling background task processing.Syntax
To use queues in NestJS, first import BullModule in your module with Redis connection options. Then create a processor class decorated with @Processor('queueName'). Inside it, use @Process('jobName') to define job handlers. Add jobs to the queue using queue.add('jobName', data).
BullModule.forRoot(): Configures Redis connection.BullModule.registerQueue(): Registers a named queue.@Processor('queueName'): Marks a class as a queue processor.@Process('jobName'): Handles specific jobs.queue.add(): Adds jobs to the queue.
import { Module } from '@nestjs/common'; import { BullModule, Processor, Process } from '@nestjs/bull'; import { Injectable } from '@nestjs/common'; import { Job } from 'bullmq'; @Module({ imports: [ BullModule.forRoot({ connection: { host: 'localhost', port: 6379 }, }), BullModule.registerQueue({ name: 'email' }), ], }) export class AppModule {} @Processor('email') @Injectable() export class EmailProcessor { @Process('send') async handleSendEmail(job: Job) { // job.data contains the payload console.log('Sending email to:', job.data.email); } }
Example
This example shows a NestJS module that sets up a queue named email and a processor that handles send jobs. The AppService adds a job to the queue, which the processor then logs to simulate sending an email.
import { Module, Injectable } from '@nestjs/common'; import { BullModule, Processor, Process, InjectQueue } from '@nestjs/bull'; import { Queue, Job } from 'bullmq'; @Module({ imports: [ BullModule.forRoot({ connection: { host: 'localhost', port: 6379 }, }), BullModule.registerQueue({ name: 'email' }), ], providers: [EmailProcessor, AppService], }) export class AppModule {} @Injectable() export class AppService { constructor(@InjectQueue('email') private emailQueue: Queue) {} async sendEmail(email: string) { await this.emailQueue.add('send', { email }); } } @Processor('email') export class EmailProcessor { @Process('send') async handleSendEmail(job: Job) { console.log(`Sending email to: ${job.data.email}`); } } // Usage example (e.g., in a controller or bootstrap): // const appService = new AppService(emailQueue); // appService.sendEmail('user@example.com');
Common Pitfalls
Common mistakes when using queues in NestJS include:
- Not running a Redis server or incorrect Redis connection settings, causing queue failures.
- Forgetting to register the queue with
BullModule.registerQueue(), so processors never receive jobs. - Not injecting the queue properly with
@InjectQueue()when adding jobs. - Using
@Process()without matching job names, so jobs are ignored. - Not handling errors inside processors, which can cause silent failures.
Always ensure Redis is running and connection details are correct. Match job names exactly between add() and @Process(). Use try-catch inside processors to handle errors gracefully.
/* Wrong: Missing queue registration and injection */ @Processor('email') export class EmailProcessor { @Process('send') async handleSendEmail(job: Job) { console.log(job.data.email); } } /* Right: Register queue and inject it properly */ import { Module, Injectable } from '@nestjs/common'; import { BullModule, InjectQueue } from '@nestjs/bull'; import { Queue } from 'bullmq'; @Module({ imports: [ BullModule.forRoot({ connection: { host: 'localhost', port: 6379 } }), BullModule.registerQueue({ name: 'email' }), ], }) export class AppModule {} @Injectable() export class AppService { constructor(@InjectQueue('email') private emailQueue: Queue) {} async sendEmail(email: string) { await this.emailQueue.add('send', { email }); } }
Quick Reference
Here is a quick summary of key queue usage in NestJS:
| Concept | Description |
|---|---|
| BullModule.forRoot() | Configure Redis connection for all queues |
| BullModule.registerQueue({ name }) | Register a named queue to use |
| @Processor('queueName') | Class decorator to handle jobs from a queue |
| @Process('jobName') | Method decorator to process specific jobs |
| @InjectQueue('queueName') | Inject queue instance to add jobs |
| queue.add('jobName', data) | Add a job with data to the queue |