@openclaw/discord 2026.8.1 → 2026.8.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.
Files changed (89) hide show
  1. package/dist/account-inspect-BY-ve3yH.js +45 -0
  2. package/dist/account-inspect-api.js +1 -1
  3. package/dist/{accounts-CfQ-vSyf.js → accounts-CwJQoLjM.js} +89 -45
  4. package/dist/action-runtime-api.js +1 -1
  5. package/dist/{activities-api-Dl-TOyOX.js → activities-api-CkKcHUB6.js} +14 -13
  6. package/dist/activities-api.js +1 -1
  7. package/dist/{allow-list-BDMimASD.js → allow-list-C2JuH-R0.js} +10 -6
  8. package/dist/{api-DNVbJyEy.js → api-BfmEP6wp.js} +6 -5
  9. package/dist/api.js +17 -17
  10. package/dist/{approval-handler.runtime-q4Zqo44V.js → approval-handler.runtime-DZM6Kt1Z.js} +8 -7
  11. package/dist/{audit-DgrvFPGt.js → audit-DIbQA4VT.js} +8 -7
  12. package/dist/{channel-BsQUalPw.js → channel-CarzU3bg.js} +24 -22
  13. package/dist/{channel-actions.runtime-UMGGIfSy.js → channel-actions.runtime-B2wMqeVK.js} +13 -11
  14. package/dist/channel-config-api.js +1 -1
  15. package/dist/channel-plugin-api.js +1 -1
  16. package/dist/{channel.setup-rPs4dsk_.js → channel.setup-z_ewMVa9.js} +18 -18
  17. package/dist/{components-Dk35LTf_.js → components-gvRA0oaI.js} +1 -1
  18. package/dist/{config-schema-CxPqtVI1.js → config-schema-B797-Spt.js} +5 -4
  19. package/dist/{conversation-binding-route-BjvX4e35.js → conversation-binding-route-DPpBRpYI.js} +1 -1
  20. package/dist/{directory-config-B7DY_pNG.js → directory-config-AA8wQx0D.js} +2 -2
  21. package/dist/directory-contract-api.js +1 -1
  22. package/dist/{directory-live-DuAXKkan.js → directory-live-D_kFz_Fj.js} +4 -4
  23. package/dist/{doctor-zQTtn6hm.js → doctor-QQTOkBfW.js} +5 -5
  24. package/dist/{doctor-contract-DsWvKIXF.js → doctor-contract-Co5vRCZ6.js} +9 -6
  25. package/dist/doctor-contract-api.js +3 -2
  26. package/dist/{handle-action.guild-admin-DZewwLr1.js → handle-action.guild-admin-Cc88ZGon.js} +2 -2
  27. package/dist/index.js +1 -1
  28. package/dist/{ingress-identity-CzZKcPK8.js → ingress-identity-BCzfPPYM.js} +1 -1
  29. package/dist/{message-handler-C5By3yl5.js → message-handler-CAeEpqWo.js} +14 -10
  30. package/dist/{message-handler.preflight-DrszWuHw.js → message-handler.preflight-CoKoE3dY.js} +24 -19
  31. package/dist/{message-handler.process-DyFPDLCt.js → message-handler.process-cdIJ_fDT.js} +56 -74
  32. package/dist/{message-text-Ca8M6TU8.js → message-text-C0K4-fkg.js} +9 -4
  33. package/dist/{outbound-adapter-Dif8p481.js → outbound-adapter-Ch0At5Ra.js} +34 -24
  34. package/dist/{outbound-components-wjv7yyAj.js → outbound-components-Bnt_7x7r.js} +3 -3
  35. package/dist/{outbound-session-route-Bn4uXaoE.js → outbound-session-route-CzzerX2K.js} +10 -7
  36. package/dist/{owner-access-UlYi9t0M.js → owner-access-yc1sX7Gx.js} +7 -6
  37. package/dist/{pluralkit-9EuEN4UD.js → pluralkit-B3cUVI7i.js} +2 -2
  38. package/dist/{probe-n6ZXxK8V.js → probe-3ovFAp3b.js} +3 -3
  39. package/dist/{probe.runtime-CN4bdPfZ.js → probe.runtime-BckHn3cJ.js} +1 -1
  40. package/dist/{provider-LXiOcJrH.js → provider-CjI8BSzS.js} +97 -76
  41. package/dist/{provider-session.runtime-DSNe7r2W.js → provider-session.runtime-DdKRMcE9.js} +3 -3
  42. package/dist/provider.runtime-Bo1WbLLr.js +2 -0
  43. package/dist/{realtime-session.runtime-DOViOIjY.js → realtime-session.runtime-37IC-p5K.js} +5 -5
  44. package/dist/{resolve-allowlist-common-BLoYaxEG.js → resolve-allowlist-common-BJ5UZNNT.js} +3 -3
  45. package/dist/{resolve-channels-D2yl_2CN.js → resolve-channels-BexR2eUn.js} +4 -4
  46. package/dist/{resolve-users-BLxfqajZ.js → resolve-users-BtXBCH5W.js} +5 -4
  47. package/dist/{retry-after-DdLPmPoa.js → retry-after-BrLjLUJi.js} +2 -1
  48. package/dist/{retry-DqHCW6PV.js → retry-t5RcEsPk.js} +37 -29
  49. package/dist/{runtime-DrxVBTtp.js → runtime-BNlDfLwS.js} +2 -2
  50. package/dist/{runtime-BYamRVPN.js → runtime-DydyfxST.js} +126 -92
  51. package/dist/runtime-api.js +19 -19
  52. package/dist/{secret-config-contract-B3i6WxV5.js → secret-config-contract-DFu9hfU8.js} +14 -6
  53. package/dist/secret-contract-api.js +1 -1
  54. package/dist/{send-UJHiAm4C.js → send-mTKSBdmZ.js} +76 -48
  55. package/dist/{send.components-CrBJpGT_.js → send.components-nsPnc7kK.js} +20 -14
  56. package/dist/{send.outbound-D7JYmfm9.js → send.outbound-CaOs9Zy1.js} +34 -20
  57. package/dist/{send.shared-DZJ1akvQ.js → send.shared-BJHt0Vyf.js} +24 -17
  58. package/dist/{sender-identity-BJtfyise.js → sender-identity-Dt0imZyY.js} +1 -1
  59. package/dist/setup-plugin-api.js +1 -1
  60. package/dist/{shared-Dii2HTn7.js → shared-BNesVA4P.js} +17 -14
  61. package/dist/{subagent-hooks-JyGrtQIl.js → subagent-hooks-IeZVPLGj.js} +2 -2
  62. package/dist/subagent-hooks-api.js +1 -1
  63. package/dist/{system-events-BEmcj4xJ.js → system-events-Be5EJI3b.js} +2 -2
  64. package/dist/{target-resolver-V-IYae6s.js → target-resolver-C0MnwEki.js} +6 -5
  65. package/dist/targets-DQSye1Rv.js +3 -0
  66. package/dist/{thread-bindings-DvYP79fy.js → thread-bindings-wECUSIIG.js} +6 -5
  67. package/dist/{thread-bindings.manager-Clm77DBM.js → thread-bindings.manager-B-3UHCc1.js} +28 -25
  68. package/dist/{thread-bindings.session-updates-CJb-BpPL.js → thread-bindings.session-updates-CC7HoQvt.js} +2 -1
  69. package/dist/{threading-CXuu_7o9.js → threading-te5ADPQI.js} +8 -6
  70. package/dist/{timeouts-B9cy6RvQ.js → timeouts-D86uWLt_.js} +1 -1
  71. package/dist/{transcripts-source-BLEMH_yi.js → transcripts-source-DkUhR7YK.js} +3 -3
  72. package/dist/transcripts-source-api.js +1 -1
  73. package/dist/{typing-B9snnwMe.js → typing-DAwJF5VT.js} +2 -2
  74. package/dist/{voice-runtime-DY6_o73o.js → voice-runtime-COyYYTDD.js} +348 -14
  75. package/node_modules/@discord/embedded-app-sdk/node_modules/@types/lodash/README.md +1 -1
  76. package/node_modules/@discord/embedded-app-sdk/node_modules/@types/lodash/conforms.d.ts +2 -0
  77. package/node_modules/@discord/embedded-app-sdk/node_modules/@types/lodash/package.json +3 -3
  78. package/node_modules/@discord/embedded-app-sdk/node_modules/@types/lodash/stubArray.d.ts +2 -0
  79. package/node_modules/@discord/embedded-app-sdk/node_modules/@types/lodash/stubObject.d.ts +2 -0
  80. package/node_modules/@discord/embedded-app-sdk/node_modules/@types/lodash/stubString.d.ts +2 -0
  81. package/node_modules/typebox/build/format/email.mjs +1 -1
  82. package/node_modules/typebox/build/format/idna/idn-hostname.mjs +19 -1
  83. package/node_modules/typebox/package.json +1 -1
  84. package/openclaw.plugin.json +2 -2
  85. package/package.json +5 -5
  86. package/dist/account-inspect-BDfKyuvL.js +0 -89
  87. package/dist/provider.runtime-DiInaDXO.js +0 -2
  88. package/dist/sdk-runtime-6tfgYDjY.js +0 -338
  89. package/dist/targets-CQp53cGj.js +0 -3
