@satorijs/adapter-discord 3.5.7 → 3.6.1
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/lib/bot.d.ts +5 -1
- package/lib/index.js +183 -42
- package/lib/index.js.map +3 -3
- package/lib/message.d.ts +7 -6
- package/lib/types/application.d.ts +1 -1
- package/lib/types/channel.d.ts +1 -1
- package/lib/utils.d.ts +1 -0
- package/package.json +2 -2
package/lib/bot.d.ts
CHANGED
|
@@ -1,11 +1,15 @@
|
|
|
1
1
|
import { Bot, Context, Fragment, Quester, Schema, SendOptions } from '@satorijs/satori';
|
|
2
2
|
import { DiscordMessenger } from './message';
|
|
3
|
-
import { Internal } from './types';
|
|
3
|
+
import { Internal, Webhook } from './types';
|
|
4
4
|
import { WsClient } from './ws';
|
|
5
5
|
export declare class DiscordBot extends Bot<DiscordBot.Config> {
|
|
6
6
|
http: Quester;
|
|
7
7
|
internal: Internal;
|
|
8
|
+
webhooks: Record<string, Webhook>;
|
|
9
|
+
webhookLock: Record<string, Promise<Webhook>>;
|
|
8
10
|
constructor(ctx: Context, config: DiscordBot.Config);
|
|
11
|
+
private _ensureWebhook;
|
|
12
|
+
ensureWebhook(channelId: string): Promise<Webhook>;
|
|
9
13
|
getSelf(): Promise<import("@satorijs/core").Universal.User>;
|
|
10
14
|
sendMessage(channelId: string, content: Fragment, guildId?: string, options?: SendOptions): Promise<string[]>;
|
|
11
15
|
sendPrivateMessage(channelId: string, content: Fragment, options?: SendOptions): Promise<string[]>;
|
package/lib/index.js
CHANGED
|
@@ -41,7 +41,8 @@ __export(src_exports, {
|
|
|
41
41
|
adaptSession: () => adaptSession,
|
|
42
42
|
adaptUser: () => adaptUser,
|
|
43
43
|
default: () => src_default,
|
|
44
|
-
prepareMessage: () => prepareMessage
|
|
44
|
+
prepareMessage: () => prepareMessage,
|
|
45
|
+
sanitize: () => sanitize
|
|
45
46
|
});
|
|
46
47
|
module.exports = __toCommonJS(src_exports);
|
|
47
48
|
|
|
@@ -50,6 +51,7 @@ var import_satori5 = require("@satorijs/satori");
|
|
|
50
51
|
|
|
51
52
|
// satori/adapters/discord/src/utils.ts
|
|
52
53
|
var import_satori = require("@satorijs/satori");
|
|
54
|
+
var sanitize = /* @__PURE__ */ __name((val) => val.replace(/[\\*_`~|()\[\]]/g, "\\$&").replace(/@everyone/g, () => "\\@everyone").replace(/@here/g, () => "\\@here"), "sanitize");
|
|
53
55
|
var adaptUser = /* @__PURE__ */ __name((user) => ({
|
|
54
56
|
userId: user.id,
|
|
55
57
|
avatar: `https://cdn.discordapp.com/avatars/${user.id}/${user.avatar}.png`,
|
|
@@ -87,20 +89,20 @@ async function adaptMessage(bot, meta, session = {}) {
|
|
|
87
89
|
session.content = meta.content.replace(/<@[!&]?(.+?)>/g, (_, id) => {
|
|
88
90
|
var _a2;
|
|
89
91
|
if (meta.mention_roles.includes(id)) {
|
|
90
|
-
return (0, import_satori.
|
|
92
|
+
return (0, import_satori.h)("at", { role: id }).toString();
|
|
91
93
|
} else {
|
|
92
94
|
const user = (_a2 = meta.mentions) == null ? void 0 : _a2.find((u) => u.id === id || `${u.username}#${u.discriminator}` === id);
|
|
93
|
-
return import_satori.
|
|
95
|
+
return import_satori.h.at(id, { name: user == null ? void 0 : user.username }).toString();
|
|
94
96
|
}
|
|
95
97
|
}).replace(/<a?:(.*):(.+?)>/g, (_, name, id) => {
|
|
96
98
|
const animated = _[1] === "a";
|
|
97
|
-
return (0, import_satori.
|
|
98
|
-
import_satori.
|
|
99
|
+
return (0, import_satori.h)("face", { id, name, animated, platform }, [
|
|
100
|
+
import_satori.h.image(`https://cdn.discordapp.com/emojis/${id}.gif?quality=lossless`)
|
|
99
101
|
]).toString();
|
|
100
|
-
}).replace(/@everyone/g, () => (0, import_satori.
|
|
102
|
+
}).replace(/@everyone/g, () => (0, import_satori.h)("at", { type: "all" }).toString()).replace(/@here/g, () => (0, import_satori.h)("at", { type: "here" }).toString()).replace(/<#(.+?)>/g, (_, id) => {
|
|
101
103
|
var _a2;
|
|
102
104
|
const channel = (_a2 = meta.mention_channels) == null ? void 0 : _a2.find((c) => c.id === id);
|
|
103
|
-
return import_satori.
|
|
105
|
+
return import_satori.h.sharp(id, { name: channel == null ? void 0 : channel.name }).toString();
|
|
104
106
|
});
|
|
105
107
|
}
|
|
106
108
|
if ((_c = meta.attachments) == null ? void 0 : _c.length) {
|
|
@@ -109,25 +111,25 @@ async function adaptMessage(bot, meta, session = {}) {
|
|
|
109
111
|
session.content += meta.attachments.map((v) => {
|
|
110
112
|
var _a2, _b2, _c2;
|
|
111
113
|
if (v.height && v.width && ((_a2 = v.content_type) == null ? void 0 : _a2.startsWith("image/"))) {
|
|
112
|
-
return (0, import_satori.
|
|
114
|
+
return (0, import_satori.h)("image", {
|
|
113
115
|
url: v.url,
|
|
114
116
|
proxy_url: v.proxy_url,
|
|
115
117
|
file: v.filename
|
|
116
118
|
});
|
|
117
119
|
} else if (v.height && v.width && ((_b2 = v.content_type) == null ? void 0 : _b2.startsWith("video/"))) {
|
|
118
|
-
return (0, import_satori.
|
|
120
|
+
return (0, import_satori.h)("video", {
|
|
119
121
|
url: v.url,
|
|
120
122
|
proxy_url: v.proxy_url,
|
|
121
123
|
file: v.filename
|
|
122
124
|
});
|
|
123
125
|
} else if ((_c2 = v.content_type) == null ? void 0 : _c2.startsWith("audio/")) {
|
|
124
|
-
return (0, import_satori.
|
|
126
|
+
return (0, import_satori.h)("record", {
|
|
125
127
|
url: v.url,
|
|
126
128
|
proxy_url: v.proxy_url,
|
|
127
129
|
file: v.filename
|
|
128
130
|
});
|
|
129
131
|
} else {
|
|
130
|
-
return (0, import_satori.
|
|
132
|
+
return (0, import_satori.h)("file", {
|
|
131
133
|
url: v.url,
|
|
132
134
|
proxy_url: v.proxy_url,
|
|
133
135
|
file: v.filename
|
|
@@ -137,16 +139,16 @@ async function adaptMessage(bot, meta, session = {}) {
|
|
|
137
139
|
}
|
|
138
140
|
for (const embed of meta.embeds) {
|
|
139
141
|
if (embed.image) {
|
|
140
|
-
session.content += (0, import_satori.
|
|
142
|
+
session.content += (0, import_satori.h)("image", { url: embed.image.url, proxy_url: embed.image.proxy_url });
|
|
141
143
|
}
|
|
142
144
|
if (embed.thumbnail) {
|
|
143
|
-
session.content += (0, import_satori.
|
|
145
|
+
session.content += (0, import_satori.h)("image", { url: embed.thumbnail.url, proxy_url: embed.thumbnail.proxy_url });
|
|
144
146
|
}
|
|
145
147
|
if (embed.video) {
|
|
146
|
-
session.content += (0, import_satori.
|
|
148
|
+
session.content += (0, import_satori.h)("video", { url: embed.video.url, proxy_url: embed.video.proxy_url });
|
|
147
149
|
}
|
|
148
150
|
}
|
|
149
|
-
session.elements = import_satori.
|
|
151
|
+
session.elements = import_satori.h.parse(session.content);
|
|
150
152
|
if (meta.message_reference) {
|
|
151
153
|
const { message_id, channel_id } = meta.message_reference;
|
|
152
154
|
session.quote = await bot.getMessage(channel_id, message_id);
|
|
@@ -175,6 +177,12 @@ __name(prepareReactionSession, "prepareReactionSession");
|
|
|
175
177
|
async function adaptSession(bot, input) {
|
|
176
178
|
const session = bot.session();
|
|
177
179
|
if (input.t === "MESSAGE_CREATE") {
|
|
180
|
+
if (input.d.webhook_id) {
|
|
181
|
+
const webhook = await bot.ensureWebhook(input.d.channel_id);
|
|
182
|
+
if (webhook.id === input.d.webhook_id) {
|
|
183
|
+
return;
|
|
184
|
+
}
|
|
185
|
+
}
|
|
178
186
|
session.type = "message";
|
|
179
187
|
await adaptMessage(bot, input.d, session);
|
|
180
188
|
} else if (input.t === "MESSAGE_UPDATE") {
|
|
@@ -215,36 +223,78 @@ __name(adaptSession, "adaptSession");
|
|
|
215
223
|
// satori/adapters/discord/src/message.ts
|
|
216
224
|
var import_satori2 = require("@satorijs/satori");
|
|
217
225
|
var import_form_data = __toESM(require("form-data"));
|
|
226
|
+
var logger = new import_satori2.Logger("discord");
|
|
227
|
+
var State = class {
|
|
228
|
+
// forward: send the first message and create a thread
|
|
229
|
+
constructor(type) {
|
|
230
|
+
this.type = type;
|
|
231
|
+
this.author = {};
|
|
232
|
+
this.quote = {};
|
|
233
|
+
this.channel = {};
|
|
234
|
+
this.fakeMessageMap = {};
|
|
235
|
+
// [userInput] = discord messages
|
|
236
|
+
this.threadCreated = false;
|
|
237
|
+
}
|
|
238
|
+
};
|
|
239
|
+
__name(State, "State");
|
|
218
240
|
var DiscordMessenger = class extends import_satori2.Messenger {
|
|
219
241
|
constructor() {
|
|
220
242
|
super(...arguments);
|
|
243
|
+
this.stack = [new State("message")];
|
|
221
244
|
this.buffer = "";
|
|
222
245
|
this.addition = {};
|
|
223
246
|
this.figure = null;
|
|
224
247
|
this.mode = "default";
|
|
225
248
|
}
|
|
226
249
|
async post(data, headers) {
|
|
250
|
+
var _a, _b, _c;
|
|
227
251
|
try {
|
|
228
|
-
|
|
252
|
+
let url = `/channels/${this.channelId}/messages`;
|
|
253
|
+
if (this.stack[0].author.nickname || this.stack[0].author.avatar || this.stack[0].type === "forward" && !this.stack[0].threadCreated) {
|
|
254
|
+
const webhook = await this.ensureWebhook();
|
|
255
|
+
url = `/webhooks/${webhook.id}/${webhook.token}?wait=true`;
|
|
256
|
+
}
|
|
257
|
+
if (this.stack[0].type === "forward" && ((_a = this.stack[0].channel) == null ? void 0 : _a.id)) {
|
|
258
|
+
if (this.stack[1].author.nickname || this.stack[1].author.avatar) {
|
|
259
|
+
const webhook = await this.ensureWebhook();
|
|
260
|
+
url = `/webhooks/${webhook.id}/${webhook.token}?wait=true&thread_id=${(_b = this.stack[0].channel) == null ? void 0 : _b.id}`;
|
|
261
|
+
} else {
|
|
262
|
+
url = `/channels/${this.stack[0].channel.id}/messages`;
|
|
263
|
+
}
|
|
264
|
+
}
|
|
265
|
+
const result = await this.bot.http.post(url, data, { headers });
|
|
229
266
|
const session = this.bot.session();
|
|
230
|
-
await adaptMessage(this.bot, result, session);
|
|
267
|
+
const message = await adaptMessage(this.bot, result, session);
|
|
231
268
|
session.app.emit(session, "send", session);
|
|
232
269
|
this.results.push(session);
|
|
270
|
+
if (this.stack[0].type === "forward" && !this.stack[0].threadCreated) {
|
|
271
|
+
this.stack[0].threadCreated = true;
|
|
272
|
+
const thread = await this.bot.internal.startThreadFromMessage(this.channelId, result.id, {
|
|
273
|
+
name: "Forward",
|
|
274
|
+
auto_archive_duration: 60
|
|
275
|
+
});
|
|
276
|
+
this.stack[0].channel = thread;
|
|
277
|
+
}
|
|
278
|
+
return message;
|
|
233
279
|
} catch (e) {
|
|
280
|
+
if (import_satori2.Quester.isAxiosError(e) && ((_c = e.response) == null ? void 0 : _c.data.code) === 10015) {
|
|
281
|
+
logger.debug("webhook has been deleted, recreating..., %o", e.response.data);
|
|
282
|
+
if (!this.bot.webhookLock[this.channelId])
|
|
283
|
+
this.bot.webhooks[this.channelId] = null;
|
|
284
|
+
await this.ensureWebhook();
|
|
285
|
+
return this.post(data, headers);
|
|
286
|
+
}
|
|
234
287
|
this.errors.push(e);
|
|
235
288
|
}
|
|
236
289
|
}
|
|
237
290
|
async sendEmbed(attrs, payload) {
|
|
238
|
-
const { filename, data, mime } = await this.bot.ctx.http.file(attrs.url);
|
|
291
|
+
const { filename, data, mime } = await this.bot.ctx.http.file(attrs.url, attrs);
|
|
239
292
|
const form = new import_form_data.default();
|
|
240
293
|
const value = process.env.KOISHI_ENV === "browser" ? new Blob([data], { type: mime }) : Buffer.from(data);
|
|
241
294
|
form.append("file", value, attrs.file || filename);
|
|
242
295
|
form.append("payload_json", JSON.stringify(payload));
|
|
243
296
|
return this.post(form, form.getHeaders());
|
|
244
297
|
}
|
|
245
|
-
async sendContent(content, addition) {
|
|
246
|
-
return this.post({ ...addition, content });
|
|
247
|
-
}
|
|
248
298
|
async sendAsset(type, attrs, addition) {
|
|
249
299
|
const { handleMixedContent, handleExternalAsset } = this.bot.config;
|
|
250
300
|
if (handleMixedContent === "separate" && addition.content) {
|
|
@@ -268,7 +318,8 @@ var DiscordMessenger = class extends import_satori2.Messenger {
|
|
|
268
318
|
return sendDirect();
|
|
269
319
|
}
|
|
270
320
|
return await this.bot.ctx.http.head(attrs.url, {
|
|
271
|
-
headers: { accept: type + "/*" }
|
|
321
|
+
headers: { accept: type + "/*" },
|
|
322
|
+
timeout: +attrs.timeout || void 0
|
|
272
323
|
}).then((headers) => {
|
|
273
324
|
if (headers["content-type"].startsWith(type)) {
|
|
274
325
|
return sendDirect();
|
|
@@ -277,6 +328,9 @@ var DiscordMessenger = class extends import_satori2.Messenger {
|
|
|
277
328
|
}
|
|
278
329
|
}, sendDownload);
|
|
279
330
|
}
|
|
331
|
+
async ensureWebhook() {
|
|
332
|
+
return this.bot.ensureWebhook(this.channelId);
|
|
333
|
+
}
|
|
280
334
|
async flush() {
|
|
281
335
|
const content = this.buffer.trim();
|
|
282
336
|
if (!content)
|
|
@@ -286,9 +340,10 @@ var DiscordMessenger = class extends import_satori2.Messenger {
|
|
|
286
340
|
this.addition = {};
|
|
287
341
|
}
|
|
288
342
|
async visit(element) {
|
|
343
|
+
var _a;
|
|
289
344
|
const { type, attrs, children } = element;
|
|
290
345
|
if (type === "text") {
|
|
291
|
-
this.buffer += attrs.content
|
|
346
|
+
this.buffer += sanitize(attrs.content);
|
|
292
347
|
} else if (type === "b" || type === "strong") {
|
|
293
348
|
this.buffer += "**";
|
|
294
349
|
await this.render(children);
|
|
@@ -355,7 +410,7 @@ var DiscordMessenger = class extends import_satori2.Messenger {
|
|
|
355
410
|
...this.addition,
|
|
356
411
|
embeds: [{ ...attrs }]
|
|
357
412
|
});
|
|
358
|
-
} else if (type === "
|
|
413
|
+
} else if (type === "audio") {
|
|
359
414
|
await this.sendAsset("file", attrs, {
|
|
360
415
|
...this.addition,
|
|
361
416
|
content: this.buffer.trim()
|
|
@@ -371,20 +426,78 @@ var DiscordMessenger = class extends import_satori2.Messenger {
|
|
|
371
426
|
});
|
|
372
427
|
this.buffer = "";
|
|
373
428
|
this.mode = "default";
|
|
374
|
-
} else if (type === "
|
|
375
|
-
await this.flush();
|
|
376
|
-
this.addition.message_reference = {
|
|
377
|
-
message_id: attrs.id
|
|
378
|
-
};
|
|
379
|
-
} else if (type === "message") {
|
|
429
|
+
} else if (type === "message" && !attrs.forward) {
|
|
380
430
|
if (this.mode === "figure") {
|
|
381
431
|
await this.render(children);
|
|
382
432
|
this.buffer += "\n";
|
|
383
433
|
} else {
|
|
434
|
+
const resultLength = +this.results.length;
|
|
384
435
|
await this.flush();
|
|
436
|
+
const [author] = import_satori2.segment.select(children, "author");
|
|
437
|
+
if (author) {
|
|
438
|
+
const { avatar, nickname } = author.attrs;
|
|
439
|
+
if (avatar)
|
|
440
|
+
this.addition.avatar_url = avatar;
|
|
441
|
+
if (nickname)
|
|
442
|
+
this.addition.username = nickname;
|
|
443
|
+
if (this.stack[0].type === "message") {
|
|
444
|
+
this.stack[0].author = author.attrs;
|
|
445
|
+
}
|
|
446
|
+
if (this.stack[0].type === "forward") {
|
|
447
|
+
this.stack[1].author = author.attrs;
|
|
448
|
+
}
|
|
449
|
+
}
|
|
450
|
+
const [quote] = import_satori2.segment.select(children, "quote");
|
|
451
|
+
if (quote) {
|
|
452
|
+
const parse = /* @__PURE__ */ __name((val) => val.replace(/\\([\\*_`~|()\[\]])/g, "$1"), "parse");
|
|
453
|
+
const message = this.stack[this.stack[0].type === "forward" ? 1 : 0];
|
|
454
|
+
if (!message.author.avatar && !message.author.nickname && this.stack[0].type !== "forward") {
|
|
455
|
+
await this.flush();
|
|
456
|
+
this.addition.message_reference = {
|
|
457
|
+
message_id: quote.attrs.id
|
|
458
|
+
};
|
|
459
|
+
} else {
|
|
460
|
+
let replyId = quote.attrs.id, channelId = this.channelId;
|
|
461
|
+
if (this.stack[0].type === "forward" && ((_a = this.stack[0].fakeMessageMap[quote.attrs.id]) == null ? void 0 : _a.length) >= 1) {
|
|
462
|
+
replyId = this.stack[0].fakeMessageMap[quote.attrs.id][0].messageId;
|
|
463
|
+
channelId = this.stack[0].fakeMessageMap[quote.attrs.id][0].channelId;
|
|
464
|
+
}
|
|
465
|
+
const quoted = await this.bot.getMessage(channelId, replyId);
|
|
466
|
+
this.addition.embeds = [{
|
|
467
|
+
description: [
|
|
468
|
+
sanitize(parse(quoted.elements.filter((v) => v.type === "text").join("")).slice(0, 30)),
|
|
469
|
+
`<t:${Math.ceil(quoted.timestamp / 1e3)}:R> [[ ↑ ]](https://discord.com/channels/${this.guildId}/${channelId}/${replyId})`
|
|
470
|
+
].join("\n\n"),
|
|
471
|
+
author: {
|
|
472
|
+
name: quoted.author.nickname || quoted.author.username,
|
|
473
|
+
icon_url: quoted.author.avatar
|
|
474
|
+
}
|
|
475
|
+
}];
|
|
476
|
+
}
|
|
477
|
+
}
|
|
385
478
|
await this.render(children);
|
|
386
479
|
await this.flush();
|
|
480
|
+
const newLength = +this.results.length;
|
|
481
|
+
const sentMessages = this.results.slice(resultLength, newLength);
|
|
482
|
+
if (this.stack[0].type === "forward" && attrs.id) {
|
|
483
|
+
this.stack[0].fakeMessageMap[attrs.id] = sentMessages;
|
|
484
|
+
}
|
|
485
|
+
if (this.stack[0].type === "message") {
|
|
486
|
+
this.stack[0].author = {};
|
|
487
|
+
}
|
|
488
|
+
if (this.stack[0].type === "forward") {
|
|
489
|
+
this.stack[1].author = {};
|
|
490
|
+
}
|
|
387
491
|
}
|
|
492
|
+
} else if (type === "message" && attrs.forward) {
|
|
493
|
+
this.stack.unshift(new State("forward"));
|
|
494
|
+
await this.render(children);
|
|
495
|
+
await this.flush();
|
|
496
|
+
await this.bot.internal.modifyChannel(this.stack[0].channel.id, {
|
|
497
|
+
archived: true,
|
|
498
|
+
locked: true
|
|
499
|
+
});
|
|
500
|
+
this.stack.shift();
|
|
388
501
|
} else {
|
|
389
502
|
await this.render(children);
|
|
390
503
|
}
|
|
@@ -1445,13 +1558,13 @@ Internal.define({
|
|
|
1445
1558
|
|
|
1446
1559
|
// satori/adapters/discord/src/types/webhook.ts
|
|
1447
1560
|
var Webhook2;
|
|
1448
|
-
((
|
|
1561
|
+
((Webhook4) => {
|
|
1449
1562
|
let Type;
|
|
1450
1563
|
((Type2) => {
|
|
1451
1564
|
Type2[Type2["INCOMING"] = 1] = "INCOMING";
|
|
1452
1565
|
Type2[Type2["CHANNEL_FOLLOWER"] = 2] = "CHANNEL_FOLLOWER";
|
|
1453
1566
|
Type2[Type2["APPLICATION"] = 3] = "APPLICATION";
|
|
1454
|
-
})(Type =
|
|
1567
|
+
})(Type = Webhook4.Type || (Webhook4.Type = {}));
|
|
1455
1568
|
})(Webhook2 || (Webhook2 = {}));
|
|
1456
1569
|
Internal.define({
|
|
1457
1570
|
"/channels/{channel.id}/webhooks": {
|
|
@@ -1487,7 +1600,7 @@ Internal.define({
|
|
|
1487
1600
|
|
|
1488
1601
|
// satori/adapters/discord/src/ws.ts
|
|
1489
1602
|
var import_satori4 = require("@satorijs/satori");
|
|
1490
|
-
var
|
|
1603
|
+
var logger2 = new import_satori4.Logger("discord");
|
|
1491
1604
|
var WsClient = class extends import_satori4.Adapter.WsClient {
|
|
1492
1605
|
constructor() {
|
|
1493
1606
|
super(...arguments);
|
|
@@ -1502,7 +1615,7 @@ var WsClient = class extends import_satori4.Adapter.WsClient {
|
|
|
1502
1615
|
return this.bot.http.ws(url);
|
|
1503
1616
|
}
|
|
1504
1617
|
heartbeat() {
|
|
1505
|
-
|
|
1618
|
+
logger2.debug(`heartbeat d ${this._d}`);
|
|
1506
1619
|
this.bot.socket.send(JSON.stringify({
|
|
1507
1620
|
op: 1 /* HEARTBEAT */,
|
|
1508
1621
|
d: this._d
|
|
@@ -1515,16 +1628,16 @@ var WsClient = class extends import_satori4.Adapter.WsClient {
|
|
|
1515
1628
|
try {
|
|
1516
1629
|
parsed = JSON.parse(data.toString());
|
|
1517
1630
|
} catch (error) {
|
|
1518
|
-
return
|
|
1631
|
+
return logger2.warn("cannot parse message", data);
|
|
1519
1632
|
}
|
|
1520
|
-
|
|
1633
|
+
logger2.debug(require("util").inspect(parsed, false, null, true));
|
|
1521
1634
|
if (parsed.s) {
|
|
1522
1635
|
this._d = parsed.s;
|
|
1523
1636
|
}
|
|
1524
1637
|
if (parsed.op === 10 /* HELLO */) {
|
|
1525
1638
|
this._ping = setInterval(() => this.heartbeat(), parsed.d.heartbeat_interval);
|
|
1526
1639
|
if (this._sessionId) {
|
|
1527
|
-
|
|
1640
|
+
logger2.debug("resuming");
|
|
1528
1641
|
this.bot.socket.send(JSON.stringify({
|
|
1529
1642
|
op: 6 /* RESUME */,
|
|
1530
1643
|
d: {
|
|
@@ -1549,7 +1662,7 @@ var WsClient = class extends import_satori4.Adapter.WsClient {
|
|
|
1549
1662
|
if (parsed.d)
|
|
1550
1663
|
return;
|
|
1551
1664
|
this._sessionId = "";
|
|
1552
|
-
|
|
1665
|
+
logger2.warn("offline: invalid session");
|
|
1553
1666
|
this.bot.offline();
|
|
1554
1667
|
(_a = this.bot.socket) == null ? void 0 : _a.close();
|
|
1555
1668
|
}
|
|
@@ -1561,7 +1674,7 @@ var WsClient = class extends import_satori4.Adapter.WsClient {
|
|
|
1561
1674
|
self.selfId = self.userId;
|
|
1562
1675
|
delete self.userId;
|
|
1563
1676
|
Object.assign(this.bot, self);
|
|
1564
|
-
|
|
1677
|
+
logger2.debug("session_id " + this._sessionId);
|
|
1565
1678
|
return this.bot.online();
|
|
1566
1679
|
}
|
|
1567
1680
|
if (parsed.t === "RESUMED") {
|
|
@@ -1573,7 +1686,7 @@ var WsClient = class extends import_satori4.Adapter.WsClient {
|
|
|
1573
1686
|
}
|
|
1574
1687
|
if (parsed.op === 7 /* RECONNECT */) {
|
|
1575
1688
|
this.bot.offline();
|
|
1576
|
-
|
|
1689
|
+
logger2.warn("offline: discord request reconnect");
|
|
1577
1690
|
(_b = this.bot.socket) == null ? void 0 : _b.close();
|
|
1578
1691
|
}
|
|
1579
1692
|
});
|
|
@@ -1597,6 +1710,8 @@ var import_package = require("../package.json");
|
|
|
1597
1710
|
var DiscordBot = class extends import_satori5.Bot {
|
|
1598
1711
|
constructor(ctx, config) {
|
|
1599
1712
|
super(ctx, config);
|
|
1713
|
+
this.webhooks = {};
|
|
1714
|
+
this.webhookLock = {};
|
|
1600
1715
|
this.http = ctx.http.extend({
|
|
1601
1716
|
...config,
|
|
1602
1717
|
headers: {
|
|
@@ -1608,6 +1723,31 @@ var DiscordBot = class extends import_satori5.Bot {
|
|
|
1608
1723
|
this.internal = new Internal(this.http);
|
|
1609
1724
|
ctx.plugin(WsClient, this);
|
|
1610
1725
|
}
|
|
1726
|
+
async _ensureWebhook(channelId) {
|
|
1727
|
+
let webhook;
|
|
1728
|
+
const webhooks = await this.internal.getChannelWebhooks(channelId);
|
|
1729
|
+
const selfId = this.selfId;
|
|
1730
|
+
if (!webhooks.find((v) => v.name === "Koishi" && v.user.id === selfId)) {
|
|
1731
|
+
webhook = await this.internal.createWebhook(channelId, {
|
|
1732
|
+
name: "Koishi"
|
|
1733
|
+
});
|
|
1734
|
+
} else {
|
|
1735
|
+
webhook = webhooks.find((v) => v.name === "Koishi" && v.user.id === this.selfId);
|
|
1736
|
+
}
|
|
1737
|
+
return this.webhooks[channelId] = webhook;
|
|
1738
|
+
}
|
|
1739
|
+
async ensureWebhook(channelId) {
|
|
1740
|
+
var _a;
|
|
1741
|
+
if (this.webhooks[channelId] === null) {
|
|
1742
|
+
delete this.webhooks[channelId];
|
|
1743
|
+
delete this.webhookLock[channelId];
|
|
1744
|
+
}
|
|
1745
|
+
if (this.webhooks[channelId]) {
|
|
1746
|
+
delete this.webhookLock[channelId];
|
|
1747
|
+
return this.webhooks[channelId];
|
|
1748
|
+
}
|
|
1749
|
+
return (_a = this.webhookLock)[channelId] || (_a[channelId] = this._ensureWebhook(channelId));
|
|
1750
|
+
}
|
|
1611
1751
|
async getSelf() {
|
|
1612
1752
|
const data = await this.internal.getCurrentUser();
|
|
1613
1753
|
return adaptUser(data);
|
|
@@ -1622,7 +1762,7 @@ var DiscordBot = class extends import_satori5.Bot {
|
|
|
1622
1762
|
await this.internal.deleteMessage(channelId, messageId);
|
|
1623
1763
|
}
|
|
1624
1764
|
async editMessage(channelId, messageId, content) {
|
|
1625
|
-
const elements = import_satori5.
|
|
1765
|
+
const elements = import_satori5.h.normalize(content);
|
|
1626
1766
|
content = elements.toString();
|
|
1627
1767
|
const image = elements.find((v) => v.type === "image");
|
|
1628
1768
|
if (image) {
|
|
@@ -1702,6 +1842,7 @@ var src_default = DiscordBot;
|
|
|
1702
1842
|
adaptMessage,
|
|
1703
1843
|
adaptSession,
|
|
1704
1844
|
adaptUser,
|
|
1705
|
-
prepareMessage
|
|
1845
|
+
prepareMessage,
|
|
1846
|
+
sanitize
|
|
1706
1847
|
});
|
|
1707
1848
|
//# sourceMappingURL=index.js.map
|