0
0
NestJSframework~5 mins

Bull queue integration in NestJS

Choose your learning style9 modes available
Introduction

Bull queue helps your NestJS app handle tasks in the background. It makes your app faster by doing heavy work later.

You want to send emails without making users wait.
You need to process images or files after upload.
You want to retry failed tasks automatically.
You want to schedule jobs to run later or repeatedly.
Syntax
NestJS
import { Processor, Process } from '@nestjs/bull';
import { Job } from 'bull';

@Processor('queueName')
export class QueueProcessor {
  @Process('jobName')
  async handleJob(job: Job<any>) {
    // job.data contains the data sent to the queue
    // Your job logic here
  }
}

@Processor('queueName') marks the class to handle jobs from a named queue.

@Process('jobName') marks the method to handle a specific job type.

Examples
This example processes an email sending job with email address data.
NestJS
import { Processor, Process } from '@nestjs/bull';
import { Job } from 'bull';

@Processor('email')
export class EmailProcessor {
  @Process('sendEmail')
  async sendEmailJob(job: Job<{ email: string }>) {
    console.log(`Sending email to ${job.data.email}`);
  }
}
This example shows handling a job with a check for missing data.
NestJS
import { Processor, Process } from '@nestjs/bull';
import { Job } from 'bull';

@Processor('image')
export class ImageProcessor {
  @Process('resize')
  async resizeImage(job: Job<{ imagePath: string }>) {
    if (!job.data.imagePath) {
      throw new Error('No image path provided');
    }
    console.log(`Resizing image at ${job.data.imagePath}`);
  }
}
This example handles a job that might have no data.
NestJS
import { Processor, Process } from '@nestjs/bull';
import { Job } from 'bull';

@Processor('emptyQueue')
export class EmptyProcessor {
  @Process('emptyJob')
  async handleEmpty(job: Job) {
    console.log('Job received but no data');
  }
}
Sample Program

This complete NestJS app sets up Bull with Redis, creates an email queue, and processes a sendEmail job. It adds a job with an email address and prints a message when processing.

NestJS
import { Module } from '@nestjs/common';
import { BullModule } from '@nestjs/bull';
import { Processor, Process } from '@nestjs/bull';
import { Job } from 'bull';

@Processor('email')
export class EmailProcessor {
  @Process('sendEmail')
  async sendEmailJob(job: Job<{ email: string }>) {
    console.log(`Sending email to ${job.data.email}`);
  }
}

@Module({
  imports: [
    BullModule.forRoot({
      redis: {
        host: 'localhost',
        port: 6379
      }
    }),
    BullModule.registerQueue({ name: 'email' })
  ],
  providers: [EmailProcessor]
})
export class AppModule {}

// Simulate adding a job to the queue
import { NestFactory } from '@nestjs/core';
import { Queue } from 'bull';
import { InjectQueue } from '@nestjs/bull';

async function bootstrap() {
  const app = await NestFactory.createApplicationContext(AppModule);
  const emailQueue = app.get<Queue>('BullQueue_email');
  await emailQueue.add('sendEmail', { email: 'user@example.com' });
  // Wait a moment to let the processor print
  setTimeout(() => app.close(), 1000);
}

bootstrap();
OutputSuccess
Important Notes

Time complexity: Adding and processing jobs is usually fast, O(1) for queue operations.

Space complexity: Depends on the number and size of jobs stored in Redis.

Common mistake: Forgetting to register the queue in the module or missing Redis connection causes errors.

Use Bull queues when you want to do work outside the main request flow, like sending emails or processing files.

Summary

Bull queues let NestJS apps handle tasks in the background.

Use @Processor and @Process decorators to define job handlers.

Register queues and connect to Redis in your module to use Bull.