123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353 |
- import { ROLES, CODEMEG, EVENT, FROMTYPE } from "../../enum/index.js";
- import { getCurrentUser, updateUser, removeRoomAllUsers, getAllRoomUsers, updateRoomUser, removeRoomUser, isUserInRoom } from "../../service/userService.js";
- // import { watchRoomService } from "../../service/watchRoomService.js";
- import { setRoomConfig, getRoomConfig, updateRoomConfigByKey, isRoomMaster } from "../../service/roomConfigService.js";
- import { RoomAssistant } from "./assistant.js";
- import { Notify } from "./notify.js";
- import { BasicController } from "../basicController.js";
- export class RoomController extends BasicController {
- constructor(...args) {
- super(...args);
- this.roomAssistant = new RoomAssistant(this.socket, this.redisCli, this);
- this.notify = new Notify(this.socket, this.redisCli, this);
- this.roomId = null;
- this.sessionId = null;
- this.userId = null;
- this.roomConfigId = null;
- this.debugger = true;
- this.user = {
- sig: null,
- roomId: null,
- userId: null,
- sceneNum: null,
- isClient: null,
- avatar: "",
- role: null,
- userLimitNum: null,
- sceneNumber: null,
- order: 2,
- from: null,
- assistantId: null,
- onlineStatus: 0,
- voiceStatus: 0,
- isAssistant: 0,
- enableTalk: null,
- oid: null, // openid
- };
- }
- // 以小程序user信息作为主要信息
- async currentUser() {
- const data = await getCurrentUser(this.userId, FROMTYPE.MiniAPP);
- const user = data ? JSON.parse(data) : this.user;
- return user;
- }
- async run() {
- this.logger.info("socket conetcted has start!");
- try {
- await this.init();
- this.initBaseAction();
- this.roomMasterAutoRejoin();
- this.roomAssistant.watchRoomExpired();
- // setInterval(async () => {
- // if ([FROMTYPE.Bridge].includes(Number(this.user.from))) {
- // const AllRoomUsers = await getAllRoomUsers(this.roomId);
- // this.socket.broadcast.to(this.roomId).emit(EVENT.roomStatus, {
- // roomsPerson: AllRoomUsers,
- // });
- // console.log("定时测试", this.roomId);
- // }
- // }, 10000);
- } catch (error) {
- this.logger.error("roomController::run::error", error);
- }
- }
- async init() {
- let user = this.socket.handshake.query;
- this.logger.info("init-user-query:", this.socket.handshake.query);
- if (user) {
- this.user = Object.assign({}, user);
- this.user.sig = this.getSig(this.user.userId);
- const oneSceneNum = this.user.sceneNumber || this.user.sceneNum;
- const { userId, roomId } = this.user;
- await this.initParams(userId, roomId, oneSceneNum);
- //role的顺序
- let order = 2;
- if (this.user.role === "leader") {
- order = 0;
- }
- if (this.user.role === "customer" && Number(this.user.isAssistant) === 1) {
- order = 1;
- }
- const userObj = { ...this.user, onlineStatus: 1, isConnected: true, order };
- const assistantId = await this.roomAssistant.getRoomAssistant(this.roomId);
- if (!this.isHoster(this.user.role) && assistantId) {
- console.log("assistantId", assistantId);
- console.log("this.userId", this.user.userId);
- this.logger.info("房间已存助手", assistantId, this.roomId);
- userObj.isAssistant = Number(this.user.userId) === Number(assistantId) ? 1 : 0;
- userObj.order = Number(this.user.userId) === Number(assistantId) ? 1 : 2;
- // if (assistantId) {
- // this.logger.info("已存在默认助手变更:" + "room助手ID: " + assistantId + " userId: " + this.user.userId);
- // }
- }
- // if (assistantId && Number(this.userId) !== Number(assistantId) && !this.isHoster(this.user.role)) {
- // userObj.role = "customer";
- // }
- this.logger.info("update-user-info:", userObj);
- updateUser(this.userId, userObj);
- // 将更新同步一份到process
- this.user = userObj;
- // this.sysUsers.push(this.user);
- // 只有来源于小程序用户信息才记录到redis
- if (this.isHoster(this.user.role)) {
- if ([FROMTYPE.MiniAPP].includes(Number(this.user.from))) {
- const roomConfig = getRoomConfig(this.roomId);
- const checkoutMaster = await isRoomMaster(this.roomId, this.userId);
- const isNoExistMaster = "masterId" in roomConfig;
- // console.log("checkoutMaster-isNoExistMaster", checkoutMaster, !isNoExistMaster);
- if (checkoutMaster || !isNoExistMaster) {
- console.log("房主进入记录信息::: checkoutMaster: %s, isNoExistMaster: %s ,roomId %s", checkoutMaster, !isNoExistMaster, this.roomId);
- const roomConfig = {
- masterId: this.userId,
- userLimitNum: this.user.userLimitNum,
- enableTalk: this.user.enableTalk === "true" ? true : false,
- };
- console.log("roomConfig", roomConfig);
- // console.log("roomConfig", roomConfig);
- await setRoomConfig(this.roomId, roomConfig);
- }
- }
- }
- // 加入
- console.log("roomId", this.roomId);
- this.socket.join(this.roomId);
- const isInRoom = await isUserInRoom(this.roomId, this.userId);
- console.log("测试-强制上线", isInRoom, this.roomId, this.userId);
- if (isInRoom) {
- if (Number(isInRoom.onlineStatus) === 0) {
- console.log("在房间人员掉线人员,强制上线!", isInRoom);
- this.roomAssistant.setOnlineStatus(this.roomId, this.userId, isInRoom);
- }
- }
- } else {
- this.logger.info("user-query-不存在 :", this.socket.handshake.query);
- this.socket.disconnect();
- }
- }
- async initParams(userId, roomId, oneSceneNum) {
- this.userId = `user:${userId}`;
- this.syncId = `sync:${oneSceneNum}:${userId}`;
- this.sessionId = `session:${oneSceneNum}:${userId}`;
- const uRoomId = await this.roomAssistant.prepearRoom(this.sessionId, roomId);
- // this.roomId = `room:${uRoomId}_${oneSceneNum}`;
- this.roomId = `room:${oneSceneNum}:${uRoomId}`;
- this.user.roomId = uRoomId;
- this.roomConfigId = `config:${this.roomId}`;
- return Promise.resolve(true);
- }
- initBaseAction() {
- // 通知 baseView 减少大量通知
- this.socket.on(EVENT.webSyncAction, (data) => {
- // socket.broadcast.to(roomUniqueId).emit(EVENT.webSyncAction, data);
- try {
- if ([FROMTYPE.base].includes(Number(this.user.from))) {
- this.socket.broadcast.to(this.roomId).emit(EVENT.webSyncAction, data);
- }
- } catch (error) {
- this.logger.error("roomController::EVENT.webSyncAction", error);
- }
- });
- // 转发action
- this.socket.on(EVENT.action, (data) => {
- try {
- this.logger.debug("room-action", this.roomId, this.socket.rooms.has(this.roomId), JSON.stringify(data));
- if (this.socket.rooms.has(this.roomId)) {
- this.socket.broadcast.to(this.roomId).emit(EVENT.action, data);
- } else {
- this.logger.error("action 事件不在房间内", this.user);
- }
- } catch (error) {
- this.logger.error("roomController::EVENT.action", error);
- }
- });
- this.socket.on(EVENT.startCall, async () => {
- const user = await this.currentUser();
- this.roomAssistant.startCall(this.roomId, this.userId, user);
- // console.log("startCall-from", this.user.from);
- if (this.isHoster(this.user.role)) {
- // 以startCall做为真正的进入房间
- await updateRoomConfigByKey(this.roomId, "isStart", true);
- }
- });
- this.socket.on(EVENT.stopCall, () => {
- setTimeout(() => {
- console.log("EVENT.stopCall-delay");
- this.roomAssistant.stopCall(this.roomId, this.userId, this.user);
- if (this.isHoster(this.user.role)) {
- // 以stopCall断开做为真正的退出房间
- this.roomAssistant.destoryRoom(this.sessionId, this.roomConfigId);
- }
- }, 1000);
- });
- this.socket.on(EVENT.changeRoomEnableTalk, async (data) => {
- // this._roomsConfig[roomId].enableTalk = data;
- try {
- const roomConfig = await getRoomConfig(this.roomId);
- roomConfig.enableTalk = data;
- await setRoomConfig(this.roomId, roomConfig);
- this.logger.info("changeRoomEnableTalk", JSON.stringify(data));
- this.socket.broadcast.to(this.roomId).emit(EVENT.changeRoomEnableTalk, roomConfig);
- } catch (error) {
- this.logger.error("event:changeRoomEnableTalk", error);
- }
- });
- this.socket.on(EVENT.changeOnlineStatus, async (data) => {
- try {
- const user = await this.currentUser();
- user.onlineStatus = Number(data.status);
- await updateRoomUser(this.roomId, this.userId, user);
- this.user = user;
- //更新一份
- let actionName = Number(user.onlineStatus) === 1 ? "inRoom" : "leaveRoom";
- this.logger.info("changeOnlineStatus", JSON.stringify(user));
- const AllRoomUsers = await getAllRoomUsers(this.roomId);
- this.socket.broadcast.to(this.roomId).emit(EVENT.roomPersonChange, {
- roomsPerson: AllRoomUsers,
- actionName,
- user: user,
- });
- } catch (error) {
- this.logger.error("event:changeOnlineStatus", error);
- }
- });
- /**
- * 踢人管理
- */
- this.socket.on(EVENT.kickUser, async ({ data, from }) => {
- // 要前端断线才可以踢人
- try {
- const userId = `user:${data.userId}`;
- const roomId = `room:${data.sceneNumber}:${data.roomId}`;
- const currentUser = await getCurrentUser(userId, FROMTYPE.MiniAPP);
- const user = JSON.parse(currentUser);
- // 被踢人不能是hoster
- console.log("user", JSON.stringify(user));
- if (user && !this.isHoster(user.role)) {
- console.log("currentUser.role", user.role);
- // 如果踢人后 如何通知?
- this.socket.broadcast.to(roomId).emit(EVENT.beKicked, data);
- // 被踢人是助手
- const assistantId = await this.roomAssistant.getRoomAssistant(this.roomId);
- if (assistantId == data.userId) {
- const roomConfig = await getRoomConfig(roomId);
- if (roomConfig.assistantId) {
- delete roomConfig.assistantId;
- }
- await setRoomConfig(roomId, roomConfig);
- }
- setTimeout(async () => {
- const isKick = await this.roomAssistant.kickPersion(roomId, userId);
- if (isKick) {
- const AllRoomUsers = await getAllRoomUsers(roomId);
- console.log("kickUser-AllRoomUsers", AllRoomUsers.length);
- this.logger.info("kickUser", currentUser, userId, roomId);
- // 通知管理
- this.socket.emit(EVENT.someOneLeaveRoom, {
- user: user,
- roomsPerson: AllRoomUsers,
- });
- // 通知房间人员变动
- this.socket.broadcast.to(roomId).emit(EVENT.someOneLeaveRoom, {
- user: user,
- roomsPerson: AllRoomUsers,
- });
- }
- }, 2000);
- } else {
- const nickname = user.nickname || "";
- this.logger.warn(nickname + "是房主,不能被踢!!");
- }
- } catch (error) {
- console.error("error", error);
- }
- });
- /**
- * 设置助手
- */
- this.socket.on("setAssistant", async ({ data, from }) => {
- const userId = `user:${data.userId}`;
- const roomId = `room:${data.sceneNumber}:${data.roomId}`;
- console.log("设置助手", userId, roomId);
- this.roomAssistant.setAssistant(roomId, userId, data.cancel);
- });
- /**
- * 设置MIC权
- */
- this.socket.on("setUserhasMic", async ({ data, from, isAllowMic }) => {
- const userId = `user:${data.userId}`;
- const roomId = `room:${data.sceneNumber}:${data.roomId}`;
- console.log("设置MIC权", userId, roomId, data.isAllowMic);
- this.roomAssistant.setMicRight(roomId, userId, data.isAllowMic);
- });
- if (this.debugger) {
- this.socket.onAny((event, data) => {
- // if (event !== "webSyncAction") {
- // console.log(`onAny:get ${event}, data:${JSON.stringify(data)}`);
- this.logger.info(`onAny:get ${event}, data:${JSON.stringify(data)}`);
- // }
- });
- }
- }
- async roomMasterAutoRejoin() {
- try {
- const sessionExist = await this.redisCli.exists(this.sessionId);
- const roomConfig = await getRoomConfig(this.roomId);
- if (sessionExist > 0 && roomConfig.isStart && roomConfig.isStart === "true") {
- const AllRoomUsers = await getAllRoomUsers(this.roomId);
- // 房主
- if (this.isHoster(this.user.role)) {
- console.log("自动接连", this.roomId, this.user.from);
- this.socket.join(this.roomId);
- this.socket.emit("autoReJoin", {
- user: this.user,
- roomsPerson: AllRoomUsers,
- roomId: this.user.roomId,
- });
- //TODO someOneInRoom是用来触发语音与更新房间状态
- }
- //TODO someOneInRoom是用来触发语音与更新房间状态
- // setTimeout(() => {
- // this.socket.emit("someOneInRoom", {
- // user: this.user,
- // roomsPerson: AllRoomUsers,
- // });
- // });
- }
- } catch (error) {
- this.logger.error("room::roomMasterAutoRejoin", error);
- }
- }
- }
|