UNPKG

@cavai/adonis-queue

Version:
97 lines (96 loc) 2.86 kB
import { DateTime } from 'luxon'; import SuperJSON from 'superjson'; export default class DatabaseDriver { config; #trx; #database; pollingDelay; constructor(config, database) { this.config = config; this.pollingDelay = config.pollingDelay || 2000; this.#database = database; } /** * Store job to database */ async store(path, payload, options) { const job = await this.#database .table(this.config.tableName) .insert({ class_path: path, payload: SuperJSON.serialize(payload), available_at: options?.availableAt || DateTime.now().toSQL({ includeOffset: false }), }) .returning('id'); return { id: job[0].id, }; } /** * Get next job from database */ async getNext() { this.#trx = await this.#database.transaction(); const job = await this.#trx .from(this.config.tableName) .where('available_at', '<', DateTime.now().toSQL({ includeOffset: false })) .where({ failed: false }) .forUpdate() .skipLocked() .first(); if (!job) { await this.#trx.commit(); return null; } return job; } /** * Get job from database by its ID */ getJob(id) { return this.#database .from(this.config.tableName) .where('available_at', '<', DateTime.now().toSQL({ includeOffset: false })) .where({ id: id }) .first(); } /** * Re-schedule job (update attempts and available_at) in Database */ async reSchedule(job, retryAfter) { if (!this.#trx) { throw new Error('Cannot reschedule job without an active transaction'); } await this.#trx .from(this.config.tableName) .where({ id: job.id }) .update({ attempts: job.attempts + 1, available_at: DateTime.now().plus({ seconds: retryAfter }), }); await this.#trx.commit(); } /** * Mark job as failed in database */ async markFailed(job) { if (!this.#trx) { throw new Error('Cannot mark job as failed without an active transaction'); } await this.#trx.from(this.config.tableName).where({ id: job.id }).update({ failed: true, attempts: job.attempts, }); await this.#trx.commit(); } /** * Remove job from database */ async remove(id) { if (!this.#trx) { throw new Error('Cannot remove job without an active transaction'); } await this.#trx.from(this.config.tableName).where({ id: id }).delete(); await this.#trx.commit(); } }