@@ -1,89 +0,0 @@
1
- import { o as mergeDiscordAccountConfig, s as resolveDefaultDiscordAccountId, u as resolveDiscordAccountConfig } from "./accounts-CfQ-vSyf.js";
2
- import { DEFAULT_ACCOUNT_ID, normalizeAccountId } from "openclaw/plugin-sdk/account-id";
3
- import { normalizeOptionalString } from "openclaw/plugin-sdk/string-coerce-runtime";
4
- import { hasConfiguredSecretInput, normalizeSecretInputString } from "openclaw/plugin-sdk/secret-input";
5
- //#region extensions/discord/src/account-token-inspect.ts
6
- function inspectDiscordConfiguredToken(value) {
7
- const normalized = normalizeSecretInputString(value);
8
- if (normalized) return {
9
- token: normalized.replace(/^Bot\s+/i, ""),
10
- tokenSource: "config",
11
- tokenStatus: "available"
12
- };
13
- if (hasConfiguredSecretInput(value)) return {
14
- token: "",
15
- tokenSource: "config",
16
- tokenStatus: "configured_unavailable"
17
- };
18
- return null;
19
- }
20
- function inspectDiscordAccountTokenState(params) {
21
- const accountToken = inspectDiscordConfiguredToken(params.accountToken);
22
- if (accountToken) return {
23
- ...params.base,
24
- ...accountToken,
25
- configured: true,
26
- config: params.config
27
- };
28
- if (params.hasAccountToken) return {
29
- ...params.base,
30
- token: "",
31
- tokenSource: "none",
32
- tokenStatus: "missing",
33
- configured: false,
34
- config: params.config
35
- };
36
- const channelToken = inspectDiscordConfiguredToken(params.channelToken);
37
- if (channelToken) return {
38
- ...params.base,
39
- ...channelToken,
40
- configured: true,
41
- config: params.config
42
- };
43
- const fallback = params.resolveFallbackToken();
44
- if (fallback.token) return {
45
- ...params.base,
46
- token: fallback.token,
47
- tokenSource: fallback.source,
48
- tokenStatus: "available",
49
- configured: true,
50
- config: params.config
51
- };
52
- return {
53
- ...params.base,
54
- token: "",
55
- tokenSource: "none",
56
- tokenStatus: "missing",
57
- configured: false,
58
- config: params.config
59
- };
60
- }
61
- //#endregion
62
- //#region extensions/discord/src/account-inspect.ts
63
- function inspectDiscordAccount(params) {
64
- const accountId = normalizeAccountId(params.accountId ?? resolveDefaultDiscordAccountId(params.cfg));
65
- const merged = mergeDiscordAccountConfig(params.cfg, accountId);
66
- const enabled = params.cfg.channels?.discord?.enabled !== false && merged.enabled !== false;
67
- const accountConfig = resolveDiscordAccountConfig(params.cfg, accountId);
68
- const hasAccountToken = Boolean(accountConfig && Object.hasOwn(accountConfig, "token"));
69
- return inspectDiscordAccountTokenState({
70
- base: {
71
- accountId,
72
- enabled,
73
- name: normalizeOptionalString(merged.name)
74
- },
75
- config: merged,
76
- accountToken: accountConfig?.token,
77
- hasAccountToken,
78
- channelToken: params.cfg.channels?.discord?.token,
79
- resolveFallbackToken: () => {
80
- const envToken = accountId === DEFAULT_ACCOUNT_ID ? normalizeSecretInputString(params.envToken ?? process.env.DISCORD_BOT_TOKEN) : void 0;
81
- return {
82
- token: envToken?.replace(/^Bot\s+/i, "") ?? "",
83
- source: envToken ? "env" : "none"
84
- };
85
- }
86
- });
87
- }
88
- //#endregion
89
- export { inspectDiscordAccountTokenState as n, inspectDiscordAccount as t };
@@ -1,2 +0,0 @@
1
- import { t as monitorDiscordProvider } from "./provider-LXiOcJrH.js";
2
- export { monitorDiscordProvider };
@@ -1,338 +0,0 @@
1
- import { y as discord_exports } from "./retry-DqHCW6PV.js";
2
- import { createRequire } from "node:module";
3
- import fs from "node:fs/promises";
4
- import { formatErrorMessage } from "openclaw/plugin-sdk/ssrf-runtime";
5
- import { logVerbose, shouldLogVerbose } from "openclaw/plugin-sdk/runtime-env";
6
- import { truncateUtf16Safe } from "openclaw/plugin-sdk/text-utility-runtime";
7
- import { resolveFfmpegBin } from "openclaw/plugin-sdk/media-runtime";
8
- import { resolvePreferredOpenClawTmpDir, tempWorkspace } from "openclaw/plugin-sdk/temp-path";
9
- import { controlRealtimeVoiceAgentRun, resamplePcm, shouldAutoControlRealtimeVoiceAgentText } from "openclaw/plugin-sdk/realtime-voice";
10
- import { spawn } from "node:child_process";
11
- import { Transform } from "node:stream";
12
- import { StringDecoder } from "node:string_decoder";
13
- import { Application, createDecoder, createEncoder } from "libopus-wasm";
14
- //#region extensions/discord/src/voice/log-preview.ts
15
- const DISCORD_VOICE_LOG_PREVIEW_CHARS = 500;
16
- function formatVoiceLogPreview(text) {
17
- const oneLine = text.replace(/\s+/g, " ").trim();
18
- if (oneLine.length <= DISCORD_VOICE_LOG_PREVIEW_CHARS) return oneLine;
19
- return `${truncateUtf16Safe(oneLine, DISCORD_VOICE_LOG_PREVIEW_CHARS)}...`;
20
- }
21
- //#endregion
22
- //#region extensions/discord/src/voice/agent-control.ts
23
- async function maybeControlDiscordVoiceAgentRun(params) {
24
- if (!shouldAutoControlRealtimeVoiceAgentText(params.text)) return { handled: false };
25
- const result = await controlRealtimeVoiceAgentRun({
26
- sessionKey: params.entry.route.sessionKey,
27
- text: params.text
28
- });
29
- if (!result.active) return {
30
- handled: false,
31
- result
32
- };
33
- return {
34
- handled: true,
35
- result,
36
- ...result.speak && !result.suppress ? { speakText: result.message } : {}
37
- };
38
- }
39
- //#endregion
40
- //#region extensions/discord/src/voice/prompt.ts
41
- const DISCORD_VOICE_SPOKEN_OUTPUT_CONTRACT = [
42
- "You are OpenClaw's Discord voice interface in a live voice channel.",
43
- "Discord voice reply requirements:",
44
- "- Return only the concise text that should be spoken aloud in the voice channel.",
45
- "- Treat the transcript as speech-to-text from a live conversation; repair obvious transcription artifacts and ignore repeated partial fragments caused by voice buffering.",
46
- "- If the transcript is garbled, incomplete, or missing the user's intent, ask one brief clarifying question instead of guessing.",
47
- "- If the request needs deeper reasoning, current information, or tools, use the available tools before answering.",
48
- "- Do not call the tts tool; Discord voice will synthesize and play the returned text.",
49
- "- Do not reply with NO_REPLY unless no spoken response is appropriate.",
50
- "- Keep the response brief, natural, and conversational. Prefer one to three short sentences.",
51
- "- Avoid markdown tables, code fences, citations, and visual formatting unless the user explicitly asks for something that cannot be spoken naturally."
52
- ].join("\n");
53
- function formatVoiceIngressPrompt(transcript, speakerLabel) {
54
- const cleanedTranscript = transcript.trim();
55
- const cleanedLabel = speakerLabel?.trim();
56
- const voiceInput = cleanedLabel ? [`Voice transcript from speaker "${cleanedLabel}":`, cleanedTranscript].join("\n") : cleanedTranscript;
57
- return [DISCORD_VOICE_SPOKEN_OUTPUT_CONTRACT, voiceInput].join("\n\n");
58
- }
59
- //#endregion
60
- //#region extensions/discord/src/voice/audio.ts
61
- const SAMPLE_RATE = 48e3;
62
- const CHANNELS = 2;
63
- const BIT_DEPTH = 16;
64
- const FFMPEG_ERROR_OUTPUT_BYTES = 8192;
65
- const DISCORD_OPUS_FRAME_SIZE = 960;
66
- const DISCORD_OPUS_FRAME_BYTES = DISCORD_OPUS_FRAME_SIZE * CHANNELS * (BIT_DEPTH / 8);
67
- const FFMPEG_PCM_ARGUMENTS = [
68
- "-analyzeduration",
69
- "0",
70
- "-loglevel",
71
- "error",
72
- "-vn",
73
- "-sn",
74
- "-dn",
75
- "-f",
76
- "s16le",
77
- "-ar",
78
- String(SAMPLE_RATE),
79
- "-ac",
80
- String(CHANNELS)
81
- ];
82
- let warnedOpusMissing = false;
83
- function buildWavBuffer(pcm) {
84
- const blockAlign = CHANNELS * BIT_DEPTH / 8;
85
- const byteRate = SAMPLE_RATE * blockAlign;
86
- const header = Buffer.alloc(44);
87
- header.write("RIFF", 0);
88
- header.writeUInt32LE(36 + pcm.length, 4);
89
- header.write("WAVE", 8);
90
- header.write("fmt ", 12);
91
- header.writeUInt32LE(16, 16);
92
- header.writeUInt16LE(1, 20);
93
- header.writeUInt16LE(CHANNELS, 22);
94
- header.writeUInt32LE(SAMPLE_RATE, 24);
95
- header.writeUInt32LE(byteRate, 28);
96
- header.writeUInt16LE(blockAlign, 32);
97
- header.writeUInt16LE(BIT_DEPTH, 34);
98
- header.write("data", 36);
99
- header.writeUInt32LE(pcm.length, 40);
100
- return Buffer.concat([header, pcm]);
101
- }
102
- function createDiscordOpusEncodeStream() {
103
- return new DiscordOpusEncodeStream();
104
- }
105
- function createDiscordOpusPlaybackStream(input) {
106
- const inputSource = typeof input === "string" ? input : "pipe:0";
107
- const ffmpeg = spawn(resolveFfmpegBin(), [
108
- "-i",
109
- inputSource,
110
- ...FFMPEG_PCM_ARGUMENTS,
111
- "pipe:1"
112
- ], {
113
- stdio: [
114
- "pipe",
115
- "pipe",
116
- "pipe"
117
- ],
118
- windowsHide: true
119
- });
120
- const opusStream = createDiscordOpusEncodeStream();
121
- const stderr = Buffer.alloc(FFMPEG_ERROR_OUTPUT_BYTES);
122
- let stderrBytes = 0;
123
- let ffmpegClosed = false;
124
- const killFfmpeg = (signal = "SIGTERM") => {
125
- if (!ffmpegClosed && !ffmpeg.killed) ffmpeg.kill(signal);
126
- };
127
- ffmpeg.stderr.on("data", (chunk) => {
128
- if (stderrBytes < FFMPEG_ERROR_OUTPUT_BYTES) stderrBytes += chunk.copy(stderr, stderrBytes, 0, FFMPEG_ERROR_OUTPUT_BYTES - stderrBytes);
129
- });
130
- ffmpeg.once("error", (err) => {
131
- opusStream.destroy(err);
132
- });
133
- ffmpeg.once("close", (code, signal) => {
134
- ffmpegClosed = true;
135
- if (code && code !== 0) {
136
- const stderrText = new StringDecoder("utf8").write(stderr.subarray(0, stderrBytes)).trim();
137
- const suffix = stderrText ? `: ${stderrText}` : "";
138
- opusStream.destroy(/* @__PURE__ */ new Error(`ffmpeg exited with code ${code}${suffix}`));
139
- return;
140
- }
141
- if (signal) opusStream.destroy(/* @__PURE__ */ new Error(`ffmpeg exited with signal ${signal}`));
142
- });
143
- for (const readable of [ffmpeg.stdout, ffmpeg.stderr]) readable.on("error", (err) => {
144
- killFfmpeg("SIGKILL");
145
- opusStream.destroy(err);
146
- });
147
- ffmpeg.stdin.on("error", (err) => {
148
- if (err.code !== "EPIPE") opusStream.destroy(err);
149
- });
150
- ffmpeg.stdout.pipe(opusStream);
151
- opusStream.once("close", () => {
152
- if (!opusStream.readableEnded) killFfmpeg();
153
- });
154
- if (typeof input !== "string") {
155
- input.on("error", (err) => {
156
- ffmpeg.stdin.destroy(err);
157
- opusStream.destroy(err);
158
- });
159
- input.pipe(ffmpeg.stdin);
160
- } else ffmpeg.stdin.end();
161
- return opusStream;
162
- }
163
- var DiscordOpusEncodeStream = class extends Transform {
164
- #buffer = Buffer.alloc(0);
165
- #encoder;
166
- constructor() {
167
- super({ readableObjectMode: true });
168
- }
169
- _construct(done) {
170
- createEncoder({
171
- application: Application.Audio,
172
- channels: CHANNELS,
173
- sampleRate: SAMPLE_RATE
174
- }).then((encoder) => {
175
- this.#encoder = encoder;
176
- done();
177
- }, (err) => done(err instanceof Error ? err : new Error(formatErrorMessage(err))));
178
- }
179
- _transform(chunk, _encoding, done) {
180
- try {
181
- this.#buffer = this.#buffer.length > 0 ? Buffer.concat([this.#buffer, chunk]) : Buffer.from(chunk);
182
- while (this.#buffer.length >= DISCORD_OPUS_FRAME_BYTES) {
183
- const frame = this.#buffer.subarray(0, DISCORD_OPUS_FRAME_BYTES);
184
- this.#buffer = this.#buffer.subarray(DISCORD_OPUS_FRAME_BYTES);
185
- this.#encodeFrame(frame);
186
- }
187
- done();
188
- } catch (err) {
189
- done(err instanceof Error ? err : new Error(formatErrorMessage(err)));
190
- }
191
- }
192
- _flush(done) {
193
- try {
194
- if (this.#buffer.length > 0) {
195
- const frame = Buffer.alloc(DISCORD_OPUS_FRAME_BYTES);
196
- this.#buffer.copy(frame);
197
- this.#buffer = Buffer.alloc(0);
198
- this.#encodeFrame(frame);
199
- }
200
- done();
201
- } catch (err) {
202
- done(err instanceof Error ? err : new Error(formatErrorMessage(err)));
203
- }
204
- }
205
- _destroy(err, done) {
206
- this.#encoder?.free();
207
- this.#buffer = Buffer.alloc(0);
208
- done(err);
209
- }
210
- #encodeFrame(frame) {
211
- this.push(Buffer.from(this.#encoder.encode(frame, { frameSize: DISCORD_OPUS_FRAME_SIZE })));
212
- }
213
- };
214
- function pcmInt16ToBuffer(pcm) {
215
- return Buffer.from(pcm.buffer, pcm.byteOffset, pcm.byteLength);
216
- }
217
- async function decodeOpusStream(stream, params) {
218
- const chunks = [];
219
- await decodeOpusStreamChunks(stream, {
220
- ...params,
221
- onChunk: (chunk) => chunks.push(chunk)
222
- });
223
- return Buffer.concat(chunks);
224
- }
225
- async function decodeOpusStreamChunks(stream, params) {
226
- let decoder;
227
- try {
228
- decoder = await createDecoder({
229
- channels: CHANNELS,
230
- sampleRate: SAMPLE_RATE
231
- });
232
- } catch (err) {
233
- if (!warnedOpusMissing) {
234
- warnedOpusMissing = true;
235
- params.onWarn(`discord voice: no usable opus decoder available (libopus-wasm: ${formatErrorMessage(err)}); cannot decode voice audio`);
236
- }
237
- return;
238
- }
239
- params.onVerbose("opus decoder: libopus-wasm");
240
- try {
241
- for await (const chunk of stream) {
242
- if (!chunk || !(chunk instanceof Buffer) || chunk.length === 0) continue;
243
- const decoded = decoder.decode(chunk, { maxFrameSize: DISCORD_OPUS_FRAME_SIZE });
244
- if (decoded.length > 0) params.onChunk(pcmInt16ToBuffer(decoded));
245
- }
246
- } catch (err) {
247
- params.onError?.(err);
248
- if (shouldLogVerbose()) logVerbose(`discord voice: opus decode failed: ${formatErrorMessage(err)}`);
249
- } finally {
250
- decoder.free();
251
- }
252
- }
253
- function convertDiscordPcm48kStereoToRealtimePcm24kMono(pcm) {
254
- const frameCount = Math.floor(pcm.length / 4);
255
- if (frameCount === 0) return Buffer.alloc(0);
256
- const mono48k = Buffer.alloc(frameCount * 2);
257
- for (let frame = 0; frame < frameCount; frame += 1) {
258
- const offset = frame * 4;
259
- const left = pcm.readInt16LE(offset);
260
- const right = pcm.readInt16LE(offset + 2);
261
- mono48k.writeInt16LE(Math.round((left + right) / 2), frame * 2);
262
- }
263
- return resamplePcm(mono48k, SAMPLE_RATE, 24e3);
264
- }
265
- function convertRealtimePcm24kMonoToDiscordPcm48kStereo(pcm) {
266
- const mono48k = resamplePcm(pcm, 24e3, SAMPLE_RATE);
267
- const sampleCount = Math.floor(mono48k.length / 2);
268
- if (sampleCount === 0) return Buffer.alloc(0);
269
- const stereo = Buffer.alloc(sampleCount * 4);
270
- for (let sampleIndex = 0; sampleIndex < sampleCount; sampleIndex += 1) {
271
- const sample = mono48k.readInt16LE(sampleIndex * 2);
272
- const offset = sampleIndex * 4;
273
- stereo.writeInt16LE(sample, offset);
274
- stereo.writeInt16LE(sample, offset + 2);
275
- }
276
- return stereo;
277
- }
278
- function estimateDurationSeconds(pcm) {
279
- const bytesPerSample = BIT_DEPTH / 8 * CHANNELS;
280
- return pcm.length / (bytesPerSample * SAMPLE_RATE);
281
- }
282
- async function writeVoiceWavFile(pcm) {
283
- const workspace = await tempWorkspace({
284
- rootDir: resolvePreferredOpenClawTmpDir(),
285
- prefix: "discord-voice-"
286
- });
287
- scheduleTempCleanup(workspace.dir);
288
- const wav = buildWavBuffer(pcm);
289
- return {
290
- path: await workspace.write("segment.wav", wav),
291
- durationSeconds: estimateDurationSeconds(pcm)
292
- };
293
- }
294
- function scheduleTempCleanup(tempDir, delayMs = 1800 * 1e3) {
295
- setTimeout(() => {
296
- fs.rm(tempDir, {
297
- recursive: true,
298
- force: true
299
- }).catch((err) => {
300
- if (shouldLogVerbose()) logVerbose(`discord voice: temp cleanup failed for ${tempDir}: ${formatErrorMessage(err)}`);
301
- });
302
- }, delayMs).unref();
303
- }
304
- //#endregion
305
- //#region extensions/discord/src/voice/session.ts
306
- const MIN_SEGMENT_SECONDS = .35;
307
- const CAPTURE_FINALIZE_GRACE_MS = 2e3;
308
- const VOICE_CONNECT_READY_TIMEOUT_MS = 3e4;
309
- const VOICE_RECONNECT_GRACE_MS = 15e3;
310
- const PLAYBACK_READY_TIMEOUT_MS = 6e4;
311
- function resolveVoiceTimeoutMs(value, fallbackMs) {
312
- if (typeof value !== "number" || !Number.isFinite(value) || value <= 0) return fallbackMs;
313
- return Math.floor(value);
314
- }
315
- function resolveDiscordVoiceMode(voice) {
316
- const mode = voice?.mode;
317
- if (mode === "stt-tts" || mode === "bidi") return mode;
318
- return "agent-proxy";
319
- }
320
- function isDiscordRealtimeVoiceMode(mode) {
321
- return mode === "agent-proxy" || mode === "bidi";
322
- }
323
- function logVoiceVerbose(message) {
324
- logVerbose(`discord voice: ${message}`);
325
- }
326
- function isVoiceChannel(type) {
327
- return type === discord_exports.ChannelType.GuildVoice || type === discord_exports.ChannelType.GuildStageVoice;
328
- }
329
- //#endregion
330
- //#region extensions/discord/src/voice/sdk-runtime.ts
331
- let cachedDiscordVoiceSdk = null;
332
- function loadDiscordVoiceSdk() {
333
- if (cachedDiscordVoiceSdk) return cachedDiscordVoiceSdk;
334
- cachedDiscordVoiceSdk = createRequire(import.meta.url)("@discordjs/voice");
335
- return cachedDiscordVoiceSdk;
336
- }
337
- //#endregion
338
- export { decodeOpusStreamChunks as _, VOICE_CONNECT_READY_TIMEOUT_MS as a, maybeControlDiscordVoiceAgentRun as b, isVoiceChannel as c, resolveVoiceTimeoutMs as d, convertDiscordPcm48kStereoToRealtimePcm24kMono as f, decodeOpusStream as g, createDiscordOpusPlaybackStream as h, PLAYBACK_READY_TIMEOUT_MS as i, logVoiceVerbose as l, createDiscordOpusEncodeStream as m, CAPTURE_FINALIZE_GRACE_MS as n, VOICE_RECONNECT_GRACE_MS as o, convertRealtimePcm24kMonoToDiscordPcm48kStereo as p, MIN_SEGMENT_SECONDS as r, isDiscordRealtimeVoiceMode as s, loadDiscordVoiceSdk as t, resolveDiscordVoiceMode as u, writeVoiceWavFile as v, formatVoiceLogPreview as x, formatVoiceIngressPrompt as y };
@@ -1,3 +0,0 @@
1
- import "./retry-DqHCW6PV.js";
2
- import "./target-resolver-V-IYae6s.js";
3
- export {};