or run

npx @tessl/cli init
Log in

Version

Tile

Overview

Evals

Files

docs

event-system.mdindex.mdjob-creation.mdjob-processing.mdjob-state.mdqueue-management.mdqueue-monitoring.mdrepeatable-jobs.mdutils.md
tile.json

job-creation.mddocs/

Job Creation and Management

Add jobs to queues with various options, bulk operations, and lifecycle management.

Capabilities

Basic Job Creation

Add jobs to the queue with data and optional configuration.

/**
 * Add an anonymous job to the queue
 * @param data - Job payload data
 * @param opts - Job configuration options
 * @returns Promise that resolves to the created Job instance
 */
add(data: any, opts?: JobOptions): Promise<Job>;

/**
 * Add a named job to the queue
 * @param name - Job name/type identifier
 * @param data - Job payload data  
 * @param opts - Job configuration options
 * @returns Promise that resolves to the created Job instance
 */
add(name: string, data: any, opts?: JobOptions): Promise<Job>;

Usage Examples:

const Queue = require('bull');
const emailQueue = new Queue('email processing');

// Add anonymous job
const job1 = await emailQueue.add({
  email: 'user@example.com',
  subject: 'Welcome!',
  body: 'Welcome to our service'
});

// Add named job
const job2 = await emailQueue.add('welcome-email', {
  email: 'user@example.com', 
  name: 'John Doe'
});

console.log(`Created job ${job1.id}`);
console.log(`Created job ${job2.id} with name: ${job2.name}`);

Job Options Configuration

Configure job behavior with comprehensive options.

interface JobOptions {
  /** Job priority (1 = highest, higher numbers = lower priority) */
  priority?: number;
  /** Delay before job becomes available for processing (milliseconds) */
  delay?: number;
  /** Number of attempts before job fails permanently */
  attempts?: number;
  /** Repeat job according to schedule */
  repeat?: RepeatOptions;
  /** Backoff strategy for retries */
  backoff?: number | BackoffOptions;
  /** Add job to front of queue (LIFO) instead of back (FIFO) */
  lifo?: boolean;
  /** Job timeout in milliseconds */
  timeout?: number;
  /** Custom job ID (must be unique) */
  jobId?: string | number;
  /** Remove job when completed (boolean, number of jobs to keep, or options) */
  removeOnComplete?: boolean | number | KeepJobsOptions;
  /** Remove job when failed (boolean, number of jobs to keep, or options) */
  removeOnFail?: boolean | number | KeepJobsOptions;
  /** Debounce options to prevent duplicate jobs */
  debounce?: DebounceOptions;
  /** Limit stack trace lines recorded on failure */
  stackTraceLimit?: number;
  /** Prevent JSON parsing of job data */
  preventParsingData?: boolean;
}

interface KeepJobsOptions {
  /** Maximum age in seconds for jobs to keep */
  age?: number;
  /** Maximum number of jobs to keep */
  count?: number;
}

interface DebounceOptions {
  /** Debounce identifier */
  id: string;
  /** Time to live in milliseconds */
  ttl?: number;
}

interface BackoffOptions {
  /** Backoff type ('fixed' or 'exponential') */
  type: string;
  /** Base delay in milliseconds */
  delay?: number;
  /** Additional options for custom strategies */
  options?: any;
}

Usage Examples:

// Job with priority and retry configuration
const importantJob = await emailQueue.add('urgent-email', {
  email: 'ceo@company.com',
  subject: 'Critical Alert'
}, {
  priority: 1,           // High priority
  attempts: 5,           // Retry up to 5 times
  backoff: {
    type: 'exponential',
    delay: 2000
  }
});

// Delayed job
const delayedJob = await emailQueue.add('scheduled-email', {
  email: 'user@example.com',
  subject: 'Reminder'
}, {
  delay: 60000,          // Execute in 1 minute
  attempts: 3
});

// Job with cleanup settings
const tempJob = await emailQueue.add('temp-task', { data: 'temp' }, {
  removeOnComplete: 5,   // Keep only 5 completed jobs
  removeOnFail: 3,       // Keep only 3 failed jobs
  timeout: 30000         // 30 second timeout
});

// Job with custom ID and debouncing
const uniqueJob = await emailQueue.add('user-notification', {
  userId: 123,
  message: 'Update available'
}, {
  jobId: 'user-123-notification',
  debounce: {
    id: 'user-123-notifications',
    ttl: 5000  // Prevent duplicate notifications for 5 seconds
  }
});

Bulk Job Creation

Add multiple jobs efficiently in a single operation.

/**
 * Add multiple jobs to the queue in bulk
 * @param jobs - Array of job definitions
 * @returns Promise that resolves to array of created Job instances
 */
addBulk(jobs: Array<{
  name?: string;
  data: any;
  opts?: Omit<JobOptions, 'repeat'>;  // repeat not supported in bulk
}>): Promise<Job[]>;

Usage Examples:

// Add multiple jobs at once
const users = [
  { id: 1, email: 'user1@example.com', name: 'Alice' },
  { id: 2, email: 'user2@example.com', name: 'Bob' },
  { id: 3, email: 'user3@example.com', name: 'Charlie' }
];

const bulkJobs = await emailQueue.addBulk(
  users.map(user => ({
    name: 'welcome-email',
    data: user,
    opts: {
      attempts: 3,
      removeOnComplete: 10
    }
  }))
);

