diff --git a/config/config.yaml b/config/config.yaml index d66f15704..aef26ace0 100644 --- a/config/config.yaml +++ b/config/config.yaml @@ -364,6 +364,10 @@ callback: enable: false timeout: 5 failedContinue: true + afterCreateGroup: + enable: false + timeout: 5 + failedContinue: true beforeMemberJoinGroup: enable: false timeout: 5 diff --git a/deployments/templates/openim.yaml b/deployments/templates/openim.yaml index 44a28adff..4d48284dd 100644 --- a/deployments/templates/openim.yaml +++ b/deployments/templates/openim.yaml @@ -312,7 +312,7 @@ iosPush: # Timeout in seconds # Whether to continue execution if callback fails callback: - url: + url: "http://192.168.62.1:18888/sdkName" beforeSendSingleMsg: enable: false timeout: 5 @@ -361,13 +361,17 @@ callback: timeout: 5 failedContinue: true beforeCreateGroup: - enable: false + enable: true timeout: 5 - failedContinue: true + failedContinue: false + afterCreateGroup: + enable: true + timeout: 5 + failedContinue: false beforeMemberJoinGroup: enable: false timeout: 5 - failedContinue: true + failedContinue: false beforeSetGroupMemberInfo: enable: false timeout: 5 diff --git a/go.mod b/go.mod index e7d9097d2..006cd8747 100644 --- a/go.mod +++ b/go.mod @@ -12,7 +12,6 @@ require ( github.com/golang-jwt/jwt/v4 v4.5.0 github.com/golang/protobuf v1.5.3 github.com/gorilla/websocket v1.5.0 - github.com/grpc-ecosystem/go-grpc-prometheus v1.2.0 github.com/jinzhu/copier v0.4.0 github.com/lestrrat-go/file-rotatelogs v2.4.0+incompatible // indirect github.com/minio/minio-go/v7 v7.0.63 @@ -38,7 +37,7 @@ require github.com/google/uuid v1.3.1 require ( github.com/IBM/sarama v1.41.3 github.com/OpenIMSDK/protocol v0.0.31 - github.com/OpenIMSDK/tools v0.0.16 + github.com/OpenIMSDK/tools v0.0.17 github.com/aliyun/aliyun-oss-go-sdk v2.2.9+incompatible github.com/go-redis/redis v6.15.9+incompatible github.com/go-sql-driver/mysql v1.7.1 diff --git a/go.sum b/go.sum index b1ee37912..7601da0be 100644 --- a/go.sum +++ b/go.sum @@ -20,8 +20,8 @@ github.com/IBM/sarama v1.41.3 h1:MWBEJ12vHC8coMjdEXFq/6ftO6DUZnQlFYcxtOJFa7c= github.com/IBM/sarama v1.41.3/go.mod h1:Xxho9HkHd4K/MDUo/T/sOqwtX/17D33++E9Wib6hUdQ= github.com/OpenIMSDK/protocol v0.0.31 h1:ax43x9aqA6EKNXNukS5MT5BSTqkUmwO4uTvbJLtzCgE= github.com/OpenIMSDK/protocol v0.0.31/go.mod h1:F25dFrwrIx3lkNoiuf6FkCfxuwf8L4Z8UIsdTHP/r0Y= -github.com/OpenIMSDK/tools v0.0.16 h1:te/GIq2imCMsrRPgU9OObYKbzZ3rT08Lih/o+3QFIz0= -github.com/OpenIMSDK/tools v0.0.16/go.mod h1:eg+q4A34Qmu73xkY0mt37FHGMCMfC6CtmOnm0kFEGFI= +github.com/OpenIMSDK/tools v0.0.17 h1:1E1HUOL2W09YUHBb4wBwrXoTSZm5ONVwLxlEX1GhlKw= +github.com/OpenIMSDK/tools v0.0.17/go.mod h1:eg+q4A34Qmu73xkY0mt37FHGMCMfC6CtmOnm0kFEGFI= github.com/QcloudApi/qcloud_sign_golang v0.0.0-20141224014652-e4130a326409/go.mod h1:1pk82RBxDY/JZnPQrtqHlUFfCctgdorsd9M06fMynOM= github.com/alcortesm/tgz v0.0.0-20161220082320-9c5fe88206d7 h1:uSoVVbwJiQipAclBbw+8quDsfcvFjOpI5iCf4p/cqCs= github.com/alcortesm/tgz v0.0.0-20161220082320-9c5fe88206d7/go.mod h1:6zEj6s6u/ghQa61ZWa/C2Aw3RkjiTBOix7dkqa1VLIs= @@ -165,8 +165,6 @@ github.com/gorilla/securecookie v1.1.1/go.mod h1:ra0sb63/xPlUeL+yeDciTfxMRAA+MP+ github.com/gorilla/sessions v1.2.1/go.mod h1:dk2InVEVJ0sfLlnXv9EAgkf6ecYs/i80K/zI+bUmuGM= github.com/gorilla/websocket v1.5.0 h1:PPwGk2jz7EePpoHN/+ClbZu8SPxiqlu12wZP/3sWmnc= github.com/gorilla/websocket v1.5.0/go.mod h1:YR8l580nyteQvAITg2hZ9XVh4b55+EU/adAjf1fMHhE= -github.com/grpc-ecosystem/go-grpc-prometheus v1.2.0 h1:Ovs26xHkKqVztRpIrF/92BcuyuQ/YW4NSIpoGtfXNho= -github.com/grpc-ecosystem/go-grpc-prometheus v1.2.0/go.mod h1:8NvIoxWQoOIhqOTXgfV/d3M/q6VIi02HzZEHgUlZvzk= github.com/hashicorp/errwrap v1.0.0 h1:hLrqtEDnRye3+sgx6z4qVLNuviH3MR5aQ0ykNJa/UYA= github.com/hashicorp/errwrap v1.0.0/go.mod h1:YH+1FKiLXxHSkmPseP+kNlulaMuP3n2brvKWEqk/Jc4= github.com/hashicorp/go-multierror v1.1.1 h1:H5DkEtf6CXdFp0N0Em5UCwQpXMWke8IA0+lD48awMYo= diff --git a/internal/rpc/group/callback.go b/internal/rpc/group/callback.go index 38174738b..982a57140 100644 --- a/internal/rpc/group/callback.go +++ b/internal/rpc/group/callback.go @@ -18,6 +18,8 @@ import ( "context" "time" + "github.com/OpenIMSDK/tools/log" + "github.com/OpenIMSDK/protocol/constant" "github.com/OpenIMSDK/protocol/group" "github.com/OpenIMSDK/protocol/wrapperspb" @@ -66,23 +68,53 @@ func CallbackBeforeCreateGroup(ctx context.Context, req *group.CreateGroupReq) ( config.Config.Callback.CallbackBeforeCreateGroup, ) if err != nil { - if err == errs.ErrCallbackContinue { + if errs.Unwrap(err) == errs.ErrCallbackContinue { + log.ZWarn(ctx, "callback failed but continue", err, "url", config.Config.Callback.CallbackUrl) return nil } return err } - utils.NotNilReplace(&req.GroupInfo.GroupID, resp.GroupID) - utils.NotNilReplace(&req.GroupInfo.GroupName, resp.GroupName) - utils.NotNilReplace(&req.GroupInfo.Notification, resp.Notification) - utils.NotNilReplace(&req.GroupInfo.Introduction, resp.Introduction) - utils.NotNilReplace(&req.GroupInfo.FaceURL, resp.FaceURL) - utils.NotNilReplace(&req.GroupInfo.OwnerUserID, resp.OwnerUserID) - utils.NotNilReplace(&req.GroupInfo.Ex, resp.Ex) - utils.NotNilReplace(&req.GroupInfo.Status, resp.Status) - utils.NotNilReplace(&req.GroupInfo.CreatorUserID, resp.CreatorUserID) - utils.NotNilReplace(&req.GroupInfo.GroupType, resp.GroupType) - utils.NotNilReplace(&req.GroupInfo.NeedVerification, resp.NeedVerification) - utils.NotNilReplace(&req.GroupInfo.LookMemberInfo, resp.LookMemberInfo) + + utils.StructFieldNotNilReplace(req, resp) + return nil +} + +func CallbackAfterCreateGroup(ctx context.Context, req *group.CreateGroupReq) (err error) { + if !config.Config.Callback.CallbackAfterCreateGroup.Enable { + return nil + } + cbReq := &callbackstruct.CallbackAfterCreateGroupReq{ + CallbackCommand: "callbackAfterCreateGroupCommand", + OperationID: mcontext.GetOperationID(ctx), + GroupInfo: req.GroupInfo, + } + cbReq.InitMemberList = append(cbReq.InitMemberList, &apistruct.GroupAddMemberInfo{ + UserID: req.OwnerUserID, + RoleLevel: constant.GroupOwner, + }) + for _, userID := range req.AdminUserIDs { + cbReq.InitMemberList = append(cbReq.InitMemberList, &apistruct.GroupAddMemberInfo{ + UserID: userID, + RoleLevel: constant.GroupAdmin, + }) + } + for _, userID := range req.MemberUserIDs { + cbReq.InitMemberList = append(cbReq.InitMemberList, &apistruct.GroupAddMemberInfo{ + UserID: userID, + RoleLevel: constant.GroupOrdinaryUsers, + }) + } + resp := &callbackstruct.CallbackAfterCreateGroupResp{} + err = http.CallBackPostReturn( + ctx, + config.Config.Callback.CallbackUrl, + cbReq, + resp, + config.Config.Callback.CallbackAfterCreateGroup, + ) + if err != nil { + return err + } return nil } diff --git a/internal/rpc/group/group.go b/internal/rpc/group/group.go index 85b78cfb2..9fbce7b55 100644 --- a/internal/rpc/group/group.go +++ b/internal/rpc/group/group.go @@ -225,6 +225,7 @@ func (s *groupServer) CreateGroup(ctx context.Context, req *pbgroup.CreateGroupR if len(userMap) != len(userIDs) { return nil, errs.ErrUserIDNotFound.Wrap("user not found") } + // Callback Before create Group if err := CallbackBeforeCreateGroup(ctx, req); err != nil { return nil, err } @@ -298,6 +299,17 @@ func (s *groupServer) CreateGroup(ctx context.Context, req *pbgroup.CreateGroupR } s.Notification.GroupCreatedNotification(ctx, tips) } + reqCallBackAfter := &pbgroup.CreateGroupReq{ + MemberUserIDs: userIDs, + GroupInfo: resp.GroupInfo, + OwnerUserID: req.OwnerUserID, + AdminUserIDs: req.AdminUserIDs, + } + + if err := CallbackAfterCreateGroup(ctx, reqCallBackAfter); err != nil { + return nil, err + } + return resp, nil } diff --git a/pkg/callbackstruct/common.go b/pkg/callbackstruct/common.go index ef84d52b9..c58b9e415 100644 --- a/pkg/callbackstruct/common.go +++ b/pkg/callbackstruct/common.go @@ -14,8 +14,10 @@ package callbackstruct -import ( - "github.com/OpenIMSDK/tools/errs" +import "github.com/OpenIMSDK/tools/errs" + +const ( + Next = 1 ) type CommonCallbackReq struct { @@ -51,14 +53,15 @@ type CallbackResp interface { } type CommonCallbackResp struct { - ActionCode int `json:"actionCode"` + ActionCode int32 `json:"actionCode"` ErrCode int32 `json:"errCode"` ErrMsg string `json:"errMsg"` ErrDlt string `json:"errDlt"` + NextCode int32 `json:"nextCode"` } func (c CommonCallbackResp) Parse() error { - if c.ActionCode != errs.NoError || c.ErrCode != errs.NoError { + if c.ActionCode != errs.NoError || c.NextCode == Next { return errs.NewCodeError(int(c.ErrCode), c.ErrMsg).WithDetail(c.ErrDlt) } return nil diff --git a/pkg/callbackstruct/friend.go b/pkg/callbackstruct/friend.go index 7e89824e2..bbafb7f2f 100644 --- a/pkg/callbackstruct/friend.go +++ b/pkg/callbackstruct/friend.go @@ -25,3 +25,26 @@ type CallbackBeforeAddFriendReq struct { type CallbackBeforeAddFriendResp struct { CommonCallbackResp } + +type CallBackAddFriendReplyBeforeReq struct { + CallbackCommand `json:"callbackCommand"` + FromUserID string `json:"fromUserID" ` + ToUserID string `json:"toUserID"` + OperationID string `json:"operationID"` +} + +type CallBackAddFriendReplyBeforeResp struct { + CommonCallbackResp +} + +type CallbackAfterAddFriendReq struct { + CallbackCommand `json:"callbackCommand"` + FromUserID string `json:"fromUserID" ` + ToUserID string `json:"toUserID"` + ReqMsg string `json:"reqMsg"` + OperationID string `json:"operationID"` +} + +type CallbackAfterAddFriendResp struct { + CommonCallbackResp +} diff --git a/pkg/callbackstruct/group.go b/pkg/callbackstruct/group.go index 11b33bf0a..5ec6433b6 100644 --- a/pkg/callbackstruct/group.go +++ b/pkg/callbackstruct/group.go @@ -50,6 +50,17 @@ type CallbackBeforeCreateGroupResp struct { ApplyMemberFriend *int32 `json:"applyMemberFriend"` } +type CallbackAfterCreateGroupReq struct { + OperationID string `json:"operationID"` + CallbackCommand `json:"callbackCommand"` + *common.GroupInfo + InitMemberList []*apistruct.GroupAddMemberInfo `json:"initMemberList"` +} + +type CallbackAfterCreateGroupResp struct { + CommonCallbackResp +} + type CallbackBeforeMemberJoinGroupReq struct { CallbackCommand `json:"callbackCommand"` OperationID string `json:"operationID"` @@ -86,3 +97,74 @@ type CallbackBeforeSetGroupMemberInfoResp struct { FaceURL *string `json:"faceURL"` RoleLevel *int32 `json:"roleLevel"` } + +type CallbackAfterGroupMemberExitReq struct { + CallbackCommand `json:"callbackCommand"` + OperationID string `json:"operationID"` + GroupID string `json:"groupID"` + UserID string `json:"userID"` + GroupType *int32 `json:"groupType"` + ExitType string `json:"exitType"` + MuteEndTime *int64 `json:"muteEndTime"` +} + +type CallbackAfterGroupMemberExitResp struct { + CommonCallbackResp +} + +type CallbackAfterUngroupReq struct { + CallbackCommand `json:"callbackCommand"` + OperationID string `json:"operationID"` + GroupID string `json:"groupID"` + GroupType *int32 `json:"groupType"` + OwnerID string `json:"ownerID"` + MemberList []string `json:"memberList"` + MuteEndTime *int64 `json:"muteEndTime"` +} + +type CallbackAfterUngroupResp struct { + CommonCallbackResp +} + +type CallbackAfterSetGroupInfoReq struct { + CallbackCommand `json:"callbackCommand"` + OperationID string `json:"operationID"` + GroupID string `json:"groupID"` + GroupType *int32 `json:"groupType"` + UserID string `json:"userID"` + Name string `json:"name"` + Notification string `json:"notification"` + GroupUrl string `json:"groupUrl"` + MuteEndTime *int64 `json:"muteEndTime"` +} + +type CallbackAfterSetGroupInfoResp struct { + CommonCallbackResp +} + +type CallbackAfterRevokeMsgReq struct { + CallbackCommand `json:"callbackCommand"` + OperationID string `json:"operationID"` + GroupID string `json:"groupID"` + GroupType *int32 `json:"groupType"` + UserID string `json:"userID"` + Content string `json:"content"` + MuteEndTime *int64 `json:"muteEndTime"` +} + +type CallbackAfterRevokeMsgResp struct { + CommonCallbackResp +} + +type CallbackGroupMsgReadReq struct { + CallbackCommand `json:"callbackCommand"` + OperationID string `json:"operationID"` + SendID string `json:"sendID"` + ReceiveID string `json:"receiveID"` + UnreadMsgNum int64 `json:"UnreadMsgNum"` + MuteEndTime *int64 `json:"muteEndTime"` +} + +type CallbackGroupMsgReadResp struct { + CommonCallbackResp +} diff --git a/pkg/callbackstruct/message.go b/pkg/callbackstruct/message.go index f404088e8..e5916e326 100644 --- a/pkg/callbackstruct/message.go +++ b/pkg/callbackstruct/message.go @@ -79,3 +79,37 @@ type CallbackMsgModifyCommandResp struct { AttachedInfo *string `json:"attachedInfo"` Ex *string `json:"ex"` } + +type CallbackSendGroupMsgErrorReq struct { + CommonCallbackReq + GroupID string `json:"groupID"` +} + +type CallbackSendGroupMsgErrorResp struct { + CommonCallbackResp +} + +type CallbackSingleMsgReadReq struct { + CallbackCommand string `json:"callbackCommand"` + OperationID string `json:"operationID"` + SendID string `json:"sendID"` + ReceiveID string `json:"receiveID"` + MuteEndTime *int64 `json:"muteEndTime"` +} + +type CallbackSingleMsgReadResp struct { + CommonCallbackResp +} + +type CallbackSingleMsgRevokeReq struct { + CallbackCommand `json:"callbackCommand"` + OperationID string `json:"operationID"` + SendID string `json:"sendID"` + ReceiveID string `json:"receiveID"` + Content string `json:"content"` + MuteEndTime *int64 `json:"muteEndTime"` +} + +type CallbackSingleMsgRevokeResp struct { + CommonCallbackResp +} diff --git a/pkg/common/config/config.go b/pkg/common/config/config.go index fdb1cee00..645ec91d9 100644 --- a/pkg/common/config/config.go +++ b/pkg/common/config/config.go @@ -262,6 +262,7 @@ type configStruct struct { CallbackBeforeAddFriend CallBackConfig `yaml:"beforeAddFriend"` CallbackBeforeUpdateUserInfo CallBackConfig `yaml:"beforeUpdateUserInfo"` CallbackBeforeCreateGroup CallBackConfig `yaml:"beforeCreateGroup"` + CallbackAfterCreateGroup CallBackConfig `yaml:"afterCreateGroup"` CallbackBeforeMemberJoinGroup CallBackConfig `yaml:"beforeMemberJoinGroup"` CallbackBeforeSetGroupMemberInfo CallBackConfig `yaml:"beforeSetGroupMemberInfo"` } `yaml:"callback"` diff --git a/pkg/common/http/http_client.go b/pkg/common/http/http_client.go index e0cedf357..abdc6d822 100644 --- a/pkg/common/http/http_client.go +++ b/pkg/common/http/http_client.go @@ -20,7 +20,6 @@ import ( "encoding/json" "io" "net/http" - urllib "net/url" "time" "github.com/OpenIMSDK/protocol/constant" @@ -58,7 +57,8 @@ func Get(url string) (response []byte, err error) { return body, nil } -func Post(ctx context.Context, url string, header map[string]string, data interface{}, timeout int) (content []byte, err error) { +func Post(ctx context.Context, url string, header map[string]string, data interface{}, timeout int) (result []byte, err error) { + defer log.ZDebug(ctx, "callbackPost", "url", url, "header", header, "input", data, "output", result, "timeout", timeout, "output") if timeout > 0 { var cancel func() ctx, cancel = context.WithTimeout(ctx, time.Second*time.Duration(timeout)) @@ -89,7 +89,7 @@ func Post(ctx context.Context, url string, header map[string]string, data interf } defer resp.Body.Close() - result, err := io.ReadAll(resp.Body) + result, err = io.ReadAll(resp.Body) if err != nil { return nil, err } @@ -107,25 +107,24 @@ func PostReturn(ctx context.Context, url string, header map[string]string, input } func callBackPostReturn(ctx context.Context, url, command string, input interface{}, output callbackstruct.CallbackResp, callbackConfig config.CallBackConfig) error { - defer log.ZDebug(ctx, "callback", "url", url, "command", command, "input", input, "callbackConfig", callbackConfig) + defer log.ZDebug(ctx, "callback", "url", url, "input", input, "output", output, "timeout", callbackConfig.CallbackTimeOut) - v := urllib.Values{} - v.Set(constant.CallbackCommand, command) - url = url + "?" + v.Encode() + //v := urllib.Values{} + //v.Set(constant.CallbackCommand, command) + //url = url + "/" + v.Encode() + url = url + "/" + command b, err := Post(ctx, url, nil, input, callbackConfig.CallbackTimeOut) if err != nil { if callbackConfig.CallbackFailedContinue != nil && *callbackConfig.CallbackFailedContinue { - log.ZWarn(ctx, "callback failed but continue", err, "url", url) - return errs.ErrCallbackContinue + return errs.ErrCallbackContinue.Wrap(err.Error()) } return errs.ErrNetwork.Wrap(err.Error()) } if err = json.Unmarshal(b, output); err != nil { if callbackConfig.CallbackFailedContinue != nil && *callbackConfig.CallbackFailedContinue { - log.ZWarn(ctx, "callback failed but continue", err, "url", url) - return errs.ErrCallbackContinue + return errs.ErrCallbackContinue.Wrap(err.Error()) } return errs.ErrData.Wrap(err.Error()) }