@openclaw/discord 2026.7.2-beta.7 → 2026.8.1-beta.2
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/dist/{account-inspect-SXiCBCgP.js → account-inspect-CqzrH14k.js} +48 -42
- package/dist/account-inspect-api.js +1 -1
- package/dist/action-runtime-api.js +1 -1
- package/dist/{active-turn-thread-route-MlKWp8RD.js → active-turn-thread-route-fmHl1HNd.js} +9 -11
- package/dist/{activities-api-DTKsuDxf.js → activities-api-DS7vpdtp.js} +4 -4
- package/dist/activities-api.js +1 -1
- package/dist/{allow-list-DzKrtfah.js → allow-list-DnxIlPP2.js} +2 -3
- package/dist/{api-DnrK9gML.js → api-DNVbJyEy.js} +7 -2
- package/dist/api.js +15 -15
- package/dist/{approval-handler.runtime-HymvFTYn.js → approval-handler.runtime-B6yEV79q.js} +5 -5
- package/dist/{approval-message-safety-DEyKVsAw.js → approval-message-safety-AcIxvrf3.js} +1 -1
- package/dist/{audit-CjsrabP8.js → audit-Db-rlntl.js} +4 -4
- package/dist/{channel-vKa-76xY.js → channel-CnnbJSt5.js} +46 -72
- package/dist/{channel-actions-uXFTJX3o.js → channel-actions-5s_hjYKd.js} +4 -4
- package/dist/{channel-actions.runtime-CIYU90sl.js → channel-actions.runtime-CLKrx6tr.js} +53 -36
- package/dist/channel-config-api.js +1 -1
- package/dist/channel-plugin-api.js +1 -1
- package/dist/{channel.setup-CmcwZ_qd.js → channel.setup-BFAO-V1P.js} +15 -53
- package/dist/{config-schema-WHRQcY19.js → config-schema-BgEskFAs.js} +9 -4
- package/dist/{directory-config-D_LojtCe.js → directory-config-BVX7Cflc.js} +1 -1
- package/dist/directory-contract-api.js +1 -1
- package/dist/{directory-live-Bw5Ephzv.js → directory-live-DGIGxpIo.js} +6 -3
- package/dist/{doctor-Bc4S1qyd.js → doctor-BzC-TLnB.js} +4 -4
- package/dist/{doctor-contract-CCFMIDk9.js → doctor-contract-DLa-BTiU.js} +2 -3
- package/dist/doctor-contract-api.js +147 -2
- package/dist/{handle-action.guild-admin-D6VRRW-C.js → handle-action.guild-admin-BNVTUISF.js} +4 -7
- package/dist/{inbound-event-delivery-CEPlt2uz.js → inbound-event-delivery-De2qxTrP.js} +4 -25
- package/dist/index.js +4 -2
- package/dist/{message-handler-CeiSulIw.js → message-handler-Unk_f10F.js} +41 -32
- package/dist/{message-handler.preflight-DibgQFf2.js → message-handler.preflight-C9zecxR9.js} +50 -26
- package/dist/{message-handler.process-Dnc_oz9y.js → message-handler.process-DWQ6UHHu.js} +130 -166
- package/dist/{message-utils-BgTwT_q7.js → message-utils-BSCPVgy0.js} +4 -4
- package/dist/{model-picker-preference-primitives-D25pnCOu.js → model-picker-preference-primitives-BHT1LkR_.js} +3 -3
- package/dist/{outbound-adapter-DtE-i2OJ.js → outbound-adapter-D9nRivT1.js} +91 -32
- package/dist/{outbound-components-C7GVyfPh.js → outbound-components-cTzwBJ60.js} +3 -3
- package/dist/{outbound-session-route-H-HoyH5U.js → outbound-session-route-DxLkrgKQ.js} +68 -95
- package/dist/{pluralkit-CD4B11JB.js → pluralkit-DdiJ9KMK.js} +1 -1
- package/dist/{preflight-audio-BjnQZ5yS.js → preflight-audio-DrnqFA8U.js} +22 -28
- package/dist/{probe-BeWKhjqX.js → probe-Bl-k5_Ku.js} +36 -12
- package/dist/probe.runtime-M9fREKvp.js +2 -0
- package/dist/{provider-DfQJX3z5.js → provider-DvSNb-2v.js} +969 -1248
- package/dist/{provider-session.runtime-Bo88k0pV.js → provider-session.runtime-BUEqD0rA.js} +3 -3
- package/dist/provider.runtime-C9PnJZbZ.js +2 -0
- package/dist/realtime-session.runtime-C7wen-aF.js +1340 -0
- package/dist/{resolve-allowlist-common-DHERApxi.js → resolve-allowlist-common-D04lpEzb.js} +2 -2
- package/dist/{resolve-channels-BjepAj8b.js → resolve-channels-Dm7jEeg6.js} +4 -4
- package/dist/{resolve-users-Bc28htgt.js → resolve-users-bktrCUUU.js} +3 -3
- package/dist/{chunk-DX4jpFQP.js → retry-CLpJcXXf.js} +291 -68
- package/dist/{runtime-_aRC6V2s.js → runtime-DGsSyDTS.js} +30 -25
- package/dist/{runtime-BmW_j_hl.js → runtime-DoHjckYm.js} +4 -6
- package/dist/runtime-api.actions.js +2 -2
- package/dist/runtime-api.js +22 -23
- package/dist/runtime-api.lookup.js +5 -5
- package/dist/runtime-api.monitor-CHxrFPnW.js +5 -0
- package/dist/runtime-api.monitor.js +5 -5
- package/dist/runtime-api.send.js +6 -6
- package/dist/runtime-api.threads.js +5 -6
- package/dist/sdk-runtime-QpY8PvCh.js +370 -0
- package/dist/{send-CdkZ6zeW.js → send-B7Q6Oc1I.js} +175 -86
- package/dist/{send.components-5uqwkjgE.js → send.components-iJyFXw9L.js} +24 -28
- package/dist/{send.outbound-D-80Ej-t.js → send.outbound-DS5tHwfR.js} +37 -24
- package/dist/{send.reactions-CtlmGd_o.js → send.reactions-BAn0iiVQ.js} +14 -21
- package/dist/{send.receipt-CuwRrpFz.js → send.receipt-IPI1p-SP.js} +19 -1
- package/dist/{send.shared-jpvAG_u6.js → send.shared-BmwFjW6T.js} +16 -85
- package/dist/{sender-identity-mG_zsdox.js → sender-identity-QtalnCYv.js} +1 -1
- package/dist/setup-entry.js +0 -5
- package/dist/setup-plugin-api.js +1 -1
- package/dist/{shared-CXF1tup1.js → shared-BIXIX6uJ.js} +16 -17
- package/dist/{subagent-hooks-Dxy7Fmnq.js → subagent-hooks-CTt5KCJr.js} +2 -2
- package/dist/subagent-hooks-api.js +2 -6
- package/dist/subagent-progress-DhaE_h8a.js +109 -0
- package/dist/{system-events-DdUqf91B.js → system-events-CTqDf6_s.js} +2 -2
- package/dist/{target-resolver-C3s_2m0t.js → target-resolver-maOKSqO0.js} +2 -2
- package/dist/targets-yUFTHoAx.js +3 -0
- package/dist/{thread-bindings-C-M-ly7P.js → thread-bindings-3L8p82GV.js} +5 -7
- package/dist/{thread-bindings.manager-DYvSlrva.js → thread-bindings.manager-DCIH6WDC.js} +257 -29
- package/dist/{thread-bindings.session-updates-DAIlp7Px.js → thread-bindings.session-updates-bJ2KQFY6.js} +1 -1
- package/dist/{thread-bindings.state-Cgi5uRn-.js → thread-bindings.state-aeV8HNgV.js} +2 -15
- package/dist/{transcripts-source-DIKGsTGT.js → transcripts-source-CfFMexGt.js} +1 -1
- package/dist/transcripts-source-api.js +1 -1
- package/dist/{typing--Mzo2kM7.js → typing-CS-nNVoe.js} +1 -1
- package/dist/voice-runtime-BEdqNcST.js +2459 -0
- package/openclaw.plugin.json +203 -19
- package/package.json +15 -9
- package/skills/discord/SKILL.md +22 -115
- package/dist/legacy-state-migrations-api.js +0 -138
- package/dist/manager.runtime-Bjav3pfC.js +0 -3655
- package/dist/preflight-audio.runtime-CoCXMM8r.js +0 -7
- package/dist/probe.runtime-DqFGFMbZ.js +0 -2
- package/dist/provider.runtime-Cy7XZmyh.js +0 -2
- package/dist/runtime-api.monitor-CCRubd3-.js +0 -5
- package/dist/session-binding-contract-api.js +0 -2
- package/dist/subagent-progress-DI3sYLLo.js +0 -664
- package/dist/targets-Dv_RN7vT.js +0 -3
- package/dist/thread-bindings.discord-api-BoDNqamb.js +0 -246
|
@@ -1,10 +1,11 @@
|
|
|
1
|
-
import {
|
|
1
|
+
import { $t as removeGuildMemberRole, At as listChannelPins, Bt as createGuildSticker, Ct as editChannel, Et as getChannelMessage, F as readDiscordMessage, Ft as addGuildMemberRole, Gt as listGuildActiveThreads, Ht as getGuild, I as readRetryAfter, It as createGuildBan, Jt as listGuildRoles, Kt as listGuildChannels, Lt as createGuildChannel, M as RateLimitError, Mt as searchGuildMessages, N as isUnknownDiscordVoiceStateError, Nt as sendChannelTyping, Ot as listChannelArchivedThreads, P as readDiscordCode, Pt as unpinChannelMessage, Qt as removeGuildMember, Rt as createGuildEmoji, St as deleteChannelMessage, Tt as getChannel, Ut as getGuildMember, Vt as deleteChannelPermission, Wt as getGuildVoiceState, Xt as moveGuildChannels, Yt as listGuildScheduledEvents, Zt as putChannelPermission, bt as createThread, en as timeoutGuildMember, i as recordDiscordMessageCreateAmbiguity, j as DiscordError, jt as pinChannelMessage, kt as listChannelMessages, n as createDiscordRetryRunner, qt as listGuildEmojis, t as classifyDiscordDeliveryFailure, tn as __exportAll, wt as editChannelMessage, xt as deleteChannel, zt as createGuildScheduledEvent } from "./retry-CLpJcXXf.js";
|
|
2
2
|
import { s as resolveDiscordAccount } from "./accounts-DJTf1LtA.js";
|
|
3
|
-
import {
|
|
4
|
-
import { n as
|
|
5
|
-
import { n as
|
|
3
|
+
import { t as parseDiscordRetryAfterBodySeconds } from "./retry-after-DdLPmPoa.js";
|
|
4
|
+
import { A as hasAllGuildPermissionsDiscord, C as DISCORD_MAX_STICKER_BYTES, D as canViewDiscordGuildChannel, E as canManageGuildRoleDiscord, L as resolveDiscordClientAccountContext, M as hasAnyGuildPermissionDiscord, O as fetchChannelPermissionsDiscord, P as createDiscordClient, R as resolveDiscordRest, S as DISCORD_MAX_EVENT_COVER_BYTES, T as canManageGuildMemberRoleDiscord, W as parseAndResolveChannelRecipient, _ as resolveDiscordMessageFlags, b as resolveDiscordSuppressEmbeds, g as createDiscordMessageNonce, j as hasAnyChannelPermissionDiscord, k as fetchMemberGuildPermissionsDiscord, l as resolveChannelId, n as buildDiscordTextChunks, o as normalizeEmojiName, p as sendDiscordText, t as buildDiscordSendError, w as DiscordSendError, x as DISCORD_MAX_EMOJI_BYTES, z as DISCORD_REST_TIMEOUT_MS } from "./send.shared-BmwFjW6T.js";
|
|
5
|
+
import { n as sendPollDiscord, o as rewriteDiscordKnownMentions, r as sendStickerDiscord, t as sendMessageDiscord } from "./send.outbound-DS5tHwfR.js";
|
|
6
|
+
import { r as createDiscordSendResult } from "./send.receipt-IPI1p-SP.js";
|
|
6
7
|
import { n as DISCORD_ATTACHMENT_TOTAL_TIMEOUT_MS } from "./timeouts-B9cy6RvQ.js";
|
|
7
|
-
import {
|
|
8
|
+
import { i as removeReactionDiscord, n as reactMessageDiscord, r as removeOwnReactionsDiscord, t as fetchReactionsDiscord } from "./send.reactions-BAn0iiVQ.js";
|
|
8
9
|
import { normalizeLowercaseStringOrEmpty, normalizeOptionalLowercaseString, normalizeOptionalString, normalizeStringEntries } from "openclaw/plugin-sdk/string-coerce-runtime";
|
|
9
10
|
import fs from "node:fs/promises";
|
|
10
11
|
import { ChannelType } from "discord-api-types/v10";
|
|
@@ -18,11 +19,11 @@ import { truncateUtf16Safe } from "openclaw/plugin-sdk/text-utility-runtime";
|
|
|
18
19
|
import { recordChannelActivity } from "openclaw/plugin-sdk/channel-activity-runtime";
|
|
19
20
|
import { requireRuntimeConfig } from "openclaw/plugin-sdk/plugin-config-runtime";
|
|
20
21
|
import { recordOutboundMessageIdentity } from "openclaw/plugin-sdk/channel-outbound";
|
|
21
|
-
import { MEDIA_FFMPEG_MAX_AUDIO_DURATION_SECS, extensionForMime, maxBytesForKind, parseFfprobeCodecAndSampleRate, runFfmpeg, runFfprobe, unlinkIfExists } from "openclaw/plugin-sdk/media-runtime";
|
|
22
|
+
import { MEDIA_FFMPEG_MAX_AUDIO_DURATION_SECS, buildOutboundMediaLoadOptions, extensionForMime, maxBytesForKind, parseFfprobeCodecAndSampleRate, runFfmpeg, runFfprobe, unlinkIfExists } from "openclaw/plugin-sdk/media-runtime";
|
|
22
23
|
import { loadWebMediaRaw } from "openclaw/plugin-sdk/web-media";
|
|
23
24
|
import { buildTimeoutAbortSignal } from "openclaw/plugin-sdk/extension-shared";
|
|
24
25
|
import path from "node:path";
|
|
25
|
-
import { resolvePreferredOpenClawTmpDir,
|
|
26
|
+
import { resolvePreferredOpenClawTmpDir, withTempWorkspace } from "openclaw/plugin-sdk/temp-path";
|
|
26
27
|
import { writeExternalFileWithinRoot } from "openclaw/plugin-sdk/security-runtime";
|
|
27
28
|
//#region extensions/discord/src/send.channels.ts
|
|
28
29
|
async function createChannelDiscord(payload, opts) {
|
|
@@ -218,8 +219,11 @@ async function banMemberDiscord(payload, opts) {
|
|
|
218
219
|
}
|
|
219
220
|
//#endregion
|
|
220
221
|
//#region extensions/discord/src/send.messages.ts
|
|
221
|
-
|
|
222
|
-
|
|
222
|
+
const DISCORD_THREAD_TRANSPORT_ONLY_MAX_LINES = Number.MAX_SAFE_INTEGER;
|
|
223
|
+
function resolveDiscordThreadStarterMessageId(thread) {
|
|
224
|
+
const starterMessage = "message" in thread ? thread.message : void 0;
|
|
225
|
+
if (starterMessage && typeof starterMessage === "object" && "id" in starterMessage && typeof starterMessage.id === "string") return starterMessage.id;
|
|
226
|
+
return thread.id;
|
|
223
227
|
}
|
|
224
228
|
function assertDiscordResponseArray(value, label) {
|
|
225
229
|
if (!Array.isArray(value)) throw new Error(`Unexpected Discord response for ${label}: expected array.`);
|
|
@@ -233,12 +237,22 @@ function resolveDefaultThreadAutoArchiveDuration(channel) {
|
|
|
233
237
|
if (!channel || !("default_auto_archive_duration" in channel)) return;
|
|
234
238
|
return channel.default_auto_archive_duration;
|
|
235
239
|
}
|
|
240
|
+
function describeDiscordThreadInitialMessageFailure(delivery) {
|
|
241
|
+
if (delivery?.failedChunkDelivery === "unknown") return delivery.deliveredChunkCount > 0 ? "Discord thread was created, but delivery of the remaining initial content could not be confirmed" : "Discord thread was created, but initial message delivery could not be confirmed";
|
|
242
|
+
return delivery && delivery.deliveredChunkCount > 0 ? "Discord thread was created, but its initial content was only partially delivered" : "Discord thread was created, but sending the initial message failed";
|
|
243
|
+
}
|
|
236
244
|
var DiscordThreadInitialMessageError = class extends Error {
|
|
237
|
-
constructor(thread, error) {
|
|
238
|
-
const initialMessageError =
|
|
239
|
-
|
|
245
|
+
constructor(thread, error, initialMessageDelivery) {
|
|
246
|
+
const initialMessageError = formatErrorMessage(error);
|
|
247
|
+
const initialMessageWarning = describeDiscordThreadInitialMessageFailure(initialMessageDelivery);
|
|
248
|
+
super(`${initialMessageWarning}: ${initialMessageError}`, { cause: error });
|
|
240
249
|
this.name = "DiscordThreadInitialMessageError";
|
|
250
|
+
this.initialMessageDelivery = initialMessageDelivery ? {
|
|
251
|
+
...initialMessageDelivery,
|
|
252
|
+
deliveredMessageIds: [...initialMessageDelivery.deliveredMessageIds]
|
|
253
|
+
} : void 0;
|
|
241
254
|
this.initialMessageError = initialMessageError;
|
|
255
|
+
this.initialMessageWarning = initialMessageWarning;
|
|
242
256
|
this.thread = thread;
|
|
243
257
|
}
|
|
244
258
|
};
|
|
@@ -278,7 +292,7 @@ async function listPinsDiscord(channelId, opts) {
|
|
|
278
292
|
return await listChannelPins(resolveDiscordRest(opts), channelId);
|
|
279
293
|
}
|
|
280
294
|
async function createThreadDiscord(channelId, payload, opts) {
|
|
281
|
-
const rest =
|
|
295
|
+
const { rest, request } = createDiscordClient(opts);
|
|
282
296
|
const body = { name: payload.name };
|
|
283
297
|
if (!payload.messageId && payload.type !== void 0) body.type = payload.type;
|
|
284
298
|
let channel;
|
|
@@ -288,16 +302,52 @@ async function createThreadDiscord(channelId, payload, opts) {
|
|
|
288
302
|
const archiveDuration = payload.autoArchiveMinutes ?? resolveDefaultThreadAutoArchiveDuration(channel);
|
|
289
303
|
if (archiveDuration !== void 0) body.auto_archive_duration = archiveDuration;
|
|
290
304
|
const isForumLike = channel?.type === ChannelType.GuildForum || channel?.type === ChannelType.GuildMedia;
|
|
305
|
+
const initialMessageChunks = buildDiscordTextChunks(isForumLike ? payload.content?.trim() ? payload.content : payload.name : payload.content?.trim() ? payload.content : "", { maxLinesPerMessage: DISCORD_THREAD_TRANSPORT_ONLY_MAX_LINES });
|
|
291
306
|
if (isForumLike) {
|
|
292
|
-
body.message = { content:
|
|
307
|
+
body.message = { content: initialMessageChunks[0] ?? payload.name };
|
|
293
308
|
if (payload.appliedTags?.length) body.applied_tags = payload.appliedTags;
|
|
294
309
|
}
|
|
295
310
|
if (!payload.messageId && !isForumLike && body.type === void 0) body.type = ChannelType.PublicThread;
|
|
296
311
|
const thread = await createThread(rest, channelId, { body }, payload.messageId);
|
|
297
|
-
|
|
298
|
-
|
|
299
|
-
|
|
300
|
-
|
|
312
|
+
const followupChunks = isForumLike ? initialMessageChunks.slice(1) : initialMessageChunks;
|
|
313
|
+
if (followupChunks.length && "id" in thread) {
|
|
314
|
+
const deliveredMessageIds = isForumLike ? [resolveDiscordThreadStarterMessageId(thread)] : [];
|
|
315
|
+
let deliveredChunkCount = isForumLike ? 1 : 0;
|
|
316
|
+
const firstFollowupChunkIndex = isForumLike ? 1 : 0;
|
|
317
|
+
for (const [followupIndex, content] of followupChunks.entries()) {
|
|
318
|
+
let chunkMayHaveDelivered = false;
|
|
319
|
+
const trackedRequest = (fn, label, options) => request(async () => {
|
|
320
|
+
try {
|
|
321
|
+
return await fn();
|
|
322
|
+
} catch (error) {
|
|
323
|
+
chunkMayHaveDelivered ||= classifyDiscordDeliveryFailure(error) === "ambiguous";
|
|
324
|
+
throw error;
|
|
325
|
+
}
|
|
326
|
+
}, label, options);
|
|
327
|
+
try {
|
|
328
|
+
const result = await sendDiscordText({
|
|
329
|
+
rest,
|
|
330
|
+
request: trackedRequest,
|
|
331
|
+
channelId: thread.id,
|
|
332
|
+
text: content,
|
|
333
|
+
maxLinesPerMessage: DISCORD_THREAD_TRANSPORT_ONLY_MAX_LINES
|
|
334
|
+
});
|
|
335
|
+
deliveredMessageIds.push(...result.platformMessageIds);
|
|
336
|
+
deliveredChunkCount += 1;
|
|
337
|
+
} catch (error) {
|
|
338
|
+
const finalFailure = classifyDiscordDeliveryFailure(error);
|
|
339
|
+
const failedChunkDelivery = chunkMayHaveDelivered || finalFailure === "ambiguous" || finalFailure === "unknown" ? "unknown" : "not_delivered";
|
|
340
|
+
if (failedChunkDelivery === "unknown") recordDiscordMessageCreateAmbiguity(error);
|
|
341
|
+
throw new DiscordThreadInitialMessageError(thread, error, {
|
|
342
|
+
starterMessageDelivered: isForumLike,
|
|
343
|
+
deliveredChunkCount,
|
|
344
|
+
deliveredMessageIds,
|
|
345
|
+
failedChunkDelivery,
|
|
346
|
+
failedChunkIndex: firstFollowupChunkIndex + followupIndex,
|
|
347
|
+
totalChunkCount: initialMessageChunks.length
|
|
348
|
+
});
|
|
349
|
+
}
|
|
350
|
+
}
|
|
301
351
|
}
|
|
302
352
|
return thread;
|
|
303
353
|
}
|
|
@@ -322,7 +372,15 @@ async function searchMessagesDiscord(query, opts) {
|
|
|
322
372
|
const limit = Math.min(Math.max(Math.floor(query.limit), 1), 25);
|
|
323
373
|
params.set("limit", String(limit));
|
|
324
374
|
}
|
|
325
|
-
|
|
375
|
+
const result = assertDiscordResponseObject(await searchGuildMessages(rest, query.guildId, params), "message search");
|
|
376
|
+
if (result.code === 11e4) {
|
|
377
|
+
const message = typeof result.message === "string" && result.message.trim() ? result.message.trim() : "Discord search index is not yet available";
|
|
378
|
+
const retryAfter = parseDiscordRetryAfterBodySeconds(result.retry_after);
|
|
379
|
+
const retryHint = retryAfter === void 0 ? "" : ` (retry after ${retryAfter}s)`;
|
|
380
|
+
throw new Error(`Discord message search unavailable: ${message}${retryHint}`);
|
|
381
|
+
}
|
|
382
|
+
if (!Array.isArray(result.messages)) throw new Error("Unexpected Discord response for message search: expected messages array.");
|
|
383
|
+
return result;
|
|
326
384
|
}
|
|
327
385
|
//#endregion
|
|
328
386
|
//#region extensions/discord/src/send.webhook.ts
|
|
@@ -376,6 +434,7 @@ async function sendWebhookMessageDiscord(text, opts) {
|
|
|
376
434
|
accountId: account.accountId,
|
|
377
435
|
mentionAliases: account.config.mentionAliases
|
|
378
436
|
});
|
|
437
|
+
const flags = resolveDiscordMessageFlags({ suppressEmbeds: resolveDiscordSuppressEmbeds({ configured: account.config.suppressEmbeds }) });
|
|
379
438
|
const threadConversationId = opts.threadId == null ? "" : String(opts.threadId).trim();
|
|
380
439
|
if (threadConversationId) recordOutboundMessageIdentity({
|
|
381
440
|
channel: "discord",
|
|
@@ -393,19 +452,25 @@ async function sendWebhookMessageDiscord(text, opts) {
|
|
|
393
452
|
timeoutMs: DISCORD_WEBHOOK_TIMEOUT_MS,
|
|
394
453
|
operation: "discord.webhook.send"
|
|
395
454
|
});
|
|
455
|
+
const request = createDiscordRetryRunner({ signal: deadline.signal });
|
|
396
456
|
try {
|
|
397
|
-
const response = await (
|
|
398
|
-
|
|
399
|
-
|
|
400
|
-
|
|
401
|
-
content:
|
|
402
|
-
|
|
403
|
-
|
|
404
|
-
|
|
405
|
-
|
|
406
|
-
|
|
407
|
-
|
|
408
|
-
|
|
457
|
+
const response = await request(async () => {
|
|
458
|
+
await opts.onPlatformSendDispatch?.();
|
|
459
|
+
const attemptResponse = await (proxyFetch ?? fetch)(url, {
|
|
460
|
+
method: "POST",
|
|
461
|
+
headers: { "content-type": "application/json" },
|
|
462
|
+
body: JSON.stringify({
|
|
463
|
+
content: rewrittenText,
|
|
464
|
+
username: normalizeOptionalString(opts.username),
|
|
465
|
+
avatar_url: normalizeOptionalString(opts.avatarUrl),
|
|
466
|
+
...flags ? { flags } : {},
|
|
467
|
+
...messageReference ? { message_reference: messageReference } : {}
|
|
468
|
+
}),
|
|
469
|
+
signal: deadline.signal
|
|
470
|
+
});
|
|
471
|
+
if (!attemptResponse.ok) await throwWebhookResponseError(attemptResponse, deadline.signal);
|
|
472
|
+
return attemptResponse;
|
|
473
|
+
}, "webhook", { safety: "non-idempotent-create" });
|
|
409
474
|
const payload = response.status === 204 ? {} : await readProviderJsonResponse(response, "Discord webhook send").catch(() => {
|
|
410
475
|
throwIfWebhookDeadlineExpired(deadline.signal);
|
|
411
476
|
return {};
|
|
@@ -735,7 +800,20 @@ async function sendDiscordVoiceMessage(rest, channelId, audioBuffer, metadata, r
|
|
|
735
800
|
message_id: replyTo,
|
|
736
801
|
fail_if_not_exists: false
|
|
737
802
|
};
|
|
738
|
-
|
|
803
|
+
let messageCreateMayHaveCommitted = false;
|
|
804
|
+
try {
|
|
805
|
+
return await request(async () => {
|
|
806
|
+
try {
|
|
807
|
+
return await rest.post(`/channels/${channelId}/messages`, { body: messagePayload });
|
|
808
|
+
} catch (error) {
|
|
809
|
+
messageCreateMayHaveCommitted ||= classifyDiscordDeliveryFailure(error) === "ambiguous";
|
|
810
|
+
throw error;
|
|
811
|
+
}
|
|
812
|
+
}, "voice-message", { safety: "nonce-protected-create" });
|
|
813
|
+
} catch (error) {
|
|
814
|
+
if (messageCreateMayHaveCommitted) recordDiscordMessageCreateAmbiguity(error);
|
|
815
|
+
throw error;
|
|
816
|
+
}
|
|
739
817
|
}
|
|
740
818
|
//#endregion
|
|
741
819
|
//#region extensions/discord/src/send.voice.ts
|
|
@@ -747,19 +825,20 @@ function toDiscordSendResult(result, fallbackChannelId, reply) {
|
|
|
747
825
|
reply
|
|
748
826
|
});
|
|
749
827
|
}
|
|
750
|
-
async function
|
|
751
|
-
const media = await loadWebMediaRaw(mediaUrl,
|
|
828
|
+
async function withMaterializedVoiceMessageInput(mediaUrl, opts, run) {
|
|
829
|
+
const media = await loadWebMediaRaw(mediaUrl, buildOutboundMediaLoadOptions({
|
|
830
|
+
maxBytes: maxBytesForKind("audio"),
|
|
831
|
+
mediaAccess: opts.mediaAccess,
|
|
832
|
+
mediaLocalRoots: opts.mediaLocalRoots,
|
|
833
|
+
mediaReadFile: opts.mediaReadFile
|
|
834
|
+
}));
|
|
752
835
|
const extFromName = media.fileName ? path.extname(media.fileName) : "";
|
|
753
836
|
const extFromMime = media.contentType ? extensionForMime(media.contentType) : "";
|
|
754
837
|
const ext = extFromName || extFromMime || ".bin";
|
|
755
|
-
|
|
838
|
+
return await withTempWorkspace({
|
|
756
839
|
rootDir: resolvePreferredOpenClawTmpDir(),
|
|
757
840
|
prefix: "voice-src-"
|
|
758
|
-
});
|
|
759
|
-
return {
|
|
760
|
-
filePath: await workspace.write(`input${ext}`, media.buffer),
|
|
761
|
-
cleanup: () => workspace.cleanup().then(() => void 0)
|
|
762
|
-
};
|
|
841
|
+
}, async (workspace) => await run(await workspace.write(`input${ext}`, media.buffer)));
|
|
763
842
|
}
|
|
764
843
|
/**
|
|
765
844
|
* Send a voice message to Discord.
|
|
@@ -772,52 +851,62 @@ async function materializeVoiceMessageInput(mediaUrl) {
|
|
|
772
851
|
* @param opts - Send options
|
|
773
852
|
*/
|
|
774
853
|
async function sendVoiceMessageDiscord(to, audioPath, opts) {
|
|
775
|
-
const { filePath: localInputPath, cleanup: cleanupLocalInput } = await materializeVoiceMessageInput(audioPath);
|
|
776
|
-
let oggPath = null;
|
|
777
|
-
let oggCleanup = false;
|
|
778
|
-
let token;
|
|
779
|
-
let rest;
|
|
780
|
-
let channelId;
|
|
781
854
|
const cfg = requireRuntimeConfig(opts.cfg, "Discord voice send");
|
|
782
|
-
|
|
783
|
-
|
|
784
|
-
|
|
785
|
-
|
|
786
|
-
|
|
787
|
-
|
|
788
|
-
|
|
789
|
-
|
|
790
|
-
|
|
791
|
-
|
|
792
|
-
|
|
793
|
-
|
|
794
|
-
|
|
795
|
-
|
|
796
|
-
|
|
797
|
-
|
|
798
|
-
|
|
799
|
-
|
|
800
|
-
|
|
801
|
-
|
|
802
|
-
|
|
803
|
-
|
|
804
|
-
|
|
805
|
-
|
|
806
|
-
|
|
807
|
-
|
|
808
|
-
|
|
809
|
-
|
|
810
|
-
|
|
811
|
-
|
|
812
|
-
|
|
813
|
-
|
|
814
|
-
|
|
815
|
-
})
|
|
816
|
-
|
|
817
|
-
|
|
818
|
-
|
|
819
|
-
|
|
820
|
-
|
|
855
|
+
return await withMaterializedVoiceMessageInput(audioPath, opts, async (localInputPath) => {
|
|
856
|
+
let oggPath = null;
|
|
857
|
+
let oggCleanup = false;
|
|
858
|
+
let token;
|
|
859
|
+
let rest;
|
|
860
|
+
let channelId;
|
|
861
|
+
try {
|
|
862
|
+
const accountInfo = resolveDiscordAccount({
|
|
863
|
+
cfg,
|
|
864
|
+
accountId: opts.accountId
|
|
865
|
+
});
|
|
866
|
+
const client = createDiscordClient({
|
|
867
|
+
...opts,
|
|
868
|
+
cfg
|
|
869
|
+
});
|
|
870
|
+
token = client.token;
|
|
871
|
+
rest = client.rest;
|
|
872
|
+
const request = client.request;
|
|
873
|
+
const recipient = await parseAndResolveChannelRecipient(to, cfg, opts.accountId);
|
|
874
|
+
channelId = (await resolveChannelId(rest, recipient, request)).channelId;
|
|
875
|
+
const ogg = await ensureOggOpus(localInputPath);
|
|
876
|
+
oggPath = ogg.path;
|
|
877
|
+
oggCleanup = ogg.cleanup;
|
|
878
|
+
const metadata = await getVoiceMessageMetadata(oggPath);
|
|
879
|
+
const audioBuffer = await fs.readFile(oggPath);
|
|
880
|
+
await opts.onPlatformSendDispatch?.();
|
|
881
|
+
const result = await sendDiscordVoiceMessage(rest, channelId, audioBuffer, metadata, opts.reply?.messageId, request, opts.silent, token);
|
|
882
|
+
recordChannelActivity({
|
|
883
|
+
channel: "discord",
|
|
884
|
+
accountId: accountInfo.accountId,
|
|
885
|
+
direction: "outbound"
|
|
886
|
+
});
|
|
887
|
+
return toDiscordSendResult(result, channelId, opts.reply);
|
|
888
|
+
} catch (err) {
|
|
889
|
+
if (channelId && rest && token) throw await buildDiscordSendError(err, {
|
|
890
|
+
channelId,
|
|
891
|
+
cfg,
|
|
892
|
+
rest,
|
|
893
|
+
token,
|
|
894
|
+
hasMedia: true
|
|
895
|
+
});
|
|
896
|
+
throw err;
|
|
897
|
+
} finally {
|
|
898
|
+
await unlinkIfExists(oggCleanup ? oggPath : null);
|
|
899
|
+
}
|
|
900
|
+
});
|
|
901
|
+
}
|
|
902
|
+
//#endregion
|
|
903
|
+
//#region extensions/discord/src/send.typing.ts
|
|
904
|
+
async function sendTypingDiscord(channelId, opts) {
|
|
905
|
+
await sendChannelTyping(resolveDiscordRest(opts), channelId);
|
|
906
|
+
return {
|
|
907
|
+
ok: true,
|
|
908
|
+
channelId
|
|
909
|
+
};
|
|
821
910
|
}
|
|
822
911
|
//#endregion
|
|
823
912
|
//#region extensions/discord/src/send.ts
|
|
@@ -877,4 +966,4 @@ var send_exports = /* @__PURE__ */ __exportAll({
|
|
|
877
966
|
uploadStickerDiscord: () => uploadStickerDiscord
|
|
878
967
|
});
|
|
879
968
|
//#endregion
|
|
880
|
-
export {
|
|
969
|
+
export { listGuildEmojisDiscord as A, fetchVoiceStatusDiscord as C, removeRoleDiscord as D, listScheduledEventsDiscord as E, editChannelDiscord as F, moveChannelDiscord as I, removeChannelPermissionDiscord as L, uploadStickerDiscord as M, createChannelDiscord as N, resolveEventCoverImage as O, deleteChannelDiscord as P, setChannelPermissionDiscord as R, fetchRoleInfoDiscord as S, listGuildChannelsDiscord as T, banMemberDiscord as _, DiscordThreadInitialMessageError as a, fetchGuildInfoDiscord as b, editMessageDiscord as c, listThreadsDiscord as d, pinMessageDiscord as f, addRoleDiscord as g, unpinMessageDiscord as h, sendWebhookMessageDiscord as i, uploadEmojiDiscord as j, timeoutMemberDiscord as k, fetchMessageDiscord as l, searchMessagesDiscord as m, sendTypingDiscord as n, createThreadDiscord as o, readMessagesDiscord as p, sendVoiceMessageDiscord as r, deleteMessageDiscord as s, send_exports as t, listPinsDiscord as u, createScheduledEventDiscord as v, kickMemberDiscord as w, fetchMemberInfoDiscord as x, fetchChannelInfoDiscord as y };
|
|
@@ -1,12 +1,12 @@
|
|
|
1
|
-
import {
|
|
1
|
+
import { H as serializePayload, ft as stripUndefinedFields, tn as __exportAll, wt as editChannelMessage, yt as createChannelMessage } from "./retry-CLpJcXXf.js";
|
|
2
2
|
import { s as resolveDiscordAccount } from "./accounts-DJTf1LtA.js";
|
|
3
|
-
import { f as buildDiscordComponentMessage, g as resolveDiscordComponentAttachmentName, p as buildDiscordComponentMessageFlags } from "./outbound-session-route-
|
|
4
|
-
import { P as createDiscordClient, W as parseAndResolveChannelRecipient,
|
|
3
|
+
import { f as buildDiscordComponentMessage, g as resolveDiscordComponentAttachmentName, p as buildDiscordComponentMessageFlags } from "./outbound-session-route-DxLkrgKQ.js";
|
|
4
|
+
import { P as createDiscordClient, W as parseAndResolveChannelRecipient, g as createDiscordMessageNonce, l as resolveChannelId, m as SUPPRESS_NOTIFICATIONS_FLAG, t as buildDiscordSendError, u as resolveDiscordChannel } from "./send.shared-BmwFjW6T.js";
|
|
5
5
|
import { n as getOptionalDiscordRuntime } from "./runtime-DgnVQ7zW.js";
|
|
6
|
-
import "./config-schema-
|
|
6
|
+
import "./config-schema-BgEskFAs.js";
|
|
7
7
|
import "./channel-api-CAJ0wMoV.js";
|
|
8
|
-
import { t as sendMessageDiscord } from "./send.outbound-
|
|
9
|
-
import {
|
|
8
|
+
import { t as sendMessageDiscord } from "./send.outbound-DS5tHwfR.js";
|
|
9
|
+
import { r as createDiscordSendResult } from "./send.receipt-IPI1p-SP.js";
|
|
10
10
|
import "openclaw/plugin-sdk/account-helpers";
|
|
11
11
|
import "openclaw/plugin-sdk/account-id";
|
|
12
12
|
import "openclaw/plugin-sdk/channel-config-helpers";
|
|
@@ -18,27 +18,27 @@ import { asDateTimestampMs, isFutureDateTimestampMs, resolveDateTimestampMs, res
|
|
|
18
18
|
import { assertMediaNotDataUrl, jsonResult as jsonResult$1, parseAvailableTags, readNonNegativeIntegerParam, readPositiveIntegerParam, readReactionParams, readStringArrayParam, readStringParam as readStringParam$1, resolvePollMaxSelections, withNormalizedTimestamp } from "openclaw/plugin-sdk/channel-actions";
|
|
19
19
|
import { recordChannelActivity } from "openclaw/plugin-sdk/channel-activity-runtime";
|
|
20
20
|
import { requireRuntimeConfig } from "openclaw/plugin-sdk/plugin-config-runtime";
|
|
21
|
-
import {
|
|
21
|
+
import { createPluginStateErrorReporter } from "openclaw/plugin-sdk/plugin-state-runtime";
|
|
22
|
+
import { resolveGlobalSingleton } from "openclaw/plugin-sdk/global-singleton";
|
|
22
23
|
import "openclaw/plugin-sdk/channel-status";
|
|
23
24
|
import "openclaw/plugin-sdk/channel-config-schema";
|
|
24
25
|
import { readBooleanParam as readBooleanParam$1 } from "openclaw/plugin-sdk/boolean-param";
|
|
25
26
|
import "openclaw/plugin-sdk/channel-plugin-common";
|
|
26
27
|
import { loadOutboundMediaFromUrl } from "openclaw/plugin-sdk/outbound-media";
|
|
27
28
|
//#region extensions/discord/src/components-registry-state.ts
|
|
28
|
-
const discordComponentRegistryState = {
|
|
29
|
-
componentEntries:
|
|
30
|
-
modalEntries:
|
|
29
|
+
const discordComponentRegistryState = resolveGlobalSingleton(Symbol.for("openclaw.discord.componentRegistryState"), () => ({
|
|
30
|
+
componentEntries: /* @__PURE__ */ new Map(),
|
|
31
|
+
modalEntries: /* @__PURE__ */ new Map(),
|
|
31
32
|
persistentComponentStore: void 0,
|
|
32
33
|
persistentModalStore: void 0,
|
|
33
|
-
persistentRegistryDisabled: false
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
};
|
|
34
|
+
persistentRegistryDisabled: false
|
|
35
|
+
}), (state) => {
|
|
36
|
+
state.componentEntries.clear();
|
|
37
|
+
state.modalEntries.clear();
|
|
38
|
+
state.persistentComponentStore = void 0;
|
|
39
|
+
state.persistentModalStore = void 0;
|
|
40
|
+
state.persistentRegistryDisabled = false;
|
|
41
|
+
});
|
|
42
42
|
//#endregion
|
|
43
43
|
//#region extensions/discord/src/components-registry.ts
|
|
44
44
|
const DEFAULT_COMPONENT_TTL_MS = 1800 * 1e3;
|
|
@@ -52,14 +52,6 @@ function getComponentEntries() {
|
|
|
52
52
|
function getModalEntries() {
|
|
53
53
|
return discordComponentRegistryState.modalEntries;
|
|
54
54
|
}
|
|
55
|
-
function reportPersistentComponentRegistryError(error) {
|
|
56
|
-
try {
|
|
57
|
-
getOptionalDiscordRuntime()?.logging.getChildLogger({
|
|
58
|
-
plugin: "discord",
|
|
59
|
-
feature: "component-registry-state"
|
|
60
|
-
}).warn("Discord persistent component registry state failed", formatRegistryError(error));
|
|
61
|
-
} catch {}
|
|
62
|
-
}
|
|
63
55
|
function formatRegistryError(error) {
|
|
64
56
|
if (!(error instanceof Error)) return { error: formatRegistryErrorValue(error) };
|
|
65
57
|
const details = {
|
|
@@ -77,6 +69,7 @@ function formatRegistryError(error) {
|
|
|
77
69
|
} else if (cause !== void 0) details.errorCause = formatRegistryErrorValue(cause);
|
|
78
70
|
return details;
|
|
79
71
|
}
|
|
72
|
+
const reportPersistentComponentRegistryError = createPluginStateErrorReporter(getOptionalDiscordRuntime, "discord", "component-registry-state", "Discord persistent component registry state failed", formatRegistryError);
|
|
80
73
|
function formatRegistryErrorValue(value) {
|
|
81
74
|
if (typeof value === "string") return value;
|
|
82
75
|
if (typeof value === "number" || typeof value === "boolean" || typeof value === "bigint" || typeof value === "symbol") return String(value);
|
|
@@ -385,7 +378,8 @@ async function buildDiscordComponentPayload(params) {
|
|
|
385
378
|
spec = withImplicitComponentAttachmentBlock(spec, resolvedFileName);
|
|
386
379
|
files = [{
|
|
387
380
|
data: media.buffer,
|
|
388
|
-
name: resolvedFileName
|
|
381
|
+
name: resolvedFileName,
|
|
382
|
+
contentType: media.contentType
|
|
389
383
|
}];
|
|
390
384
|
}
|
|
391
385
|
const uniqueAttachmentNames = uniqueStrings(extractComponentAttachmentNames(spec));
|
|
@@ -433,6 +427,7 @@ async function sendDiscordComponentMessage(to, spec, opts) {
|
|
|
433
427
|
tableMode: opts.tableMode,
|
|
434
428
|
chunkMode: opts.chunkMode,
|
|
435
429
|
onDeliveryResult: opts.onDeliveryResult,
|
|
430
|
+
onPlatformSendDispatch: opts.onPlatformSendDispatch,
|
|
436
431
|
...opts.suppressEmbeds === void 0 ? {} : { suppressEmbeds: opts.suppressEmbeds }
|
|
437
432
|
});
|
|
438
433
|
const cfg = requireRuntimeConfig(opts.cfg, "Discord component send");
|
|
@@ -459,6 +454,7 @@ async function sendDiscordComponentMessage(to, spec, opts) {
|
|
|
459
454
|
};
|
|
460
455
|
let result;
|
|
461
456
|
try {
|
|
457
|
+
await opts.onPlatformSendDispatch?.();
|
|
462
458
|
result = await request(() => createChannelMessage(rest, channelId, { body }), "components", { safety: "nonce-protected-create" });
|
|
463
459
|
} catch (err) {
|
|
464
460
|
throw await buildDiscordSendError(err, {
|
|
@@ -1,8 +1,8 @@
|
|
|
1
|
-
import {
|
|
1
|
+
import { bt as createThread, o as createReusableDiscordReplyReference, yt as createChannelMessage } from "./retry-CLpJcXXf.js";
|
|
2
2
|
import { s as resolveDiscordAccount } from "./accounts-DJTf1LtA.js";
|
|
3
|
-
import { P as createDiscordClient, W as parseAndResolveChannelRecipient, _ as resolveDiscordMessageFlags, a as normalizeDiscordPollInput, c as normalizeStickerIds, f as sendDiscordMedia, g as createDiscordMessageNonce, h as buildDiscordMessageRequest, l as resolveChannelId, n as buildDiscordTextChunks, p as sendDiscordText, t as buildDiscordSendError, u as resolveDiscordChannel, v as resolveDiscordSendComponents, y as resolveDiscordSendEmbeds } from "./send.shared-
|
|
4
|
-
import { i as normalizeDiscordHandleKey, o as resolveDiscordDirectoryUserId } from "./directory-live-
|
|
5
|
-
import { n as createDiscordSendResult } from "./send.receipt-
|
|
3
|
+
import { P as createDiscordClient, W as parseAndResolveChannelRecipient, _ as resolveDiscordMessageFlags, a as normalizeDiscordPollInput, b as resolveDiscordSuppressEmbeds, c as normalizeStickerIds, f as sendDiscordMedia, g as createDiscordMessageNonce, h as buildDiscordMessageRequest, l as resolveChannelId, n as buildDiscordTextChunks, p as sendDiscordText, t as buildDiscordSendError, u as resolveDiscordChannel, v as resolveDiscordSendComponents, y as resolveDiscordSendEmbeds } from "./send.shared-BmwFjW6T.js";
|
|
4
|
+
import { i as normalizeDiscordHandleKey, o as resolveDiscordDirectoryUserId } from "./directory-live-DGIGxpIo.js";
|
|
5
|
+
import { n as createDiscordSendReceiptFromResults, r as createDiscordSendResult } from "./send.receipt-IPI1p-SP.js";
|
|
6
6
|
import { normalizeLowercaseStringOrEmpty, normalizeOptionalString, normalizeOptionalStringifiedId } from "openclaw/plugin-sdk/string-coerce-runtime";
|
|
7
7
|
import { ChannelType } from "discord-api-types/v10";
|
|
8
8
|
import { expectDefined } from "openclaw/plugin-sdk/expect-runtime";
|
|
@@ -416,6 +416,8 @@ function discordTextHasBroadcastMention(text) {
|
|
|
416
416
|
//#endregion
|
|
417
417
|
//#region extensions/discord/src/send.outbound.ts
|
|
418
418
|
const DEFAULT_DISCORD_MEDIA_MAX_MB = 100;
|
|
419
|
+
/** Discord's ChannelFlags.RequireTag is bit 4 on forum/media parent channels. */
|
|
420
|
+
const DISCORD_FORUM_REQUIRE_TAG_FLAG = 16;
|
|
419
421
|
async function sendDiscordThreadTextChunks(params) {
|
|
420
422
|
for (const chunk of params.chunks) await sendDiscordText({
|
|
421
423
|
rest: params.rest,
|
|
@@ -428,12 +430,10 @@ async function sendDiscordThreadTextChunks(params) {
|
|
|
428
430
|
suppressEmbeds: params.suppressEmbeds,
|
|
429
431
|
allowedMentions: params.allowedMentions,
|
|
430
432
|
maxChars: params.maxChars,
|
|
431
|
-
onResult: params.onResult
|
|
433
|
+
onResult: params.onResult,
|
|
434
|
+
onPlatformSendDispatch: params.onPlatformSendDispatch
|
|
432
435
|
});
|
|
433
436
|
}
|
|
434
|
-
function resolveDiscordSuppressEmbeds(params) {
|
|
435
|
-
return params.override ?? params.configured ?? true;
|
|
436
|
-
}
|
|
437
437
|
/** Discord thread names are capped at 100 characters. */
|
|
438
438
|
const DISCORD_THREAD_NAME_LIMIT = 100;
|
|
439
439
|
/** Derive a thread title from the first non-empty line of the message text. */
|
|
@@ -499,6 +499,7 @@ async function sendMessageDiscord(to, text, opts) {
|
|
|
499
499
|
const { channelId } = await resolveChannelId(rest, await parseAndResolveChannelRecipient(to, cfg, opts.accountId), request);
|
|
500
500
|
const channel = await resolveDiscordChannel(rest, channelId);
|
|
501
501
|
if (isForumLikeChannel(channel)) {
|
|
502
|
+
if (((channel.flags ?? 0) & DISCORD_FORUM_REQUIRE_TAG_FLAG) !== 0) throw new Error(`Discord forum channel ${channelId} requires an applied tag; use thread-create with appliedTags, then send to the created thread.`);
|
|
502
503
|
const threadName = deriveForumThreadName(renderedText);
|
|
503
504
|
const chunks = buildDiscordTextChunks(textWithMentions, {
|
|
504
505
|
maxLinesPerMessage,
|
|
@@ -528,6 +529,7 @@ async function sendMessageDiscord(to, text, opts) {
|
|
|
528
529
|
});
|
|
529
530
|
let threadRes;
|
|
530
531
|
try {
|
|
532
|
+
await opts.onPlatformSendDispatch?.();
|
|
531
533
|
threadRes = await request(() => createThread(rest, channelId, { body: {
|
|
532
534
|
name: threadName,
|
|
533
535
|
...channel.default_auto_archive_duration === void 0 ? {} : { auto_archive_duration: channel.default_auto_archive_duration },
|
|
@@ -546,18 +548,22 @@ async function sendMessageDiscord(to, text, opts) {
|
|
|
546
548
|
const messageId = threadRes.message?.id ?? threadId;
|
|
547
549
|
const resultChannelId = threadRes.message?.channel_id ?? threadId;
|
|
548
550
|
const remainingChunks = chunks.slice(1);
|
|
549
|
-
|
|
551
|
+
const starterResult = toDiscordSendResult({
|
|
550
552
|
id: messageId,
|
|
551
553
|
channel_id: resultChannelId
|
|
552
554
|
}, channelId, {
|
|
553
555
|
kind: "text",
|
|
554
556
|
threadId
|
|
555
|
-
})
|
|
557
|
+
});
|
|
558
|
+
const deliveredResults = [starterResult];
|
|
559
|
+
await opts.onDeliveryResult?.(starterResult);
|
|
556
560
|
const reportThreadResult = async (result, kind) => {
|
|
557
|
-
|
|
561
|
+
const deliveredResult = toDiscordSendResult(result, threadId, {
|
|
558
562
|
kind,
|
|
559
563
|
threadId
|
|
560
|
-
})
|
|
564
|
+
});
|
|
565
|
+
deliveredResults.push(deliveredResult);
|
|
566
|
+
await opts.onDeliveryResult?.(deliveredResult);
|
|
561
567
|
};
|
|
562
568
|
try {
|
|
563
569
|
if (opts.mediaUrl) {
|
|
@@ -579,7 +585,8 @@ async function sendMessageDiscord(to, text, opts) {
|
|
|
579
585
|
suppressEmbeds,
|
|
580
586
|
allowedMentions: opts.allowedMentions,
|
|
581
587
|
maxChars: textLimit,
|
|
582
|
-
onResult: reportThreadResult
|
|
588
|
+
onResult: reportThreadResult,
|
|
589
|
+
onPlatformSendDispatch: opts.onPlatformSendDispatch
|
|
583
590
|
});
|
|
584
591
|
await sendDiscordThreadTextChunks({
|
|
585
592
|
rest,
|
|
@@ -592,7 +599,8 @@ async function sendMessageDiscord(to, text, opts) {
|
|
|
592
599
|
silent: opts.silent,
|
|
593
600
|
suppressEmbeds,
|
|
594
601
|
allowedMentions: opts.allowedMentions,
|
|
595
|
-
onResult: reportThreadResult
|
|
602
|
+
onResult: reportThreadResult,
|
|
603
|
+
onPlatformSendDispatch: opts.onPlatformSendDispatch
|
|
596
604
|
});
|
|
597
605
|
} else await sendDiscordThreadTextChunks({
|
|
598
606
|
rest,
|
|
@@ -605,7 +613,8 @@ async function sendMessageDiscord(to, text, opts) {
|
|
|
605
613
|
silent: opts.silent,
|
|
606
614
|
suppressEmbeds,
|
|
607
615
|
allowedMentions: opts.allowedMentions,
|
|
608
|
-
onResult: reportThreadResult
|
|
616
|
+
onResult: reportThreadResult,
|
|
617
|
+
onPlatformSendDispatch: opts.onPlatformSendDispatch
|
|
609
618
|
});
|
|
610
619
|
} catch (err) {
|
|
611
620
|
throw await buildDiscordSendError(err, {
|
|
@@ -621,13 +630,13 @@ async function sendMessageDiscord(to, text, opts) {
|
|
|
621
630
|
accountId: accountInfo.accountId,
|
|
622
631
|
direction: "outbound"
|
|
623
632
|
});
|
|
624
|
-
return
|
|
625
|
-
|
|
626
|
-
|
|
627
|
-
|
|
628
|
-
|
|
629
|
-
|
|
630
|
-
}
|
|
633
|
+
return {
|
|
634
|
+
...starterResult,
|
|
635
|
+
receipt: createDiscordSendReceiptFromResults({
|
|
636
|
+
results: deliveredResults,
|
|
637
|
+
threadId
|
|
638
|
+
})
|
|
639
|
+
};
|
|
631
640
|
}
|
|
632
641
|
let result;
|
|
633
642
|
const reportResult = async (progressResult, kind, replyToId) => {
|
|
@@ -657,7 +666,8 @@ async function sendMessageDiscord(to, text, opts) {
|
|
|
657
666
|
suppressEmbeds,
|
|
658
667
|
allowedMentions: opts.allowedMentions,
|
|
659
668
|
maxChars: textLimit,
|
|
660
|
-
onResult: reportResult
|
|
669
|
+
onResult: reportResult,
|
|
670
|
+
onPlatformSendDispatch: opts.onPlatformSendDispatch
|
|
661
671
|
});
|
|
662
672
|
else result = await sendDiscordText({
|
|
663
673
|
rest,
|
|
@@ -673,7 +683,8 @@ async function sendMessageDiscord(to, text, opts) {
|
|
|
673
683
|
suppressEmbeds,
|
|
674
684
|
allowedMentions: opts.allowedMentions,
|
|
675
685
|
maxChars: textLimit,
|
|
676
|
-
onResult: reportResult
|
|
686
|
+
onResult: reportResult,
|
|
687
|
+
onPlatformSendDispatch: opts.onPlatformSendDispatch
|
|
677
688
|
});
|
|
678
689
|
} catch (err) {
|
|
679
690
|
throw await buildDiscordSendError(err, {
|
|
@@ -705,6 +716,7 @@ async function sendStickerDiscord(to, stickerIds, opts) {
|
|
|
705
716
|
enforce_nonce: true,
|
|
706
717
|
...flags ? { flags } : {}
|
|
707
718
|
};
|
|
719
|
+
await opts.onPlatformSendDispatch?.();
|
|
708
720
|
return toDiscordSendResult(await request(() => createChannelMessage(rest, channelId, { body }), "sticker", { safety: "nonce-protected-create" }), channelId, { kind: "card" });
|
|
709
721
|
}
|
|
710
722
|
async function sendPollDiscord(to, poll, opts) {
|
|
@@ -722,6 +734,7 @@ async function sendPollDiscord(to, poll, opts) {
|
|
|
722
734
|
enforce_nonce: true,
|
|
723
735
|
...flags ? { flags } : {}
|
|
724
736
|
};
|
|
737
|
+
await opts.onPlatformSendDispatch?.();
|
|
725
738
|
return toDiscordSendResult(await request(() => createChannelMessage(rest, channelId, { body }), "poll", { safety: "nonce-protected-create" }), channelId, { kind: "card" });
|
|
726
739
|
}
|
|
727
740
|
async function resolveDiscordStructuredSendContext(to, opts) {
|