@nicnocquee/dataqueue 1.34.0 → 1.35.0-beta.20260224075710
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/ai/docs-content.json +23 -11
- package/ai/rules/advanced.md +77 -1
- package/ai/rules/basic.md +72 -3
- package/ai/rules/react-dashboard.md +5 -1
- package/ai/skills/dataqueue-advanced/SKILL.md +159 -0
- package/ai/skills/dataqueue-core/SKILL.md +107 -3
- package/ai/skills/dataqueue-react/SKILL.md +19 -7
- package/dist/index.cjs +937 -108
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +358 -11
- package/dist/index.d.ts +358 -11
- package/dist/index.js +937 -108
- package/dist/index.js.map +1 -1
- package/migrations/1781200000005_add_retry_config_to_job_queue.sql +17 -0
- package/migrations/1781200000006_add_output_to_job_queue.sql +3 -0
- package/package.json +1 -1
- package/src/backend.ts +36 -3
- package/src/backends/postgres.ts +344 -42
- package/src/backends/redis-scripts.ts +173 -8
- package/src/backends/redis.test.ts +668 -0
- package/src/backends/redis.ts +244 -15
- package/src/db-util.ts +1 -1
- package/src/index.test.ts +811 -12
- package/src/index.ts +106 -14
- package/src/processor.ts +133 -49
- package/src/queue.test.ts +477 -0
- package/src/queue.ts +20 -3
- package/src/supervisor.test.ts +340 -0
- package/src/supervisor.ts +177 -0
- package/src/types.ts +318 -3
package/src/types.ts
CHANGED
|
@@ -1,6 +1,33 @@
|
|
|
1
1
|
// Utility type for job type keys
|
|
2
2
|
export type JobType<PayloadMap> = keyof PayloadMap & string;
|
|
3
3
|
|
|
4
|
+
/**
|
|
5
|
+
* Abstract database client interface for transactional job creation.
|
|
6
|
+
* Compatible with `pg.Pool`, `pg.PoolClient`, `pg.Client`, or any object
|
|
7
|
+
* that exposes a `.query()` method matching the `pg` signature.
|
|
8
|
+
*/
|
|
9
|
+
export interface DatabaseClient {
|
|
10
|
+
query(
|
|
11
|
+
text: string,
|
|
12
|
+
values?: any[],
|
|
13
|
+
): Promise<{ rows: any[]; rowCount: number | null }>;
|
|
14
|
+
}
|
|
15
|
+
|
|
16
|
+
/**
|
|
17
|
+
* Options for `addJob()` beyond the job itself.
|
|
18
|
+
* Use `db` to insert the job within an existing database transaction.
|
|
19
|
+
*/
|
|
20
|
+
export interface AddJobOptions {
|
|
21
|
+
/**
|
|
22
|
+
* An external database client (e.g., a `pg.PoolClient` inside a transaction).
|
|
23
|
+
* When provided, the INSERT runs on this client instead of the internal pool,
|
|
24
|
+
* so the job is part of the caller's transaction.
|
|
25
|
+
*
|
|
26
|
+
* **PostgreSQL only.** Throws if used with the Redis backend.
|
|
27
|
+
*/
|
|
28
|
+
db?: DatabaseClient;
|
|
29
|
+
}
|
|
30
|
+
|
|
4
31
|
export interface JobOptions<PayloadMap, T extends JobType<PayloadMap>> {
|
|
5
32
|
jobType: T;
|
|
6
33
|
payload: PayloadMap[T];
|
|
@@ -73,6 +100,26 @@ export interface JobOptions<PayloadMap, T extends JobType<PayloadMap>> {
|
|
|
73
100
|
* Once a key exists, it cannot be reused until the job is cleaned up (via `cleanupOldJobs`).
|
|
74
101
|
*/
|
|
75
102
|
idempotencyKey?: string;
|
|
103
|
+
/**
|
|
104
|
+
* Base delay between retries in seconds. When `retryBackoff` is true (the default),
|
|
105
|
+
* this is the base for exponential backoff: `retryDelay * 2^attempts`.
|
|
106
|
+
* When `retryBackoff` is false, retries use this fixed delay.
|
|
107
|
+
* @default 60
|
|
108
|
+
*/
|
|
109
|
+
retryDelay?: number;
|
|
110
|
+
/**
|
|
111
|
+
* Whether to use exponential backoff for retries. When true, delay doubles
|
|
112
|
+
* with each attempt and includes jitter to prevent thundering herd.
|
|
113
|
+
* When false, a fixed `retryDelay` is used between every retry.
|
|
114
|
+
* @default true
|
|
115
|
+
*/
|
|
116
|
+
retryBackoff?: boolean;
|
|
117
|
+
/**
|
|
118
|
+
* Maximum delay between retries in seconds. Caps the exponential backoff
|
|
119
|
+
* so retries never wait longer than this value. Only meaningful when
|
|
120
|
+
* `retryBackoff` is true. No limit when omitted.
|
|
121
|
+
*/
|
|
122
|
+
retryDelayMax?: number;
|
|
76
123
|
}
|
|
77
124
|
|
|
78
125
|
/**
|
|
@@ -196,6 +243,23 @@ export interface JobRecord<PayloadMap, T extends JobType<PayloadMap>> {
|
|
|
196
243
|
* Updated by the handler via `ctx.setProgress(percent)`.
|
|
197
244
|
*/
|
|
198
245
|
progress?: number | null;
|
|
246
|
+
/**
|
|
247
|
+
* Handler output stored via `ctx.setOutput(data)` or by returning a value
|
|
248
|
+
* from the handler. `null` if no output has been stored.
|
|
249
|
+
*/
|
|
250
|
+
output?: unknown;
|
|
251
|
+
/**
|
|
252
|
+
* Base delay between retries in seconds, or null if using legacy default.
|
|
253
|
+
*/
|
|
254
|
+
retryDelay?: number | null;
|
|
255
|
+
/**
|
|
256
|
+
* Whether exponential backoff is enabled for retries, or null if using legacy default.
|
|
257
|
+
*/
|
|
258
|
+
retryBackoff?: boolean | null;
|
|
259
|
+
/**
|
|
260
|
+
* Maximum delay cap for retries in seconds, or null if no cap.
|
|
261
|
+
*/
|
|
262
|
+
retryDelayMax?: number | null;
|
|
199
263
|
}
|
|
200
264
|
|
|
201
265
|
/**
|
|
@@ -292,6 +356,17 @@ export interface JobContext {
|
|
|
292
356
|
* @throws If percent is outside the 0-100 range.
|
|
293
357
|
*/
|
|
294
358
|
setProgress: (percent: number) => Promise<void>;
|
|
359
|
+
|
|
360
|
+
/**
|
|
361
|
+
* Store an output/result for this job. The value is persisted to the database
|
|
362
|
+
* as JSONB and can be read by clients via `getJob()` or the React SDK's `useJob()` hook.
|
|
363
|
+
*
|
|
364
|
+
* Can be called multiple times — each call overwrites the previous value.
|
|
365
|
+
* If `setOutput()` is called, the handler's return value is ignored.
|
|
366
|
+
*
|
|
367
|
+
* @param data - Any JSON-serializable value to store as the job's output.
|
|
368
|
+
*/
|
|
369
|
+
setOutput: (data: unknown) => Promise<void>;
|
|
295
370
|
}
|
|
296
371
|
|
|
297
372
|
/**
|
|
@@ -380,7 +455,7 @@ export type JobHandler<PayloadMap, T extends keyof PayloadMap> = (
|
|
|
380
455
|
payload: PayloadMap[T],
|
|
381
456
|
signal: AbortSignal,
|
|
382
457
|
ctx: JobContext,
|
|
383
|
-
) => Promise<
|
|
458
|
+
) => Promise<unknown>;
|
|
384
459
|
|
|
385
460
|
export type JobHandlers<PayloadMap> = {
|
|
386
461
|
[K in keyof PayloadMap]: JobHandler<PayloadMap, K>;
|
|
@@ -452,6 +527,91 @@ export interface Processor {
|
|
|
452
527
|
start: () => Promise<number>;
|
|
453
528
|
}
|
|
454
529
|
|
|
530
|
+
export interface SupervisorOptions {
|
|
531
|
+
/**
|
|
532
|
+
* How often the maintenance loop runs, in milliseconds.
|
|
533
|
+
* @default 60000 (1 minute)
|
|
534
|
+
*/
|
|
535
|
+
intervalMs?: number;
|
|
536
|
+
/**
|
|
537
|
+
* Reclaim jobs stuck in `processing` longer than this many minutes.
|
|
538
|
+
* @default 10
|
|
539
|
+
*/
|
|
540
|
+
stuckJobsTimeoutMinutes?: number;
|
|
541
|
+
/**
|
|
542
|
+
* Auto-delete completed jobs older than this many days. Set to 0 to disable.
|
|
543
|
+
* @default 30
|
|
544
|
+
*/
|
|
545
|
+
cleanupJobsDaysToKeep?: number;
|
|
546
|
+
/**
|
|
547
|
+
* Auto-delete job events older than this many days. Set to 0 to disable.
|
|
548
|
+
* @default 30
|
|
549
|
+
*/
|
|
550
|
+
cleanupEventsDaysToKeep?: number;
|
|
551
|
+
/**
|
|
552
|
+
* Batch size for cleanup deletions.
|
|
553
|
+
* @default 1000
|
|
554
|
+
*/
|
|
555
|
+
cleanupBatchSize?: number;
|
|
556
|
+
/**
|
|
557
|
+
* Whether to reclaim stuck jobs each cycle.
|
|
558
|
+
* @default true
|
|
559
|
+
*/
|
|
560
|
+
reclaimStuckJobs?: boolean;
|
|
561
|
+
/**
|
|
562
|
+
* Whether to expire timed-out waitpoint tokens each cycle.
|
|
563
|
+
* @default true
|
|
564
|
+
*/
|
|
565
|
+
expireTimedOutTokens?: boolean;
|
|
566
|
+
/**
|
|
567
|
+
* Called when a maintenance task throws. One failure does not block other tasks.
|
|
568
|
+
* @default console.error
|
|
569
|
+
*/
|
|
570
|
+
onError?: (error: Error) => void;
|
|
571
|
+
/** Enable verbose logging. */
|
|
572
|
+
verbose?: boolean;
|
|
573
|
+
}
|
|
574
|
+
|
|
575
|
+
export interface SupervisorRunResult {
|
|
576
|
+
/** Number of stuck jobs reclaimed back to pending. */
|
|
577
|
+
reclaimedJobs: number;
|
|
578
|
+
/** Number of old completed jobs deleted. */
|
|
579
|
+
cleanedUpJobs: number;
|
|
580
|
+
/** Number of old job events deleted. */
|
|
581
|
+
cleanedUpEvents: number;
|
|
582
|
+
/** Number of timed-out waitpoint tokens expired. */
|
|
583
|
+
expiredTokens: number;
|
|
584
|
+
}
|
|
585
|
+
|
|
586
|
+
export interface Supervisor {
|
|
587
|
+
/**
|
|
588
|
+
* Run all maintenance tasks once and return the results.
|
|
589
|
+
* Ideal for serverless or cron-triggered invocations.
|
|
590
|
+
*/
|
|
591
|
+
start: () => Promise<SupervisorRunResult>;
|
|
592
|
+
/**
|
|
593
|
+
* Start the maintenance loop in the background.
|
|
594
|
+
* Runs every `intervalMs` milliseconds (default: 60 000).
|
|
595
|
+
* Call `stop()` or `stopAndDrain()` to halt the loop.
|
|
596
|
+
*/
|
|
597
|
+
startInBackground: () => void;
|
|
598
|
+
/**
|
|
599
|
+
* Stop the background maintenance loop immediately.
|
|
600
|
+
* Does not wait for an in-flight maintenance run to complete.
|
|
601
|
+
*/
|
|
602
|
+
stop: () => void;
|
|
603
|
+
/**
|
|
604
|
+
* Stop the background loop and wait for the current maintenance run
|
|
605
|
+
* (if any) to finish before resolving.
|
|
606
|
+
*
|
|
607
|
+
* @param timeoutMs - Maximum time to wait (default: 30 000 ms).
|
|
608
|
+
* If the run does not finish within this time the promise resolves anyway.
|
|
609
|
+
*/
|
|
610
|
+
stopAndDrain: (timeoutMs?: number) => Promise<void>;
|
|
611
|
+
/** Whether the background maintenance loop is currently running. */
|
|
612
|
+
isRunning: () => boolean;
|
|
613
|
+
}
|
|
614
|
+
|
|
455
615
|
export interface DatabaseSSLConfig {
|
|
456
616
|
/**
|
|
457
617
|
* CA certificate as PEM string or file path. If the value starts with 'file://', it will be loaded from file, otherwise treated as PEM string.
|
|
@@ -474,10 +634,13 @@ export interface DatabaseSSLConfig {
|
|
|
474
634
|
/**
|
|
475
635
|
* Configuration for PostgreSQL backend (default).
|
|
476
636
|
* Backward-compatible: omitting `backend` defaults to 'postgres'.
|
|
637
|
+
*
|
|
638
|
+
* Provide either `databaseConfig` (the library creates a pool) or `pool`
|
|
639
|
+
* (bring your own `pg.Pool`). At least one must be set.
|
|
477
640
|
*/
|
|
478
641
|
export interface PostgresJobQueueConfig {
|
|
479
642
|
backend?: 'postgres';
|
|
480
|
-
databaseConfig
|
|
643
|
+
databaseConfig?: {
|
|
481
644
|
connectionString?: string;
|
|
482
645
|
host?: string;
|
|
483
646
|
port?: number;
|
|
@@ -503,6 +666,11 @@ export interface PostgresJobQueueConfig {
|
|
|
503
666
|
*/
|
|
504
667
|
connectionTimeoutMillis?: number;
|
|
505
668
|
};
|
|
669
|
+
/**
|
|
670
|
+
* Bring your own `pg.Pool` instance. When provided, `databaseConfig` is
|
|
671
|
+
* ignored and the library will not close the pool on shutdown.
|
|
672
|
+
*/
|
|
673
|
+
pool?: import('pg').Pool;
|
|
506
674
|
verbose?: boolean;
|
|
507
675
|
}
|
|
508
676
|
|
|
@@ -518,10 +686,13 @@ export interface RedisTLSConfig {
|
|
|
518
686
|
|
|
519
687
|
/**
|
|
520
688
|
* Configuration for Redis backend.
|
|
689
|
+
*
|
|
690
|
+
* Provide either `redisConfig` (the library creates an ioredis client) or
|
|
691
|
+
* `client` (bring your own ioredis instance). At least one must be set.
|
|
521
692
|
*/
|
|
522
693
|
export interface RedisJobQueueConfig {
|
|
523
694
|
backend: 'redis';
|
|
524
|
-
redisConfig
|
|
695
|
+
redisConfig?: {
|
|
525
696
|
/** Redis URL (e.g. redis://localhost:6379) */
|
|
526
697
|
url?: string;
|
|
527
698
|
host?: string;
|
|
@@ -536,6 +707,17 @@ export interface RedisJobQueueConfig {
|
|
|
536
707
|
*/
|
|
537
708
|
keyPrefix?: string;
|
|
538
709
|
};
|
|
710
|
+
/**
|
|
711
|
+
* Bring your own ioredis client instance. When provided, `redisConfig` is
|
|
712
|
+
* ignored and the library will not close the client on shutdown.
|
|
713
|
+
* Use `keyPrefix` to set the key namespace (default: 'dq:').
|
|
714
|
+
*/
|
|
715
|
+
client?: unknown;
|
|
716
|
+
/**
|
|
717
|
+
* Key prefix when using an external `client`. Ignored when `redisConfig` is used
|
|
718
|
+
* (set `redisConfig.keyPrefix` instead). Default: 'dq:'.
|
|
719
|
+
*/
|
|
720
|
+
keyPrefix?: string;
|
|
539
721
|
verbose?: boolean;
|
|
540
722
|
}
|
|
541
723
|
|
|
@@ -592,6 +774,12 @@ export interface CronScheduleOptions<
|
|
|
592
774
|
* is still pending, processing, or waiting.
|
|
593
775
|
*/
|
|
594
776
|
allowOverlap?: boolean;
|
|
777
|
+
/** Base delay between retries in seconds for each job instance (default: 60). */
|
|
778
|
+
retryDelay?: number;
|
|
779
|
+
/** Whether to use exponential backoff for retries (default: true). */
|
|
780
|
+
retryBackoff?: boolean;
|
|
781
|
+
/** Maximum delay cap for retries in seconds. */
|
|
782
|
+
retryDelayMax?: number;
|
|
595
783
|
}
|
|
596
784
|
|
|
597
785
|
/**
|
|
@@ -616,6 +804,9 @@ export interface CronScheduleRecord {
|
|
|
616
804
|
nextRunAt: Date | null;
|
|
617
805
|
createdAt: Date;
|
|
618
806
|
updatedAt: Date;
|
|
807
|
+
retryDelay: number | null;
|
|
808
|
+
retryBackoff: boolean | null;
|
|
809
|
+
retryDelayMax: number | null;
|
|
619
810
|
}
|
|
620
811
|
|
|
621
812
|
/**
|
|
@@ -632,15 +823,87 @@ export interface EditCronScheduleOptions {
|
|
|
632
823
|
tags?: string[] | null;
|
|
633
824
|
timezone?: string;
|
|
634
825
|
allowOverlap?: boolean;
|
|
826
|
+
retryDelay?: number | null;
|
|
827
|
+
retryBackoff?: boolean | null;
|
|
828
|
+
retryDelayMax?: number | null;
|
|
635
829
|
}
|
|
636
830
|
|
|
831
|
+
// ── Event hooks ──────────────────────────────────────────────────────
|
|
832
|
+
|
|
833
|
+
/**
|
|
834
|
+
* Payload types for each event emitted by the job queue.
|
|
835
|
+
*/
|
|
836
|
+
export interface QueueEventMap {
|
|
837
|
+
/** Fired after a job is successfully added to the queue. */
|
|
838
|
+
'job:added': { jobId: number; jobType: string };
|
|
839
|
+
/** Fired when a processor claims a job and begins executing its handler. */
|
|
840
|
+
'job:processing': { jobId: number; jobType: string };
|
|
841
|
+
/** Fired when a job handler completes successfully. */
|
|
842
|
+
'job:completed': { jobId: number; jobType: string };
|
|
843
|
+
/** Fired when a job handler fails. `willRetry` indicates whether the job will be retried. */
|
|
844
|
+
'job:failed': {
|
|
845
|
+
jobId: number;
|
|
846
|
+
jobType: string;
|
|
847
|
+
error: Error;
|
|
848
|
+
willRetry: boolean;
|
|
849
|
+
};
|
|
850
|
+
/** Fired after a job is cancelled via `cancelJob()`. */
|
|
851
|
+
'job:cancelled': { jobId: number };
|
|
852
|
+
/** Fired after a failed job is manually retried via `retryJob()`. */
|
|
853
|
+
'job:retried': { jobId: number };
|
|
854
|
+
/** Fired when a job enters the `waiting` state (via `ctx.waitFor`, `ctx.waitUntil`, or `ctx.waitForToken`). */
|
|
855
|
+
'job:waiting': { jobId: number; jobType: string };
|
|
856
|
+
/** Fired when a job reports progress via `ctx.setProgress()`. */
|
|
857
|
+
'job:progress': { jobId: number; progress: number };
|
|
858
|
+
/** Fired when a job stores output via `ctx.setOutput()`. */
|
|
859
|
+
'job:output': { jobId: number; output: unknown };
|
|
860
|
+
/** Fired on internal errors from the processor or supervisor. */
|
|
861
|
+
error: Error;
|
|
862
|
+
}
|
|
863
|
+
|
|
864
|
+
/** Union of all event names supported by the job queue. */
|
|
865
|
+
export type QueueEventName = keyof QueueEventMap;
|
|
866
|
+
|
|
867
|
+
/**
|
|
868
|
+
* Callback type for `emit`. Used internally to pass the emitter
|
|
869
|
+
* from `initJobQueue` into the processor and supervisor.
|
|
870
|
+
*/
|
|
871
|
+
export type QueueEmitFn = <K extends QueueEventName>(
|
|
872
|
+
event: K,
|
|
873
|
+
data: QueueEventMap[K],
|
|
874
|
+
) => void;
|
|
875
|
+
|
|
637
876
|
export interface JobQueue<PayloadMap> {
|
|
638
877
|
/**
|
|
639
878
|
* Add a job to the job queue.
|
|
879
|
+
*
|
|
880
|
+
* @param job - The job to enqueue.
|
|
881
|
+
* @param options - Optional. Pass `{ db }` with an external database client
|
|
882
|
+
* to insert the job within an existing transaction (PostgreSQL only).
|
|
640
883
|
*/
|
|
641
884
|
addJob: <T extends JobType<PayloadMap>>(
|
|
642
885
|
job: JobOptions<PayloadMap, T>,
|
|
886
|
+
options?: AddJobOptions,
|
|
643
887
|
) => Promise<number>;
|
|
888
|
+
/**
|
|
889
|
+
* Add multiple jobs to the queue in a single operation.
|
|
890
|
+
*
|
|
891
|
+
* More efficient than calling `addJob` in a loop because it batches the
|
|
892
|
+
* INSERT into a single database round-trip (PostgreSQL) or a single
|
|
893
|
+
* atomic Lua script (Redis).
|
|
894
|
+
*
|
|
895
|
+
* Returns an array of job IDs in the same order as the input array.
|
|
896
|
+
* Each job may independently have an `idempotencyKey`; duplicates
|
|
897
|
+
* resolve to the existing job's ID without creating a new row.
|
|
898
|
+
*
|
|
899
|
+
* @param jobs - Array of jobs to enqueue.
|
|
900
|
+
* @param options - Optional. Pass `{ db }` with an external database client
|
|
901
|
+
* to insert the jobs within an existing transaction (PostgreSQL only).
|
|
902
|
+
*/
|
|
903
|
+
addJobs: <T extends JobType<PayloadMap>>(
|
|
904
|
+
jobs: JobOptions<PayloadMap, T>[],
|
|
905
|
+
options?: AddJobOptions,
|
|
906
|
+
) => Promise<number[]>;
|
|
644
907
|
/**
|
|
645
908
|
* Get a job by its ID.
|
|
646
909
|
*/
|
|
@@ -795,6 +1058,13 @@ export interface JobQueue<PayloadMap> {
|
|
|
795
1058
|
options?: ProcessorOptions,
|
|
796
1059
|
) => Processor;
|
|
797
1060
|
|
|
1061
|
+
/**
|
|
1062
|
+
* Create a background supervisor that automatically reclaims stuck jobs,
|
|
1063
|
+
* cleans up old completed jobs/events, and expires timed-out waitpoint
|
|
1064
|
+
* tokens on a configurable interval.
|
|
1065
|
+
*/
|
|
1066
|
+
createSupervisor: (options?: SupervisorOptions) => Supervisor;
|
|
1067
|
+
|
|
798
1068
|
/**
|
|
799
1069
|
* Get the job events for a job.
|
|
800
1070
|
*/
|
|
@@ -898,6 +1168,51 @@ export interface JobQueue<PayloadMap> {
|
|
|
898
1168
|
*/
|
|
899
1169
|
enqueueDueCronJobs: () => Promise<number>;
|
|
900
1170
|
|
|
1171
|
+
// ── Event hooks ───────────────────────────────────────────────────────
|
|
1172
|
+
|
|
1173
|
+
/**
|
|
1174
|
+
* Register a listener for a queue event. The listener is called every
|
|
1175
|
+
* time the event fires. Works identically with both PostgreSQL and Redis.
|
|
1176
|
+
*
|
|
1177
|
+
* @param event - The event name (e.g. `'job:completed'`, `'error'`).
|
|
1178
|
+
* @param listener - Callback receiving the event payload.
|
|
1179
|
+
*/
|
|
1180
|
+
on: <K extends QueueEventName>(
|
|
1181
|
+
event: K,
|
|
1182
|
+
listener: (data: QueueEventMap[K]) => void,
|
|
1183
|
+
) => void;
|
|
1184
|
+
|
|
1185
|
+
/**
|
|
1186
|
+
* Register a one-time listener. The listener is automatically removed
|
|
1187
|
+
* after it fires once.
|
|
1188
|
+
*
|
|
1189
|
+
* @param event - The event name.
|
|
1190
|
+
* @param listener - Callback receiving the event payload.
|
|
1191
|
+
*/
|
|
1192
|
+
once: <K extends QueueEventName>(
|
|
1193
|
+
event: K,
|
|
1194
|
+
listener: (data: QueueEventMap[K]) => void,
|
|
1195
|
+
) => void;
|
|
1196
|
+
|
|
1197
|
+
/**
|
|
1198
|
+
* Remove a previously registered listener.
|
|
1199
|
+
*
|
|
1200
|
+
* @param event - The event name.
|
|
1201
|
+
* @param listener - The exact function reference passed to `on` or `once`.
|
|
1202
|
+
*/
|
|
1203
|
+
off: <K extends QueueEventName>(
|
|
1204
|
+
event: K,
|
|
1205
|
+
listener: (data: QueueEventMap[K]) => void,
|
|
1206
|
+
) => void;
|
|
1207
|
+
|
|
1208
|
+
/**
|
|
1209
|
+
* Remove all listeners for a specific event, or all listeners for
|
|
1210
|
+
* all events when called without arguments.
|
|
1211
|
+
*
|
|
1212
|
+
* @param event - Optional event name. If omitted, removes everything.
|
|
1213
|
+
*/
|
|
1214
|
+
removeAllListeners: (event?: QueueEventName) => void;
|
|
1215
|
+
|
|
901
1216
|
// ── Advanced access ───────────────────────────────────────────────────
|
|
902
1217
|
|
|
903
1218
|
/**
|