pull/1427/head
withchao 2 years ago
parent 88ca79a0ec
commit 371a592c0e

@ -16,6 +16,10 @@ package cache
import ( import (
"context" "context"
"fmt"
"github.com/OpenIMSDK/protocol/constant"
"github.com/OpenIMSDK/tools/errs"
"strconv"
"time" "time"
"github.com/OpenIMSDK/tools/log" "github.com/OpenIMSDK/tools/log"
@ -34,8 +38,10 @@ const (
groupMemberIDsKey = "GROUP_MEMBER_IDS:" groupMemberIDsKey = "GROUP_MEMBER_IDS:"
groupMembersHashKey = "GROUP_MEMBERS_HASH2:" groupMembersHashKey = "GROUP_MEMBERS_HASH2:"
groupMemberInfoKey = "GROUP_MEMBER_INFO:" groupMemberInfoKey = "GROUP_MEMBER_INFO:"
//groupOwnerInfoKey = "GROUP_OWNER_INFO:"
joinedGroupsKey = "JOIN_GROUPS_KEY:" joinedGroupsKey = "JOIN_GROUPS_KEY:"
groupMemberNumKey = "GROUP_MEMBER_NUM_CACHE:" groupMemberNumKey = "GROUP_MEMBER_NUM_CACHE:"
groupRoleLevelMemberIDsKey = "GROUP_ROLE_LEVEL_MEMBER_IDS:"
) )
type GroupCache interface { type GroupCache interface {
@ -61,9 +67,15 @@ type GroupCache interface {
GetGroupMembersInfo(ctx context.Context, groupID string, userID []string) (groupMembers []*relationtb.GroupMemberModel, err error) GetGroupMembersInfo(ctx context.Context, groupID string, userID []string) (groupMembers []*relationtb.GroupMemberModel, err error)
GetAllGroupMembersInfo(ctx context.Context, groupID string) (groupMembers []*relationtb.GroupMemberModel, err error) GetAllGroupMembersInfo(ctx context.Context, groupID string) (groupMembers []*relationtb.GroupMemberModel, err error)
GetGroupMembersPage(ctx context.Context, groupID string, userID []string, showNumber, pageNumber int32) (total uint32, groupMembers []*relationtb.GroupMemberModel, err error) GetGroupMembersPage(ctx context.Context, groupID string, userID []string, showNumber, pageNumber int32) (total uint32, groupMembers []*relationtb.GroupMemberModel, err error)
FindGroupMemberUser(ctx context.Context, groupIDs []string, userID string) ([]*relationtb.GroupMemberModel, error)
GetGroupOwner(ctx context.Context, groupID string) (*relationtb.GroupMemberModel, error)
GetGroupsOwner(ctx context.Context, groupIDs []string) ([]*relationtb.GroupMemberModel, error)
DelGroupRoleLevel(groupID string, roleLevel []int32) GroupCache
DelGroupAllRoleLevel(groupID string) GroupCache
DelGroupMembersInfo(groupID string, userID ...string) GroupCache DelGroupMembersInfo(groupID string, userID ...string) GroupCache
GetGroupRoleLevelMemberInfo(ctx context.Context, groupID string, roleLevel int32) ([]*relationtb.GroupMemberModel, error)
GetGroupRolesLevelMemberInfo(ctx context.Context, groupID string, roleLevels []int32) ([]*relationtb.GroupMemberModel, error)
GetGroupMemberNum(ctx context.Context, groupID string) (memberNum int64, err error) GetGroupMemberNum(ctx context.Context, groupID string) (memberNum int64, err error)
DelGroupsMemberNum(groupID ...string) GroupCache DelGroupsMemberNum(groupID ...string) GroupCache
} }
@ -131,6 +143,10 @@ func (g *GroupCacheRedis) getGroupMemberNumKey(groupID string) string {
return groupMemberNumKey + groupID return groupMemberNumKey + groupID
} }
func (g *GroupCacheRedis) getGroupRoleLevelMemberIDsKey(groupID string, roleLevel int32) string {
return groupRoleLevelMemberIDsKey + groupID + "-" + strconv.Itoa(int(roleLevel))
}
func (g *GroupCacheRedis) GetGroupIndex(group *relationtb.GroupModel, keys []string) (int, error) { func (g *GroupCacheRedis) GetGroupIndex(group *relationtb.GroupModel, keys []string) (int, error) {
key := g.getGroupInfoKey(group.GroupID) key := g.getGroupInfoKey(group.GroupID)
for i, _key := range keys { for i, _key := range keys {
@ -153,7 +169,7 @@ func (g *GroupCacheRedis) GetGroupMemberIndex(groupMember *relationtb.GroupMembe
return 0, errIndex return 0, errIndex
} }
// / groupInfo. // groupInfo.
func (g *GroupCacheRedis) GetGroupsInfo(ctx context.Context, groupIDs []string) (groups []*relationtb.GroupModel, err error) { func (g *GroupCacheRedis) GetGroupsInfo(ctx context.Context, groupIDs []string) (groups []*relationtb.GroupModel, err error) {
return batchGetCache2(ctx, g.rcClient, g.expireTime, groupIDs, func(groupID string) string { return batchGetCache2(ctx, g.rcClient, g.expireTime, groupIDs, func(groupID string) string {
return g.getGroupInfoKey(groupID) return g.getGroupInfoKey(groupID)
@ -179,6 +195,31 @@ func (g *GroupCacheRedis) DelGroupsInfo(groupIDs ...string) GroupCache {
return newGroupCache return newGroupCache
} }
func (g *GroupCacheRedis) DelGroupsOwner(groupIDs ...string) GroupCache {
newGroupCache := g.NewCache()
keys := make([]string, 0, len(groupIDs))
for _, groupID := range groupIDs {
keys = append(keys, g.getGroupRoleLevelMemberIDsKey(groupID, constant.GroupOwner))
}
newGroupCache.AddKeys(keys...)
return newGroupCache
}
func (g *GroupCacheRedis) DelGroupRoleLevel(groupID string, roleLevels []int32) GroupCache {
newGroupCache := g.NewCache()
keys := make([]string, 0, len(roleLevels))
for _, roleLevel := range roleLevels {
keys = append(keys, g.getGroupRoleLevelMemberIDsKey(groupID, roleLevel))
}
newGroupCache.AddKeys(keys...)
return newGroupCache
}
func (g *GroupCacheRedis) DelGroupAllRoleLevel(groupID string) GroupCache {
return g.DelGroupRoleLevel(groupID, []int32{constant.GroupOwner, constant.GroupAdmin, constant.GroupOrdinaryUsers})
}
// groupMembersHash. // groupMembersHash.
func (g *GroupCacheRedis) GetGroupMembersHash(ctx context.Context, groupID string) (hashCode uint64, err error) { func (g *GroupCacheRedis) GetGroupMembersHash(ctx context.Context, groupID string) (hashCode uint64, err error) {
return getCache(ctx, g.rcClient, g.getGroupMembersHashKey(groupID), g.expireTime, func(ctx context.Context) (uint64, error) { return getCache(ctx, g.rcClient, g.getGroupMembersHashKey(groupID), g.expireTime, func(ctx context.Context) (uint64, error) {
@ -211,7 +252,6 @@ func (g *GroupCacheRedis) DelGroupMembersHash(groupID string) GroupCache {
return cache return cache
} }
// groupMemberIDs.
func (g *GroupCacheRedis) GetGroupMemberIDs(ctx context.Context, groupID string) (groupMemberIDs []string, err error) { func (g *GroupCacheRedis) GetGroupMemberIDs(ctx context.Context, groupID string) (groupMemberIDs []string, err error) {
return getCache(ctx, g.rcClient, g.getGroupMemberIDsKey(groupID), g.expireTime, func(ctx context.Context) ([]string, error) { return getCache(ctx, g.rcClient, g.getGroupMemberIDsKey(groupID), g.expireTime, func(ctx context.Context) ([]string, error) {
return g.groupMemberDB.FindMemberUserID(ctx, groupID) return g.groupMemberDB.FindMemberUserID(ctx, groupID)
@ -269,12 +309,7 @@ func (g *GroupCacheRedis) GetGroupMembersInfo(ctx context.Context, groupID strin
}) })
} }
func (g *GroupCacheRedis) GetGroupMembersPage( func (g *GroupCacheRedis) GetGroupMembersPage(ctx context.Context, groupID string, userIDs []string, showNumber, pageNumber int32) (total uint32, groupMembers []*relationtb.GroupMemberModel, err error) {
ctx context.Context,
groupID string,
userIDs []string,
showNumber, pageNumber int32,
) (total uint32, groupMembers []*relationtb.GroupMemberModel, err error) {
groupMemberIDs, err := g.GetGroupMemberIDs(ctx, groupID) groupMemberIDs, err := g.GetGroupMemberIDs(ctx, groupID)
if err != nil { if err != nil {
return 0, nil, err return 0, nil, err
@ -333,3 +368,68 @@ func (g *GroupCacheRedis) DelGroupsMemberNum(groupID ...string) GroupCache {
return cache return cache
} }
func (g *GroupCacheRedis) GetGroupOwner(ctx context.Context, groupID string) (*relationtb.GroupMemberModel, error) {
members, err := g.GetGroupRoleLevelMemberInfo(ctx, groupID, constant.GroupOwner)
if err != nil {
return nil, err
}
if len(members) == 0 {
return nil, errs.ErrRecordNotFound.Wrap(fmt.Sprintf("group %s owner not found", groupID))
}
return members[0], nil
}
func (g *GroupCacheRedis) GetGroupsOwner(ctx context.Context, groupIDs []string) ([]*relationtb.GroupMemberModel, error) {
members := make([]*relationtb.GroupMemberModel, 0, len(groupIDs))
for _, groupID := range groupIDs {
items, err := g.GetGroupRoleLevelMemberInfo(ctx, groupID, constant.GroupOwner)
if err != nil {
return nil, err
}
if len(items) > 0 {
members = append(members, items[0])
}
}
return members, nil
}
func (g *GroupCacheRedis) GetGroupRoleLevelMemberIDs(ctx context.Context, groupID string, roleLevel int32) ([]string, error) {
return getCache(ctx, g.rcClient, g.getGroupRoleLevelMemberIDsKey(groupID, roleLevel), g.expireTime, func(ctx context.Context) ([]string, error) {
return g.groupMemberDB.FindRoleLevelUserIDs(ctx, groupID, roleLevel)
})
}
func (g *GroupCacheRedis) GetGroupRoleLevelMemberInfo(ctx context.Context, groupID string, roleLevel int32) ([]*relationtb.GroupMemberModel, error) {
userIDs, err := g.GetGroupRoleLevelMemberIDs(ctx, groupID, roleLevel)
if err != nil {
return nil, err
}
return g.GetGroupMembersInfo(ctx, groupID, userIDs)
}
func (g *GroupCacheRedis) GetGroupRolesLevelMemberInfo(ctx context.Context, groupID string, roleLevels []int32) ([]*relationtb.GroupMemberModel, error) {
var userIDs []string
for _, roleLevel := range roleLevels {
ids, err := g.GetGroupRoleLevelMemberIDs(ctx, groupID, roleLevel)
if err != nil {
return nil, err
}
userIDs = append(userIDs, ids...)
}
return g.GetGroupMembersInfo(ctx, groupID, userIDs)
}
func (g *GroupCacheRedis) FindGroupMemberUser(ctx context.Context, groupIDs []string, userID string) (_ []*relationtb.GroupMemberModel, err error) {
if len(groupIDs) == 0 {
groupIDs, err = g.GetJoinedGroupIDs(ctx, userID)
if err != nil {
return nil, err
}
}
return batchGetCache2(ctx, g.rcClient, g.expireTime, groupIDs, func(groupID string) string {
return g.getGroupMemberInfoKey(groupID, userID)
}, func(ctx context.Context, groupID string) (*relationtb.GroupMemberModel, error) {
return g.groupMemberDB.Take(ctx, groupID, userID)
})
}

@ -38,7 +38,7 @@ const (
var errIndex = errors.New("err index") var errIndex = errors.New("err index")
type metaCache interface { type metaCache interface {
ExecDel(ctx context.Context) error ExecDel(ctx context.Context, distinct ...bool) error
// delete key rapid // delete key rapid
DelKey(ctx context.Context, key string) error DelKey(ctx context.Context, key string) error
AddKeys(keys ...string) AddKeys(keys ...string)
@ -57,7 +57,10 @@ type metaCacheRedis struct {
retryInterval time.Duration retryInterval time.Duration
} }
func (m *metaCacheRedis) ExecDel(ctx context.Context) error { func (m *metaCacheRedis) ExecDel(ctx context.Context, distinct ...bool) error {
if len(distinct) > 0 && distinct[0] {
m.keys = utils.Distinct(m.keys)
}
if len(m.keys) > 0 { if len(m.keys) > 0 {
log.ZDebug(ctx, "delete cache", "keys", m.keys) log.ZDebug(ctx, "delete cache", "keys", m.keys)
for _, key := range m.keys { for _, key := range m.keys {

@ -16,7 +16,6 @@ package controller
import ( import (
"context" "context"
"fmt"
"github.com/dtm-labs/rockscache" "github.com/dtm-labs/rockscache"
"github.com/openimsdk/open-im-server/v3/pkg/common/pagination" "github.com/openimsdk/open-im-server/v3/pkg/common/pagination"
"time" "time"
@ -95,16 +94,24 @@ type groupDatabase struct {
cache cache.GroupCache cache cache.GroupCache
} }
func (g *groupDatabase) FindGroupMemberUserID(ctx context.Context, groupID string) ([]string, error) { func (g *groupDatabase) FindGroupMembers(ctx context.Context, groupID string, userIDs []string) ([]*relationtb.GroupMemberModel, error) {
return g.cache.GetGroupMemberIDs(ctx, groupID) return g.cache.GetGroupMembersInfo(ctx, groupID, userIDs)
} }
func (g *groupDatabase) FindGroupMemberNum(ctx context.Context, groupID string) (uint32, error) { func (g *groupDatabase) FindGroupMemberUser(ctx context.Context, groupIDs []string, userID string) ([]*relationtb.GroupMemberModel, error) {
num, err := g.cache.GetGroupMemberNum(ctx, groupID) return g.cache.FindGroupMemberUser(ctx, groupIDs, userID)
if err != nil { }
return 0, err
} func (g *groupDatabase) FindGroupMemberRoleLevels(ctx context.Context, groupID string, roleLevels []int32) ([]*relationtb.GroupMemberModel, error) {
return uint32(num), nil return g.cache.GetGroupRolesLevelMemberInfo(ctx, groupID, roleLevels)
}
func (g *groupDatabase) FindGroupMemberAll(ctx context.Context, groupID string) ([]*relationtb.GroupMemberModel, error) {
return g.cache.GetAllGroupMembersInfo(ctx, groupID)
}
func (g *groupDatabase) FindGroupsOwner(ctx context.Context, groupIDs []string) ([]*relationtb.GroupMemberModel, error) {
return g.cache.GetGroupsOwner(ctx, groupIDs)
} }
func (g *groupDatabase) CreateGroup(ctx context.Context, groups []*relationtb.GroupModel, groupMembers []*relationtb.GroupMemberModel) error { func (g *groupDatabase) CreateGroup(ctx context.Context, groups []*relationtb.GroupModel, groupMembers []*relationtb.GroupMemberModel) error {
@ -118,37 +125,48 @@ func (g *groupDatabase) CreateGroup(ctx context.Context, groups []*relationtb.Gr
return err return err
} }
for _, group := range groups { for _, group := range groups {
c = c.DelGroupsInfo(group.GroupID) c = c.DelGroupsInfo(group.GroupID).
c = c.DelGroupMembersHash(group.GroupID) DelGroupMembersHash(group.GroupID).
c = c.DelGroupsMemberNum(group.GroupID) DelGroupMembersHash(group.GroupID).
c = c.DelGroupMemberIDs(group.GroupID) DelGroupsMemberNum(group.GroupID).
DelGroupMemberIDs(group.GroupID).
DelGroupAllRoleLevel(group.GroupID)
} }
} }
if len(groupMembers) > 0 { if len(groupMembers) > 0 {
if err := g.groupMemberDB.Create(ctx, groupMembers); err != nil { if err := g.groupMemberDB.Create(ctx, groupMembers); err != nil {
return err return err
} }
temp := make(map[string]struct{})
for _, groupMember := range groupMembers { for _, groupMember := range groupMembers {
if _, ok := temp[groupMember.GroupID]; !ok { c = c.DelGroupMembersHash(groupMember.GroupID).
temp[groupMember.GroupID] = struct{}{} DelGroupsMemberNum(groupMember.GroupID).
c = c.DelGroupMembersHash(groupMember.GroupID) DelGroupMemberIDs(groupMember.GroupID).
c = c.DelGroupsMemberNum(groupMember.GroupID) DelJoinedGroupID(groupMember.UserID).
c = c.DelGroupMemberIDs(groupMember.GroupID) DelGroupMembersInfo(groupMember.GroupID, groupMember.UserID).
DelGroupAllRoleLevel(groupMember.GroupID)
} }
c = c.DelJoinedGroupID(groupMember.UserID)
c = c.DelGroupMembersInfo(groupMember.GroupID, groupMember.UserID)
} }
} return c.ExecDel(ctx, true)
return c.ExecDel(ctx)
}) })
} }
func (g *groupDatabase) TakeGroup(ctx context.Context, groupID string) (group *relationtb.GroupModel, err error) { func (g *groupDatabase) FindGroupMemberUserID(ctx context.Context, groupID string) ([]string, error) {
return g.cache.GetGroupMemberIDs(ctx, groupID)
}
func (g *groupDatabase) FindGroupMemberNum(ctx context.Context, groupID string) (uint32, error) {
num, err := g.cache.GetGroupMemberNum(ctx, groupID)
if err != nil {
return 0, err
}
return uint32(num), nil
}
func (g *groupDatabase) TakeGroup(ctx context.Context, groupID string) (*relationtb.GroupModel, error) {
return g.cache.GetGroupInfo(ctx, groupID) return g.cache.GetGroupInfo(ctx, groupID)
} }
func (g *groupDatabase) FindGroup(ctx context.Context, groupIDs []string) (groups []*relationtb.GroupModel, err error) { func (g *groupDatabase) FindGroup(ctx context.Context, groupIDs []string) ([]*relationtb.GroupModel, error) {
return g.cache.GetGroupsInfo(ctx, groupIDs) return g.cache.GetGroupsInfo(ctx, groupIDs)
} }
@ -164,39 +182,36 @@ func (g *groupDatabase) UpdateGroup(ctx context.Context, groupID string, data ma
} }
func (g *groupDatabase) DismissGroup(ctx context.Context, groupID string, deleteMember bool) error { func (g *groupDatabase) DismissGroup(ctx context.Context, groupID string, deleteMember bool) error {
cache := g.cache.NewCache() return g.ctxTx.Transaction(ctx, func(ctx context.Context) error {
if err := g.tx.Transaction(func(tx any) error { c := g.cache.NewCache()
if err := g.groupDB.NewTx(tx).UpdateStatus(ctx, groupID, constant.GroupStatusDismissed); err != nil { if err := g.groupDB.UpdateState(ctx, groupID, constant.GroupStatusDismissed); err != nil {
return err return err
} }
if deleteMember { if deleteMember {
if err := g.groupMemberDB.NewTx(tx).DeleteGroup(ctx, []string{groupID}); err != nil {
return err
}
userIDs, err := g.cache.GetGroupMemberIDs(ctx, groupID) userIDs, err := g.cache.GetGroupMemberIDs(ctx, groupID)
if err != nil { if err != nil {
return err return err
} }
cache = cache.DelJoinedGroupID(userIDs...).DelGroupMemberIDs(groupID).DelGroupsMemberNum(groupID).DelGroupMembersHash(groupID) if err := g.groupMemberDB.Delete(ctx, groupID, nil); err != nil {
}
cache = cache.DelGroupsInfo(groupID)
return nil
}); err != nil {
return err return err
} }
return cache.ExecDel(ctx) c = c.DelJoinedGroupID(userIDs...).
DelGroupMemberIDs(groupID).
DelGroupsMemberNum(groupID).
DelGroupMembersHash(groupID).
DelGroupAllRoleLevel(groupID).
DelGroupMembersInfo(groupID, userIDs...)
}
return c.DelGroupsInfo(groupID).ExecDel(ctx)
})
} }
func (g *groupDatabase) TakeGroupMember( func (g *groupDatabase) TakeGroupMember(ctx context.Context, groupID string, userID string) (*relationtb.GroupMemberModel, error) {
ctx context.Context,
groupID string,
userID string,
) (groupMember *relationtb.GroupMemberModel, err error) {
return g.cache.GetGroupMemberInfo(ctx, groupID, userID) return g.cache.GetGroupMemberInfo(ctx, groupID, userID)
} }
func (g *groupDatabase) TakeGroupOwner(ctx context.Context, groupID string) (*relationtb.GroupMemberModel, error) { func (g *groupDatabase) TakeGroupOwner(ctx context.Context, groupID string) (*relationtb.GroupMemberModel, error) {
return g.groupMemberDB.TakeOwner(ctx, groupID) // todo cache group owner return g.cache.GetGroupOwner(ctx, groupID)
} }
func (g *groupDatabase) FindUserManagedGroupID(ctx context.Context, userID string) (groupIDs []string, err error) { func (g *groupDatabase) FindUserManagedGroupID(ctx context.Context, userID string) (groupIDs []string, err error) {
@ -207,112 +222,57 @@ func (g *groupDatabase) PageGroupRequest(ctx context.Context, groupIDs []string,
return g.groupRequestDB.PageGroup(ctx, groupIDs, pagination) return g.groupRequestDB.PageGroup(ctx, groupIDs, pagination)
} }
func (g *groupDatabase) FindGroupMember(ctx context.Context, groupIDs []string, userIDs []string, roleLevels []int32) (totalGroupMembers []*relationtb.GroupMemberModel, err error) { func (g *groupDatabase) PageGetJoinGroup(ctx context.Context, userID string, pagination pagination.Pagination) (total int64, totalGroupMembers []*relationtb.GroupMemberModel, err error) {
if len(groupIDs) == 0 && len(roleLevels) == 0 && len(userIDs) == 1 {
gIDs, err := g.cache.GetJoinedGroupIDs(ctx, userIDs[0])
if err != nil {
return nil, err
}
var res []*relationtb.GroupMemberModel
for _, groupID := range gIDs {
v, err := g.cache.GetGroupMemberInfo(ctx, groupID, userIDs[0])
if err != nil {
return nil, err
}
res = append(res, v)
}
return res, nil
}
if len(roleLevels) == 0 {
for _, groupID := range groupIDs {
groupMembers, err := g.cache.GetGroupMembersInfo(ctx, groupID, userIDs)
if err != nil {
return nil, err
}
totalGroupMembers = append(totalGroupMembers, groupMembers...)
}
return totalGroupMembers, nil
}
return g.groupMemberDB.Find(ctx, groupIDs, userIDs, roleLevels)
}
func (g *groupDatabase) PageGetJoinGroup(
ctx context.Context,
userID string,
pagination pagination.Pagination,
) (total int64, totalGroupMembers []*relationtb.GroupMemberModel, err error) {
groupIDs, err := g.cache.GetJoinedGroupIDs(ctx, userID) groupIDs, err := g.cache.GetJoinedGroupIDs(ctx, userID)
if err != nil { if err != nil {
return 0, nil, err return 0, nil, err
} }
for _, groupID := range utils.Paginate(groupIDs, int(pageNumber), int(showNumber)) { for _, groupID := range utils.Paginate(groupIDs, int(pagination.GetPageNumber()), int(pagination.GetShowNumber())) {
groupMembers, err := g.cache.GetGroupMembersInfo(ctx, groupID, []string{userID}) groupMembers, err := g.cache.GetGroupMembersInfo(ctx, groupID, []string{userID})
if err != nil { if err != nil {
return 0, nil, err return 0, nil, err
} }
totalGroupMembers = append(totalGroupMembers, groupMembers...) totalGroupMembers = append(totalGroupMembers, groupMembers...)
} }
return uint32(len(groupIDs)), totalGroupMembers, nil return int64(len(groupIDs)), totalGroupMembers, nil
} }
func (g *groupDatabase) PageGetGroupMember( func (g *groupDatabase) PageGetGroupMember(ctx context.Context, groupID string, pagination pagination.Pagination) (total int64, totalGroupMembers []*relationtb.GroupMemberModel, err error) {
ctx context.Context,
groupID string,
pagination pagination.Pagination,
) (total int64, totalGroupMembers []*relationtb.GroupMemberModel, err error) {
groupMemberIDs, err := g.cache.GetGroupMemberIDs(ctx, groupID) groupMemberIDs, err := g.cache.GetGroupMemberIDs(ctx, groupID)
if err != nil { if err != nil {
return 0, nil, err return 0, nil, err
} }
pageIDs := utils.Paginate(groupMemberIDs, int(pageNumber), int(showNumber)) pageIDs := utils.Paginate(groupMemberIDs, int(pagination.GetPageNumber()), int(pagination.GetShowNumber()))
if len(pageIDs) == 0 { if len(pageIDs) == 0 {
return uint32(len(groupMemberIDs)), nil, nil return int64(len(groupMemberIDs)), nil, nil
} }
members, err := g.cache.GetGroupMembersInfo(ctx, groupID, pageIDs) members, err := g.cache.GetGroupMembersInfo(ctx, groupID, pageIDs)
if err != nil { if err != nil {
return 0, nil, err return 0, nil, err
} }
return uint32(len(groupMemberIDs)), members, nil return int64(len(groupMemberIDs)), members, nil
} }
func (g *groupDatabase) SearchGroupMember(ctx context.Context, keyword string, groupID string, pagination pagination.Pagination) (int64, []*relationtb.GroupMemberModel, error) { func (g *groupDatabase) SearchGroupMember(ctx context.Context, keyword string, groupID string, pagination pagination.Pagination) (int64, []*relationtb.GroupMemberModel, error) {
return g.groupMemberDB.SearchMember(ctx, keyword, groupIDs, userIDs, roleLevels, pagination) return g.groupMemberDB.SearchMember(ctx, keyword, groupID, pagination)
} }
func (g *groupDatabase) HandlerGroupRequest( func (g *groupDatabase) HandlerGroupRequest(ctx context.Context, groupID string, userID string, handledMsg string, handleResult int32, member *relationtb.GroupMemberModel) error {
ctx context.Context, return g.ctxTx.Transaction(ctx, func(ctx context.Context) error {
groupID string, if err := g.groupRequestDB.UpdateHandler(ctx, groupID, userID, handledMsg, handleResult); err != nil {
userID string,
handledMsg string,
handleResult int32,
member *relationtb.GroupMemberModel,
) error {
//cache := g.cache.NewCache()
//if err := g.tx.Transaction(func(tx any) error {
// if err := g.groupRequestDB.NewTx(tx).UpdateHandler(ctx, groupID, userID, handledMsg, handleResult); err != nil {
// return err
// }
// if member != nil {
// if err := g.groupMemberDB.NewTx(tx).Create(ctx, []*relationtb.GroupMemberModel{member}); err != nil {
// return err
// }
// cache = cache.DelGroupMembersHash(groupID).DelGroupMemberIDs(groupID).DelGroupsMemberNum(groupID).DelJoinedGroupID(member.UserID)
// }
// return nil
//}); err != nil {
// return err
//}
//return cache.ExecDel(ctx)
return g.tx.Transaction(func(tx any) error {
if err := g.groupRequestDB.NewTx(tx).UpdateHandler(ctx, groupID, userID, handledMsg, handleResult); err != nil {
return err return err
} }
if member != nil { if member != nil {
if err := g.groupMemberDB.NewTx(tx).Create(ctx, []*relationtb.GroupMemberModel{member}); err != nil { if err := g.groupMemberDB.Create(ctx, []*relationtb.GroupMemberModel{member}); err != nil {
return err return err
} }
if err := g.cache.NewCache().DelGroupMembersHash(groupID).DelGroupMembersInfo(groupID, member.UserID).DelGroupMemberIDs(groupID).DelGroupsMemberNum(groupID).DelJoinedGroupID(member.UserID).ExecDel(ctx); err != nil { c := g.cache.DelGroupMembersHash(groupID).
DelGroupMembersInfo(groupID, member.UserID).
DelGroupMemberIDs(groupID).
DelGroupsMemberNum(groupID).
DelJoinedGroupID(member.UserID).
DelGroupRoleLevel(groupID, []int32{member.RoleLevel})
if err := c.ExecDel(ctx); err != nil {
return err return err
} }
} }
@ -329,13 +289,11 @@ func (g *groupDatabase) DeleteGroupMember(ctx context.Context, groupID string, u
DelGroupsMemberNum(groupID). DelGroupsMemberNum(groupID).
DelJoinedGroupID(userIDs...). DelJoinedGroupID(userIDs...).
DelGroupMembersInfo(groupID, userIDs...). DelGroupMembersInfo(groupID, userIDs...).
DelGroupAllRoleLevel(groupID).
ExecDel(ctx) ExecDel(ctx)
} }
func (g *groupDatabase) MapGroupMemberUserID( func (g *groupDatabase) MapGroupMemberUserID(ctx context.Context, groupIDs []string) (map[string]*relationtb.GroupSimpleUserID, error) {
ctx context.Context,
groupIDs []string,
) (map[string]*relationtb.GroupSimpleUserID, error) {
return g.cache.GetGroupMemberHashMap(ctx, groupIDs) return g.cache.GetGroupMemberHashMap(ctx, groupIDs)
} }
@ -352,62 +310,54 @@ func (g *groupDatabase) MapGroupMemberNum(ctx context.Context, groupIDs []string
} }
func (g *groupDatabase) TransferGroupOwner(ctx context.Context, groupID string, oldOwnerUserID, newOwnerUserID string, roleLevel int32) error { func (g *groupDatabase) TransferGroupOwner(ctx context.Context, groupID string, oldOwnerUserID, newOwnerUserID string, roleLevel int32) error {
return g.tx.Transaction(func(tx any) error { return g.ctxTx.Transaction(ctx, func(ctx context.Context) error {
rowsAffected, err := g.groupMemberDB.NewTx(tx).UpdateRoleLevel(ctx, groupID, oldOwnerUserID, roleLevel) if err := g.groupMemberDB.UpdateRoleLevel(ctx, groupID, oldOwnerUserID, roleLevel); err != nil {
if err != nil {
return err return err
} }
if rowsAffected != 1 { if err := g.groupMemberDB.UpdateRoleLevel(ctx, groupID, newOwnerUserID, constant.GroupOwner); err != nil {
return utils.Wrap(fmt.Errorf("oldOwnerUserID %s rowsAffected = %d", oldOwnerUserID, rowsAffected), "")
}
rowsAffected, err = g.groupMemberDB.NewTx(tx).UpdateRoleLevel(ctx, groupID, newOwnerUserID, constant.GroupOwner)
if err != nil {
return err return err
} }
if rowsAffected != 1 { return g.cache.DelGroupMembersInfo(groupID, oldOwnerUserID, newOwnerUserID).
return utils.Wrap(fmt.Errorf("newOwnerUserID %s rowsAffected = %d", newOwnerUserID, rowsAffected), "") DelGroupAllRoleLevel(groupID).
} DelGroupMembersHash(groupID).ExecDel(ctx)
return g.cache.DelGroupMembersInfo(groupID, oldOwnerUserID, newOwnerUserID).DelGroupMembersHash(groupID).ExecDel(ctx)
}) })
} }
func (g *groupDatabase) UpdateGroupMember( func (g *groupDatabase) UpdateGroupMember(ctx context.Context, groupID string, userID string, data map[string]any) error {
ctx context.Context,
groupID string,
userID string,
data map[string]any,
) error {
if err := g.groupMemberDB.Update(ctx, groupID, userID, data); err != nil { if err := g.groupMemberDB.Update(ctx, groupID, userID, data); err != nil {
return err return err
} }
return g.cache.DelGroupMembersInfo(groupID, userID).ExecDel(ctx) c := g.cache.DelGroupMembersInfo(groupID, userID)
if g.groupMemberDB.IsUpdateRoleLevel(data) {
c = c.DelGroupAllRoleLevel(groupID)
}
return c.ExecDel(ctx)
} }
func (g *groupDatabase) UpdateGroupMembers(ctx context.Context, data []*relationtb.BatchUpdateGroupMember) error { func (g *groupDatabase) UpdateGroupMembers(ctx context.Context, data []*relationtb.BatchUpdateGroupMember) error {
cache := g.cache.NewCache() return g.ctxTx.Transaction(ctx, func(ctx context.Context) error {
if err := g.tx.Transaction(func(tx any) error { c := g.cache.NewCache()
for _, item := range data { for _, item := range data {
if err := g.groupMemberDB.NewTx(tx).Update(ctx, item.GroupID, item.UserID, item.Map); err != nil { if err := g.groupMemberDB.Update(ctx, item.GroupID, item.UserID, item.Map); err != nil {
return err return err
} }
cache = cache.DelGroupMembersInfo(item.GroupID, item.UserID) if g.groupMemberDB.IsUpdateRoleLevel(item.Map) {
c = c.DelGroupAllRoleLevel(item.GroupID)
} }
return nil c = c.DelGroupMembersInfo(item.GroupID, item.UserID).DelGroupMembersHash(item.GroupID)
}); err != nil {
return err
} }
return cache.ExecDel(ctx) return c.ExecDel(ctx, true)
})
} }
func (g *groupDatabase) CreateGroupRequest(ctx context.Context, requests []*relationtb.GroupRequestModel) error { func (g *groupDatabase) CreateGroupRequest(ctx context.Context, requests []*relationtb.GroupRequestModel) error {
return g.tx.Transaction(func(tx any) error { return g.ctxTx.Transaction(ctx, func(ctx context.Context) error {
db := g.groupRequestDB.NewTx(tx)
for _, request := range requests { for _, request := range requests {
if err := db.Delete(ctx, request.GroupID, request.UserID); err != nil { if err := g.groupRequestDB.Delete(ctx, request.GroupID, request.UserID); err != nil {
return err return err
} }
} }
return db.Create(ctx, requests) return g.groupRequestDB.Create(ctx, requests)
}) })
} }
@ -419,12 +369,8 @@ func (g *groupDatabase) TakeGroupRequest(
return g.groupRequestDB.Take(ctx, groupID, userID) return g.groupRequestDB.Take(ctx, groupID, userID)
} }
func (g *groupDatabase) PageGroupRequestUser( func (g *groupDatabase) PageGroupRequestUser(ctx context.Context, userID string, pagination pagination.Pagination) (int64, []*relationtb.GroupRequestModel, error) {
ctx context.Context, return g.groupRequestDB.Page(ctx, userID, pagination)
userID string,
pagination pagination.Pagination,
) (int64, []*relationtb.GroupRequestModel, error) {
return g.groupRequestDB.Page(ctx, userID, pageNumber, showNumber)
} }
func (g *groupDatabase) CountTotal(ctx context.Context, before *time.Time) (count int64, err error) { func (g *groupDatabase) CountTotal(ctx context.Context, before *time.Time) (count int64, err error) {
@ -447,6 +393,5 @@ func (g *groupDatabase) DeleteGroupMemberHash(ctx context.Context, groupIDs []st
for _, groupID := range groupIDs { for _, groupID := range groupIDs {
c = c.DelGroupMembersHash(groupID) c = c.DelGroupMembersHash(groupID)
} }
return c.ExecDel(ctx) return c.ExecDel(ctx)
} }

@ -24,6 +24,10 @@ func (g *GroupMgo) Create(ctx context.Context, groups []*relation.GroupModel) (e
return mgotool.InsertMany(ctx, g.coll, groups) return mgotool.InsertMany(ctx, g.coll, groups)
} }
func (g *GroupMgo) UpdateState(ctx context.Context, groupID string, state int32) (err error) {
return g.UpdateMap(ctx, groupID, map[string]any{"state": state})
}
func (g *GroupMgo) UpdateMap(ctx context.Context, groupID string, args map[string]any) (err error) { func (g *GroupMgo) UpdateMap(ctx context.Context, groupID string, args map[string]any) (err error) {
if len(args) == 0 { if len(args) == 0 {
return nil return nil

@ -27,6 +27,10 @@ func (g *GroupMemberMgo) Delete(ctx context.Context, groupID string, userIDs []s
return mgotool.DeleteMany(ctx, g.coll, bson.M{"group_id": groupID, "user_id": bson.M{"$in": userIDs}}) return mgotool.DeleteMany(ctx, g.coll, bson.M{"group_id": groupID, "user_id": bson.M{"$in": userIDs}})
} }
func (g *GroupMemberMgo) UpdateRoleLevel(ctx context.Context, groupID string, userID string, roleLevel int32) error {
return g.Update(ctx, groupID, userID, bson.M{"role_level": roleLevel})
}
func (g *GroupMemberMgo) Update(ctx context.Context, groupID string, userID string, data map[string]any) (err error) { func (g *GroupMemberMgo) Update(ctx context.Context, groupID string, userID string, data map[string]any) (err error) {
return mgotool.UpdateOne(ctx, g.coll, bson.M{"group_id": groupID, "user_id": userID}, bson.M{"$set": data}, true) return mgotool.UpdateOne(ctx, g.coll, bson.M{"group_id": groupID, "user_id": userID}, bson.M{"$set": data}, true)
} }
@ -48,7 +52,11 @@ func (g *GroupMemberMgo) TakeOwner(ctx context.Context, groupID string) (groupMe
return mgotool.FindOne[*relation.GroupMemberModel](ctx, g.coll, bson.M{"group_id": groupID, "role_level": constant.GroupOwner}) return mgotool.FindOne[*relation.GroupMemberModel](ctx, g.coll, bson.M{"group_id": groupID, "role_level": constant.GroupOwner})
} }
func (g *GroupMemberMgo) SearchMember(ctx context.Context, keyword string, groupIDs []string, userIDs []string, roleLevels []int32, pagination pagination.Pagination) (total int64, groupList []*relation.GroupMemberModel, err error) { func (g *GroupMemberMgo) FindRoleLevelUserIDs(ctx context.Context, groupID string, roleLevel int32) ([]string, error) {
return mgotool.Find[string](ctx, g.coll, bson.M{"group_id": groupID, "role_level": roleLevel}, options.Find().SetProjection(bson.M{"user_id": 1}))
}
func (g *GroupMemberMgo) SearchMember(ctx context.Context, keyword string, groupID string, pagination pagination.Pagination) (total int64, groupList []*relation.GroupMemberModel, err error) {
//TODO implement me //TODO implement me
panic("implement me") panic("implement me")
} }
@ -70,3 +78,11 @@ func (g *GroupMemberMgo) FindUserManagedGroupID(ctx context.Context, userID stri
} }
return mgotool.Find[string](ctx, g.coll, filter, options.Find().SetProjection(bson.M{"group_id": 1})) return mgotool.Find[string](ctx, g.coll, filter, options.Find().SetProjection(bson.M{"group_id": 1}))
} }
func (g *GroupMemberMgo) IsUpdateRoleLevel(data map[string]any) bool {
if len(data) == 0 {
return false
}
_, ok := data["role_level"]
return ok
}

@ -67,12 +67,10 @@ func (GroupModel) TableName() string {
type GroupModelInterface interface { type GroupModelInterface interface {
Create(ctx context.Context, groups []*GroupModel) (err error) Create(ctx context.Context, groups []*GroupModel) (err error)
UpdateMap(ctx context.Context, groupID string, args map[string]any) (err error) UpdateMap(ctx context.Context, groupID string, args map[string]any) (err error)
//UpdateStatus(ctx context.Context, groupID string, status int32) (err error) UpdateState(ctx context.Context, groupID string, state int32) (err error)
Find(ctx context.Context, groupIDs []string) (groups []*GroupModel, err error) Find(ctx context.Context, groupIDs []string) (groups []*GroupModel, err error)
//FindNotDismissedGroup(ctx context.Context, groupIDs []string) (groups []*GroupModel, err error)
Take(ctx context.Context, groupID string) (group *GroupModel, err error) Take(ctx context.Context, groupID string) (group *GroupModel, err error)
Search(ctx context.Context, keyword string, pagination pagination.Pagination) (total int64, groups []*GroupModel, err error) Search(ctx context.Context, keyword string, pagination pagination.Pagination) (total int64, groups []*GroupModel, err error)
//GetGroupIDsByGroupType(ctx context.Context, groupType int) (groupIDs []string, err error)
// 获取群总数 // 获取群总数
CountTotal(ctx context.Context, before *time.Time) (count int64, err error) CountTotal(ctx context.Context, before *time.Time) (count int64, err error)
// 获取范围内群增量 // 获取范围内群增量

@ -62,16 +62,17 @@ type GroupMemberModelInterface interface {
Delete(ctx context.Context, groupID string, userIDs []string) (err error) Delete(ctx context.Context, groupID string, userIDs []string) (err error)
//DeleteGroup(ctx context.Context, groupIDs []string) (err error) //DeleteGroup(ctx context.Context, groupIDs []string) (err error)
Update(ctx context.Context, groupID string, userID string, data map[string]any) (err error) Update(ctx context.Context, groupID string, userID string, data map[string]any) (err error)
//UpdateRoleLevel(ctx context.Context, groupID string, userID string, roleLevel int32) (rowsAffected int64, err error) UpdateRoleLevel(ctx context.Context, groupID string, userID string, roleLevel int32) error
Find(ctx context.Context, groupIDs []string, userIDs []string, roleLevels []int32) (groupMembers []*GroupMemberModel, err error)
FindMemberUserID(ctx context.Context, groupID string) (userIDs []string, err error) FindMemberUserID(ctx context.Context, groupID string) (userIDs []string, err error)
Take(ctx context.Context, groupID string, userID string) (groupMember *GroupMemberModel, err error) Take(ctx context.Context, groupID string, userID string) (groupMember *GroupMemberModel, err error)
TakeOwner(ctx context.Context, groupID string) (groupMember *GroupMemberModel, err error) TakeOwner(ctx context.Context, groupID string) (groupMember *GroupMemberModel, err error)
SearchMember(ctx context.Context, keyword string, groupIDs []string, userIDs []string, roleLevels []int32, pagination pagination.Pagination) (total int64, groupList []*GroupMemberModel, err error) SearchMember(ctx context.Context, keyword string, groupID string, pagination pagination.Pagination) (total int64, groupList []*GroupMemberModel, err error)
FindRoleLevelUserIDs(ctx context.Context, groupID string, roleLevel int32) ([]string, error)
//MapGroupMemberNum(ctx context.Context, groupIDs []string) (count map[string]uint32, err error) //MapGroupMemberNum(ctx context.Context, groupIDs []string) (count map[string]uint32, err error)
//FindJoinUserID(ctx context.Context, groupIDs []string) (groupUsers map[string][]string, err error) //FindJoinUserID(ctx context.Context, groupIDs []string) (groupUsers map[string][]string, err error)
FindUserJoinedGroupID(ctx context.Context, userID string) (groupIDs []string, err error) FindUserJoinedGroupID(ctx context.Context, userID string) (groupIDs []string, err error)
TakeGroupMemberNum(ctx context.Context, groupID string) (count int64, err error) TakeGroupMemberNum(ctx context.Context, groupID string) (count int64, err error)
//FindUsersJoinedGroupID(ctx context.Context, userIDs []string) (map[string][]string, error) //FindUsersJoinedGroupID(ctx context.Context, userIDs []string) (map[string][]string, error)
FindUserManagedGroupID(ctx context.Context, userID string) (groupIDs []string, err error) FindUserManagedGroupID(ctx context.Context, userID string) (groupIDs []string, err error)
IsUpdateRoleLevel(data map[string]any) bool
} }

Loading…
Cancel
Save