user_friend.go 11 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482
  1. package friend
  2. import (
  3. "bet24.com/log"
  4. "bet24.com/servers/common"
  5. cash "bet24.com/servers/micros/money/proto"
  6. notification "bet24.com/servers/micros/notification/proto"
  7. task "bet24.com/servers/micros/task/proto"
  8. userlabel "bet24.com/servers/micros/userlabel/proto"
  9. userservices "bet24.com/servers/micros/userservices/proto"
  10. "encoding/json"
  11. "sync"
  12. )
  13. type user_friend struct {
  14. lock *sync.RWMutex
  15. UserID int
  16. GiveTimes int // 今天剩余赠送礼物次数
  17. FriendList []*FriendItem // 好友列表
  18. ApplyList []*FriendBase // 申请列表(自己申请的)
  19. VerifyList []*FriendBase // 审核列表(谁来申请的)
  20. RoomInviteHistory []*RoomInviteInfo // 私人场房间邀请
  21. potentialList []PotentialFriend // 潜在好友列表
  22. blackList []BlackItem // 黑名单
  23. }
  24. func newUserFriend(userId int) *user_friend {
  25. u := new(user_friend)
  26. u.lock = &sync.RWMutex{}
  27. u.UserID = userId
  28. // 获取好友列表
  29. u.GiveTimes, u.FriendList = getList(u.UserID)
  30. go func(u *user_friend) {
  31. for _, v := range u.FriendList {
  32. if mgr.isOnline(v.FriendID) {
  33. v.GameStatus = GameStatus_Online
  34. }
  35. }
  36. //获取审核列表(谁来申请的)
  37. u.VerifyList = getVerifyList(u.UserID)
  38. for _, v := range u.VerifyList {
  39. if mgr.isOnline(v.FriendID) {
  40. v.GameStatus = GameStatus_Online
  41. }
  42. }
  43. //获取申请列表(自己申请的)
  44. u.ApplyList = getApplyList(u.UserID)
  45. for _, v := range u.ApplyList {
  46. if mgr.isOnline(v.FriendID) {
  47. v.GameStatus = GameStatus_Online
  48. }
  49. }
  50. // 获取房间邀请
  51. u.roomInviteLoadFromRedis()
  52. u.potentialList = getPotentialFriendList(u.UserID)
  53. // 黑名单
  54. u.blackList = trans_GetBlackList(u.UserID)
  55. }(u)
  56. return u
  57. }
  58. func (u *user_friend) refreshGift() {
  59. dayIndex := common.GetDayIndex(common.GetTimeStamp())
  60. giveTimes := 0
  61. for j := 0; j < len(u.FriendList); j++ {
  62. //领取
  63. if common.GetDayIndex(u.FriendList[j].GiftTime) < dayIndex &&
  64. u.FriendList[j].IsGift == GIFT_STATUS_RECEIVED {
  65. u.FriendList[j].IsGift = GIFT_STATUS_NOT
  66. }
  67. //赠送
  68. if common.GetDayIndex(u.FriendList[j].GiveTime) >= dayIndex {
  69. if u.FriendList[j].IsGive == GIVE_STATUS_HAVE {
  70. u.FriendList[j].IsGive = GIVE_STATUS_NOT
  71. }
  72. giveTimes++
  73. }
  74. }
  75. //计算剩余赠送次数
  76. u.GiveTimes = MAX_GIVETIMES - giveTimes
  77. }
  78. func (u *user_friend) friendApply(toUserId int) int {
  79. //已经是我的好友?
  80. for _, v := range u.FriendList {
  81. if v.FriendID == toUserId {
  82. return ALREADY_A_FRIEND
  83. }
  84. }
  85. //已经申请过
  86. for _, v := range u.ApplyList {
  87. if v.FriendID == toUserId {
  88. return ADD_TO_EXAMINE
  89. }
  90. }
  91. //待审核
  92. for _, v := range u.VerifyList {
  93. if v.FriendID == toUserId {
  94. return ADD_TO_EXAMINE
  95. }
  96. }
  97. // 在黑名单中,返回成功,无限期等待
  98. if exist := trans_IsBlack(u.UserID, toUserId); exist {
  99. return ADD_SUCCESS
  100. }
  101. // 检查自己的好友栏是否上限
  102. myFriendCount := mgr.getMaxFriendCount(u.UserID)
  103. if len(u.FriendList) >= myFriendCount.Base+myFriendCount.Extra {
  104. return FRIEND_LIMIT
  105. }
  106. //还不是我的好友
  107. apply(u.UserID, toUserId)
  108. // 刷新自己的申请列表
  109. mgr.refreshFriends(u.UserID, false, true, false, u.UserID, "apply")
  110. // TODO: 通知数据库要申请好友
  111. go mgr.refreshFriends(toUserId, false, false, true, u.UserID, "apply")
  112. // 触发任务
  113. task.DoTaskAction(u.UserID, task.TaskAction_addfriend, 1, task.TaskScope{})
  114. return ADD_SUCCESS
  115. }
  116. func (u *user_friend) delFriend(toUserId int) ([]*FriendItem, bool) {
  117. ret := false
  118. for i := 0; i < len(u.FriendList); i++ {
  119. if u.FriendList[i].FriendID == toUserId {
  120. //从好友列表中删除
  121. u.FriendList = append(u.FriendList[:i], u.FriendList[i+1:]...)
  122. //TODO: go 通知数据库删除好友
  123. go func(toUserId int) {
  124. //数据库删除
  125. del(u.UserID, toUserId)
  126. mgr.refreshFriends(toUserId, true, false, false, u.UserID, "delete")
  127. }(toUserId)
  128. i--
  129. // return u.FriendList
  130. ret = true
  131. }
  132. }
  133. //还不是我的好友, 直接返回
  134. return u.FriendList, ret
  135. }
  136. func (u *user_friend) friendHandleApply(toUserId, apply int) []*FriendItem {
  137. // 检查自己的好友栏是否上限
  138. myFriendCount := mgr.getMaxFriendCount(u.UserID)
  139. if len(u.FriendList) >= myFriendCount.Base+myFriendCount.Extra {
  140. // 不需要拒绝也不需要提示,请求继续保留在审核列表中
  141. return nil
  142. }
  143. //删除申请列表中的数据
  144. for i := 0; i < len(u.VerifyList); i++ {
  145. if u.VerifyList[i].FriendID == toUserId {
  146. u.VerifyList = append(u.VerifyList[:i], u.VerifyList[i+1:]...)
  147. break
  148. }
  149. }
  150. //TODO:通知数据库更新好友申请数据等
  151. deal(u.UserID, toUserId, apply)
  152. //已经在我的好友列表
  153. for _, v := range u.FriendList {
  154. if v.FriendID == toUserId {
  155. return u.FriendList
  156. }
  157. }
  158. //不同意申请,不需要更新好友列表
  159. // 1=同意 2=拒绝
  160. if apply != 1 {
  161. //通知对方
  162. go mgr.refreshFriends(toUserId, false, true, false, u.UserID, "reject")
  163. return u.FriendList
  164. }
  165. //同意申请
  166. //刷新自己的好友列表
  167. mgr.refreshFriends(u.UserID, true, false, true, u.UserID, "agree")
  168. //通知对方
  169. go mgr.refreshFriends(toUserId, true, true, false, u.UserID, "agree")
  170. // 8=交际类(好友模块)(用户标签)
  171. go userlabel.TriggerEvent(u.UserID, userlabel.Type_Friend, userlabel.Scope{Num: 1})
  172. go userlabel.TriggerEvent(toUserId, userlabel.Type_Friend, userlabel.Scope{Num: 1})
  173. return u.FriendList
  174. }
  175. func (u *user_friend) friendGiveGift(toUserId int) int {
  176. // 没有赠送次数了
  177. if u.GiveTimes <= 0 {
  178. return 12
  179. }
  180. dayIndex := common.GetDayIndex(common.GetTimeStamp())
  181. for _, v := range u.FriendList {
  182. if v.FriendID != toUserId {
  183. continue
  184. }
  185. //今天已经赠送过了
  186. if common.GetDayIndex(v.GiveTime) >= dayIndex {
  187. return 1
  188. }
  189. //TODO: 通知数据库向对方赠送礼物,记录赠送时间
  190. go giveGift(u.UserID, toUserId)
  191. v.IsGive = GIVE_STATUS_HAVE
  192. v.GiveTime = common.GetTimeStamp()
  193. u.GiveTimes--
  194. // 通知对方
  195. mgr.notifyGift(u.UserID, toUserId)
  196. return 1
  197. }
  198. return 0
  199. }
  200. func (u *user_friend) friendGetGift(toUserId int, ipAddress string) int {
  201. dayIndex := common.GetDayIndex(common.GetTimeStamp())
  202. for _, v := range u.FriendList {
  203. if v.FriendID != toUserId {
  204. continue
  205. }
  206. //是否有可领取
  207. if v.IsGift != GIFT_STATUS_HAVE {
  208. return 0
  209. }
  210. //今天是否已经领取过
  211. if common.GetDayIndex(v.GiftTime) >= dayIndex {
  212. return 0
  213. }
  214. //更新礼物状态
  215. v.IsGift = GIFT_STATUS_RECEIVED
  216. //TODO: 数据库操作获取礼物,目前只有金币
  217. go func() {
  218. //TODO: 数据库操作
  219. getGift(u.UserID, toUserId)
  220. //TODO:送礼物
  221. cash.GiveMoney(u.UserID, GIVE_GOLD, common.LOGTYPE_FRIEND, "好友模块", "赠送金币", ipAddress)
  222. }()
  223. return 1
  224. }
  225. return 0
  226. }
  227. func (u *user_friend) setUserStatus(toUserId int, status string) {
  228. for _, v := range u.FriendList {
  229. if v.FriendID == toUserId {
  230. v.GameStatus = status
  231. buf, _ := json.Marshal(notification.NotificationFriend{
  232. NotifyId: Friend_Notify_Status,
  233. UserId: toUserId,
  234. Data: status,
  235. })
  236. //发送通知
  237. go notification.AddNotification(u.UserID, notification.Notification_Friend, string(buf))
  238. return
  239. }
  240. }
  241. }
  242. // 返回 0=不是好友 1=好友 2=已申请(自己申请的,待对方审核) 3=待审核(对方申请的,待自己审核) 4=黑名单
  243. func (u *user_friend) ifFriend(friendId int) int {
  244. for _, v := range u.FriendList {
  245. if v.FriendID == friendId {
  246. return FriendShip_Friend
  247. }
  248. }
  249. for _, v := range u.ApplyList {
  250. if v.FriendID == friendId {
  251. return FriendShip_AlreadyApplied
  252. }
  253. }
  254. for _, v := range u.VerifyList {
  255. if v.FriendID == friendId {
  256. return FriendShip_ToBeReviewed
  257. }
  258. }
  259. for _, v := range u.blackList {
  260. if v.UserId == friendId {
  261. return FriendShip_Black
  262. }
  263. }
  264. return FriendShip_Normal
  265. }
  266. const max_potential_count = 50
  267. func (u *user_friend) getPotentialFriendList() string {
  268. // 清理并补充数据
  269. for i := 0; i < len(u.potentialList); {
  270. pf := &u.potentialList[i]
  271. if u.ifFriend(pf.UserId) != 0 {
  272. u.potentialList = append(u.potentialList[:i], u.potentialList[i+1:]...)
  273. go deletePotentialFriend(u.UserID, pf.UserId)
  274. continue
  275. }
  276. i++
  277. // 补充数据
  278. if pf.NickName == "" {
  279. usr := userservices.GetUserInfo(pf.UserId)
  280. if usr != nil {
  281. pf.NickName = usr.NickName
  282. pf.FaceID = usr.FaceId
  283. pf.FriendID = pf.UserId
  284. pf.FaceUrl = usr.FaceUrl
  285. pf.Decorations = usr.Decorations
  286. }
  287. }
  288. }
  289. d, _ := json.Marshal(u.potentialList)
  290. return string(d)
  291. }
  292. func (u *user_friend) addPotentialFriend(userId int, memo string) {
  293. if u.ifFriend(userId) != 0 {
  294. log.Release("user_friend.addPotentialFriend already friend")
  295. return
  296. }
  297. // 列表已存在
  298. for _, v := range u.potentialList {
  299. if v.UserId == userId {
  300. return
  301. }
  302. }
  303. pf := PotentialFriend{
  304. UserId: userId,
  305. MetTime: common.GetTimeStamp(),
  306. Memo: memo,
  307. }
  308. u.potentialList = append([]PotentialFriend{pf}, u.potentialList...)
  309. go addPotentialFriend(u.UserID, userId, pf.MetTime, memo)
  310. if len(u.potentialList) <= max_potential_count {
  311. return
  312. }
  313. for i := max_potential_count; i < len(u.potentialList); i++ {
  314. go deletePotentialFriend(u.UserID, u.potentialList[i].UserId)
  315. }
  316. u.potentialList = u.potentialList[:max_potential_count]
  317. }
  318. func (u *user_friend) removePotentialFriend(userId int) {
  319. for i := 0; i < len(u.potentialList); i++ {
  320. if u.potentialList[i].UserId == userId {
  321. u.potentialList = append(u.potentialList[:i], u.potentialList[i+1:]...)
  322. go deletePotentialFriend(u.UserID, userId)
  323. return
  324. }
  325. }
  326. }
  327. // 获取黑名单列表
  328. func (u *user_friend) getBlackList() []BlackItem {
  329. return u.blackList
  330. }
  331. // 添加黑名单
  332. func (u *user_friend) addBlack(userId int) (retCode int, message string) {
  333. if u.UserID == userId {
  334. retCode, message = 14, "Can't add myself as blacklist"
  335. return
  336. }
  337. // 已经在黑名单
  338. for _, v := range u.blackList {
  339. if v.UserId == userId {
  340. retCode, message = 11, "already blacklisted"
  341. return
  342. }
  343. }
  344. // 用户信息
  345. info := userservices.GetUserInfo(userId)
  346. if info == nil {
  347. retCode, message = 12, "Invalid user information"
  348. return
  349. }
  350. // 添加黑名单
  351. u.blackList = append(u.blackList, BlackItem{
  352. UserId: userId,
  353. Crdate: common.GetNowTimeStr(),
  354. })
  355. // 删除好友
  356. u.delFriend(userId)
  357. // 添加黑名单
  358. go trans_AddBlack(u.UserID, userId, common.GetNowTimeStr())
  359. retCode, message = 1, "success"
  360. return
  361. }
  362. // 删除黑名单
  363. func (u *user_friend) delBlack(userId int) (retCode int, message string) {
  364. for i := 0; i < len(u.blackList); i++ {
  365. if u.blackList[i].UserId != userId {
  366. continue
  367. }
  368. // 删除
  369. u.blackList = append(u.blackList[:i], u.blackList[i+1:]...)
  370. // 数据库删除
  371. go trans_DelBlack(u.UserID, userId)
  372. retCode, message = 1, "success"
  373. return
  374. }
  375. retCode, message = 11, "Failed to delete blacklist"
  376. return
  377. }
  378. func (u *user_friend) isBlackListUser(userId int) bool {
  379. for _, v := range u.blackList {
  380. if v.UserId == userId {
  381. return true
  382. }
  383. }
  384. return false
  385. }
  386. func (u *user_friend) isBlackListUserIn(userIds []int) bool {
  387. for _, v1 := range userIds {
  388. for _, v := range u.blackList {
  389. if v.UserId == v1 {
  390. return true
  391. }
  392. }
  393. }
  394. return false
  395. }