feat: add im kafka admin integration

This commit is contained in:
richjohnrambo
2026-08-28 00:05:54 +08:00
parent d53b0c1b62
commit 4779214591
75 changed files with 9053 additions and 185 deletions
+122
View File
@@ -11,9 +11,11 @@ import (
"fmt"
"hotgo/internal/consts"
"hotgo/internal/library/contexts"
"hotgo/internal/library/imkafka"
"hotgo/internal/library/imtenant"
"hotgo/internal/model/input/sysin"
"hotgo/internal/service"
"strconv"
"github.com/gogf/gf/v2/database/gdb"
"github.com/gogf/gf/v2/errors/gerror"
@@ -385,6 +387,22 @@ func (s *sSysImGroup) GovernanceUpdate(ctx context.Context, in *sysin.ImGroupGov
})
}
func (s *sSysImGroup) ProfileUpdate(ctx context.Context, in *sysin.ImGroupProfileUpdateInp) (res *sysin.ImGroupCommandModel, err error) {
if err = in.Filter(ctx); err != nil {
return nil, err
}
payload := map[string]any{
"topic": in.Topic,
"actor_user_id": strconv.FormatInt(contexts.GetUserId(ctx), 10),
"profile": map[string]any{
"name": in.Name,
"avatar_file_id": in.AvatarFileId,
"description": in.Description,
},
}
return s.publishGroupCommand(ctx, in.TenantId, in.Topic, consts.ImAdminCommandGroupProfileUpdate, payload, in.Version)
}
// Dissolve 解散IM群
func (s *sSysImGroup) Dissolve(ctx context.Context, in *sysin.ImGroupDissolveInp) (err error) {
if err = in.Filter(ctx); err != nil {
@@ -483,6 +501,22 @@ func (s *sSysImGroup) Mute(ctx context.Context, in *sysin.ImGroupMuteInp) (err e
})
}
func (s *sSysImGroup) MemberMute(ctx context.Context, in *sysin.ImGroupMuteInp) (res *sysin.ImGroupCommandModel, err error) {
if err = in.Filter(ctx); err != nil {
return nil, err
}
payload := map[string]any{
"topic": in.Topic,
"actor_user_id": strconv.FormatInt(contexts.GetUserId(ctx), 10),
"user_id": strconv.FormatInt(in.UserId, 10),
"reason": in.Reason,
}
if in.ExpiresAt != nil {
payload["expires_at"] = in.ExpiresAt.Time.Format("2006-01-02T15:04:05.000Z07:00")
}
return s.publishGroupCommand(ctx, in.TenantId, in.Topic, consts.ImAdminCommandGroupMemberMute, payload, 0)
}
// Unmute 解除IM群成员禁言
func (s *sSysImGroup) Unmute(ctx context.Context, in *sysin.ImGroupUnmuteInp) (err error) {
if err = in.Filter(ctx); err != nil {
@@ -529,6 +563,31 @@ func (s *sSysImGroup) Unmute(ctx context.Context, in *sysin.ImGroupUnmuteInp) (e
})
}
func (s *sSysImGroup) MemberUnmute(ctx context.Context, in *sysin.ImGroupUnmuteInp) (res *sysin.ImGroupCommandModel, err error) {
if err = in.Filter(ctx); err != nil {
return nil, err
}
payload := map[string]any{
"topic": in.Topic,
"actor_user_id": strconv.FormatInt(contexts.GetUserId(ctx), 10),
"user_id": strconv.FormatInt(in.UserId, 10),
}
return s.publishGroupCommand(ctx, in.TenantId, in.Topic, consts.ImAdminCommandGroupMemberUnmute, payload, 0)
}
func (s *sSysImGroup) MemberRemove(ctx context.Context, in *sysin.ImGroupMemberRemoveInp) (res *sysin.ImGroupCommandModel, err error) {
if err = in.Filter(ctx); err != nil {
return nil, err
}
payload := map[string]any{
"topic": in.Topic,
"actor_user_id": strconv.FormatInt(contexts.GetUserId(ctx), 10),
"user_id": strconv.FormatInt(in.UserId, 10),
"reason": in.Reason,
}
return s.publishGroupCommand(ctx, in.TenantId, in.Topic, consts.ImAdminCommandGroupMemberRemove, payload, 0)
}
// JoinRequestApprove 通过IM入群申请
func (s *sSysImGroup) JoinRequestApprove(ctx context.Context, in *sysin.ImGroupJoinRequestResolveInp) (err error) {
if err = in.Filter(ctx); err != nil {
@@ -683,6 +742,30 @@ func (s *sSysImGroup) RoleUpdate(ctx context.Context, in *sysin.ImGroupRoleUpdat
})
}
func (s *sSysImGroup) AdminSet(ctx context.Context, in *sysin.ImGroupRoleUpdateInp) (res *sysin.ImGroupCommandModel, err error) {
if err = in.Filter(ctx); err != nil {
return nil, err
}
payload := map[string]any{
"topic": in.Topic,
"actor_user_id": strconv.FormatInt(contexts.GetUserId(ctx), 10),
"user_ids": []string{strconv.FormatInt(in.UserId, 10)},
}
return s.publishGroupCommand(ctx, in.TenantId, in.Topic, consts.ImAdminCommandGroupAdminSet, payload, 0)
}
func (s *sSysImGroup) AdminRemove(ctx context.Context, in *sysin.ImGroupRoleUpdateInp) (res *sysin.ImGroupCommandModel, err error) {
if err = in.Filter(ctx); err != nil {
return nil, err
}
payload := map[string]any{
"topic": in.Topic,
"actor_user_id": strconv.FormatInt(contexts.GetUserId(ctx), 10),
"user_id": strconv.FormatInt(in.UserId, 10),
}
return s.publishGroupCommand(ctx, in.TenantId, in.Topic, consts.ImAdminCommandGroupAdminRemove, payload, 0)
}
// OwnerTransfer 转让IM群主
func (s *sSysImGroup) OwnerTransfer(ctx context.Context, in *sysin.ImGroupOwnerTransferInp) (err error) {
if err = in.Filter(ctx); err != nil {
@@ -785,6 +868,45 @@ func (s *sSysImGroup) OwnerTransfer(ctx context.Context, in *sysin.ImGroupOwnerT
})
}
func (s *sSysImGroup) publishGroupCommand(ctx context.Context, tenantId int64, topic string, eventType string, payload map[string]any, version int64) (*sysin.ImGroupCommandModel, error) {
_, tenant, err := resolveImTenantDB(ctx, tenantId)
if err != nil {
return nil, err
}
user := contexts.GetUser(ctx)
actorName := ""
if user != nil {
actorName = user.RealName
}
command, err := imkafka.PublishAdminCommand(ctx, imkafka.AdminCommandInput{
TenantID: tenant.Id,
TenantCode: tenant.Code,
EventType: eventType,
BizType: "group",
BizID: topic,
Version: version,
Actor: &imkafka.Actor{
Type: "admin",
ID: strconv.FormatInt(contexts.GetUserId(ctx), 10),
DisplayName: actorName,
},
Payload: payload,
CreatedBy: contexts.GetUserId(ctx),
})
if err != nil {
return nil, err
}
return &sysin.ImGroupCommandModel{
CommandID: command.CommandID,
EventID: command.EventID,
Status: command.Status,
TenantID: command.TenantID,
TenantCode: command.TenantCode,
EventType: command.EventType,
IdempotencyKey: command.IdempotencyKey,
}, nil
}
func (s *sSysImGroup) groupGovernanceSnapshot(ctx context.Context, tx gdb.TX, topic string) (res gdb.Record, err error) {
return tx.Model("im_group_settings").Safe().Ctx(ctx).
Fields(