From 5a4b4218509f87f368dd71099720ab5129d13c87 Mon Sep 17 00:00:00 2001 From: Mrs4s Date: Tue, 16 Mar 2021 18:34:47 +0800 Subject: [PATCH] feat: self private msg event. --- client/builders.go | 7 +++---- client/c2c_processor.go | 40 ++++++++++++++++++++++++---------------- client/events.go | 18 +++++++++++++++++- client/online_push.go | 2 +- client/private_msg.go | 4 +++- client/sync.go | 13 +++++++++++++ 6 files changed, 61 insertions(+), 23 deletions(-) diff --git a/client/builders.go b/client/builders.go index 4a8a5e65..84b236ec 100644 --- a/client/builders.go +++ b/client/builders.go @@ -570,8 +570,8 @@ func (c *QQClient) buildDeleteMessageRequestPacket(msg []*pb.MessageItem) (uint1 } // OnlinePush.RespPush -func (c *QQClient) buildDeleteOnlinePushPacket(uin int64, seq uint16, delMsg []jce.PushMessageInfo) []byte { - req := &jce.SvcRespPushMsg{Uin: uin} +func (c *QQClient) buildDeleteOnlinePushPacket(uin int64, svrip int32, pushToken []byte, seq uint16, delMsg []jce.PushMessageInfo) []byte { + req := &jce.SvcRespPushMsg{Uin: uin, Svrip: svrip, PushToken: pushToken, DelInfos: []jce.IJceStruct{}} for _, m := range delMsg { req.DelInfos = append(req.DelInfos, &jce.DelMsgInfo{ FromUin: m.FromUin, @@ -580,8 +580,7 @@ func (c *QQClient) buildDeleteOnlinePushPacket(uin int64, seq uint16, delMsg []j MsgTime: m.MsgTime, }) } - b := append([]byte{0x0A}, req.ToBytes()...) - b = append(b, 0x0B) + b := packUniRequestData(req.ToBytes()) buf := &jce.RequestDataVersion3{ Map: map[string][]byte{"resp": b}, } diff --git a/client/c2c_processor.go b/client/c2c_processor.go index 34966cb2..87b56110 100644 --- a/client/c2c_processor.go +++ b/client/c2c_processor.go @@ -54,20 +54,7 @@ func (c *QQClient) c2cMessageSyncProcessor(rsp *msg.GetMessageResponse, info *in if (int64(pairMsg.GetLastReadTime()) & 4294967295) > int64(pMsg.Head.GetMsgTime()) { continue } - strKey := fmt.Sprintf("%d%d%d%d", pMsg.Head.GetFromUin(), pMsg.Head.GetToUin(), pMsg.Head.GetMsgSeq(), pMsg.Head.GetMsgUid()) - if _, ok := c.msgSvcCache.GetAndUpdate(strKey, time.Minute*5); ok { - c.Debug("c2c msg %v already exists in cache. skip.", pMsg.Head.GetMsgUid()) - continue - } - c.msgSvcCache.Add(strKey, "", time.Minute*5) - if info.Params.bool("init") { - continue - } - if decoder, ok := c2cDecoders[pMsg.Head.GetMsgType()]; ok { - decoder(c, pMsg, info) - } else { - c.Debug("unknown msg type on c2c processor: %v", pMsg.Head.GetMsgType()) - } + c.commMsgProcessor(pMsg, info) } } if delItems != nil { @@ -80,6 +67,23 @@ func (c *QQClient) c2cMessageSyncProcessor(rsp *msg.GetMessageResponse, info *in } } +func (c *QQClient) commMsgProcessor(pMsg *msg.Message, info *incomingPacketInfo) { + strKey := fmt.Sprintf("%d%d%d%d", pMsg.Head.GetFromUin(), pMsg.Head.GetToUin(), pMsg.Head.GetMsgSeq(), pMsg.Head.GetMsgUid()) + if _, ok := c.msgSvcCache.GetAndUpdate(strKey, time.Minute*5); ok { + c.Debug("c2c msg %v already exists in cache. skip.", pMsg.Head.GetMsgUid()) + return + } + c.msgSvcCache.Add(strKey, "", time.Minute*5) + if info.Params.bool("init") { + return + } + if decoder, ok := c2cDecoders[pMsg.Head.GetMsgType()]; ok { + decoder(c, pMsg, info) + } else { + c.Debug("unknown msg type on c2c processor: %v", pMsg.Head.GetMsgType()) + } +} + func privateMessageDecoder(c *QQClient, pMsg *msg.Message, _ *incomingPacketInfo) { switch pMsg.Head.GetC2CCmd() { case 11, 175: // friend msg @@ -98,7 +102,11 @@ func privateMessageDecoder(c *QQClient, pMsg *msg.Message, _ *incomingPacketInfo if pMsg.Body.RichText == nil || pMsg.Body.RichText.Elems == nil { return } - c.dispatchFriendMessage(c.parsePrivateMessage(pMsg)) + if pMsg.Head.GetFromUin() == c.Uin { + c.dispatchPrivateMessageSelf(c.parsePrivateMessage(pMsg)) + return + } + c.dispatchPrivateMessage(c.parsePrivateMessage(pMsg)) default: c.Debug("unknown c2c cmd on private msg decoder: %v", pMsg.Head.GetC2CCmd()) } @@ -112,7 +120,7 @@ func privatePttDecoder(c *QQClient, pMsg *msg.Message, _ *incomingPacketInfo) { // m := binary.NewReader(pMsg.Body.RichText.Ptt.Reserve[1:]).ReadTlvMap(1) // T3 -> timestamp T8 -> voiceType T9 -> voiceLength T10 -> PbReserveStruct } - c.dispatchFriendMessage(c.parsePrivateMessage(pMsg)) + c.dispatchPrivateMessage(c.parsePrivateMessage(pMsg)) } func tempSessionDecoder(c *QQClient, pMsg *msg.Message, _ *incomingPacketInfo) { diff --git a/client/events.go b/client/events.go index 1d78cf35..3b05ee83 100644 --- a/client/events.go +++ b/client/events.go @@ -12,6 +12,7 @@ type eventHandlers struct { privateMessageHandlers []func(*QQClient, *message.PrivateMessage) tempMessageHandlers []func(*QQClient, *message.TempMessage) groupMessageHandlers []func(*QQClient, *message.GroupMessage) + selfPrivateMessageHandlers []func(*QQClient, *message.PrivateMessage) selfGroupMessageHandlers []func(*QQClient, *message.GroupMessage) groupMuteEventHandlers []func(*QQClient, *GroupMuteEvent) groupRecalledHandlers []func(*QQClient, *GroupMessageRecalledEvent) @@ -58,6 +59,10 @@ func (c *QQClient) OnGroupMessage(f func(*QQClient, *message.GroupMessage)) { c.eventHandlers.groupMessageHandlers = append(c.eventHandlers.groupMessageHandlers, f) } +func (c *QQClient) OnSelfPrivateMessage(f func(*QQClient, *message.PrivateMessage)) { + c.eventHandlers.selfPrivateMessageHandlers = append(c.eventHandlers.selfPrivateMessageHandlers, f) +} + func (c *QQClient) OnSelfGroupMessage(f func(*QQClient, *message.GroupMessage)) { c.eventHandlers.selfGroupMessageHandlers = append(c.eventHandlers.selfGroupMessageHandlers, f) } @@ -165,7 +170,7 @@ func (c *QQClient) onGroupMessageReceipt(id string, f ...func(*QQClient, *groupM c.eventHandlers.groupMessageReceiptHandlers.LoadOrStore(id, f[0]) } -func (c *QQClient) dispatchFriendMessage(msg *message.PrivateMessage) { +func (c *QQClient) dispatchPrivateMessage(msg *message.PrivateMessage) { if msg == nil { return } @@ -198,6 +203,17 @@ func (c *QQClient) dispatchGroupMessage(msg *message.GroupMessage) { } } +func (c *QQClient) dispatchPrivateMessageSelf(msg *message.PrivateMessage) { + if msg == nil { + return + } + for _, f := range c.eventHandlers.selfPrivateMessageHandlers { + cover(func() { + f(c, msg) + }) + } +} + func (c *QQClient) dispatchGroupMessageSelf(msg *message.GroupMessage) { if msg == nil { return diff --git a/client/online_push.go b/client/online_push.go index f4210be3..1a3dec71 100644 --- a/client/online_push.go +++ b/client/online_push.go @@ -31,7 +31,7 @@ func decodeOnlinePushReqPacket(c *QQClient, info *incomingPacketInfo, payload [] msgInfos := []jce.PushMessageInfo{} uin := jr.ReadInt64(0) jr.ReadSlice(&msgInfos, 2) - _ = c.send(c.buildDeleteOnlinePushPacket(uin, info.SequenceId, msgInfos)) + _ = c.send(c.buildDeleteOnlinePushPacket(uin, 0, nil, info.SequenceId, msgInfos)) for _, m := range msgInfos { k := fmt.Sprintf("%v%v%v", m.MsgSeq, m.MsgTime, m.MsgUid) if _, ok := c.onlinePushCache.Get(k); ok { diff --git a/client/private_msg.go b/client/private_msg.go index d39f6154..bfd7d922 100644 --- a/client/private_msg.go +++ b/client/private_msg.go @@ -31,7 +31,7 @@ func (c *QQClient) SendPrivateMessage(target int64, m *message.SendingMessage) * _ = c.send(pkt) } c.stat.MessageSent++ - return &message.PrivateMessage{ + ret := &message.PrivateMessage{ Id: seq, InternalId: mr, Target: target, @@ -43,6 +43,8 @@ func (c *QQClient) SendPrivateMessage(target int64, m *message.SendingMessage) * }, Elements: m.Elements, } + go c.dispatchPrivateMessageSelf(ret) + return ret } func (c *QQClient) SendTempMessage(groupCode, target int64, m *message.SendingMessage) *message.TempMessage { diff --git a/client/sync.go b/client/sync.go index 11016b99..789d4cec 100644 --- a/client/sync.go +++ b/client/sync.go @@ -26,6 +26,7 @@ func init() { decoders["RegPrxySvc.PbSyncMsg"] = decodeMsgSyncResponse decoders["PbMessageSvc.PbMsgReadedReport"] = decodeMsgReadedResponse decoders["MessageSvc.PushReaded"] = ignoreDecoder + decoders["OnlinePush.PbC2CMsgSync"] = decodeC2CSyncPacket } type ( @@ -72,6 +73,7 @@ func (c *QQClient) RefreshStatus() error { return err } +// SyncSessions 同步会话列表 func (c *QQClient) SyncSessions() (*SessionSyncResponse, error) { ret := &SessionSyncResponse{} notifyChan := make(chan bool) @@ -397,6 +399,17 @@ func decodeMsgSyncResponse(c *QQClient, info *incomingPacketInfo, payload []byte return ret, nil } +// OnlinePush.PbC2CMsgSync +func decodeC2CSyncPacket(c *QQClient, info *incomingPacketInfo, payload []byte) (interface{}, error) { + m := msg.PbPushMsg{} + if err := proto.Unmarshal(payload, &m); err != nil { + return nil, err + } + _ = c.send(c.buildDeleteOnlinePushPacket(c.Uin, m.GetSvrip(), m.GetPushToken(), info.SequenceId, nil)) + c.commMsgProcessor(m.Msg, info) + return nil, nil +} + func decodeMsgReadedResponse(_ *QQClient, _ *incomingPacketInfo, payload []byte) (interface{}, error) { rsp := msg.PbMsgReadedReportResp{} if err := proto.Unmarshal(payload, &rsp); err != nil {