Skip to content

Commit 0dfaad1

Browse files
committed
enhance: add poke_recall event handling and improve message processing
1 parent 56589e9 commit 0dfaad1

File tree

14 files changed

+1756
-18
lines changed

14 files changed

+1756
-18
lines changed

doc/更新日志.txt

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,12 @@
1+
V5.7.0
2+
更新时间
3+
4+
* 新增撤回戳一戳事件,`sub_type: poke_recall`,其他内容与戳一戳一致
5+
* 修复日志中 message_sent 的 sub_type 没有正确显示
6+
* 修复 `get_friend_list` 获取不到新加的好友
7+
8+
=================
9+
110
V5.6.1
211
更新时间 2025-8-2 21:04:08
312

src/common/utils/upgrade.ts

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -5,8 +5,8 @@ import { log, fetchFile } from '.'
55
import { TEMP_DIR } from '../globalVars'
66
import { compare } from 'compare-versions'
77

8-
const downloadMirrors = ['https://ghgo.xyz/']
9-
const releasesMirrors = ['https://kkgithub.com/']
8+
const downloadMirrors = ['https://ghfast.top/']
9+
const releasesMirrors = ['https://ghfast.top/', 'https://kkgithub.com/']
1010

1111
export async function checkNewVersion() {
1212
const latestVersion = await getRemoteVersion()

src/ntqqapi/core.ts

Lines changed: 19 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -231,6 +231,25 @@ class Core extends Service {
231231
}
232232
})
233233

234+
registerReceiveHook<[Peer, string[]]>(ReceiveCmdS.DELETE_MSG, payload => {
235+
// 撤回普通消息不会经过这里
236+
// 撤回戳一戳会经过这里
237+
const [peer, msgIds] = payload;
238+
for (const msgId of msgIds) {
239+
const msg = this.ctx.store.getMsgCache(msgId)
240+
if (!msg) {
241+
this.ctx.ntMsgApi.getMsgsByMsgId(peer, [msgId]).then(r=>{
242+
for(const _msg of r.msgList) {
243+
this.ctx.parallel('nt/message-deleted', _msg)
244+
}
245+
})
246+
}
247+
else{
248+
this.ctx.parallel('nt/message-deleted', msg)
249+
}
250+
}
251+
})
252+
234253
registerReceiveHook<RawMessage>(ReceiveCmdS.SELF_SEND_MSG, payload => {
235254
sentMsgIds.set(payload.msgId, true)
236255
})
@@ -275,7 +294,6 @@ class Core extends Service {
275294
}
276295
})
277296

278-
279297
registerReceiveHook<number[]>('nodeIKernelMsgListener/onRecvSysMsg', payload => {
280298
this.ctx.parallel('nt/system-message-created', Uint8Array.from(payload))
281299
})

