@fedify/amqp 2.0.0-dev.1593 → 2.0.0-dev.1641
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/deno.json +2 -1
- package/dist/_virtual/rolldown_runtime.cjs +30 -0
- package/dist/mod.cjs +3 -0
- package/dist/mod.d.cts +2 -0
- package/dist/mq.cjs +121 -0
- package/dist/mq.d.cts +72 -0
- package/package.json +15 -5
- package/tsdown.config.ts +1 -0
package/deno.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@fedify/amqp",
|
|
3
|
-
"version": "2.0.0-dev.
|
|
3
|
+
"version": "2.0.0-dev.1641+6b0c942c",
|
|
4
4
|
"license": "MIT",
|
|
5
5
|
"exports": {
|
|
6
6
|
".": "./src/mod.ts",
|
|
@@ -11,6 +11,7 @@
|
|
|
11
11
|
},
|
|
12
12
|
"exclude": [
|
|
13
13
|
".github",
|
|
14
|
+
"dist",
|
|
14
15
|
"node_modules",
|
|
15
16
|
"npm",
|
|
16
17
|
"pnpm-lock.yaml"
|
|
@@ -0,0 +1,30 @@
|
|
|
1
|
+
//#region rolldown:runtime
|
|
2
|
+
var __create = Object.create;
|
|
3
|
+
var __defProp = Object.defineProperty;
|
|
4
|
+
var __getOwnPropDesc = Object.getOwnPropertyDescriptor;
|
|
5
|
+
var __getOwnPropNames = Object.getOwnPropertyNames;
|
|
6
|
+
var __getProtoOf = Object.getPrototypeOf;
|
|
7
|
+
var __hasOwnProp = Object.prototype.hasOwnProperty;
|
|
8
|
+
var __copyProps = (to, from, except, desc) => {
|
|
9
|
+
if (from && typeof from === "object" || typeof from === "function") for (var keys = __getOwnPropNames(from), i = 0, n = keys.length, key; i < n; i++) {
|
|
10
|
+
key = keys[i];
|
|
11
|
+
if (!__hasOwnProp.call(to, key) && key !== except) __defProp(to, key, {
|
|
12
|
+
get: ((k) => from[k]).bind(null, key),
|
|
13
|
+
enumerable: !(desc = __getOwnPropDesc(from, key)) || desc.enumerable
|
|
14
|
+
});
|
|
15
|
+
}
|
|
16
|
+
return to;
|
|
17
|
+
};
|
|
18
|
+
var __toESM = (mod, isNodeMode, target) => (target = mod != null ? __create(__getProtoOf(mod)) : {}, __copyProps(isNodeMode || !mod || !mod.__esModule ? __defProp(target, "default", {
|
|
19
|
+
value: mod,
|
|
20
|
+
enumerable: true
|
|
21
|
+
}) : target, mod));
|
|
22
|
+
|
|
23
|
+
//#endregion
|
|
24
|
+
|
|
25
|
+
Object.defineProperty(exports, '__toESM', {
|
|
26
|
+
enumerable: true,
|
|
27
|
+
get: function () {
|
|
28
|
+
return __toESM;
|
|
29
|
+
}
|
|
30
|
+
});
|
package/dist/mod.cjs
ADDED
package/dist/mod.d.cts
ADDED
package/dist/mq.cjs
ADDED
|
@@ -0,0 +1,121 @@
|
|
|
1
|
+
const require_rolldown_runtime = require('./_virtual/rolldown_runtime.cjs');
|
|
2
|
+
const node_buffer = require_rolldown_runtime.__toESM(require("node:buffer"));
|
|
3
|
+
|
|
4
|
+
//#region src/mq.ts
|
|
5
|
+
/**
|
|
6
|
+
* A message queue that uses AMQP.
|
|
7
|
+
*
|
|
8
|
+
* @example
|
|
9
|
+
* ``` typescript
|
|
10
|
+
* import { createFederation } from "@fedify/fedify";
|
|
11
|
+
* import { AmqpMessageQueue } from "@fedify/amqp";
|
|
12
|
+
* import { connect } from "amqplib";
|
|
13
|
+
*
|
|
14
|
+
* const federation = createFederation({
|
|
15
|
+
* queue: new AmqpMessageQueue(await connect("amqp://localhost")),
|
|
16
|
+
* // ... other configurations
|
|
17
|
+
* });
|
|
18
|
+
* ```
|
|
19
|
+
*/
|
|
20
|
+
var AmqpMessageQueue = class {
|
|
21
|
+
#connection;
|
|
22
|
+
#queue;
|
|
23
|
+
#delayedQueuePrefix;
|
|
24
|
+
#durable;
|
|
25
|
+
#senderChannel;
|
|
26
|
+
nativeRetrial;
|
|
27
|
+
/**
|
|
28
|
+
* Creates a new `AmqpMessageQueue`.
|
|
29
|
+
* @param connection A connection to the AMQP server.
|
|
30
|
+
* @param options Options for the message queue.
|
|
31
|
+
*/
|
|
32
|
+
constructor(connection, options = {}) {
|
|
33
|
+
this.#connection = connection;
|
|
34
|
+
this.#queue = options.queue ?? "fedify_queue";
|
|
35
|
+
this.#delayedQueuePrefix = options.delayedQueuePrefix ?? "fedify_delayed_";
|
|
36
|
+
this.#durable = options.durable ?? true;
|
|
37
|
+
this.nativeRetrial = options.nativeRetrial ?? false;
|
|
38
|
+
}
|
|
39
|
+
async #prepareQueue(channel) {
|
|
40
|
+
await channel.assertQueue(this.#queue, { durable: this.#durable });
|
|
41
|
+
}
|
|
42
|
+
async #getSenderChannel() {
|
|
43
|
+
if (this.#senderChannel != null) return this.#senderChannel;
|
|
44
|
+
const channel = await this.#connection.createChannel();
|
|
45
|
+
this.#senderChannel = channel;
|
|
46
|
+
this.#prepareQueue(channel);
|
|
47
|
+
return channel;
|
|
48
|
+
}
|
|
49
|
+
async enqueue(message, options) {
|
|
50
|
+
const channel = await this.#getSenderChannel();
|
|
51
|
+
const delay = options?.delay?.total("millisecond");
|
|
52
|
+
let queue;
|
|
53
|
+
if (delay == null || delay <= 0) queue = this.#queue;
|
|
54
|
+
else {
|
|
55
|
+
const delayStr = delay.toLocaleString("en", { useGrouping: false });
|
|
56
|
+
queue = this.#delayedQueuePrefix + delayStr;
|
|
57
|
+
await channel.assertQueue(queue, {
|
|
58
|
+
autoDelete: true,
|
|
59
|
+
durable: this.#durable,
|
|
60
|
+
deadLetterExchange: "",
|
|
61
|
+
deadLetterRoutingKey: this.#queue,
|
|
62
|
+
messageTtl: delay
|
|
63
|
+
});
|
|
64
|
+
}
|
|
65
|
+
channel.sendToQueue(queue, node_buffer.Buffer.from(JSON.stringify(message), "utf-8"), {
|
|
66
|
+
persistent: this.#durable,
|
|
67
|
+
contentType: "application/json"
|
|
68
|
+
});
|
|
69
|
+
}
|
|
70
|
+
async enqueueMany(messages, options) {
|
|
71
|
+
const channel = await this.#getSenderChannel();
|
|
72
|
+
const delay = options?.delay?.total("millisecond");
|
|
73
|
+
let queue;
|
|
74
|
+
if (delay == null || delay <= 0) queue = this.#queue;
|
|
75
|
+
else {
|
|
76
|
+
const delayStr = delay.toLocaleString("en", { useGrouping: false });
|
|
77
|
+
queue = this.#delayedQueuePrefix + delayStr;
|
|
78
|
+
await channel.assertQueue(queue, {
|
|
79
|
+
autoDelete: true,
|
|
80
|
+
durable: this.#durable,
|
|
81
|
+
deadLetterExchange: "",
|
|
82
|
+
deadLetterRoutingKey: this.#queue,
|
|
83
|
+
messageTtl: delay
|
|
84
|
+
});
|
|
85
|
+
}
|
|
86
|
+
for (const message of messages) channel.sendToQueue(queue, node_buffer.Buffer.from(JSON.stringify(message), "utf-8"), {
|
|
87
|
+
persistent: this.#durable,
|
|
88
|
+
contentType: "application/json"
|
|
89
|
+
});
|
|
90
|
+
}
|
|
91
|
+
async listen(handler, options = {}) {
|
|
92
|
+
const channel = await this.#connection.createChannel();
|
|
93
|
+
await this.#prepareQueue(channel);
|
|
94
|
+
await channel.prefetch(1);
|
|
95
|
+
const reply = await channel.consume(this.#queue, (msg) => {
|
|
96
|
+
if (msg == null) return;
|
|
97
|
+
const message = JSON.parse(msg.content.toString("utf-8"));
|
|
98
|
+
try {
|
|
99
|
+
const result = handler(message);
|
|
100
|
+
if (result instanceof Promise) if (this.nativeRetrial) result.then(() => channel.ack(msg)).catch(() => channel.nack(msg, void 0, true));
|
|
101
|
+
else result.finally(() => channel.ack(msg));
|
|
102
|
+
else if (this.nativeRetrial) channel.ack(msg);
|
|
103
|
+
} catch {
|
|
104
|
+
if (this.nativeRetrial) channel.nack(msg, void 0, true);
|
|
105
|
+
} finally {
|
|
106
|
+
if (!this.nativeRetrial) channel.ack(msg);
|
|
107
|
+
}
|
|
108
|
+
}, { noAck: false });
|
|
109
|
+
return await new Promise((resolve) => {
|
|
110
|
+
if (options.signal?.aborted) resolve();
|
|
111
|
+
options.signal?.addEventListener("abort", () => {
|
|
112
|
+
channel.cancel(reply.consumerTag).then(() => {
|
|
113
|
+
channel.close().then(() => resolve());
|
|
114
|
+
});
|
|
115
|
+
});
|
|
116
|
+
});
|
|
117
|
+
}
|
|
118
|
+
};
|
|
119
|
+
|
|
120
|
+
//#endregion
|
|
121
|
+
exports.AmqpMessageQueue = AmqpMessageQueue;
|
package/dist/mq.d.cts
ADDED
|
@@ -0,0 +1,72 @@
|
|
|
1
|
+
import { MessageQueue, MessageQueueEnqueueOptions, MessageQueueListenOptions } from "@fedify/fedify";
|
|
2
|
+
import { ChannelModel } from "amqplib";
|
|
3
|
+
|
|
4
|
+
//#region src/mq.d.ts
|
|
5
|
+
|
|
6
|
+
/**
|
|
7
|
+
* Options for {@link AmqpMessageQueue}.
|
|
8
|
+
*/
|
|
9
|
+
interface AmqpMessageQueueOptions {
|
|
10
|
+
/**
|
|
11
|
+
* The name of the queue to use. Defaults to `"fedify_queue"`.
|
|
12
|
+
* @default `"fedify_queue"`
|
|
13
|
+
*/
|
|
14
|
+
queue?: string;
|
|
15
|
+
/**
|
|
16
|
+
* The prefix to use for the delayed queue. Defaults to `"fedify_delayed_"`.
|
|
17
|
+
* Defaults to `"fedify_delayed_"`.
|
|
18
|
+
* @default `"fedify_delayed_"`
|
|
19
|
+
*/
|
|
20
|
+
delayedQueuePrefix?: string;
|
|
21
|
+
/**
|
|
22
|
+
* Whether the queue will survive a broker restart. Defaults to `true`.
|
|
23
|
+
* @default `true`
|
|
24
|
+
*/
|
|
25
|
+
durable?: boolean;
|
|
26
|
+
/**
|
|
27
|
+
* Whether to use native retrial mechanism. If set to `true`, the queue will
|
|
28
|
+
* not acknowledge messages that are not processed successfully, allowing
|
|
29
|
+
* them to be retried later. If set to `false`, messages will be acknowledged
|
|
30
|
+
* whether they are processed successfully or not.
|
|
31
|
+
*
|
|
32
|
+
* Both approaches have their own advantages and disadvantages. With native
|
|
33
|
+
* retrials, much less chance of losing messages, but timing of retrials is
|
|
34
|
+
* less predictable. With non-native retrials, retrials are handled by Fedify
|
|
35
|
+
* itself, which allows for more control over the timing and behavior of
|
|
36
|
+
* retrials, but may result in lost messages if the process crashes before
|
|
37
|
+
* acknowledging the message.
|
|
38
|
+
* @default `false`
|
|
39
|
+
* @since 0.3.0
|
|
40
|
+
*/
|
|
41
|
+
nativeRetrial?: boolean;
|
|
42
|
+
}
|
|
43
|
+
/**
|
|
44
|
+
* A message queue that uses AMQP.
|
|
45
|
+
*
|
|
46
|
+
* @example
|
|
47
|
+
* ``` typescript
|
|
48
|
+
* import { createFederation } from "@fedify/fedify";
|
|
49
|
+
* import { AmqpMessageQueue } from "@fedify/amqp";
|
|
50
|
+
* import { connect } from "amqplib";
|
|
51
|
+
*
|
|
52
|
+
* const federation = createFederation({
|
|
53
|
+
* queue: new AmqpMessageQueue(await connect("amqp://localhost")),
|
|
54
|
+
* // ... other configurations
|
|
55
|
+
* });
|
|
56
|
+
* ```
|
|
57
|
+
*/
|
|
58
|
+
declare class AmqpMessageQueue implements MessageQueue {
|
|
59
|
+
#private;
|
|
60
|
+
readonly nativeRetrial: boolean;
|
|
61
|
+
/**
|
|
62
|
+
* Creates a new `AmqpMessageQueue`.
|
|
63
|
+
* @param connection A connection to the AMQP server.
|
|
64
|
+
* @param options Options for the message queue.
|
|
65
|
+
*/
|
|
66
|
+
constructor(connection: ChannelModel, options?: AmqpMessageQueueOptions);
|
|
67
|
+
enqueue(message: any, options?: MessageQueueEnqueueOptions): Promise<void>;
|
|
68
|
+
enqueueMany(messages: any[], options?: MessageQueueEnqueueOptions): Promise<void>;
|
|
69
|
+
listen(handler: (message: any) => void | Promise<void>, options?: MessageQueueListenOptions): Promise<void>;
|
|
70
|
+
}
|
|
71
|
+
//#endregion
|
|
72
|
+
export { AmqpMessageQueue, AmqpMessageQueueOptions };
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@fedify/amqp",
|
|
3
|
-
"version": "2.0.0-dev.
|
|
3
|
+
"version": "2.0.0-dev.1641+6b0c942c",
|
|
4
4
|
"description": "AMQP/RabbitMQ driver for Fedify",
|
|
5
5
|
"keywords": [
|
|
6
6
|
"fedify",
|
|
@@ -27,25 +27,35 @@
|
|
|
27
27
|
"https://github.com/sponsors/dahlia"
|
|
28
28
|
],
|
|
29
29
|
"type": "module",
|
|
30
|
-
"main": "./dist/mod.
|
|
30
|
+
"main": "./dist/mod.cjs",
|
|
31
31
|
"module": "./dist/mod.js",
|
|
32
32
|
"types": "./dist/mod.d.ts",
|
|
33
33
|
"exports": {
|
|
34
34
|
".": {
|
|
35
|
-
"types":
|
|
35
|
+
"types": {
|
|
36
|
+
"import": "./dist/mod.d.ts",
|
|
37
|
+
"require": "./dist/mod.d.cts",
|
|
38
|
+
"default": "./dist/mod.d.ts"
|
|
39
|
+
},
|
|
36
40
|
"import": "./dist/mod.js",
|
|
41
|
+
"require": "./dist/mod.cjs",
|
|
37
42
|
"default": "./dist/mod.js"
|
|
38
43
|
},
|
|
39
44
|
"./mq": {
|
|
40
|
-
"types":
|
|
45
|
+
"types": {
|
|
46
|
+
"import": "./dist/mq.d.ts",
|
|
47
|
+
"require": "./dist/mq.d.cts",
|
|
48
|
+
"default": "./dist/mq.d.ts"
|
|
49
|
+
},
|
|
41
50
|
"import": "./dist/mq.js",
|
|
51
|
+
"require": "./dist/mq.cjs",
|
|
42
52
|
"default": "./dist/mq.js"
|
|
43
53
|
},
|
|
44
54
|
"./package.json": "./package.json"
|
|
45
55
|
},
|
|
46
56
|
"peerDependencies": {
|
|
47
57
|
"amqplib": "^0.10.8",
|
|
48
|
-
"@fedify/fedify": "^2.0.0-dev.
|
|
58
|
+
"@fedify/fedify": "^2.0.0-dev.1641+6b0c942c"
|
|
49
59
|
},
|
|
50
60
|
"devDependencies": {
|
|
51
61
|
"@alinea/suite": "^0.6.3",
|