console.log(`Created ${bulkJobs.length} jobs`);

// Mixed job types in bulk
const mixedJobs = await taskQueue.addBulk([
  {
    name: 'send-email',
    data: { email: 'user@example.com' },
    opts: { priority: 1 }
  },
  {
    name: 'generate-report', 
    data: { reportId: 'R123' },
    opts: { attempts: 5 }
  },
  {
    data: { task: 'cleanup' },  // Anonymous job
    opts: { delay: 5000 }
  }
]);

Job Retrieval

Get jobs from the queue by ID or retrieve jobs in different states.

/**
 * Get a specific job by ID
 * @param jobId - Job identifier
 * @returns Promise that resolves to Job instance or null if not found
 */
getJob(jobId: string | number): Promise<Job | null>;

/**
 * Get next job to be processed (internal use)
 * @returns Promise that resolves to next Job or undefined
 */
getNextJob(): Promise<Job | undefined>;

Usage Examples:

// Get job by ID
const job = await emailQueue.getJob(123);
if (job) {
  console.log(`Job ${job.id} status:`, await job.getState());
  console.log('Job data:', job.data);
} else {
  console.log('Job not found');
}

// Check job after creation
const newJob = await emailQueue.add('test', { message: 'hello' });
const retrievedJob = await emailQueue.getJob(newJob.id);
console.log('Jobs match:', newJob.id === retrievedJob.id);

Job Pattern Removal

Remove jobs matching specific patterns.

/**
 * Remove all jobs matching a Redis glob pattern
 * @param pattern - Redis glob pattern to match job IDs
 * @returns Promise that resolves when matching jobs are removed
 */
removeJobs(pattern: string): Promise<void>;

Usage Examples:

// Remove jobs with IDs matching pattern
await emailQueue.removeJobs('user-123-*');  // Remove all jobs for user 123
await emailQueue.removeJobs('temp-*');       // Remove all temporary jobs
await emailQueue.removeJobs('*-failed');     // Remove jobs ending with '-failed'

// Remove specific job types (if using job IDs with patterns)
await emailQueue.removeJobs('email-*');     // Remove all email jobs

Count Operations

Get counts of jobs in various states.

/**
 * Get total number of jobs waiting or paused
 * @returns Promise that resolves to job count
 */
count(): Promise<number>;

/**
 * Get counts by priority levels
 * @param priorities - Array of priority numbers to count
 * @returns Promise that resolves to object with priority counts
 */
getCountsPerPriority(priorities: number[]): Promise<{ [priority: string]: number }>;

Usage Examples:

// Get total waiting job count
const waitingCount = await emailQueue.count();
console.log(`Jobs waiting: ${waitingCount}`);

// Get counts by priority
const priorityCounts = await emailQueue.getCountsPerPriority([1, 2, 3, 4, 5]);
console.log('Priority counts:', priorityCounts);
// Output: { '1': 5, '2': 12, '3': 8, '4': 20, '5': 3 }

Job Creation Best Practices

// Example of robust job creation with best practices
async function createEmailJob(emailData, options = {}) {
  // Validate required data
  if (!emailData.email || !emailData.subject) {
    throw new Error('Email and subject are required');
  }
  
  // Set sensible defaults
  const jobOptions = {
    attempts: 3,
    backoff: {
      type: 'exponential',
      delay: 1000
    },
    removeOnComplete: 100,  // Keep last 100 completed jobs
    removeOnFail: 50,       // Keep last 50 failed jobs
    timeout: 30000,         // 30 second timeout
    ...options
  };
  
  // Create job with error handling
  try {
    const job = await emailQueue.add('send-email', emailData, jobOptions);
    
    console.log(`Created email job ${job.id} for ${emailData.email}`);
    
    return job;
  } catch (error) {
    console.error('Failed to create email job:', error);
    throw error;
  }
}

// Usage
const job = await createEmailJob({
  email: 'user@example.com',
  subject: 'Welcome',
  body: 'Welcome to our service!'
}, {
  priority: 2,
  delay: 5000  // Send in 5 seconds
});

Advanced Job Configuration Examples

// High-priority job with custom backoff
const criticalJob = await taskQueue.add('critical-task', {
  action: 'process_payment',
  paymentId: 'pay_123'
}, {
  priority: 1,
  attempts: 10,
  backoff: {
    type: 'custom',
    delay: 1000,
    options: {
      multiplier: 1.5,
      maxDelay: 30000
    }
  },
  timeout: 60000,
  removeOnComplete: false,  // Never remove completed critical jobs
  removeOnFail: false       // Never remove failed critical jobs
});

// Batch processing job
const batchJob = await taskQueue.add('batch-process', {
  items: largeDataSet,
  batchSize: 100
}, {
  attempts: 1,              // Don't retry batch jobs
  timeout: 300000,          // 5 minute timeout
  removeOnComplete: 1,      // Remove immediately after completion
  lifo: false               // Process in order (FIFO)
});

// Temporary job with auto-cleanup
const tempJob = await taskQueue.add('temp-analysis', {
  data: temporaryData
}, {
  attempts: 2,
  removeOnComplete: true,   // Remove immediately when done
  removeOnFail: true,       // Remove immediately if failed
  stackTraceLimit: 5        // Limit error stack trace
});