@wu529778790/open-im 1.10.1-beta.0 → 1.10.2-beta.0
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/config-web.js +3 -2
- package/dist/dingtalk/event-handler.js +5 -5
- package/dist/feishu/event-handler.js +4 -4
- package/dist/qq/event-handler.js +7 -7
- package/dist/telegram/event-handler.js +15 -15
- package/dist/wework/event-handler.js +4 -4
- package/dist/wework/message-sender.js +5 -5
- package/dist/workbuddy/event-handler.js +3 -3
- package/dist/workbuddy/oauth.js +10 -1
- package/package.json +1 -1
package/dist/config-web.js
CHANGED
|
@@ -509,8 +509,8 @@ async function probeWorkBuddy(config) {
|
|
|
509
509
|
if (!accessToken || !refreshToken || !userId)
|
|
510
510
|
throw new Error("WorkBuddy access token, refresh token, and user ID are required.");
|
|
511
511
|
const baseUrl = clean(String(config.baseUrl ?? "")) || "https://copilot.tencent.com";
|
|
512
|
-
// Validate credentials by attempting to register workspace
|
|
513
|
-
const response = await fetch(`${baseUrl}/
|
|
512
|
+
// Validate credentials by attempting to register workspace (same endpoint as runtime)
|
|
513
|
+
const response = await fetch(`${baseUrl}/v2/agentos/localagent/registerWorkspace`, {
|
|
514
514
|
method: "POST",
|
|
515
515
|
headers: {
|
|
516
516
|
"content-type": "application/json",
|
|
@@ -521,6 +521,7 @@ async function probeWorkBuddy(config) {
|
|
|
521
521
|
hostId: "open-im-test",
|
|
522
522
|
workspaceId: "open-im-test-workspace",
|
|
523
523
|
workspaceName: "OpenIM Test Workspace",
|
|
524
|
+
localAgentType: "ide",
|
|
524
525
|
}),
|
|
525
526
|
signal: AbortSignal.timeout(TEST_TIMEOUT_MS),
|
|
526
527
|
});
|
|
@@ -217,7 +217,7 @@ export function setupDingTalkHandlers(config, sessionManager) {
|
|
|
217
217
|
const text = message.msgtype === 'text' ? message.text?.content?.trim() ?? '' : '';
|
|
218
218
|
log.info(`[MSG] DingTalk message: type=${message.msgtype}, user=${userId}, chat=${chatId}`);
|
|
219
219
|
if (!accessControl.isAllowed(userId)) {
|
|
220
|
-
await sendTextReply(chatId,
|
|
220
|
+
await sendTextReply(chatId, `抱歉,您没有访问权限。\n您的 ID: ${userId}`);
|
|
221
221
|
ackMessage(callbackId, { denied: true });
|
|
222
222
|
return;
|
|
223
223
|
}
|
|
@@ -247,10 +247,10 @@ export function setupDingTalkHandlers(config, sessionManager) {
|
|
|
247
247
|
}
|
|
248
248
|
const enqueueResult = await enqueuePrompt(userId, chatId, prompt, dingtalkTarget);
|
|
249
249
|
if (enqueueResult === 'rejected') {
|
|
250
|
-
await sendTextReply(chatId, '
|
|
250
|
+
await sendTextReply(chatId, '请求队列已满,请稍后再试。');
|
|
251
251
|
}
|
|
252
252
|
else if (enqueueResult === 'queued') {
|
|
253
|
-
await sendTextReply(chatId, '
|
|
253
|
+
await sendTextReply(chatId, '您的请求已排队等待。');
|
|
254
254
|
}
|
|
255
255
|
ackMessage(callbackId, { queued: enqueueResult, kind });
|
|
256
256
|
return;
|
|
@@ -273,10 +273,10 @@ export function setupDingTalkHandlers(config, sessionManager) {
|
|
|
273
273
|
}
|
|
274
274
|
const enqueueResult = await enqueuePrompt(userId, chatId, text, dingtalkTarget);
|
|
275
275
|
if (enqueueResult === 'rejected') {
|
|
276
|
-
await sendTextReply(chatId, '
|
|
276
|
+
await sendTextReply(chatId, '请求队列已满,请稍后再试。');
|
|
277
277
|
}
|
|
278
278
|
else if (enqueueResult === 'queued') {
|
|
279
|
-
await sendTextReply(chatId, '
|
|
279
|
+
await sendTextReply(chatId, '您的请求已排队等待。');
|
|
280
280
|
}
|
|
281
281
|
ackMessage(callbackId, { queued: enqueueResult });
|
|
282
282
|
}
|
|
@@ -322,12 +322,12 @@ export function setupFeishuHandlers(config, sessionManager) {
|
|
|
322
322
|
await handleAIRequest({ userId: senderId, chatId, prompt: p, workDir: work, convId, replyToMessageId: messageId, signal });
|
|
323
323
|
});
|
|
324
324
|
if (enqueueResult === 'rejected') {
|
|
325
|
-
sendTextReply(chatId, '
|
|
325
|
+
sendTextReply(chatId, '请求队列已满,请稍后再试。').catch((sendErr) => {
|
|
326
326
|
log.warn('[feishu] Failed to send queue full message for image:', sendErr);
|
|
327
327
|
});
|
|
328
328
|
}
|
|
329
329
|
else if (enqueueResult === 'queued') {
|
|
330
|
-
sendTextReply(chatId, '
|
|
330
|
+
sendTextReply(chatId, '您的请求已排队等待。').catch((sendErr) => {
|
|
331
331
|
log.warn('[feishu] Failed to send queued message for image:', sendErr);
|
|
332
332
|
});
|
|
333
333
|
}
|
|
@@ -370,12 +370,12 @@ export function setupFeishuHandlers(config, sessionManager) {
|
|
|
370
370
|
await handleAIRequest({ userId: senderId, chatId, prompt: p, workDir, convId, replyToMessageId: messageId, signal });
|
|
371
371
|
});
|
|
372
372
|
if (enqueueResult === 'rejected') {
|
|
373
|
-
sendTextReply(chatId, '
|
|
373
|
+
sendTextReply(chatId, '请求队列已满,请稍后再试。').catch((sendErr) => {
|
|
374
374
|
log.warn(`[feishu] Failed to send queue full message for ${msgType}:`, sendErr);
|
|
375
375
|
});
|
|
376
376
|
}
|
|
377
377
|
else if (enqueueResult === 'queued') {
|
|
378
|
-
sendTextReply(chatId, '
|
|
378
|
+
sendTextReply(chatId, '您的请求已排队等待。').catch((sendErr) => {
|
|
379
379
|
log.warn(`[feishu] Failed to send queued message for ${msgType}:`, sendErr);
|
|
380
380
|
});
|
|
381
381
|
}
|
package/dist/qq/event-handler.js
CHANGED
|
@@ -233,9 +233,9 @@ export function setupQQHandlers(config, sessionManager) {
|
|
|
233
233
|
workDir: sessionManager.getWorkDir(userId),
|
|
234
234
|
convId: sessionManager.getConvId(userId),
|
|
235
235
|
replyToMessageId: event.id,
|
|
236
|
-
accessDeniedMessage: (userId) =>
|
|
237
|
-
queueFullMessage: "
|
|
238
|
-
queuedMessage: "
|
|
236
|
+
accessDeniedMessage: (userId) => `抱歉,您没有访问权限。\n您的 ID: ${userId}`,
|
|
237
|
+
queueFullMessage: "请求队列已满,请稍后再试。",
|
|
238
|
+
queuedMessage: "您的请求已排队等待。",
|
|
239
239
|
});
|
|
240
240
|
if (processed) {
|
|
241
241
|
log.info(`QQ message handled: user=${userId}, chat=${chatId}, text=true`);
|
|
@@ -248,7 +248,7 @@ export function setupQQHandlers(config, sessionManager) {
|
|
|
248
248
|
const convId = sessionManager.getConvId(userId);
|
|
249
249
|
// Check access control
|
|
250
250
|
if (!accessControl.isAllowed(userId)) {
|
|
251
|
-
await sendTextReply(chatId,
|
|
251
|
+
await sendTextReply(chatId, `抱歉,您没有访问权限。\n您的 ID: ${userId}`);
|
|
252
252
|
return;
|
|
253
253
|
}
|
|
254
254
|
// Set active chat
|
|
@@ -267,10 +267,10 @@ export function setupQQHandlers(config, sessionManager) {
|
|
|
267
267
|
});
|
|
268
268
|
});
|
|
269
269
|
if (enqueueResult === "rejected") {
|
|
270
|
-
await sendTextReply(chatId, "
|
|
270
|
+
await sendTextReply(chatId, "请求队列已满,请稍后再试。");
|
|
271
271
|
}
|
|
272
272
|
else if (enqueueResult === "queued") {
|
|
273
|
-
await sendTextReply(chatId, "
|
|
273
|
+
await sendTextReply(chatId, "您的请求已排队等待。");
|
|
274
274
|
}
|
|
275
275
|
log.info(`QQ message handled: user=${userId}, chat=${chatId}, attachments=${event.attachments?.length ?? 0}`);
|
|
276
276
|
}
|
|
@@ -279,7 +279,7 @@ export function setupQQHandlers(config, sessionManager) {
|
|
|
279
279
|
log.error('Unhandled error in QQ event handler:', err);
|
|
280
280
|
try {
|
|
281
281
|
if (chatId) {
|
|
282
|
-
await sendTextReply(chatId, '
|
|
282
|
+
await sendTextReply(chatId, '内部错误,请重试。');
|
|
283
283
|
}
|
|
284
284
|
}
|
|
285
285
|
catch { /* ignore */ }
|
|
@@ -303,7 +303,7 @@ export function setupTelegramHandlers(bot, config, sessionManager) {
|
|
|
303
303
|
catch (err) {
|
|
304
304
|
log.error('Unhandled error in Telegram text handler:', err);
|
|
305
305
|
try {
|
|
306
|
-
await tgCtx.reply('
|
|
306
|
+
await tgCtx.reply('内部错误,请重试。');
|
|
307
307
|
}
|
|
308
308
|
catch { /* ignore */ }
|
|
309
309
|
}
|
|
@@ -333,10 +333,10 @@ export function setupTelegramHandlers(bot, config, sessionManager) {
|
|
|
333
333
|
}
|
|
334
334
|
const enqueueResult = await enqueueSavedMedia(userId, chatId, "image", imagePath, contextText);
|
|
335
335
|
if (enqueueResult === "rejected") {
|
|
336
|
-
await sendTextReply(chatId, "
|
|
336
|
+
await sendTextReply(chatId, "请求队列已满,请稍后再试。");
|
|
337
337
|
}
|
|
338
338
|
else if (enqueueResult === "queued") {
|
|
339
|
-
await sendTextReply(chatId, "
|
|
339
|
+
await sendTextReply(chatId, "您的请求已排队等待。");
|
|
340
340
|
}
|
|
341
341
|
});
|
|
342
342
|
bot.on(message("document"), async (ctx) => {
|
|
@@ -357,15 +357,15 @@ export function setupTelegramHandlers(bot, config, sessionManager) {
|
|
|
357
357
|
const path = await downloadTelegramFile(bot, document.file_id, document.file_name ?? document.file_id, "bin");
|
|
358
358
|
const enqueueResult = await enqueueSavedMedia(userId, chatId, "document", path, contextText);
|
|
359
359
|
if (enqueueResult === "rejected") {
|
|
360
|
-
await sendTextReply(chatId, "
|
|
360
|
+
await sendTextReply(chatId, "请求队列已满,请稍后再试。");
|
|
361
361
|
}
|
|
362
362
|
else if (enqueueResult === "queued") {
|
|
363
|
-
await sendTextReply(chatId, "
|
|
363
|
+
await sendTextReply(chatId, "您的请求已排队等待。");
|
|
364
364
|
}
|
|
365
365
|
}
|
|
366
366
|
catch (err) {
|
|
367
367
|
log.error("Failed to download document:", err);
|
|
368
|
-
await sendTextReply(chatId, "
|
|
368
|
+
await sendTextReply(chatId, "文档下载失败。");
|
|
369
369
|
}
|
|
370
370
|
});
|
|
371
371
|
bot.on(message("audio"), async (ctx) => {
|
|
@@ -388,15 +388,15 @@ export function setupTelegramHandlers(bot, config, sessionManager) {
|
|
|
388
388
|
const path = await downloadTelegramFile(bot, audio.file_id, audio.file_name ?? audio.file_id, "mp3");
|
|
389
389
|
const enqueueResult = await enqueueSavedMedia(userId, chatId, "audio", path, contextText);
|
|
390
390
|
if (enqueueResult === "rejected") {
|
|
391
|
-
await sendTextReply(chatId, "
|
|
391
|
+
await sendTextReply(chatId, "请求队列已满,请稍后再试。");
|
|
392
392
|
}
|
|
393
393
|
else if (enqueueResult === "queued") {
|
|
394
|
-
await sendTextReply(chatId, "
|
|
394
|
+
await sendTextReply(chatId, "您的请求已排队等待。");
|
|
395
395
|
}
|
|
396
396
|
}
|
|
397
397
|
catch (err) {
|
|
398
398
|
log.error("Failed to download audio:", err);
|
|
399
|
-
await sendTextReply(chatId, "
|
|
399
|
+
await sendTextReply(chatId, "音频下载失败。");
|
|
400
400
|
}
|
|
401
401
|
});
|
|
402
402
|
bot.on(message("voice"), async (ctx) => {
|
|
@@ -415,15 +415,15 @@ export function setupTelegramHandlers(bot, config, sessionManager) {
|
|
|
415
415
|
const path = await downloadTelegramFile(bot, voice.file_id, voice.file_unique_id ?? voice.file_id, "ogg");
|
|
416
416
|
const enqueueResult = await enqueueSavedMedia(userId, chatId, "voice", path, contextText);
|
|
417
417
|
if (enqueueResult === "rejected") {
|
|
418
|
-
await sendTextReply(chatId, "
|
|
418
|
+
await sendTextReply(chatId, "请求队列已满,请稍后再试。");
|
|
419
419
|
}
|
|
420
420
|
else if (enqueueResult === "queued") {
|
|
421
|
-
await sendTextReply(chatId, "
|
|
421
|
+
await sendTextReply(chatId, "您的请求已排队等待。");
|
|
422
422
|
}
|
|
423
423
|
}
|
|
424
424
|
catch (err) {
|
|
425
425
|
log.error("Failed to download voice message:", err);
|
|
426
|
-
await sendTextReply(chatId, "
|
|
426
|
+
await sendTextReply(chatId, "语音下载失败。");
|
|
427
427
|
}
|
|
428
428
|
});
|
|
429
429
|
bot.on(message("video"), async (ctx) => {
|
|
@@ -446,15 +446,15 @@ export function setupTelegramHandlers(bot, config, sessionManager) {
|
|
|
446
446
|
const path = await downloadTelegramFile(bot, video.file_id, video.file_name ?? video.file_unique_id ?? video.file_id, "mp4");
|
|
447
447
|
const enqueueResult = await enqueueSavedMedia(userId, chatId, "video", path, contextText);
|
|
448
448
|
if (enqueueResult === "rejected") {
|
|
449
|
-
await sendTextReply(chatId, "
|
|
449
|
+
await sendTextReply(chatId, "请求队列已满,请稍后再试。");
|
|
450
450
|
}
|
|
451
451
|
else if (enqueueResult === "queued") {
|
|
452
|
-
await sendTextReply(chatId, "
|
|
452
|
+
await sendTextReply(chatId, "您的请求已排队等待。");
|
|
453
453
|
}
|
|
454
454
|
}
|
|
455
455
|
catch (err) {
|
|
456
456
|
log.error("Failed to download video:", err);
|
|
457
|
-
await sendTextReply(chatId, "
|
|
457
|
+
await sendTextReply(chatId, "视频下载失败。");
|
|
458
458
|
}
|
|
459
459
|
});
|
|
460
460
|
return {
|
|
@@ -202,7 +202,7 @@ export function setupWeWorkHandlers(config, sessionManager) {
|
|
|
202
202
|
await sendFinalMessages(ctx.chatId, ctx.msgId, content, note ?? '', ctx.toolId, senderCtx.reqId);
|
|
203
203
|
},
|
|
204
204
|
sendError: async (error) => {
|
|
205
|
-
await updateMessage(ctx.chatId, ctx.msgId,
|
|
205
|
+
await updateMessage(ctx.chatId, ctx.msgId, `错误:${error}`, 'error', buildErrorNote(), ctx.toolId, senderCtx.reqId);
|
|
206
206
|
},
|
|
207
207
|
});
|
|
208
208
|
// WeWork-specific init for safety timeout
|
|
@@ -244,10 +244,10 @@ export function setupWeWorkHandlers(config, sessionManager) {
|
|
|
244
244
|
await handleAIRequest({ userId, chatId, prompt: nextPrompt, workDir, convId, replyToMessageId: undefined, signal });
|
|
245
245
|
});
|
|
246
246
|
if (enqueueResult === 'rejected') {
|
|
247
|
-
await sendTextReply(chatId, '
|
|
247
|
+
await sendTextReply(chatId, '请求队列已满,请稍后再试。', reqId);
|
|
248
248
|
}
|
|
249
249
|
else if (enqueueResult === 'queued') {
|
|
250
|
-
await sendTextReply(chatId, '
|
|
250
|
+
await sendTextReply(chatId, '您的请求已排队等待。', reqId);
|
|
251
251
|
}
|
|
252
252
|
}
|
|
253
253
|
async function handleEvent(data) {
|
|
@@ -263,7 +263,7 @@ export function setupWeWorkHandlers(config, sessionManager) {
|
|
|
263
263
|
// Check access control
|
|
264
264
|
if (!ctx.accessControl.isAllowed(fromUser)) {
|
|
265
265
|
log.warn(`Access denied for sender: ${fromUser}`);
|
|
266
|
-
await sendTextReply(chatId,
|
|
266
|
+
await sendTextReply(chatId, `抱歉,您没有访问权限。\n您的 ID: ${fromUser}`, reqId);
|
|
267
267
|
return;
|
|
268
268
|
}
|
|
269
269
|
setActiveChatId('wework', chatId);
|
|
@@ -22,10 +22,10 @@ function getReqId(explicitReqId) {
|
|
|
22
22
|
return explicitReqId;
|
|
23
23
|
}
|
|
24
24
|
const STATUS_CONFIG = {
|
|
25
|
-
thinking: { icon: '
|
|
26
|
-
streaming: { icon: '
|
|
27
|
-
done: { icon: '
|
|
28
|
-
error: { icon: '
|
|
25
|
+
thinking: { icon: '🔵', title: '思考中' },
|
|
26
|
+
streaming: { icon: '🔄', title: '输出中' },
|
|
27
|
+
done: { icon: '✅', title: '完成' },
|
|
28
|
+
error: { icon: '❌', title: '错误' },
|
|
29
29
|
};
|
|
30
30
|
function getToolTitle(toolId, status) {
|
|
31
31
|
return buildMessageTitle(toolId, status, {
|
|
@@ -84,7 +84,7 @@ function formatWeWorkMessage(title, content, status, note) {
|
|
|
84
84
|
message += `${content}\n\n`;
|
|
85
85
|
}
|
|
86
86
|
else if (status === 'thinking') {
|
|
87
|
-
message += `_正在思考,请稍候..._\n\n
|
|
87
|
+
message += `_正在思考,请稍候..._\n\n🔵 **准备中**\n\n`;
|
|
88
88
|
}
|
|
89
89
|
if (note) {
|
|
90
90
|
message += formatWeWorkNote(note);
|
|
@@ -135,7 +135,7 @@ export function setupWorkBuddyHandlers(config, sessionManager) {
|
|
|
135
135
|
// Access control check
|
|
136
136
|
if (!ctx.accessControl.isAllowed(userId)) {
|
|
137
137
|
log.warn(`Access denied for sender: ${userId}`);
|
|
138
|
-
await sendErrorReply(null, chatId,
|
|
138
|
+
await sendErrorReply(null, chatId, `抱歉,您没有访问权限。\n您的 ID: ${userId}`, msgId);
|
|
139
139
|
return;
|
|
140
140
|
}
|
|
141
141
|
setActiveChatId('workbuddy', chatId);
|
|
@@ -177,10 +177,10 @@ export function setupWorkBuddyHandlers(config, sessionManager) {
|
|
|
177
177
|
await handleAIRequest(userId, chatId, msgId, nextPrompt, workDir, convId, signal);
|
|
178
178
|
});
|
|
179
179
|
if (enqueueResult === 'rejected') {
|
|
180
|
-
await sendErrorReply(null, chatId, '
|
|
180
|
+
await sendErrorReply(null, chatId, '请求队列已满,请稍后再试。', msgId);
|
|
181
181
|
}
|
|
182
182
|
else if (enqueueResult === 'queued') {
|
|
183
|
-
await sendTextReply(null, chatId, '
|
|
183
|
+
await sendTextReply(null, chatId, '您的请求已排队等待。', msgId);
|
|
184
184
|
}
|
|
185
185
|
}
|
|
186
186
|
return {
|
package/dist/workbuddy/oauth.js
CHANGED
|
@@ -2,6 +2,8 @@
|
|
|
2
2
|
* WorkBuddy OAuth - CodeBuddy authentication for WeChat KF integration
|
|
3
3
|
*/
|
|
4
4
|
import { hostname } from 'node:os';
|
|
5
|
+
import { createLogger } from '../logger.js';
|
|
6
|
+
const log = createLogger('WorkBuddyOAuth');
|
|
5
7
|
const DEFAULT_BASE_URL = 'https://copilot.tencent.com';
|
|
6
8
|
const PLATFORM = 'ide';
|
|
7
9
|
export class WorkBuddyOAuth {
|
|
@@ -196,7 +198,14 @@ export class WorkBuddyOAuth {
|
|
|
196
198
|
return { success: false, message: `获取链接失败: ${res.status} ${body}` };
|
|
197
199
|
}
|
|
198
200
|
const body = (await res.json());
|
|
199
|
-
|
|
201
|
+
log.debug('getWeChatKfLink response:', JSON.stringify(body).slice(0, 500));
|
|
202
|
+
if (body.data)
|
|
203
|
+
return body.data;
|
|
204
|
+
// API may return fields directly without data wrapper
|
|
205
|
+
if (body.success !== undefined || body.url !== undefined) {
|
|
206
|
+
return body;
|
|
207
|
+
}
|
|
208
|
+
return { success: false, message: `Empty response: ${JSON.stringify(body).slice(0, 200)}` };
|
|
200
209
|
}
|
|
201
210
|
/**
|
|
202
211
|
* Check WeChat KF binding status
|