"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
exports.JobQueue = void 0;
const uuid_1 = require("uuid");
/** @inheritdoc */
class JobQueue {
    /**
     * Creates a new JobQueue
     * @param jobListeners The listeners that will listen to jobs on this jobQueue
     * @param logger The logger that will be used to output events from the current job on this Queue
     */
    constructor(jobListeners, logger) {
        this.jobListeners = jobListeners;
        this.logger = logger;
        this.queue = [];
        this.currentJob = null;
    }
    /** @inheritdoc */
    addJob(request) {
        const id = (0, uuid_1.v7)();
        const job = {
            request: request,
            started_at: new Date(),
            capture_id: id
        };
        if (!this.currentJob) {
            this.currentJob = job;
            //kicks off async method
            const process = this.processJob(job);
            return [job, process];
        }
        else {
            this.queue.push(job);
            return [job, undefined];
        }
    }
    /** @inheritdoc */
    addListener(listenerInstance) {
        if (typeof listenerInstance.onJob === 'function') {
            this.jobListeners.add(listenerInstance.onJob.bind(listenerInstance));
        }
        else {
            throw new Error("Listener must implement an 'onJob(job: Job): Promise<void>' method.");
        }
    }
    /** @inheritdoc */
    getCurrentJob() {
        return this.currentJob;
    }
    /** @inheritdoc */
    getCount() {
        return (this.currentJob ? 1 : 0) + this.queue.length;
    }
    async processJob(job) {
        for (const listener of this.jobListeners) {
            try {
                this.logger.info(`evaluating ${listener.name}`);
                await listener(job);
            }
            catch (error) {
                job.error = error instanceof Error ? error.message : String(error);
                this.logger.error(`error processing job: ${error}`);
            }
        }
        this.currentJob = this.queue.shift() || null;
        if (this.currentJob) {
            await this.processJob(this.currentJob);
        }
    }
}
exports.JobQueue = JobQueue;
//# sourceMappingURL=job_queue.js.map