@yaoyuanchao/dingtalk 1.4.4 → 1.4.6

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 (2) hide show
  1. package/package.json +1 -1
  2. package/src/monitor.ts +52 -9
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@yaoyuanchao/dingtalk",
3
- "version": "1.4.4",
3
+ "version": "1.4.6",
4
4
  "type": "module",
5
5
  "description": "DingTalk channel plugin for Clawdbot with Stream Mode support",
6
6
  "license": "MIT",
package/src/monitor.ts CHANGED
@@ -164,23 +164,30 @@ async function extractMessageContent(
164
164
  if (chatRecordStr && typeof chatRecordStr === 'string') {
165
165
  const records = JSON.parse(chatRecordStr) as Array<{
166
166
  senderId?: string;
167
+ senderStaffId?: string; // Non-encrypted userId (available when app is published)
167
168
  senderNick?: string;
168
169
  msgType?: string;
169
170
  content?: string;
171
+ downloadCode?: string; // For media messages (picture, video, file)
170
172
  createAt?: number;
171
173
  }>;
172
174
 
173
175
  if (Array.isArray(records) && records.length > 0) {
174
- // Debug: log first record structure to understand available fields
175
- log?.info?.("[dingtalk] chatRecord first record structure: " + JSON.stringify(records[0]));
176
+ // Debug: log first record structure with all keys
177
+ const firstRecord = records[0];
178
+ log?.info?.("[dingtalk] chatRecord first record keys: " + Object.keys(firstRecord).join(', '));
179
+ log?.info?.("[dingtalk] chatRecord first record: " + JSON.stringify(firstRecord));
176
180
 
177
- // Collect unique senderIds for batch lookup
181
+ // Collect unique userIds for batch lookup
182
+ // Prefer senderStaffId (non-encrypted) over senderId
178
183
  const senderIds = [...new Set(
179
184
  records
180
- .map(r => r.senderId)
181
- .filter((id): id is string => !!id && !id.startsWith('$:')) // Skip encrypted IDs
185
+ .map(r => r.senderStaffId || (r.senderId && !r.senderId.startsWith('$:') ? r.senderId : null))
186
+ .filter((id): id is string => !!id)
182
187
  )].slice(0, 10); // Limit to 10 users
183
188
 
189
+ log?.info?.("[dingtalk] chatRecord senderIds for lookup: " + JSON.stringify(senderIds));
190
+
184
191
  // Try to resolve sender names via API
185
192
  let senderNameMap = new Map<string, string>();
186
193
  if (senderIds.length > 0 && account.clientId && account.clientSecret) {
@@ -193,14 +200,50 @@ async function extractMessageContent(
193
200
  }
194
201
 
195
202
  const formattedRecords = records.map((record, idx) => {
196
- // Try: senderNick from record > API resolved name > senderId > '未知'
203
+ // Try: senderNick > API resolved name (via staffId or senderId) > fallback
197
204
  let sender = record.senderNick;
198
- if (!sender && record.senderId) {
199
- sender = senderNameMap.get(record.senderId) || (record.senderId.startsWith('$:') ? '成员' : record.senderId);
205
+ if (!sender) {
206
+ // Try to get name from API lookup
207
+ const lookupId = record.senderStaffId || record.senderId;
208
+ if (lookupId) {
209
+ sender = senderNameMap.get(lookupId);
210
+ }
211
+ // Fallback for encrypted IDs
212
+ if (!sender && record.senderId?.startsWith('$:')) {
213
+ sender = '成员';
214
+ }
200
215
  }
201
216
  sender = sender || '未知';
202
217
 
203
- const msgContent = record.content || '[不支持的消息类型]';
218
+ // Handle different message types in chatRecord
219
+ let msgContent: string;
220
+ switch (record.msgType) {
221
+ case 'text':
222
+ msgContent = record.content || '[空消息]';
223
+ break;
224
+ case 'picture':
225
+ case 'image':
226
+ msgContent = '[图片]';
227
+ break;
228
+ case 'video':
229
+ msgContent = '[视频]';
230
+ break;
231
+ case 'file':
232
+ msgContent = '[文件]';
233
+ break;
234
+ case 'voice':
235
+ case 'audio':
236
+ msgContent = '[语音]';
237
+ break;
238
+ case 'richText':
239
+ msgContent = record.content || '[富文本消息]';
240
+ break;
241
+ case 'markdown':
242
+ msgContent = record.content || '[Markdown消息]';
243
+ break;
244
+ default:
245
+ msgContent = record.content || `[${record.msgType || '未知'}消息]`;
246
+ }
204
247
  const time = record.createAt ? new Date(record.createAt).toLocaleString('zh-CN') : '';
205
248
  return `[${idx + 1}] ${sender}${time ? ` (${time})` : ''}: ${msgContent}`;
206
249
  });