Skip to content

Commit

Permalink
feat: 添加获取群组成员列表
Browse files Browse the repository at this point in the history
  • Loading branch information
danmuking committed Apr 16, 2024
1 parent 1379fe8 commit 2870958
Show file tree
Hide file tree
Showing 4 changed files with 144 additions and 0 deletions.
16 changes: 16 additions & 0 deletions domain/dto/group_dto.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
package dto

import "time"

type GetGroupMemberDto struct {
// 用户ID
UID int64 `json:"uid"`
// 用户名
Name string `json:"name"`
// 头像
Avatar string `json:"avatar"`
// 用户状态
ActiveStatus int32 `json:"active_status"`
// 最后活跃时间
LastOptTime time.Time `json:"last_active_time"`
}
8 changes: 8 additions & 0 deletions domain/vo/req/get_group_member_list_req.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
package req

type GetGroupMemberListReq struct {
// 房间ID
ID int64 `form:"id" binding:"required"`
Cursor *string `form:"cursor" binding:"required"`
PageSize int `form:"page_size" binding:"required"`
}
1 change: 1 addition & 0 deletions routes/init_router.go
Original file line number Diff line number Diff line change
Expand Up @@ -69,6 +69,7 @@ func initGin() {
apiGroup.DELETE("/:id", service.DeleteGroupService)
apiGroup.POST("/join", service.JoinGroupService)
apiGroup.POST("/quit", service.QuitGroupService)
apiGroup.GET("/getGroupMemberList", service.GetGroupMemberListService)
}

apiContact := router.Group("/api/contact")
Expand Down
119 changes: 119 additions & 0 deletions service/group_service.go
Original file line number Diff line number Diff line change
Expand Up @@ -2,13 +2,18 @@ package service

import (
"DiTing-Go/dal/model"
"DiTing-Go/domain/dto"
"DiTing-Go/domain/enum"
"DiTing-Go/domain/vo/req"
"DiTing-Go/global"
"DiTing-Go/pkg/cursor"
"DiTing-Go/pkg/resp"
"context"
"fmt"
"github.com/gin-gonic/gin"
"gorm.io/gorm"
"strconv"
"strings"
"time"
)

Expand Down Expand Up @@ -514,3 +519,117 @@ func QuitGroupService(c *gin.Context) {
resp.SuccessResponseWithMsg(c, "success")
return
}

// GetGroupMemberListService 退出群聊
//
// @Summary 退出群聊
// @Produce json
// @Param id body int true "房间id"
// @Success 200 {object} resp.ResponseData "成功"
// @Failure 500 {object} resp.ResponseData "内部错误"
// @Router /api/group/getGroupMemberList [get]
func GetGroupMemberListService(c *gin.Context) {
uid := c.GetInt64("uid")
getGroupMemberListReq := req.GetGroupMemberListReq{}
if err := c.ShouldBindQuery(&getGroupMemberListReq); err != nil {
resp.ErrorResponse(c, "参数错误")
global.Logger.Errorf("参数错误: %v", err)
c.Abort()
return
}
ctx := context.Background()

// 查询房间表
room := global.Query.Room
roomQ := room.WithContext(ctx)
roomR, err := roomQ.Where(room.ID.Eq(getGroupMemberListReq.ID)).First()
if err != nil {
resp.ErrorResponse(c, "查询群聊失败")
global.Logger.Errorf("查询房间失败 %s", err)
c.Abort()
return
}
// 查询群聊表
roomGroup := global.Query.RoomGroup
roomGroupQ := roomGroup.WithContext(ctx)
roomGroupR, err := roomGroupQ.Where(roomGroup.RoomID.Eq(roomR.ID)).First()
if err != nil {
resp.ErrorResponse(c, "查询群聊失败")
global.Logger.Errorf("查询群聊失败 %s", err)
c.Abort()
return
}

// 查询用户是否在群聊中
groupMember := global.Query.GroupMember
groupMemberQ := groupMember.WithContext(ctx)
_, err = groupMemberQ.Where(groupMember.UID.Eq(uid), groupMember.GroupID.Eq(roomGroupR.ID)).First()
if err != nil {
resp.ErrorResponse(c, "查询群聊失败")
global.Logger.Errorf("查询群组成员表失败 %s", err)
c.Abort()
return
}

// 分页查询
// 默认值
// 划分游标,status_activateTime
var userR []dto.GetGroupMemberDto
status, activeTime := cursorSplit(getGroupMemberListReq.Cursor)
// 查询群组成员表,联表游标翻页
user := global.Query.User
userQ := user.WithContext(ctx)
if err := userQ.Select(user.Name, user.Avatar, user.ActiveStatus, user.LastOptTime).LeftJoin(groupMemberQ, user.ID.EqCol(groupMember.UID)).Where(groupMember.GroupID.Eq(roomGroupR.ID), user.ActiveStatus.Eq(int32(status)), user.LastOptTime.Gt(activeTime)).Limit(getGroupMemberListReq.PageSize).Scan(&userR); err != nil {
resp.ErrorResponse(c, "查询群聊失败")
global.Logger.Errorf("查询群组成员表失败 %s", err)
c.Abort()
return
}
// 不足,用不在线的补充
if len(userR) < getGroupMemberListReq.PageSize && status == 1 {
var add []dto.GetGroupMemberDto
if err := userQ.Select(user.Name, user.Avatar, user.ActiveStatus, user.LastOptTime).LeftJoin(groupMemberQ, user.ID.EqCol(groupMember.UID)).Where(groupMember.GroupID.Eq(roomGroupR.ID), user.ActiveStatus.Eq(2)).Limit(getGroupMemberListReq.PageSize - len(userR)).Scan(&add); err != nil {
resp.ErrorResponse(c, "查询群聊失败")
global.Logger.Errorf("查询群组成员表失败 %s", err)
c.Abort()
return
}
userR = append(userR, add...)
}

newCursor := genCursor(userR)
resp.SuccessResponse(c, cursor.PageResp{
Cursor: &newCursor,
IsLast: len(userR) < getGroupMemberListReq.PageSize,
Data: userR,
})
}

// 分割游标
func cursorSplit(cursor *string) (int, time.Time) {
if cursor == nil {
return 1, time.Time{}
}
// TODO: 抽取为常量
lines := strings.Split(*cursor, "_")
status, err := strconv.Atoi(lines[0])
if err != nil {
return 1, time.Time{}
}
timeUnix, err := strconv.ParseInt(lines[1], 10, 64)
if err != nil {
return 1, time.Time{}
}
activeTime := time.Unix(timeUnix, timeUnix%1000000000)
return status, activeTime
}

func genCursor(users []dto.GetGroupMemberDto) string {
if users == nil || len(users) == 0 {
return fmt.Sprintf("%d_%d", 2, time.Now().Unix())
}
status := users[len(users)-1].ActiveStatus
activeTime := users[len(users)-1].LastOptTime
newCursor := fmt.Sprintf("%d_%d", status, activeTime.Unix())
return newCursor
}

0 comments on commit 2870958

Please sign in to comment.