src/ntqqapi/hook.ts

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -11,6 +11,7 @@ export enum ReceiveCmdS {
1111
UPDATE_MSG = 'nodeIKernelMsgListener/onMsgInfoListUpdate',
1212
UPDATE_ACTIVE_MSG = 'nodeIKernelMsgListener/onActiveMsgInfoUpdate',
1313
NEW_MSG = 'nodeIKernelMsgListener/onRecvMsg',
14+
DELETE_MSG = 'nodeIKernelMsgListener/onMsgDelete',
1415
NEW_ACTIVE_MSG = 'nodeIKernelMsgListener/onRecvActiveMsg',
1516
SELF_SEND_MSG = 'nodeIKernelMsgListener/onAddSendMsg',
1617
USER_INFO = 'nodeIKernelProfileListener/onProfileSimpleChanged',

src/ntqqapi/types/msg.ts

Lines changed: 10 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -292,6 +292,14 @@ export enum GrayTipElementSubType {
292292
JSON = 17,
293293
}
294294

295+
export enum JsonGrayTipBusId {
296+
AddedFriend = '19324',
297+
Poke = '1061',
298+
GroupMemberTitleChanged = '2407',
299+
GroupEssenceMsg = '2401',
300+
GroupNewMemberInvited = '19217',
301+
}
302+
295303
export interface GrayTipElement {
296304
subElementType: GrayTipElementSubType
297305
revokeElement?: {
@@ -308,9 +316,10 @@ export interface GrayTipElement {
308316
groupElement?: TipGroupElement
309317
xmlElement?: TipXmlElement
310318
jsonGrayTipElement?: {
311-
busiId: string
319+
busiId: JsonGrayTipBusId
312320
jsonStr: string
313321
xmlToJsonParam?: {
322+
templId: string
314323
templParam: Map<string, string>
315324
}
316325
}

src/onebot11/action/user/GetFriendList.ts

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -16,6 +16,7 @@ export class GetFriendList extends BaseAction<Payload, OB11User[]> {
1616

1717
protected async _handle(payload: Payload) {
1818
const refresh = payload.no_cache
19-
return OB11Entities.friendsV2(await this.ctx.ntFriendApi.getBuddyList())
19+
return OB11Entities.friendsV2(await this.ctx.ntFriendApi.getBuddyV2(refresh))
20+
// return OB11Entities.friendsV2(await this.ctx.ntFriendApi.getBuddyList())
2021
}
2122
}

src/onebot11/adapter.ts

Lines changed: 54 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,14 @@
11
import { Context, Service } from 'cordis'
22
import { OB11Entities } from './entities'
3-
import { FriendRequest, GroupNotify, GroupNotifyStatus, GroupNotifyType, RawMessage } from '../ntqqapi/types'
3+
import {
4+
ChatType,
5+
FriendRequest,
6+
GroupNotify,
7+
GroupNotifyStatus,
8+
GroupNotifyType,
9+
JsonGrayTipBusId,
10+
RawMessage,
11+
} from '../ntqqapi/types'
412
import { OB11GroupRequestEvent } from './event/request/OB11GroupRequest'
513
import { OB11FriendRequestEvent } from './event/request/OB11FriendRequest'
614
import { OB11GroupDecreaseEvent } from './event/notice/OB11GroupDecreaseEvent'
@@ -19,9 +27,16 @@ import { OB11GroupIncreaseEvent } from './event/notice/OB11GroupIncreaseEvent'
1927
import { FlashFileDownloadStatus, FlashFileUploadStatus } from '@/ntqqapi/types/flashfile'
2028
import {
2129
OB11FlashFile,
22-
OB11FlashFileDownloadedEvent, OB11FlashFileDownloadingEvent,
23-
OB11FlashFileUploadedEvent, OB11FlashFileUploadingEvent,
30+
OB11FlashFileDownloadedEvent,
31+
OB11FlashFileDownloadingEvent,
32+
OB11FlashFileUploadedEvent,
33+
OB11FlashFileUploadingEvent,
2434
} from '@/onebot11/event/notice/OB11FlashFileEvent'
35+
import {
36+
OB11FriendPokeEvent,
37+
OB11FriendPokeRecallEvent,
38+
OB11GroupPokeRecallEvent,
39+
} from '@/onebot11/event/notice/OB11PokeEvent'
2540

2641
declare module 'cordis' {
2742
interface Context {
@@ -196,10 +211,33 @@ class OneBot11Adapter extends Service {
196211
peerUid: message.peerUid,
197212
chatType: message.chatType,
198213
}
214+
// 解析撤回戳一戳
215+
const grayTipElement = message.elements.find(el => el.grayTipElement)?.grayTipElement
216+
if (grayTipElement && grayTipElement.jsonGrayTipElement?.busiId == JsonGrayTipBusId.Poke){
217+
const json = JSON.parse(grayTipElement.jsonGrayTipElement.jsonStr)
218+
const templateParams = grayTipElement.jsonGrayTipElement?.xmlToJsonParam?.templParam
219+
const fromUserUin = templateParams?.get('uin_str1') || '0'
220+
const toUserUin = templateParams?.get('uin_str2') || '0'
221+
let recallEvent: OB11FriendPokeRecallEvent | OB11GroupPokeRecallEvent;
222+
if (peer.chatType === ChatType.Group) {
223+
recallEvent = new OB11GroupPokeRecallEvent(parseInt(message.peerUid), parseInt(fromUserUin), parseInt(toUserUin), json)
224+
}
225+
else{
226+
recallEvent = new OB11FriendPokeRecallEvent(parseInt(fromUserUin), parseInt(toUserUin), json)
227+
}
228+
return this.dispatch(recallEvent)
229+
}
230+
// OB11Entities.privateEvent(this.ctx, message).then(privateEvent => {
231+
// if (privateEvent?.sub_type === 'poke') {
232+
// (privateEvent as OB11FriendPokeEvent).sub_type = 'poke_recall'
233+
// this.dispatch(privateEvent)
234+
// }
235+
// })
199236
const oriMessageId = this.ctx.store.getShortIdByMsgInfo(peer, message.msgId)
200237
if (!oriMessageId) {
201238
return
202239
}
240+
203241
OB11Entities.recallEvent(this.ctx, message, oriMessageId).then((recallEvent) => {
204242
if (recallEvent) {
205243
this.dispatch(recallEvent)
@@ -401,6 +439,19 @@ class OneBot11Adapter extends Service {
401439
const event = new OB11GroupDecreaseEvent(tip.groupCode, userId, userId)
402440
this.dispatch(event)
403441
}
442+
else if (msgType === 528 && subType === 321) {
443+
// 私聊撤回戳一戳,不再从这里解析,应从 nt/message-deleted 事件中解析
444+
const fromUin: string = sysMsg.routingHead?.fromUin.low
445+
const toUin: string = sysMsg.routingHead?.toUin.low
446+
}
447+
else if (msgType === 732 && subType === 21) {
448+
// 撤回群戳一戳,不再从这里解析,应从 nt/message-deleted 事件中解析
449+
const fromUin: string = sysMsg.routingHead?.fromUin.low
450+
const toUin: string = sysMsg.routingHead?.toUin.low // 这个一直都是bot uin
451+
452+
// 这是个 tlv 格式数据
453+
const content = sysMsg.body?.msgContent
454+
}
404455
})
405456

406457
this.ctx.on('nt/flash-file-download-status', input => {

src/onebot11/connect/http.ts

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -127,7 +127,7 @@ class OB11Http {
127127
if (!client.closed) {
128128
client.write(data)
129129
if ('post_type' in event) {
130-
const eventName = event.post_type + '.' + event[event.post_type + '_type']
130+
const eventName = event.getSummaryEventName()
131131
this.ctx.logger.info('OneBot V11 HTTP SSE 事件上报', eventName)
132132
}
133133
}

src/onebot11/connect/ws.ts

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -70,7 +70,7 @@ class OB11WebSocket {
7070
this.wsClients.forEach(({ socket, emitEvent }) => {
7171
if (emitEvent && socket.readyState === WebSocket.OPEN) {
7272
socket.send(JSON.stringify(event))
73-
const eventName = event.post_type + '.' + event[event.post_type + '_type']
73+
const eventName = event.getSummaryEventName()
7474
this.ctx.logger.info('WebSocket 事件上报', socket.url ?? '', eventName)
7575
}
7676
})
@@ -201,7 +201,7 @@ class OB11WebSocketReverse {
201201
public emitEvent(event: OB11BaseEvent) {
202202
if (this.wsClient && this.wsClient.readyState === WebSocket.OPEN) {
203203
this.wsClient.send(JSON.stringify(event))
204-
const eventName = event.post_type + '.' + event[event.post_type + '_type']
204+
const eventName = event.getSummaryEventName()
205205
this.ctx.logger.info('WebSocket 事件上报', this.wsClient.url ?? '', eventName)
206206
}
207207
}

src/onebot11/entities.ts

Lines changed: 11 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -11,10 +11,12 @@ import {
1111
import {
1212
AtType,
1313
ChatType,
14-
FaceIndex, FaceType,
14+
FaceIndex,
15+
FaceType,
1516
GrayTipElementSubType,
1617
GroupMember,
1718
GroupSimpleInfo,
19+
JsonGrayTipBusId,
1820
Peer,
1921
RawMessage,
2022
Sex,
@@ -35,7 +37,6 @@ import { OB11FriendRecallNoticeEvent } from './event/notice/OB11FriendRecallNoti
3537
import { OB11GroupRecallNoticeEvent } from './event/notice/OB11GroupRecallNoticeEvent'
3638
import { OB11FriendPokeEvent, OB11GroupPokeEvent } from './event/notice/OB11PokeEvent'
3739
import { OB11BaseNoticeEvent } from './event/notice/OB11BaseNoticeEvent'
38-
import { OB11GroupRequestEvent } from './event/request/OB11GroupRequest'
3940
import { GroupBanEvent } from './event/notice/OB11GroupBanEvent'
4041
import { GroupMsgEmojiLikeEvent } from './event/notice/OB11MsgEmojiLikeEvent'
4142
import { GroupEssenceEvent } from './event/notice/OB11GroupEssenceEvent'
@@ -44,6 +45,7 @@ import { Context } from 'cordis'
4445
import { selfInfo } from '@/common/globalVars'
4546
import { pathToFileURL } from 'node:url'
4647
import OneBot11Adapter from './adapter'
48+
import { OB11GroupRequestEvent } from '@/onebot11/event/request/OB11GroupRequest'
4749

4850
export namespace OB11Entities {
4951
export async function message(
@@ -77,6 +79,9 @@ export namespace OB11Entities {
7779
message: messagePostFormat === 'string' ? '' : [],
7880
message_format: messagePostFormat === 'string' ? 'string' : 'array',
7981
post_type: selfUin === msg.senderUin ? EventType.MESSAGE_SENT : EventType.MESSAGE,
82+
getSummaryEventName(): string {
83+
return this.post_type + '.' + this.message_type
84+
}
8085
}
8186
if (debug) {
8287
resMsg.raw = msg
@@ -492,7 +497,7 @@ export namespace OB11Entities {
492497
)
493498
}
494499
}
495-
if (grayTipElement.xmlElement?.templId === '10229' || grayTipElement.jsonGrayTipElement?.busiId === '19324') {
500+
if (grayTipElement.xmlElement?.templId === '10229' || grayTipElement.jsonGrayTipElement?.busiId === JsonGrayTipBusId.AddedFriend) {
496501
ctx.logger.info('收到好友添加消息', msg.peerUid)
497502
const uin = +msg.peerUin || +(await ctx.ntUserApi.getUinByUid(msg.peerUid))
498503
return new OB11FriendAddNoticeEvent(uin)
@@ -550,15 +555,15 @@ export namespace OB11Entities {
550555
Number(param.templParam.get('uin_str2')),
551556
json.items
552557
)
553-
} else if (grayTipElement.jsonGrayTipElement?.busiId === '2401' && json.items[2]) {
558+
} else if (grayTipElement.jsonGrayTipElement?.busiId === JsonGrayTipBusId.GroupEssenceMsg && json.items[2]) {
554559
ctx.logger.info('收到群精华消息', json)
555560
return await GroupEssenceEvent.parse(ctx, new URL(json.items[2].jp))
556-
} else if (grayTipElement.jsonGrayTipElement?.busiId === '2407') {
561+
} else if (grayTipElement.jsonGrayTipElement?.busiId === JsonGrayTipBusId.GroupMemberTitleChanged) {
557562
ctx.logger.info('收到群成员新头衔消息', json)
558563
const memberUin = json.items[1].param[0]
559564
const title = json.items[3].txt
560565
return new OB11GroupTitleEvent(parseInt(msg.peerUid), parseInt(memberUin), title)
561-
} else if (grayTipElement.jsonGrayTipElement?.busiId === '19217') {
566+
} else if (grayTipElement.jsonGrayTipElement?.busiId === JsonGrayTipBusId.GroupNewMemberInvited) {
562567
ctx.logger.info('收到新人被邀请进群消息', grayTipElement)
563568
const userId = new URL(json.items[2].jp).searchParams.get('robot_uin')
564569
const operatorId = new URL(json.items[0].jp).searchParams.get('uin')

0 commit comments

Comments
 (0)