package group_power_r import ( "context" "fmt" "git.hilo.cn/hilo-common/domain" "git.hilo.cn/hilo-common/mycontext" "git.hilo.cn/hilo-common/resource/mysql" "git.hilo.cn/hilo-common/resource/redisCli" "git.hilo.cn/hilo-common/utils" "github.com/gin-gonic/gin" "hilo-group/_const/enum/groupPower_e" "hilo-group/_const/enum/group_e" "hilo-group/_const/enum/msg_e" "hilo-group/_const/redis_key" "hilo-group/cv/group_cv" "hilo-group/cv/group_power_cv" "hilo-group/cv/medal_cv" "hilo-group/cv/user_cv" "hilo-group/domain/cache/res_c" "hilo-group/domain/model/game_m" "hilo-group/domain/model/groupPower_m" "hilo-group/domain/model/group_m" "hilo-group/domain/model/res_m" "hilo-group/domain/model/rocket_m" "hilo-group/domain/model/user_m" "hilo-group/domain/service/group_power_s" "hilo-group/domain/service/group_s" "hilo-group/myerr" "hilo-group/myerr/bizerr" "hilo-group/req" "hilo-group/resp" "sort" "strconv" "strings" "time" ) // @Tags 国家势力 // @Summary 加入国家势力 // @Accept application/x-www-form-urlencoded // @Param token header string true "token" // @Param nonce header string true "随机数字" // @Param groupPowerId formData int true "国家势力Id" // @Success 200 // @Router /v1/groupPower/user [post] func GroupPowerJoin(c *gin.Context) (*mycontext.MyContext, error) { myContext := mycontext.CreateMyContext(c.Keys) groupPowerId, err := strconv.ParseUint(c.PostForm("groupPowerId"), 10, 64) if err != nil { return myContext, err } //获取用户 userId, err := req.GetUserId(c) if err != nil { return myContext, err } if err := group_power_s.NewGroupPowerService(myContext).GroupPowerUserJoin(groupPowerId, userId); err != nil { return myContext, err } resp.ResponseOk(c, nil) return myContext, nil } // @Tags 国家势力 // @Summary 退出国家势力 // @Accept application/x-www-form-urlencoded // @Param token header string true "token" // @Param nonce header string true "随机数字" // @Param groupPowerId path int true "国家势力ID" // @Success 200 // @Router /v1/groupPower/user/{groupPowerId} [delete] func GroupPowerLeave(c *gin.Context) (*mycontext.MyContext, error) { myContext := mycontext.CreateMyContext(c.Keys) groupPowerId, err := strconv.ParseUint(c.Param("groupPowerId"), 10, 64) if err != nil { return myContext, err } //获取用户 userId, err := req.GetUserId(c) if err != nil { return myContext, err } remainSeconds, err := group_power_s.NewGroupPowerService(myContext).GroupPowerUserLeave(groupPowerId, userId) if err != nil { if remainSeconds == 0 { return myContext, err } model := domain.CreateModelContext(myContext) user, newErr := user_m.GetUser(model, userId) if newErr != nil { return myContext, newErr } else if user == nil { return myContext, err } else { text := res_m.ResMultiText{MsgId: msg_e.MSG_ID_GROUP_LEAVE_POWER, Language: user.Language} if text.Get(model.Db) == nil { dayLimit := "0" day, sTime := formatSeconds(remainSeconds) sDay := fmt.Sprintf("%d", day) errmsg := strings.ReplaceAll(strings.ReplaceAll(strings.ReplaceAll(text.Content, "%d", dayLimit), "%s", sDay), "xx:xx:xx", sTime) return myContext, myerr.NewBusinessCodeNoCheck(bizerr.GroupPowerStayTooShort.GetCode(), errmsg, myerr.BusinessData{}) } else { return myContext, err } } } resp.ResponseOk(c, nil) return myContext, nil } func formatSeconds(seconds int) (int, string) { sec := seconds % 60 minute := seconds / 60 hour := minute / 60 minute %= 60 day := hour / 24 hour %= 24 sTime := fmt.Sprintf("%02d:%02d:%02d", hour, minute, sec) return day, sTime } // @Tags 国家势力 // @Summary 国家势力标题页 // @Accept application/x-www-form-urlencoded // @Param token header string true "token" // @Param nonce header string true "随机数字" // @Param groupPowerId path int true "国家势力ID" // @Success 200 {object} group_cv.GroupPowerTitle // @Router /v1/groupPower/title/{groupPowerId} [get] func GetGroupPowerTitle(c *gin.Context) (*mycontext.MyContext, error) { myContext := mycontext.CreateMyContext(c.Keys) groupPowerId, err := strconv.ParseUint(c.Param("groupPowerId"), 10, 64) if err != nil { return myContext, err } myUserId, err := req.GetUserId(c) if err != nil { return myContext, err } model := domain.CreateModelContext(myContext) groupPower, err := groupPower_m.GetGroupPower(model, groupPowerId) if err != nil { return myContext, err } if groupPower == nil { return myContext, bizerr.GroupPowerNotExist } gi, err := group_m.GetGroupInfo(model, groupPower.GroupUid) if err != nil { return myContext, err } if gi == nil { return myContext, bizerr.GroupNotFound } gpu := groupPower_m.GroupPowerUser{GroupPowerId: groupPowerId} count, err := gpu.GetCount(model.Db) if err != nil { return myContext, err } gpu = groupPower_m.GroupPowerUser{GroupPowerId: groupPowerId, Role: groupPower_e.GroupPowerUserRoleMgr} records, err := gpu.Get(model.Db) if err != nil { return myContext, err } if len(records) != 1 { return myContext, bizerr.GroupPowerNoOwner } owner := records[0].UserId userIds := []uint64{owner} assistants, err := group_m.FindRolesInGroup(model.Db, groupPower.GroupUid, group_e.GROUP_ADMIN) if err != nil { return myContext, err } userIds = append(userIds, assistants...) users, err := user_cv.GetUserBaseMap(userIds, myUserId) if err != nil { return myContext, err } result := group_cv.GroupPowerTitle{ Id: groupPowerId, Name: gi.Name, GroupId: gi.TxGroupId, Avatar: gi.FaceUrl, MemberNum: count, } if users[owner] != nil { result.Owner = *users[owner] } // FIXME:排序规则是什么? for _, i := range assistants { if users[i] != nil { result.Assistants = append(result.Assistants, *users[i]) } } if len(result.Assistants) > 4 { result.Assistants = result.Assistants[0:4] } gp, err := groupPower_m.GetGroupPowerUserOrNil(model, myUserId) if err != nil { return myContext, err } if gp != nil && gp.GroupPowerId == groupPowerId { result.IsMyGroupPower = true } else { result.IsMyGroupPower = false } resp.ResponseOk(c, result) return myContext, nil } // @Tags 国家势力 // @Summary 国家势力成员群组 // @Accept application/x-www-form-urlencoded // @Param token header string true "token" // @Param nonce header string true "随机数字" // @Param pageSize query int false "分页大小 默认:10" default(10) // @Param pageIndex query int false "第几个分页,从1开始 默认:1" default(1) // @Param groupPowerId path int true "国家势力ID" // @Success 200 {object} group_cv.PopularGroupInfo // @Router /v1/groupPower/group/{groupPowerId} [get] func GetGroupPowerGroups(c *gin.Context) (*mycontext.MyContext, error) { myContext := mycontext.CreateMyContext(c.Keys) myUserId, err := req.GetUserId(c) if err != nil { return myContext, err } pageSize, err := strconv.Atoi(c.Query("pageSize")) if err != nil || pageSize <= 0 { pageSize = 10 } pageIndex, err := strconv.Atoi(c.Query("pageIndex")) if err != nil || pageIndex <= 0 { pageIndex = 1 } groupPowerId, err := strconv.ParseUint(c.Param("groupPowerId"), 10, 64) if err != nil { return myContext, err } model := domain.CreateModelContext(myContext) groupPower, err := groupPower_m.GetGroupPower(model, groupPowerId) if err != nil { return myContext, err } if groupPower == nil { return myContext, bizerr.GroupPowerNotExist } gpu := groupPower_m.GroupPowerUser{GroupPowerId: groupPowerId} records, err := gpu.Get(model.Db) if err != nil { return myContext, err } members := make([]uint64, 0) for _, i := range records { members = append(members, i.UserId) } groupMap, err := group_m.FindGroupByOwners(model.Db, members) if err != nil { return myContext, err } groupList := make([]*group_m.GroupInfo, 0) groupIds := make([]string, 0) visitCount := make(map[string]int64, 0) for _, i := range members { if g, ok := groupMap[i]; ok { groupList = append(groupList, &g) groupIds = append(groupIds, g.ImGroupId) if count, err := group_m.GetRoomVisitCount(g.ImGroupId); err == nil { visitCount[g.ImGroupId] = count } } } model.Log.Infof("GetGroupPowerGroups, members: %v, groupMap: %v, groupList %v", members, groupMap, groupList) // 获取麦上有人的所有群组 micGroupList, err := group_m.GetMicHasInGroups() if err != nil { return myContext, err } micGroupMap := make(map[string]bool, 0) for _, i := range micGroupList { micGroupMap[i] = true } supportLevels, err := group_s.NewGroupService(myContext).GetWeekMaxSupportLevelMap() if err != nil { return myContext, err } roomMicUserMap, err := group_m.BatchGetAllMicUser(model, groupIds) if err != nil { return myContext, err } model.Log.Infof("GetGroupPowerGroups, roomMicUserMap : %v", roomMicUserMap) sort.Slice(groupList, func(i, j int) bool { gi := groupList[i].ImGroupId gj := groupList[j].ImGroupId if micGroupMap[gi] == true && micGroupMap[gj] == false { return true } else if micGroupMap[gi] == false && micGroupMap[gj] == true { return false } if supportLevels[gi] > supportLevels[gj] { return true } else if supportLevels[gi] < supportLevels[gj] { return false } if len(roomMicUserMap[gi]) > len(roomMicUserMap[gj]) { return true } else if len(roomMicUserMap[gi]) < len(roomMicUserMap[gj]) { return false } if visitCount[gi] > visitCount[gj] { return true } else if visitCount[gi] < visitCount[gj] { return false } // * Final resort: 群组CODE,短号优先,然后按字母序 return len(groupList[i].Code) < len(groupList[j].Code) || len(groupList[i].Code) == len(groupList[j].Code) && groupList[i].Code < groupList[j].Code }) // for pretty log // ^ 麦上有人 //logstr := "" //for _, i := range groupList { //hotGroupList = append(hotGroupList, groups[i]) //prefix := " " //if len(roomMicUserMap[i.ImGroupId]) > 0 { // prefix += "^" //} //logstr += prefix + i.ImGroupId + ":" + i.Code + ":" + strconv.Itoa(int(supportLevels[i.ImGroupId])) + // ":" + strconv.Itoa(len(roomMicUserMap[i.ImGroupId])) + ":" + strconv.Itoa(int(visitCount[i.ImGroupId])) //} total := len(groupList) model.Log.Infof("GetGroupPowerGroups: GroupList size = %d", total) result := make([]group_cv.PopularGroupInfo, 0) beginPos := pageSize * (pageIndex - 1) endPos := pageSize * pageIndex if beginPos < total { if endPos > total { endPos = total } groupIds := make([]string, 0) owners := make([]uint64, 0) for _, i := range groupList[beginPos:endPos] { groupIds = append(groupIds, i.ImGroupId) owners = append(owners, i.Owner) } powerIds, powerNames, powerNameplates, powerGrades, err := group_power_cv.BatchGetGroupPower(model.Db, owners) if err != nil { return myContext, err } groupMedals, err := group_m.BatchGetMedals(model.Db, groupIds) if err != nil { return myContext, err } resMedal, err := res_m.MedalGetAllMap(model.Db) if err != nil { return myContext, err } model.Log.Infof("GetGroupPowerGroups: final start = %d, end = %d, %v", beginPos, endPos, groupIds) /* txGroupInfoMap, err := cv.BatchGetGroupInfo(model, groupIds, false) if err != nil { return myContext, err }*/ countryInfo, err := res_c.GetCountryIconMap(model) if err != nil { return myContext, err } uids := make([]uint64, 0) micUsersMap := make(map[string][]uint64, 0) for _, i := range groupList[beginPos:endPos] { // 规则:麦上够4个就全用;全空的话,用群主补 u := roomMicUserMap[i.ImGroupId] if len(u) >= 4 { micUsersMap[i.ImGroupId] = u[0:4] } else if len(u) > 0 { micUsersMap[i.ImGroupId] = u } else { micUsersMap[i.ImGroupId] = []uint64{i.Owner} } uids = append(uids, micUsersMap[i.ImGroupId]...) } uids = utils.UniqueSliceUInt64(uids) userTiny, err := user_cv.GetUserTinyMap(uids) if err != nil { return myContext, err } rr := rocket_m.RocketResult{} maxStageMap, err := rr.GetMaxStage(mysql.Db, groupIds) if err != nil { return myContext, err } roomCount, err := group_m.BatchGetRoomCount(model, groupIds) if err != nil { return nil, err } // 正在进行的游戏 games := game_m.GetNotEndGamesMap(model) for _, i := range groupList[beginPos:endPos] { micUsers := make([]user_cv.CvUserTiny, 0) for _, j := range micUsersMap[i.ImGroupId] { micUsers = append(micUsers, userTiny[j]) } var maxStage *uint16 = nil if s, ok := maxStageMap[i.ImGroupId]; ok { maxStage = &s } medals := make([]medal_cv.PicElement, 0) if m, ok := groupMedals[i.ImGroupId]; ok { for _, j := range m { mId := uint32(j) if e, ok := resMedal[mId]; ok { medals = append(medals, medal_cv.PicElement{ PicUrl: e.PicUrl, }) } } } // 补上房间流水勋章 var pe *medal_cv.PicElement _, pe, err = medal_cv.GetGroupConsumeMedal(model, i.ImGroupId) if err != nil { model.Log.Infof("GetGroupPowerGroups: GetGroupConsumeMedal: %s", err.Error()) } else if pe != nil { medals = append(medals, medal_cv.PicElement{PicUrl: pe.PicUrl}) } var password *string = nil if len(i.Password) > 0 && i.Owner != myUserId { emptyStr := "" password = &emptyStr } result = append(result, group_cv.PopularGroupInfo{ GroupInfo: group_cv.GroupInfo{ GroupBasicInfo: group_cv.GroupBasicInfo{ GroupId: i.TxGroupId, Name: i.Name, Introduction: i.Introduction, Notification: i.Notification, FaceUrl: i.FaceUrl, Code: i.Code, CountryIcon: countryInfo[i.Country], Password: password, SupportLevel: supportLevels[i.ImGroupId], GroupInUserDuration: visitCount[i.ImGroupId], MicNumType: int(i.MicNumType), GroupMedals: medals, }, HasOnMic: len(roomMicUserMap[i.ImGroupId]) > 0, GroupPowerId: powerIds[i.Owner], GroupPowerName: powerNames[i.Owner], GroupPowerNameplate: powerNameplates[i.Owner], GroupPower: group_cv.GroupPower{ Id: powerIds[i.Owner], Name: powerNames[i.Owner], Nameplate: powerNameplates[i.Owner], Grade: powerGrades[i.Owner], }, }, MicUsers: micUsers, RoomUserCount: uint(roomCount[i.ImGroupId]), MaxStage: maxStage, GameTypes: games[i.TxGroupId], }) } } resp.ResponseOk(c, result) return myContext, nil } // @Tags 国家势力 // @Summary 国家势力团队信息 // @Param token header string true "token" // @Param nonce header string true "随机数字" // @Param groupPowerId query int true "国家势力ID" // @Success 200 {object} group_power_cv.CvGroupPowerTeam // @Router /v1/groupPower/team [get] func GroupPowerTeam(c *gin.Context) (*mycontext.MyContext, error) { myContext := mycontext.CreateMyContext(c.Keys) groupPowerId, err := strconv.ParseUint(c.Query("groupPowerId"), 10, 64) if err != nil { return myContext, err } usreId, err := req.GetUserId(c) if err != nil { return myContext, err } cvGroupPowerTeam, err := group_power_cv.GetCvGroupPowerTeam(myContext, groupPowerId, usreId) if err != nil { return myContext, err } resp.ResponseOk(c, cvGroupPowerTeam) return myContext, nil } // @Tags 国家势力 // @Summary 榜单排行榜,这周 // @Param token header string true "token" // @Param nonce header string true "随机数字" // @Param type query int true "week:1:thisWeek 2:lastWeek" Enums(1,2) // @Param pageSize query int true "分页大小 默认:10" default(10) // @Param pageIndex query int true "第几个分页,从1开始 默认:1" default(1) // @Success 200 {object} group_power_cv.CvGroupPowerDiamondTotal // @Router /v1/groupPower/billboard/week [get] func GroupPowerBillboardWeek(c *gin.Context) (*mycontext.MyContext, error) { myContext := mycontext.CreateMyContext(c.Keys) pageSize, err := strconv.Atoi(c.Query("pageSize")) if err != nil { pageSize = 10 } pageIndex, err := strconv.Atoi(c.Query("pageIndex")) if err != nil { pageIndex = 1 } t, err := strconv.ParseUint(c.Query("type"), 10, 64) if err != nil { return myContext, err } now := time.Now() monday := utils.GetMonday(now) midnight := time.Date(monday.Year(), monday.Month(), monday.Day(), 0, 0, 0, 0, time.Local) var beginTime, endTime time.Time if t == 1 { endTime = now beginTime = midnight } else if t == 2 { endTime = midnight beginTime = midnight.AddDate(0, 0, -7) } else { return myContext, myerr.NewSysError("type 参数错误") } cvGroupPowerDiamondTotals, err := group_power_cv.GetCvGroupPowerDiamondTotalList(beginTime, endTime, pageSize, pageIndex) if err != nil { return myContext, err } ids := make([]uint64, 0, len(cvGroupPowerDiamondTotals)) for i, _ := range cvGroupPowerDiamondTotals { ids = append(ids, cvGroupPowerDiamondTotals[i].GroupPowerId) } userMap, err := group_power_cv.GetCvGroupPowerUserMapN(ids) if err != nil { return myContext, nil } for i, _ := range cvGroupPowerDiamondTotals { cvGroupPowerDiamondTotals[i].UserN = userMap[cvGroupPowerDiamondTotals[i].GroupPowerId] } resp.ResponseOk(c, cvGroupPowerDiamondTotals) return myContext, nil } type ReturnGroupPowerBillboardOwnerWeek struct { User user_cv.CvUserDetail `json:"user"` Diamond uint `json:"diamond"` } // @Tags 国家势力 // @Summary 榜单排行榜,这周,上周,top3,势力主的信息 // @Param token header string true "token" // @Param nonce header string true "随机数字" // @Param type query int true "week:1:thisWeek 2:lastWeek" Enums(1,2) // @Success 200 {object} ReturnGroupPowerBillboardOwnerWeek // @Router /v1/groupPower/billboard/owner/week [get] func GroupPowerBillboardOwnerWeek(c *gin.Context) (*mycontext.MyContext, error) { myContext := mycontext.CreateMyContext(c.Keys) userId, err := req.GetUserId(c) if err != nil { return myContext, err } t, err := strconv.ParseUint(c.Query("type"), 10, 64) if err != nil { return myContext, err } now := time.Now() monday := utils.GetMonday(now) midnight := time.Date(monday.Year(), monday.Month(), monday.Day(), 0, 0, 0, 0, time.Local) //var beginTime, endTime time.Time var beginTime time.Time if t == 1 { //endTime = now beginTime = midnight } else if t == 2 { //endTime = midnight beginTime = midnight.AddDate(0, 0, -7) } else { return myContext, myerr.NewSysError("type 参数错误") } type R struct { DiamondNum uint UserId uint64 } rs := []R{} //fixme:解决性能问题. /* if err := mysql.Db.Raw("SELECT SUM(l.diamond_num) AS diamond_num, (SELECT u.user_id from group_power_user u where u.group_power_id = l.group_power_id and u.role = ?) as user_id FROM group_power_diamond_log l, group_power p WHERE l.group_power_id = p.id and p.status = ? and l.created_time >= ? AND l.created_time < ? GROUP BY l.group_power_id ORDER BY diamond_num DESC LIMIT 3", groupPower_m2.GroupPowerUserRoleMgr, groupPower_m2.GroupPowerUserHas, beginTime, endTime).Scan(&rs).Error; err != nil { return myContext, err }*/ //用缓存 rows, err := redisCli.GetRedis().ZRevRangeWithScores(context.Background(), redis_key.GetGroupPowerDiamondLogWeek(beginTime.Format(utils.COMPACT_DATE_FORMAT)), 0, -1).Result() if err != nil { return nil, myerr.WrapErr(err) } groupPowerIds := make([]uint64, 0, len(rows)) for i, _ := range rows { groupPowerId, err := strconv.ParseUint(rows[i].Member.(string), 10, 64) if err != nil { return nil, myerr.WrapErr(err) } groupPowerIds = append(groupPowerIds, groupPowerId) } //搜集所有的群组(有效) + 群组管理人 groupPowerUsers := []groupPower_m.GroupPowerUser{} if err := mysql.Db.Raw("SELECT u.user_id, u.group_power_id FROM group_power_user u, group_power p WHERE u.group_power_id = p.id AND u.role = ? and p.status = ? and p.id in (?)", groupPower_e.GroupPowerUserRoleMgr, groupPower_e.GroupPowerUserHas, groupPowerIds).Scan(&groupPowerUsers).Error; err != nil { return nil, myerr.WrapErr(err) } //转换成map groupPowerIdUserIdMap := map[uint64]uint64{} for _, r := range groupPowerUsers { groupPowerIdUserIdMap[r.GroupPowerId] = r.UserId } //只需找到前3个 for i, _ := range rows { groupPowerId, err := strconv.ParseUint(rows[i].Member.(string), 10, 64) if err != nil { return nil, myerr.WrapErr(err) } if len(rs) >= 3 { break } else if userId, flag := groupPowerIdUserIdMap[groupPowerId]; flag { rs = append(rs, R{ DiamondNum: uint(rows[i].Score), UserId: userId, }) } } userIds := make([]uint64, 0, 64) for i, _ := range rs { userIds = append(userIds, rs[i].UserId) } userMap, err := user_cv.GetUserDetailMap(userIds, userId) if err != nil { return myContext, err } results := make([]ReturnGroupPowerBillboardOwnerWeek, 0, len(userIds)) for i, _ := range rs { results = append(results, ReturnGroupPowerBillboardOwnerWeek{ User: *userMap[rs[i].UserId], Diamond: rs[i].DiamondNum, }) } resp.ResponseOk(c, results) return myContext, nil }