role_social.go 16 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606
  1. package model
  2. import (
  3. "rocommon/util"
  4. "roserver/baseserver/model"
  5. "roserver/serverproto"
  6. "unicode/utf8"
  7. )
  8. type RoleSocialOuter interface {
  9. //获取好友系统列表信息(不包括推荐列表信息)
  10. FriendReq(reqType int32)
  11. //添加关注
  12. FriendAdd(subUid uint64)
  13. //取消关注
  14. FriendDel(delUid uint64)
  15. //添加/删除屏蔽名单
  16. FriendBlack(blackUid uint64)
  17. //获取推荐好友列表
  18. FriendRecommend()
  19. //搜索玩家
  20. FriendSearch(searchName string)
  21. }
  22. //role interface
  23. func (this *Role) FriendReq(reqType int32) {
  24. if this.roleSocial != nil {
  25. this.roleSocial.FriendReq(reqType)
  26. }
  27. }
  28. func (this *Role) FriendAdd(subUid uint64) {
  29. if this.roleSocial != nil {
  30. err := this.roleSocial.FriendAdd(subUid)
  31. if err != serverproto.ErrorCode_ERROR_OK {
  32. ackMsg := &serverproto.SCFriendAddAck{
  33. Error: int32(err),
  34. }
  35. this.ReplayGate(ackMsg, true)
  36. }
  37. }
  38. }
  39. func (this *Role) FriendDel(delUid uint64) {
  40. if this.roleSocial != nil {
  41. err := this.roleSocial.FriendDel(delUid)
  42. if err != serverproto.ErrorCode_ERROR_OK {
  43. ackMsg := &serverproto.SCFriendDelAck{
  44. Error: int32(err),
  45. }
  46. this.ReplayGate(ackMsg, true)
  47. }
  48. }
  49. }
  50. func (this *Role) FriendBlack(blackUid uint64) {
  51. if this.roleSocial != nil {
  52. err := this.roleSocial.FriendBlack(blackUid)
  53. if err != serverproto.ErrorCode_ERROR_OK {
  54. ackMsg := &serverproto.SCFriendBlackAck{
  55. Error: int32(err),
  56. }
  57. this.ReplayGate(ackMsg, true)
  58. }
  59. }
  60. }
  61. func (this *Role) FriendRecommend() {
  62. if this.roleSocial != nil {
  63. this.roleSocial.FriendRecommend()
  64. }
  65. }
  66. func (this *Role) FriendSearch(searchName string) {
  67. if this.roleSocial != nil {
  68. err := this.roleSocial.FriendSearch(searchName)
  69. if err != serverproto.ErrorCode_ERROR_OK {
  70. ackMsg := &serverproto.SCFriendSearchAck{
  71. Error: int32(err),
  72. }
  73. this.ReplayGate(ackMsg, true)
  74. }
  75. }
  76. }
  77. const (
  78. StateTypeSub = 1 //关注列表
  79. StateTypeFans = 2 //粉丝列表
  80. StateTypeBlack = 3 //黑名单
  81. StateTypeRecommend = 4 //推荐列表
  82. StateClimbingTower = 5 //爬塔数据列表
  83. StageTypeDemonGuild = 8
  84. StageTypeDemonMvp = 9
  85. StateTypeBlack_Add = 10 //添加到黑名单状态
  86. StateGuildApply = 101 //公会申请列表Type
  87. FriendTypeNone = 0
  88. FriendTypeSub = 1 //关注该玩家
  89. FriendTypeBeSub = 2 //被关注
  90. FriendTypeAll = 3 //互为关注
  91. RECOMMEND_NUM = 6 //推荐列表玩家数量
  92. )
  93. type RoleSocial struct {
  94. SaveObject
  95. roleFriend *serverproto.RoleFriend
  96. subList map[uint64]struct{} //关注列表
  97. fansList map[uint64]struct{} //粉丝列表
  98. blackList map[uint64]struct{} //黑名单列表
  99. //db 添加或者删除对应id玩家数据
  100. dbSubList map[uint64]bool
  101. dbFansList map[uint64]bool
  102. dbBlackList map[uint64]bool
  103. recommendIdx int32
  104. }
  105. func newRoleSocial(r *Role) *RoleSocial {
  106. roleSocial := &RoleSocial{
  107. SaveObject: SaveObject{
  108. role: r,
  109. },
  110. roleFriend: &serverproto.RoleFriend{},
  111. subList: map[uint64]struct{}{},
  112. fansList: map[uint64]struct{}{},
  113. blackList: map[uint64]struct{}{},
  114. dbSubList: map[uint64]bool{},
  115. dbFansList: map[uint64]bool{},
  116. dbBlackList: map[uint64]bool{},
  117. recommendIdx: 0,
  118. }
  119. return roleSocial
  120. }
  121. func (this *RoleSocial) GetRole() *Role {
  122. return this.role
  123. }
  124. func (this *RoleSocial) Load(msg interface{}) bool {
  125. return true
  126. }
  127. func (this *RoleSocial) LoadOther(msg interface{}) bool {
  128. friendInfo := msg.(*serverproto.RoleFriend)
  129. if friendInfo != nil {
  130. this.roleFriend = friendInfo
  131. for i := 0; i < len(this.roleFriend.SubList); i++ {
  132. this.subList[this.roleFriend.SubList[i]] = struct{}{}
  133. }
  134. for i := 0; i < len(this.roleFriend.FansList); i++ {
  135. this.fansList[this.roleFriend.FansList[i]] = struct{}{}
  136. }
  137. for i := 0; i < len(this.roleFriend.BlackList); i++ {
  138. this.blackList[this.roleFriend.BlackList[i]] = struct{}{}
  139. }
  140. util.DebugF("uid=%v RoleSocial=%v", this.role.GetUUid(), friendInfo)
  141. }
  142. return true
  143. }
  144. func (this *RoleSocial) Save() {
  145. this.SetDirty(false)
  146. //根据不同列表不同类型做不同处理,例如删除,添加等操作,添加就保存的话操作太频繁
  147. dbSaveMsg := &serverproto.SSFriendDataSaveReq{}
  148. this.getDBSaveList(&dbSaveMsg.SubList, this.dbSubList)
  149. this.getDBSaveList(&dbSaveMsg.FansList, this.dbFansList)
  150. this.getDBSaveList(&dbSaveMsg.BlackList, this.dbBlackList)
  151. this.role.SendDb(dbSaveMsg)
  152. //clear
  153. this.dbSubList = map[uint64]bool{}
  154. this.dbFansList = map[uint64]bool{}
  155. this.dbBlackList = map[uint64]bool{}
  156. }
  157. func (this *RoleSocial) getDBSaveList(saveList *[]*serverproto.KeyValueType64, processList map[uint64]bool) {
  158. for key, val := range processList {
  159. var ret int32 = 1 //add
  160. if !val {
  161. ret = 2 //del
  162. }
  163. *saveList = append(*saveList, &serverproto.KeyValueType64{
  164. Key: key,
  165. Value: ret,
  166. })
  167. }
  168. }
  169. func (this *RoleSocial) isInSubList(targetUid uint64) bool {
  170. if _, ok := this.subList[targetUid]; ok {
  171. return true
  172. }
  173. return false
  174. }
  175. func (this *RoleSocial) isInFansList(targetUid uint64) bool {
  176. if _, ok := this.fansList[targetUid]; ok {
  177. return true
  178. }
  179. return false
  180. }
  181. func (this *RoleSocial) IsInBlackList(targetUid uint64) bool {
  182. if _, ok := this.blackList[targetUid]; ok {
  183. return true
  184. }
  185. return false
  186. }
  187. func (this *RoleSocial) BlackList() map[uint64]struct{} {
  188. return this.blackList
  189. }
  190. func (this *RoleSocial) friendState(targetUid uint64) int32 {
  191. if this.isInSubList(targetUid) && this.isInFansList(targetUid) {
  192. return FriendTypeAll
  193. } else if this.isInSubList(targetUid) {
  194. return FriendTypeSub
  195. } else if this.isInFansList(targetUid) {
  196. return FriendTypeBeSub
  197. }
  198. return FriendTypeNone
  199. }
  200. func (this *RoleSocial) CanAddSubList(uid uint64) serverproto.ErrorCode {
  201. if len(this.subList) >= int(model.GlobalSocialSubNumLimit) {
  202. return serverproto.ErrorCode_ERROR_SOCIAL_SUBLIST_LIMIT
  203. }
  204. if _, ok := this.subList[uid]; ok {
  205. return serverproto.ErrorCode_ERROR_SOCIAL_HAS_IN_SUB_LIST
  206. }
  207. return serverproto.ErrorCode_ERROR_OK
  208. }
  209. //true->add false->del
  210. func (this *RoleSocial) HandlerSubList(addDel bool, uid uint64, briefInfo *serverproto.CommonPlayerBriefInfo) {
  211. if addDel {
  212. this.subList[uid] = struct{}{}
  213. if ret, ok := this.dbSubList[briefInfo.Uid]; ok {
  214. if !ret {
  215. delete(this.dbSubList, briefInfo.Uid)
  216. }
  217. } else {
  218. this.dbSubList[briefInfo.Uid] = true
  219. }
  220. ackMsg := &serverproto.SCFriendAddAck{
  221. Error: int32(serverproto.ErrorCode_ERROR_OK),
  222. BriefInfo: briefInfo,
  223. }
  224. this.role.ReplayGate(ackMsg, true)
  225. util.InfoF("uid=%v SubList Add target=%v", this.role.GetUUid(), uid)
  226. } else {
  227. delete(this.subList, uid)
  228. if this.dbSubList[uid] {
  229. delete(this.dbSubList, uid)
  230. } else {
  231. this.dbSubList[uid] = false
  232. }
  233. ackMsg := &serverproto.SCFriendDelAck{
  234. Error: int32(serverproto.ErrorCode_ERROR_OK),
  235. DelUid: uid,
  236. }
  237. this.role.ReplayGate(ackMsg, true)
  238. util.InfoF("uid=%v SubList Del target=%v", this.role.GetUUid(), uid)
  239. }
  240. //Task
  241. TaskMagCheck(this.role, serverproto.TaskType_Friend_SubFan_Num, 0)
  242. this.SetDirty(true)
  243. }
  244. func (this *RoleSocial) CanAddFansList(uid uint64) serverproto.ErrorCode {
  245. if len(this.fansList) >= int(model.GlobalSocialFansNumLimit) {
  246. return serverproto.ErrorCode_ERROR_SOCIAL_FANSLIST_LIMIT
  247. }
  248. return serverproto.ErrorCode_ERROR_OK
  249. }
  250. //粉丝列表是被动操作
  251. func (this *RoleSocial) HandlerFansList(addDel bool, uid uint64, briefInfo *serverproto.CommonPlayerBriefInfo) {
  252. if addDel {
  253. this.fansList[uid] = struct{}{}
  254. if ret, ok := this.dbFansList[briefInfo.Uid]; ok {
  255. if !ret {
  256. delete(this.dbFansList, briefInfo.Uid)
  257. }
  258. } else {
  259. this.dbFansList[briefInfo.Uid] = true
  260. }
  261. ntfMsg := &serverproto.SCFriendAddNtf{
  262. BriefInfo: briefInfo,
  263. }
  264. this.role.ReplayGate(ntfMsg, true)
  265. util.InfoF("uid=%v FansList Add target=%v", this.role.GetUUid(), uid)
  266. } else {
  267. delete(this.fansList, uid)
  268. if this.dbFansList[uid] {
  269. delete(this.dbFansList, uid)
  270. } else {
  271. this.dbFansList[uid] = false
  272. }
  273. ntfMsg := &serverproto.SCFriendDelNtf{
  274. DelUid: uid,
  275. }
  276. this.role.ReplayGate(ntfMsg, true)
  277. util.InfoF("uid=%v FansList Del target=%v", this.role.GetUUid(), uid)
  278. }
  279. //Task
  280. TaskMagCheck(this.role, serverproto.TaskType_Friend_SubFan_Num, 0)
  281. this.SetDirty(true)
  282. }
  283. func (this *RoleSocial) HandlerBlackList(addDel bool, uid uint64, briefInfo *serverproto.CommonPlayerBriefInfo) {
  284. if addDel {
  285. this.blackList[briefInfo.Uid] = struct{}{}
  286. if ret, ok := this.dbBlackList[briefInfo.Uid]; ok {
  287. if !ret {
  288. delete(this.dbBlackList, briefInfo.Uid)
  289. }
  290. } else {
  291. this.dbBlackList[briefInfo.Uid] = true
  292. }
  293. ackMsg := &serverproto.SCFriendBlackAck{
  294. Error: int32(serverproto.ErrorCode_ERROR_OK),
  295. BriefInfo: briefInfo,
  296. }
  297. this.role.ReplayGate(ackMsg, true)
  298. util.InfoF("uid=%v BlackList Add target=%v", this.role.GetUUid(), uid)
  299. } else {
  300. delete(this.blackList, uid)
  301. if this.dbBlackList[uid] {
  302. delete(this.dbBlackList, uid)
  303. } else {
  304. this.dbBlackList[uid] = false
  305. }
  306. ackMsg := &serverproto.SCFriendBlackAck{
  307. Error: int32(serverproto.ErrorCode_ERROR_OK),
  308. BriefInfo: &serverproto.CommonPlayerBriefInfo{
  309. Uid: uid,
  310. },
  311. }
  312. this.role.ReplayGate(ackMsg, true)
  313. util.InfoF("uid=%v BlackList Del target=%v", this.role.GetUUid(), uid)
  314. }
  315. this.SetDirty(true)
  316. }
  317. //获取好友系统列表信息(不包括推荐列表信息)
  318. func (this *RoleSocial) FriendReq(reqType int32) serverproto.ErrorCode {
  319. ackMsg := &serverproto.SCFriendAck{
  320. Type: reqType,
  321. }
  322. //todo...
  323. // 如果是重新登录需要重新获取一次,避免有离线数据
  324. switch reqType {
  325. case StateTypeSub: //获取自己的关注列表(好友列表)
  326. ackMsg.TotalCount = int32(len(this.subList))
  327. ackMsg.TotalLimit = model.GlobalSocialSubNumLimit
  328. for key, _ := range this.subList {
  329. ackMsg.UidList = append(ackMsg.UidList, key)
  330. }
  331. case StateTypeFans: //获取自己的粉丝列表(其他玩家关注自己的列表)
  332. ackMsg.TotalCount = int32(len(this.fansList))
  333. ackMsg.TotalLimit = model.GlobalSocialFansNumLimit
  334. for key, _ := range this.fansList {
  335. ackMsg.UidList = append(ackMsg.UidList, key)
  336. }
  337. case StateTypeBlack: //获取黑名单列表
  338. ackMsg.TotalCount = int32(len(this.blackList))
  339. ackMsg.TotalLimit = model.GlobalSocialBlackNumLimit
  340. for key, _ := range this.blackList {
  341. ackMsg.UidList = append(ackMsg.UidList, key)
  342. }
  343. default:
  344. return serverproto.ErrorCode_ERROR_FAIL
  345. }
  346. //Task
  347. TaskMagCheck(this.role, serverproto.TaskType_Friend_SubFan_Num, 0)
  348. this.role.ReplayGate(ackMsg, true)
  349. util.InfoF("uid=%v FriendReq=%v", this.role.GetUUid(), ackMsg)
  350. return serverproto.ErrorCode_ERROR_OK
  351. }
  352. //添加关注(添加好友,这边添加好友是单向的)
  353. func (this *RoleSocial) FriendAdd(subUid uint64) serverproto.ErrorCode {
  354. //不能关注自己
  355. if this.role.GetUUid() == subUid || subUid <= 0 {
  356. return serverproto.ErrorCode_ERROR_FAIL
  357. }
  358. if this.isInSubList(subUid) {
  359. return serverproto.ErrorCode_ERROR_SOCIAL_HAS_IN_SUB_LIST
  360. }
  361. //预先判定好友数量
  362. ret := this.CanAddSubList(subUid)
  363. if ret != serverproto.ErrorCode_ERROR_OK {
  364. return ret
  365. }
  366. selfBriefInfo := &serverproto.CommonPlayerBriefInfo{}
  367. this.role.GetRoleBriefInfo(selfBriefInfo)
  368. tmpRole := RoleMag.GetRoleFromUUid(subUid)
  369. if tmpRole == nil {
  370. //角色在其他服务器(离线或者在线)
  371. ssReqMsg := &serverproto.SSFriendAddReq{
  372. FromUid: selfBriefInfo,
  373. AddUid: subUid,
  374. }
  375. this.role.SendSocial(ssReqMsg)
  376. return serverproto.ErrorCode_ERROR_OK
  377. }
  378. targetRole := tmpRole.(*Role)
  379. if targetRole.GetRoleSocial() == nil {
  380. return serverproto.ErrorCode_ERROR_FAIL
  381. }
  382. ret = targetRole.GetRoleSocial().CanAddFansList(this.role.GetUUid())
  383. if ret != serverproto.ErrorCode_ERROR_OK {
  384. return ret
  385. }
  386. targetBriefInfo := &serverproto.CommonPlayerBriefInfo{}
  387. targetRole.GetRoleBriefInfo(targetBriefInfo)
  388. //添加到自己的关注列表
  389. this.HandlerSubList(true, subUid, targetBriefInfo)
  390. //并添加到对方的粉丝列表
  391. targetRole.GetRoleSocial().HandlerFansList(true, this.role.GetUUid(), selfBriefInfo)
  392. return serverproto.ErrorCode_ERROR_OK
  393. }
  394. //取消关注
  395. func (this *RoleSocial) FriendDel(delUid uint64) serverproto.ErrorCode {
  396. //不能操作自己
  397. if this.role.GetUUid() == delUid || delUid <= 0 {
  398. return serverproto.ErrorCode_ERROR_FAIL
  399. }
  400. if !this.isInSubList(delUid) {
  401. return serverproto.ErrorCode_ERROR_SOCIAL_NOT_IN_SUB_LIST
  402. }
  403. this.HandlerSubList(false, delUid, nil)
  404. tmpTargetRole := RoleMag.GetRoleFromUUid(delUid)
  405. if tmpTargetRole == nil {
  406. // 发送给其他服务器,移除粉丝列表中的自己
  407. ssMsg := &serverproto.SSFriendDelReq{
  408. FromUid: this.role.GetUUid(),
  409. DelUid: delUid,
  410. }
  411. this.role.SendSocial(ssMsg)
  412. } else {
  413. targetRole := tmpTargetRole.(*Role)
  414. if targetRole.GetRoleSocial() == nil {
  415. return serverproto.ErrorCode_ERROR_FAIL
  416. }
  417. targetRole.GetRoleSocial().HandlerFansList(false, this.role.GetUUid(), nil)
  418. }
  419. return serverproto.ErrorCode_ERROR_OK
  420. }
  421. func (this *RoleSocial) FriendBlack(blackUid uint64) serverproto.ErrorCode {
  422. if this.role.GetUUid() == blackUid || blackUid <= 0 {
  423. return serverproto.ErrorCode_ERROR_FAIL
  424. }
  425. //移除操作
  426. if this.IsInBlackList(blackUid) {
  427. this.HandlerBlackList(false, blackUid, nil)
  428. } else {
  429. if len(this.blackList) >= int(model.GlobalSocialBlackNumLimit) {
  430. return serverproto.ErrorCode_ERROR_SOCIAL_BLACK_LIMIT
  431. }
  432. //添加操作
  433. tmpTargetRole := RoleMag.GetRoleFromUUid(blackUid)
  434. if tmpTargetRole == nil {
  435. //发送给其他服务器,获取详细信息
  436. ssMsg := &serverproto.SSGetRoleBriefInfoReq{
  437. Type: StateTypeBlack_Add,
  438. PlayerUidList: []uint64{blackUid},
  439. }
  440. this.role.SendDb(ssMsg)
  441. } else {
  442. targetRole := tmpTargetRole.(*Role)
  443. if targetRole.GetRoleSocial() == nil {
  444. return serverproto.ErrorCode_ERROR_FAIL
  445. }
  446. targetBriefInfo := &serverproto.CommonPlayerBriefInfo{}
  447. targetRole.GetRoleBriefInfo(targetBriefInfo)
  448. this.HandlerBlackList(true, blackUid, targetBriefInfo)
  449. }
  450. }
  451. return serverproto.ErrorCode_ERROR_OK
  452. }
  453. func (this *RoleSocial) FriendRecommend() {
  454. //先查找自己的粉丝列表
  455. //再查找
  456. ackMsg := &serverproto.SCFriendRecommendAck{
  457. Error: int32(serverproto.ErrorCode_ERROR_OK),
  458. }
  459. ssMsg := &serverproto.SSGetRoleBriefInfoReq{
  460. Type: StateTypeRecommend,
  461. }
  462. this.recommendIdx++
  463. recommendNum := RECOMMEND_NUM
  464. for key, _ := range this.fansList {
  465. if this.isInSubList(key) {
  466. continue
  467. }
  468. recommendNum--
  469. recommendRole := RoleMag.GetRoleFromUUid(key)
  470. if recommendRole != nil {
  471. bfInfo := &serverproto.CommonPlayerBriefInfo{
  472. OnlineState: true,
  473. }
  474. recommendRole.(*Role).GetRoleBriefInfo(bfInfo)
  475. ackMsg.BriefInfoList = append(ackMsg.BriefInfoList, bfInfo)
  476. } else {
  477. ssMsg.PlayerUidList = append(ssMsg.PlayerUidList, key)
  478. }
  479. if recommendNum <= 0 {
  480. break
  481. }
  482. }
  483. if recommendNum > 0 {
  484. ret, uidList := RoleMag.GetFIFOList(this.recommendIdx, int32(recommendNum), this.role, this.fansList)
  485. if !ret {
  486. this.recommendIdx = 1
  487. }
  488. if len(uidList) > 0 {
  489. ssMsg.PlayerUidList = append(ssMsg.PlayerUidList, uidList...)
  490. }
  491. }
  492. this.role.ReplayGate(ackMsg, true)
  493. if len(ssMsg.PlayerUidList) > 0 {
  494. this.role.SendDb(ssMsg)
  495. }
  496. }
  497. func (this *RoleSocial) FriendSearch(searchName string) serverproto.ErrorCode {
  498. if len(searchName) <= 0 {
  499. searchName = ""
  500. }
  501. nameLen := utf8.RuneCountInString(searchName)
  502. if nameLen > 15 {
  503. return serverproto.ErrorCode_ERROR_RENAME_NAME_LEN_ERROR
  504. }
  505. //不能查找自己
  506. if this.role.GetNickName() == searchName && searchName != "" {
  507. return serverproto.ErrorCode_ERROR_SOCIAL_SEARCH_SELF
  508. }
  509. //先查询数据库,获得玩家的Uid,再通过Uid做进一步处理
  510. ssMsg := &serverproto.SSGetUidByRoleNameReq{
  511. SelfUid: this.role.GetUUid(),
  512. SearchName: searchName,
  513. Zone: this.role.GetSelectZone(),
  514. //Zone: int32(service.GetServiceConfig().Node.Zone),
  515. }
  516. this.role.SendDb(ssMsg)
  517. return serverproto.ErrorCode_ERROR_OK
  518. }
  519. //互粉好友
  520. func (this *RoleSocial) GetFriendList() []uint64 {
  521. if len(this.subList) == 0 || len(this.fansList) == 0 {
  522. return nil
  523. }
  524. var UidList []uint64
  525. for subUid, _ := range this.subList {
  526. if _, ok := this.fansList[subUid]; ok {
  527. UidList = append(UidList, subUid)
  528. }
  529. }
  530. return UidList
  531. }