{"id":10383,"library":"bull","title":"Bull Job Queue","description":"Bull is a battle-tested, Redis-based job queue library for Node.js, designed for reliability and atomic operations. It provides a robust system for managing background jobs, handling retries, delays, and concurrent processing. The current stable version is 4.16.5. While regular bug fixes are released, Bull is currently in maintenance mode; new features are primarily being developed in BullMQ, a modern TypeScript rewrite.","status":"maintenance","version":"4.16.5","language":"javascript","source_language":"en","source_url":"git://github.com/OptimalBits/bull","tags":["javascript","job","queue","task","parallel","typescript"],"install":[{"cmd":"npm install bull","lang":"bash","label":"npm"},{"cmd":"yarn add bull","lang":"bash","label":"yarn"},{"cmd":"pnpm add bull","lang":"bash","label":"pnpm"}],"dependencies":[],"imports":[{"note":"ESM is recommended for modern Node.js and TypeScript projects.","symbol":"Queue","correct":"import { Queue } from 'bull';"},{"note":"CommonJS is also fully supported.","symbol":"Queue","correct":"const { Queue } = require('bull');"}],"quickstart":{"code":"import { Queue } from 'bull';\n\nconst REDIS_URL = process.env.REDIS_URL ?? 'redis://127.0.0.1:6379';\nconst myQueue = new Queue('my-first-queue', REDIS_URL);\n\n// Add a job to the queue\nasync function addJob() {\n  const job = await myQueue.add({ foo: 'bar' });\n  console.log(`Job ${job.id} added.`);\n}\n\n// Process jobs from the queue\nmyQueue.process(async (job) => {\n  console.log(`Processing job ${job.id} with data:`, job.data);\n  // Simulate async work\n  await new Promise(resolve => setTimeout(resolve, 1000));\n  console.log(`Job ${job.id} completed.`);\n  return { status: 'success', processedAt: new Date() };\n});\n\n// Listen for global completed event (optional)\nmyQueue.on('global:completed', (jobId, result) => {\n  console.log(`Job ${jobId} completed globally with result:`, JSON.parse(result));\n});\n\n// Call addJob to demonstrate\naddJob().catch(console.error);\n","lang":"typescript","description":"Demonstrates creating a Bull queue, adding a job to it, and setting up a worker to process jobs from that queue. It also shows a basic event listener for job completion."},"warnings":[{"fix":"For new projects, evaluate BullMQ. For existing Bull projects, continue with caution, knowing feature development is frozen.","message":"Bull is currently in maintenance mode, receiving only bug fixes. For new features or if starting a new project, consider using BullMQ, which is a modern rewrite in TypeScript.","severity":"gotcha","affected_versions":">=4.0.0"},{"fix":"Ensure your Redis server is running and accessible from your application. Verify the Redis connection string (host, port, password) is correct. Check firewall rules if applicable.","message":"Bull requires a running Redis instance to function. Connection issues (e.g., `ECONNREFUSED`) are common if Redis is not accessible.","severity":"gotcha","affected_versions":">=1.0.0"},{"fix":"Ensure you have at least one worker process running `queue.process(callback)` for each queue you intend to process jobs from. If using job types, ensure a handler exists for each type.","message":"Jobs added to a queue will not be processed unless a worker (a call to `queue.process()`) is actively listening for jobs on that queue.","severity":"gotcha","affected_versions":">=1.0.0"},{"fix":"Pass only JSON-serializable data. For complex objects, convert them to a primitive representation before adding the job and reconstruct them within the worker, or store large/complex data externally and pass a reference (e.g., ID) in the job data.","message":"Job data stored in Bull is JSON-serialized. Complex objects (e.g., Date objects, custom class instances, functions) will lose their type or methods when serialized and deserialized.","severity":"gotcha","affected_versions":">=1.0.0"},{"fix":"Configure Redis persistence (e.g., `appendonly yes` for AOF or `save` directives for RDB snapshots) to match your data durability requirements. Consult the Redis documentation for appropriate settings.","message":"By default, Redis may not persist data to disk immediately. If your Redis server crashes without proper persistence configured (e.g., AOF or RDB snapshots), pending or delayed jobs might be lost.","severity":"gotcha","affected_versions":">=1.0.0"}],"env_vars":null,"last_verified":"2026-04-18T00:00:00.000Z","next_check":"2026-07-17T00:00:00.000Z","problems":[{"fix":"Start your Redis server, check the Redis connection string (host, port) in your Bull configuration, and verify network access or firewall settings.","cause":"Bull failed to connect to the Redis server because it's not running or is inaccessible.","error":"Error: connect ECONNREFUSED 127.0.0.1:6379"},{"fix":"Ensure that your worker process calls `queue.process()` with a handler for every job type you expect to process. If you don't specify a type when adding a job, the default type is used, which also requires a handler.","cause":"A worker attempted to process a job type for which no `queue.process('jobType', ...)` handler has been defined.","error":"UnhandledPromiseRejectionWarning: Error: Missing process handler for job type [jobType]"},{"fix":"Verify that the job ID is correct and that the job still exists in the queue (i.e., it hasn't been completed, failed, or removed) before attempting to interact with it.","cause":"An operation (e.g., `getJob`, `remove`, `promote`) was attempted with a job ID that does not exist or is no longer valid in the queue.","error":"Error: This is not a valid Job ID"},{"fix":"Increase the `maxmemory` setting in your Redis configuration, reduce the amount of data stored in Redis, or scale your Redis instance. Consider offloading large job payloads to external storage.","cause":"The Redis server has reached its configured `maxmemory` limit, preventing further data writes.","error":"Error: Command failed: OOM command not allowed when used memory > 'maxmemory'."}],"ecosystem":"npm"}