diff --git a/client/operation.go b/client/operation.go index 50ec565..03d68ed 100644 --- a/client/operation.go +++ b/client/operation.go @@ -1280,3 +1280,16 @@ func (c *QQClient) ImageOcr(url string) (*oidb2.OcrResponse, error) { } return nil, errors.New("image error") } + +// SendGroupSign 发送群聊打卡消息 +func (c *QQClient) SendGroupSign(groupUin uint32) (*oidb2.BotGroupClockInResult, error) { + pkt, err := oidb2.BuildGroupSignPacket(c.Uin, groupUin, c.version().CurrentVersion) + if err != nil { + return nil, err + } + resp, err := c.sendOidbPacketAndWait(pkt) + if err != nil { + return nil, err + } + return oidb2.ParseGroupSignResp(resp) +} diff --git a/client/packets/oidb/group_sign.go b/client/packets/oidb/group_sign.go new file mode 100644 index 0000000..0261ab5 --- /dev/null +++ b/client/packets/oidb/group_sign.go @@ -0,0 +1,54 @@ +package oidb + +import ( + "errors" + "strconv" + + "github.com/LagrangeDev/LagrangeGo/client/packets/pb/service/oidb" +) + +// 群打卡 + +type BotGroupClockInResult struct { + Title string // 今日已成功打卡 + KeepDayText string // 已打卡N天 + GroupRankText string // 群内排名第N位 + ClockInUtcTime int64 // 打卡时间 + DetailURL string // Detail info url https://qun.qq.com/v2/signin/detail?... +} + +func BuildGroupSignPacket(botUin, groupUin uint32, appVersion string) (*Packet, error) { + body := &oidb.OidbSvcTrpcTcp0XEB7_1_ReqBody{ + SignInWriteReq: &oidb.StSignInWriteReq{ + Uin: strconv.Itoa(int(botUin)), + GroupUin: strconv.Itoa(int(groupUin)), + AppVersion: appVersion, + }, + } + return BuildOidbPacket(0xEB7, 1, body, false, false) +} + +func ParseGroupSignResp(data []byte) (*BotGroupClockInResult, error) { + var rsp oidb.OidbSvcTrpcTcp0XEB7_1_RspBody + _, err := ParseOidbPacket(data, &rsp) + if err != nil { + return nil, err + } + + if rsp.SignInWriteRsp == nil || rsp.SignInWriteRsp.DoneInfo == nil { + return nil, errors.New("SignInWriteRsp or SignInWriteRsp.DoneInfo nil") + } + + ret := &BotGroupClockInResult{ + Title: rsp.SignInWriteRsp.DoneInfo.Title, + KeepDayText: rsp.SignInWriteRsp.DoneInfo.KeepDayText, + DetailURL: rsp.SignInWriteRsp.DoneInfo.DetailUrl, + } + if size := len(rsp.SignInWriteRsp.DoneInfo.ClockInInfo); size > 0 { + ret.GroupRankText = rsp.SignInWriteRsp.DoneInfo.ClockInInfo[0] + if size > 1 { + ret.ClockInUtcTime, _ = strconv.ParseInt(rsp.SignInWriteRsp.DoneInfo.ClockInInfo[1], 10, 64) + } + } + return ret, nil +} diff --git a/client/packets/pb/service/oidb/OidbSvcTrpcTcp0xEB7_1.pb.go b/client/packets/pb/service/oidb/OidbSvcTrpcTcp0xEB7_1.pb.go new file mode 100644 index 0000000..5be0421 --- /dev/null +++ b/client/packets/pb/service/oidb/OidbSvcTrpcTcp0xEB7_1.pb.go @@ -0,0 +1,33 @@ +// Code generated by protoc-gen-golite. DO NOT EDIT. +// source: pb/service/oidb/OidbSvcTrpcTcp0xEB7_1.proto + +package oidb + +type OidbSvcTrpcTcp0XEB7_1_ReqBody struct { + SignInWriteReq *StSignInWriteReq `protobuf:"bytes,2,opt"` + _ [0]func() +} + +type StSignInWriteReq struct { + Uin string `protobuf:"bytes,1,opt"` + GroupUin string `protobuf:"bytes,2,opt"` + AppVersion string `protobuf:"bytes,3,opt"` // 不确定要不要加,测试过没有这个参数也是可以的 + _ [0]func() +} + +type OidbSvcTrpcTcp0XEB7_1_RspBody struct { + SignInWriteRsp *StSignInWriteRsp `protobuf:"bytes,2,opt"` + _ [0]func() +} + +type StSignInWriteRsp struct { + DoneInfo *SignInStatusDoneInfo `protobuf:"bytes,2,opt"` + _ [0]func() +} + +type SignInStatusDoneInfo struct { + Title string `protobuf:"bytes,1,opt"` // 今日已成功打卡 + KeepDayText string `protobuf:"bytes,2,opt"` // 已打卡N天 + ClockInInfo []string `protobuf:"bytes,3,rep"` // ["群内排名第N位", "[clock in timestamp (second)]"] + DetailUrl string `protobuf:"bytes,4,opt"` // https://qun.qq.com/v2/signin/detail?... +} diff --git a/client/packets/pb/service/oidb/OidbSvcTrpcTcp0xEB7_1.proto b/client/packets/pb/service/oidb/OidbSvcTrpcTcp0xEB7_1.proto new file mode 100644 index 0000000..d12ba5c --- /dev/null +++ b/client/packets/pb/service/oidb/OidbSvcTrpcTcp0xEB7_1.proto @@ -0,0 +1,30 @@ +syntax = "proto3"; + +option go_package = "github.com/LagrangeDev/LagrangeGo/client/packets/pb/service/oidb"; + +// see https://github.com/LagrangeDev/Lagrange.Core/blob/47b819d43ad101a1a066a3f8afa094d000fe19f5/Lagrange.Core/Internal/Packets/Service/Oidb/Request/OidbSvcTrpcTcp0xEB7_1.cs + +message OidbSvcTrpcTcp0xEB7_1_ReqBody { + optional StSignInWriteReq signInWriteReq = 2; +} + +message StSignInWriteReq { + string Uin = 1; + string GroupUin = 2; + string AppVersion = 3; // 不确定要不要加,测试过没有这个参数也是可以的 +} + +message OidbSvcTrpcTcp0xEB7_1_RspBody { + optional StSignInWriteRsp signInWriteRsp = 2; +} + +message StSignInWriteRsp { + optional SignInStatusDoneInfo doneInfo = 2; +} + +message SignInStatusDoneInfo { + string Title = 1; // 今日已成功打卡 + string KeepDayText = 2; // 已打卡N天 + repeated string ClockInInfo = 3; // ["群内排名第N位", "[clock in timestamp (second)]"] + string DetailUrl = 4; // https://qun.qq.com/v2/signin/detail?... +}