roomQueue.js 8.0 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213
  1. /**
  2. * 直播间男女端共用Manager
  3. */
  4. 'use strict';
  5. const F = require('../common/function');
  6. const C = require('../config');
  7. const _ = require('underscore');
  8. _.str = require('underscore.string');
  9. _.v = require('validator');
  10. const co = require('co');
  11. module.exports = function (app, commonManager) {
  12. let modelMap = app.model_mgr.model_map;
  13. let managerMap = commonManager.mgr_map;
  14. let that = this;
  15. var model_map = app.model_mgr.model_map;
  16. var mgr_map = commonManager.mgr_map;
  17. /**
  18. * 加入队列函数
  19. * @param operator_uid 操作人id
  20. * @param room_id 房间id
  21. * @param key 坑位key
  22. * @param uid 被操作id
  23. */
  24. this.addToRoomQueue = function* (operator_uid, room_id, key, uid, appCode) {
  25. // TODO 添加用户是否在房间判断
  26. let user_info = yield mgr_map.member.getJavaUserInfo(uid);
  27. if (F.isNull(user_info)) F.throwErrCode(100101);
  28. let room_info = yield mgr_map.room.getRoomInfo(room_id);
  29. if (F.isNull(room_info)) F.throwErrCode(100200);
  30. let operator_role;// 操作人角色
  31. if (room_info.uid == operator_uid) {
  32. operator_role = 9;// 房主
  33. } else {
  34. operator_role = yield mgr_map.redis.getRole(room_id, operator_uid);
  35. }
  36. let uid_role;// 被操作人角色
  37. if (room_info.uid == uid) {
  38. uid_role = 9;// 房主
  39. } else {
  40. uid_role = yield mgr_map.redis.getRole(room_id, uid);
  41. }
  42. if (uid_role == 9) {
  43. if (key != -1) {// 房主只能在第一个位置
  44. F.throwErrCode(100300);
  45. }
  46. if (operator_role != 9) {
  47. F.throwErrCode(100301);
  48. }
  49. } else if (uid_role == 1) {
  50. if (key == -1) {// 其他人不能在第一个位置
  51. F.throwErrCode(100300);
  52. }
  53. if (operator_role != 9 && operator_role != 1) {
  54. F.throwErrCode(100301);
  55. }
  56. } else {
  57. if (key == -1) {// 其他人不能在第一个位置
  58. F.throwErrCode(100300);
  59. }
  60. }
  61. if (operator_role != 9 && operator_role != 1) {
  62. if (operator_uid != uid) { // 普通成员只能操作自己
  63. F.throwErrCode(100301);
  64. }
  65. }
  66. let lock = {};
  67. try {
  68. lock = yield mgr_map.redis.getLock(C.lock_key.room_queue + room_id, 20);
  69. if (!lock.suc) F.throwErr("get lock for addToRoomQueue timeout!");
  70. let queue_mem_list = yield mgr_map.redis.getAllQueueMember(room_id);
  71. if (!F.isNull(queue_mem_list[parseInt(key) + 1]) && queue_mem_list[parseInt(key) + 1] != uid) F.throwErrCode(100303);
  72. for (let i = 0; i < queue_mem_list.length; i++) {
  73. let mem_id = queue_mem_list[i];
  74. if (mem_id == uid) yield mgr_map.redis.delQueueMember(room_id, i - 1); // 把uid 原来所在位置删除
  75. }
  76. yield mgr_map.redis.addMemberToQueue(room_id, key, uid);
  77. co(mgr_map.extrn.addZegoStream(room_id, uid, appCode));
  78. let room_socket = yield mgr_map.redis.getRoomSocketList(room_id);
  79. yield mgr_map.notice.pushQueueMemberUpdateNotice(room_socket, room_id, 1, key, uid);
  80. co(that.pushRoomMicMsg(room_info.uid, uid, 1));
  81. }
  82. catch (e) {
  83. F.addErrLogs(['addToRoomQueue err:', e.stack]);
  84. throw e;
  85. }
  86. finally {
  87. yield mgr_map.redis.releaseLock(lock);
  88. }
  89. }
  90. /**
  91. * 把key上的人从roomid下麦
  92. * @param operator_uid 操作人id
  93. * @param room_id 房间id
  94. * @param key 坑位key
  95. */
  96. this.delFromRoomQueue = function* (operator_uid, room_id, key) {
  97. // TODO 添加用户是否在房间判断
  98. let queue_mem_list = yield mgr_map.redis.getAllQueueMember(room_id);
  99. let i = parseInt(key) + 1;
  100. let uid = queue_mem_list[i];
  101. if (F.isNull(uid)) F.throwErrCode(100101);
  102. let room_info = yield mgr_map.room.getRoomInfo(room_id);
  103. if (F.isNull(room_info)) F.throwErrCode(100200);
  104. let operator_role;// 操作人角色
  105. if (room_info.uid == operator_uid) {
  106. operator_role = 9;// 房主
  107. } else {
  108. operator_role = yield mgr_map.redis.getRole(room_id, operator_uid);
  109. }
  110. let uid_role;// 被操作人角色
  111. if (room_info.uid == uid) {
  112. uid_role = 9;// 房主
  113. } else {
  114. uid_role = yield mgr_map.redis.getRole(room_id, uid);
  115. }
  116. if (uid_role == 9) {
  117. if (operator_role != 9) {
  118. F.throwErrCode(100301);
  119. }
  120. } else if (uid_role == 1) {
  121. if (operator_role != 9 && operator_role != 1) {
  122. F.throwErrCode(100301);
  123. }
  124. }
  125. if (operator_role != 9 && operator_role != 1) {
  126. if (operator_uid != uid) { // 普通成员只能操作自己
  127. F.throwErrCode(100301);
  128. }
  129. }
  130. let lock = 0;
  131. try {
  132. lock = yield mgr_map.redis.getLock(C.lock_key.room_queue + room_id, 20);
  133. if (!lock.suc) F.throwErr("get lock for delFromRoomQueue timeout!");
  134. yield mgr_map.redis.delQueueMember(room_id, key); // 注意 queue_list 0 对应-1麦位 1对应0麦位。。。
  135. // TODO:请求即构后台流删除接口
  136. co(mgr_map.extrn.delZegoStream(room_id, uid));
  137. let room_socket = yield mgr_map.redis.getRoomSocketList(room_id);
  138. //4 推送下麦通知
  139. // 异步执行不阻塞锁
  140. co(mgr_map.notice.pushQueueMemberUpdateNotice(room_socket, room_id, 2, key, uid));
  141. co(mgr_map.roomQueue.pushRoomMicMsg(room_info.uid, uid, 2));
  142. } catch (e) {
  143. F.addErrLogs(['delFromRoomQueue err:', e.stack]);
  144. throw e;
  145. } finally {
  146. yield mgr_map.redis.releaseLock(lock);
  147. }
  148. }
  149. /**
  150. * 把uid从roomid下麦
  151. * @param operator_uid 操作人id
  152. * @param room_id 房间id
  153. * @param uid 下麦uid
  154. */
  155. this.delFromRoomQueueByUid = function* (operator_uid, room_id, uid) {
  156. let queue_list = yield mgr_map.redis.getAllQueueMember(room_id); // 注意 queue_list 0 对应-1麦位 1对应0麦位。。。
  157. for (let i = 0; i < queue_list.length; i++) {
  158. let value = queue_list[i];
  159. if (value == uid) {// 如果在麦上就调用下麦接口
  160. yield mgr_map.roomQueue.delFromRoomQueue(operator_uid, room_id, i - 1);
  161. }
  162. }
  163. }
  164. /**
  165. * 获取房间麦序(麦上成员信息一起返回)
  166. * @param room_id
  167. */
  168. this.getRoomQueueList = function* (room_id) {
  169. // TODO 添加用户是否在房间判断
  170. let room_info = yield mgr_map.room.getRoomInfo(room_id);
  171. if (F.isNull(room_info)) F.throwErrCode(100200);
  172. let queue_list = [];
  173. let mic_list = yield mgr_map.javaRedis.getRoomMicList(room_id);
  174. let member_list = yield mgr_map.redis.getAllQueueMember(room_id);
  175. if (mic_list.length != member_list.length) F.throwErr("room member and mic info not match!");
  176. for (let i = 0; i < mic_list.length; i++) {
  177. let key = i - 1;
  178. let mic_info = mic_list[i];
  179. let memberid = member_list[i];
  180. let member = yield mgr_map.member.getJavaUserInfo(memberid);
  181. queue_list.push({
  182. 'key': key,
  183. 'value': {
  184. 'mic_info': mic_info,
  185. 'member': member
  186. }
  187. });
  188. }
  189. return queue_list;
  190. };
  191. this.pushRoomMicMsg = function* (room_uid, uid, type) {
  192. F.addDebugLogs(["receiveRoomMicMsg", room_uid, uid, type]);
  193. let res = yield mgr_map.curl.httpGet(C.java_host, C.java_port, '/inner/im/v1/receiveRoomMicMsg', {
  194. 'roomUid': room_uid,
  195. 'uid': uid,
  196. 'type': type
  197. }, null, 'utf8', 'http');
  198. F.addDebugLogs(["receiveRoomMicMsg", "/inner/im/v1/receiveRoomMicMsg", res]);
  199. };
  200. };