func (Lobby) ServerVerify(server *wsevent.Server, so *wsevent.Client, data []byte) []byte { reqerr := chelpers.FilterRequest(so, authority.AuthAction(0), true) if reqerr != nil { return reqerr.Encode() } var args struct { Server *string `json:"server"` Rconpwd *string `json:"rconpwd"` } if err := chelpers.GetParams(data, &args); err != nil { return helpers.NewTPErrorFromError(err).Encode() } var count int db.DB.Table("server_records").Where("host = ?", *args.Server).Count(&count) if count != 0 { return helpers.NewTPError("A lobby is already using this server.", -1).Encode() } info := models.ServerRecord{ Host: *args.Server, RconPassword: *args.Rconpwd, } err := models.VerifyInfo(info) if err != nil { return helpers.NewTPErrorFromError(err).Encode() } return chelpers.EmptySuccessJS }
func (Player) PlayerSettingsGet(server *wsevent.Server, so *wsevent.Client, data []byte) []byte { reqerr := chelpers.FilterRequest(so, 0, true) if reqerr != nil { return reqerr.Encode() } var args struct { Key string `json:"key"` } err := chelpers.GetParams(data, &args) if err != nil { return helpers.NewTPErrorFromError(err).Encode() } player, _ := models.GetPlayerBySteamId(chelpers.GetSteamId(so.Id())) var settings []models.PlayerSetting var setting models.PlayerSetting if args.Key == "*" { settings, err = player.GetSettings() } else { setting, err = player.GetSetting(args.Key) settings = append(settings, setting) } if err != nil { return helpers.NewTPErrorFromError(err).Encode() } result := models.DecoratePlayerSettingsJson(settings) resp, _ := chelpers.BuildSuccessJSON(result).Encode() return resp }
func (Player) PlayerSettingsSet(server *wsevent.Server, so *wsevent.Client, data []byte) []byte { reqerr := chelpers.FilterRequest(so, 0, true) if reqerr != nil { return reqerr.Encode() } var args struct { Key string `json:"key"` Value string `json:"value"` } err := chelpers.GetParams(data, &args) if err != nil { return helpers.NewTPErrorFromError(err).Encode() } player, _ := models.GetPlayerBySteamId(chelpers.GetSteamId(so.Id())) err = player.SetSetting(args.Key, args.Value) if err != nil { return helpers.NewTPErrorFromError(err).Encode() } return chelpers.EmptySuccessJS }
func DebugPlayerSub(server *wsevent.Server, so *wsevent.Client, data []byte) []byte { reqerr := chelpers.FilterRequest(so, 0, true) if reqerr != nil { return reqerr.Encode() } var args struct { Id *uint `json:"id"` Team *string `json:"team"` Class *string `json:"class"` } err := chelpers.GetParams(data, &args) if err != nil { return helpers.NewTPErrorFromError(err).Encode() } lob, tperr := models.GetLobbyById(*args.Id) if tperr != nil { return tperr.Encode() } s, tperr := models.LobbyGetPlayerSlot(lob.Type, *args.Team, *args.Class) if tperr != nil { return tperr.Encode() } slot := models.LobbySlot{} err = db.DB.Where("slot = ?", s).First(&slot).Error if err != nil { helpers.Logger.Debug("", slot, s) return helpers.NewTPErrorFromError(err).Encode() } player := models.Player{} err = db.DB.First(&player, slot.PlayerId).Error if err != nil { helpers.Logger.Debug("", player) return helpers.NewTPErrorFromError(err).Encode() } sub, _ := models.NewSub(*args.Id, player.SteamId) db.DB.Save(sub) models.BroadcastSubList() return chelpers.EmptySuccessJS }
func (Lobby) LobbyLeave(server *wsevent.Server, so *wsevent.Client, data []byte) []byte { reqerr := chelpers.FilterRequest(so, authority.AuthAction(0), true) if reqerr != nil { return reqerr.Encode() } var args struct { Id *uint `json:"id"` } if err := chelpers.GetParams(data, &args); err != nil { return helpers.NewTPErrorFromError(err).Encode() } steamId := chelpers.GetSteamId(so.Id()) lob, player, tperr := removePlayerFromLobby(*args.Id, steamId) if tperr != nil { return tperr.Encode() } chelpers.AfterLobbyLeave(server, so, lob, player) return chelpers.EmptySuccessJS }
func DebugLobbyReady(server *wsevent.Server, so *wsevent.Client, data []byte) []byte { reqerr := chelpers.FilterRequest(so, 0, true) if reqerr != nil { return reqerr.Encode() } var args struct { Id *uint `json:"id"` } err := chelpers.GetParams(data, &args) if err != nil { return helpers.NewTPErrorFromError(err).Encode() } lobby, _ := models.GetLobbyById(*args.Id) var slots []models.LobbySlot db.DB.Where("lobby_id = ?", lobby.ID).Find(&slots) for _, slot := range slots { slot.Ready = true db.DB.Save(slot) } lobby.OnChange(true) return chelpers.EmptySuccessJS }
func (Player) PlayerSettingsSet(so *wsevent.Client, args struct { Key *string `json:"key"` Value *string `json:"value"` }) interface{} { player, _ := models.GetPlayerBySteamID(chelpers.GetSteamId(so.ID)) err := player.SetSetting(*args.Key, *args.Value) if err != nil { return helpers.NewTPErrorFromError(err) } switch *args.Key { case "siteAlias": profile := models.DecoratePlayerProfileJson(player) so.EmitJSON(helpers.NewRequest("playerProfile", profile)) if lobbyID, _ := player.GetLobbyID(true); lobbyID != 0 { lobby, _ := models.GetLobbyByID(lobbyID) lobbyData := lobby.LobbyData(true) lobbyData.Send() } case "mumbleNick": if !reMumbleNick.MatchString(*args.Value) { return helpers.NewTPError("Invalid Mumble nick.", -1) } } return chelpers.EmptySuccessJS }
func (Lobby) ServerVerify(so *wsevent.Client, args struct { Server *string `json:"server"` Rconpwd *string `json:"rconpwd"` }) interface{} { if !validAddress.MatchString(*args.Server) { return helpers.NewTPError("Invalid Server Address", -1) } var count int db.DB.Table("server_records").Where("host = ?", *args.Server).Count(&count) if count != 0 { return helpers.NewTPError("A lobby is already using this server.", -1) } info := &models.ServerRecord{ Host: *args.Server, RconPassword: *args.Rconpwd, } db.DB.Save(info) defer db.DB.Where("host = ?", info.Host).Delete(models.ServerRecord{}) err := models.VerifyInfo(*info) if err != nil { return helpers.NewTPErrorFromError(err) } return chelpers.EmptySuccessJS }
func (Lobby) LobbyServerReset(so *wsevent.Client, args struct { ID *uint `json:"id"` }) interface{} { player := chelpers.GetPlayerFromSocket(so.ID) lobby, tperr := models.GetLobbyByID(*args.ID) if player.SteamID != lobby.CreatedBySteamID || player.Role != helpers.RoleAdmin { return helpers.NewTPError("Player not authorized to reset server.", -1) } if tperr != nil { return tperr } if lobby.State == models.LobbyStateEnded { return helpers.NewTPError("Lobby has ended", 1) } if err := models.ReExecConfig(lobby.ID); err != nil { return helpers.NewTPErrorFromError(err) } return chelpers.EmptySuccessJS }
func (Player) PlayerProfile(server *wsevent.Server, so *wsevent.Client, data []byte) []byte { reqerr := chelpers.FilterRequest(so, 0, true) if reqerr != nil { return reqerr.Encode() } var args struct { Steamid string `json:"steamid"` } err := chelpers.GetParams(data, &args) if err != nil { return helpers.NewTPErrorFromError(err).Encode() } steamid := args.Steamid if steamid == "" { steamid = chelpers.GetSteamId(so.Id()) } player, playErr := models.GetPlayerWithStats(steamid) if playErr != nil { return playErr.Encode() } result := models.DecoratePlayerProfileJson(player) resp, _ := chelpers.BuildSuccessJSON(result).Encode() return resp }
func (Lobby) LobbySpectatorJoin(server *wsevent.Server, so *wsevent.Client, data []byte) []byte { reqerr := chelpers.FilterRequest(so, authority.AuthAction(0), true) if reqerr != nil { bytes, _ := json.Marshal(reqerr) return bytes } var args struct { Id *uint `json:"id"` } if err := chelpers.GetParams(data, &args); err != nil { return helpers.NewTPErrorFromError(err).Encode() } var lob *models.Lobby lob, tperr := models.GetLobbyById(*args.Id) if tperr != nil { return tperr.Encode() } player, tperr := models.GetPlayerBySteamId(chelpers.GetSteamId(so.Id())) if tperr != nil { return tperr.Encode() } var specSameLobby bool arr, tperr := player.GetSpectatingIds() if len(arr) != 0 { for _, id := range arr { if id == *args.Id { specSameLobby = true continue } lobby, _ := models.GetLobbyById(id) lobby.RemoveSpectator(player, true) server.RemoveClient(so.Id(), fmt.Sprintf("%d_public", id)) } } // If the player is already in the lobby (either joined a slot or is spectating), don't add them. // Just Broadcast the lobby to them, so the frontend displays it. if id, _ := player.GetLobbyId(); id != *args.Id && !specSameLobby { tperr = lob.AddSpectator(player) if tperr != nil { return tperr.Encode() } chelpers.AfterLobbySpec(server, so, lob) } models.BroadcastLobbyToUser(lob, player.SteamId) return chelpers.EmptySuccessJS }
func (Chat) ChatSend(server *wsevent.Server, so *wsevent.Client, data []byte) []byte { reqerr := chelpers.FilterRequest(so, 0, true) if reqerr != nil { return reqerr.Encode() } var args struct { Message *string `json:"message"` Room *int `json:"room"` } err := chelpers.GetParams(data, &args) if err != nil { return helpers.NewTPErrorFromError(err).Encode() } player, tperr := models.GetPlayerBySteamId(chelpers.GetSteamId(so.Id())) if tperr != nil { return tperr.Encode() } //helpers.Logger.Debug("received chat message: %s %s", *args.Message, player.Name) if *args.Room > 0 { spec := player.IsSpectatingId(uint(*args.Room)) //Check if player has either joined, or is spectating lobby lobbyId, tperr := player.GetLobbyId() if tperr != nil && !spec && lobbyId != uint(*args.Room) { return helpers.NewTPError("Player is not in the lobby.", 5).Encode() } } else { // else room is the lobby list room *args.Room, _ = strconv.Atoi(config.Constants.GlobalChatRoom) } if (*args.Message)[0] == '\n' { return helpers.NewTPError("Cannot send messages prefixed with newline", 4).Encode() } if len(*args.Message) > 120 { return helpers.NewTPError("Message too long", 4).Encode() } message := models.NewChatMessage(*args.Message, *args.Room, player) db.DB.Save(message) bytes, _ := json.Marshal(message) broadcaster.SendMessageToRoom(fmt.Sprintf("%s_public", chelpers.GetLobbyRoom(uint(*args.Room))), "chatReceive", string(bytes)) if strings.HasPrefix(*args.Message, "!admin") { chelpers.SendToSlack(*args.Message, player.Name, player.SteamId) } return chelpers.EmptySuccessJS }
func (Lobby) LobbyServerReset(server *wsevent.Server, so *wsevent.Client, data []byte) []byte { reqerr := chelpers.FilterRequest(so, authority.AuthAction(0), true) if reqerr != nil { return reqerr.Encode() } var args struct { ID *uint `json:"id"` } if err := chelpers.GetParams(data, &args); err != nil { return helpers.NewTPErrorFromError(err).Encode() } player, err := models.GetPlayerBySteamId(chelpers.GetSteamId(so.Id())) if err != nil { return err.Encode() } lobby, tperr := models.GetLobbyById(*args.ID) if player.SteamId != lobby.CreatedBySteamID { return helpers.NewTPError("Player not authorized to close lobby.", -1).Encode() } if tperr != nil { return tperr.Encode() } if lobby.State == models.LobbyStateEnded { return helpers.NewTPError("Lobby has ended", 1).Encode() } if err := models.ReExecConfig(lobby.ID); err != nil { return helpers.NewTPErrorFromError(err).Encode() } return chelpers.EmptySuccessJS }
func (Admin) AdminChangeRole(server *wsevent.Server, so *wsevent.Client, data []byte) []byte { reqerr := chelpers.FilterRequest(so, 0, true) if reqerr != nil { return reqerr.Encode() } var args struct { Steamid *string `json:"steamid"` Role *string `json:"role"` } err := chelpers.GetParams(data, &args) if err != nil { return helpers.NewTPErrorFromError(err).Encode() } role, ok := helpers.RoleMap[*args.Role] if !ok || role == helpers.RoleAdmin { return helpers.NewTPError("Invalid role parameter", 0).Encode() } otherPlayer, err := models.GetPlayerBySteamId(*args.Steamid) if err != nil { return helpers.NewTPError("Player not found.", 0).Encode() } currPlayer, _ := chelpers.GetPlayerSocket(so.Id()) models.LogAdminAction(currPlayer.ID, helpers.ActionChangeRole, otherPlayer.ID) // actual change happens otherPlayer.Role = role db.DB.Save(&otherPlayer) // rewrite session data. THIS WON'T WRITE A COOKIE SO IT ONLY WORKS WITH // STORES THAT STORE DATA IN COOKIES (AND NOT ONLY SESSION ID). session, sesserr := chelpers.GetSessionHTTP(so.Request()) if sesserr == nil { session.Values["role"] = role session.Save(so.Request(), FakeResponseWriter{}) } return chelpers.EmptySuccessJS }
func (Global) GetConstant(server *wsevent.Server, so *wsevent.Client, data []byte) []byte { var args struct { Constant string `json:"constant"` } if err := chelpers.GetParams(data, &args); err != nil { return helpers.NewTPErrorFromError(err).Encode() } output := simplejson.New() switch args.Constant { case "lobbySettingsList": output = models.LobbySettingsToJson() default: return helpers.NewTPError("Unknown constant.", -1).Encode() } bytes, _ := chelpers.BuildSuccessJSON(output).Encode() return bytes }
func (Lobby) LobbyBan(server *wsevent.Server, so *wsevent.Client, data []byte) []byte { reqerr := chelpers.FilterRequest(so, authority.AuthAction(0), true) if reqerr != nil { return reqerr.Encode() } var args struct { Id *uint `json:"id"` Steamid *string `json:"steamid"` } if err := chelpers.GetParams(data, &args); err != nil { return helpers.NewTPErrorFromError(err).Encode() } steamId := *args.Steamid selfSteamId := chelpers.GetSteamId(so.Id()) if steamId == selfSteamId { return helpers.NewTPError("Player can't kick himself.", -1).Encode() } if ok, tperr := playerCanKick(*args.Id, selfSteamId); !ok { return tperr.Encode() } lob, player, tperr := removePlayerFromLobby(*args.Id, steamId) if tperr != nil { return tperr.Encode() } lob.BanPlayer(player) so, _ = broadcaster.GetSocket(player.SteamId) chelpers.AfterLobbyLeave(server, so, lob, player) broadcaster.SendMessage(steamId, "sendNotification", fmt.Sprintf(`{"notification": "You have been removed from Lobby #%d"}`, *args.Id)) return chelpers.EmptySuccessJS }
func (Lobby) LobbyClose(server *wsevent.Server, so *wsevent.Client, data []byte) []byte { reqerr := chelpers.FilterRequest(so, authority.AuthAction(0), true) if reqerr != nil { return reqerr.Encode() } var args struct { Id *uint `json:"id"` } if err := chelpers.GetParams(data, &args); err != nil { return helpers.NewTPErrorFromError(err).Encode() } player, _ := models.GetPlayerBySteamId(chelpers.GetSteamId(so.Id())) lob, tperr := models.GetLobbyByIdServer(uint(*args.Id)) if tperr != nil { return tperr.Encode() } if player.SteamId != lob.CreatedBySteamID && player.Role != helpers.RoleAdmin { return helpers.NewTPError("Player not authorized to close lobby.", -1).Encode() } if lob.State == models.LobbyStateEnded { return helpers.NewTPError("Lobby already closed.", -1).Encode() } models.FumbleLobbyEnded(lob) lob.Close(true) models.BroadcastLobbyList() // has to be done manually for now return chelpers.EmptySuccessJS }
func (Lobby) LobbySpectatorLeave(server *wsevent.Server, so *wsevent.Client, data []byte) []byte { reqerr := chelpers.FilterRequest(so, authority.AuthAction(0), true) if reqerr != nil { return reqerr.Encode() } var args struct { Id *uint `json:"id"` } if err := chelpers.GetParams(data, &args); err != nil { return helpers.NewTPErrorFromError(err).Encode() } steamId := chelpers.GetSteamId(so.Id()) player, tperr := models.GetPlayerBySteamId(steamId) if tperr != nil { return tperr.Encode() } lob, tperr := models.GetLobbyById(*args.Id) if tperr != nil { return tperr.Encode() } if !player.IsSpectatingId(lob.ID) { if id, _ := player.GetLobbyId(); id == *args.Id { chelpers.AfterLobbySpecLeave(server, so, lob) return chelpers.EmptySuccessJS } return helpers.NewTPError("Player is not spectating", -1).Encode() } lob.RemoveSpectator(player, true) chelpers.AfterLobbySpecLeave(server, so, lob) return chelpers.EmptySuccessJS }
func (Player) PlayerSettingsGet(so *wsevent.Client, args struct { Key *string `json:"key"` }) interface{} { var err error player, _ := models.GetPlayerBySteamID(chelpers.GetSteamId(so.ID)) var settings []models.PlayerSetting var setting models.PlayerSetting if *args.Key == "*" { settings, err = player.GetSettings() } else { setting, err = player.GetSetting(*args.Key) settings = append(settings, setting) } if err != nil { return helpers.NewTPErrorFromError(err) } result := models.DecoratePlayerSettingsJson(settings) return chelpers.NewResponse(result) }
func DebugUpdateStatsFilter(server *wsevent.Server, so *wsevent.Client, data []byte) []byte { reqerr := chelpers.FilterRequest(so, 0, true) if reqerr != nil { return reqerr.Encode() } var args struct { Id *uint `json:"id"` } err := chelpers.GetParams(data, &args) if err != nil { return helpers.NewTPErrorFromError(err).Encode() } lobby, tperr := models.GetLobbyById(*args.Id) if tperr != nil { return tperr.Encode() } lobby.UpdateStats() return chelpers.EmptySuccessJS }
func (JSONCodec) Error(err error) interface{} { return helpers.NewTPErrorFromError(err) }
func (Lobby) LobbyCreate(so *wsevent.Client, args struct { Map *string `json:"map"` Type *string `json:"type" valid:"debug,6s,highlander,4v4,ultiduo,bball"` League *string `json:"league" valid:"ugc,etf2l,esea,asiafortress,ozfortress"` Server *string `json:"server"` RconPwd *string `json:"rconpwd"` WhitelistID *string `json:"whitelistID"` Mumble *bool `json:"mumbleRequired"` Password *string `json:"password" empty:"-"` SteamGroupWhitelist *string `json:"steamGroupWhitelist" empty:"-"` Requirements *struct { Classes map[string]Requirement `json:"classes,omitempty"` General Requirement `json:"general,omitempty"` } `json:"requirements" empty:"-"` }) interface{} { player := chelpers.GetPlayerFromSocket(so.ID) if banned, until := player.IsBannedWithTime(models.PlayerBanCreate); banned { str := fmt.Sprintf("You've been banned from creating lobbies till %s", until.Format(time.RFC822)) return helpers.NewTPError(str, -1) } var steamGroup string if *args.SteamGroupWhitelist != "" && !rSteamGroup.MatchString(*args.SteamGroupWhitelist) { return helpers.NewTPError("Invalid Steam group URL", -1) } else if rSteamGroup.MatchString(*args.SteamGroupWhitelist) { steamGroup = rSteamGroup.FindStringSubmatch(*args.SteamGroupWhitelist)[1] } var playermap = map[string]models.LobbyType{ "debug": models.LobbyTypeDebug, "6s": models.LobbyTypeSixes, "highlander": models.LobbyTypeHighlander, "ultiduo": models.LobbyTypeUltiduo, "bball": models.LobbyTypeBball, "4v4": models.LobbyTypeFours, } lobbyType := playermap[*args.Type] var count int db.DB.Table("server_records").Where("host = ?", *args.Server).Count(&count) if count != 0 { return helpers.NewTPError("A lobby is already using this server.", -1) } randBytes := make([]byte, 6) rand.Read(randBytes) serverPwd := base64.URLEncoding.EncodeToString(randBytes) //TODO what if playermap[lobbytype] is nil? info := models.ServerRecord{ Host: *args.Server, RconPassword: *args.RconPwd, ServerPassword: serverPwd} // err = models.VerifyInfo(info) // if err != nil { // bytes, _ := helpers.NewTPErrorFromError(err).Encode() // return string(bytes) // } lob := models.NewLobby(*args.Map, lobbyType, *args.League, info, *args.WhitelistID, *args.Mumble, steamGroup, *args.Password) lob.CreatedBySteamID = player.SteamID lob.RegionCode, lob.RegionName = chelpers.GetRegion(*args.Server) if (lob.RegionCode == "" || lob.RegionName == "") && config.Constants.GeoIP != "" { return helpers.NewTPError("Couldn't find region server.", 1) } lob.Save() err := lob.SetupServer() if err != nil { //lobby setup failed, delete lobby and corresponding server record qerr := db.DB.Where("id = ?", lob.ID).Delete(&models.Lobby{}).Error if qerr != nil { logrus.Warning(qerr.Error()) } db.DB.Delete(&lob.ServerInfo) return helpers.NewTPErrorFromError(err) } lob.State = models.LobbyStateWaiting lob.Save() models.FumbleLobbyCreated(lob) if args.Requirements != nil { for class, requirement := range (*args.Requirements).Classes { if requirement.Restricted.Blu { err := newRequirement("blu", class, requirement, lob) if err != nil { return err } } if requirement.Restricted.Red { err := newRequirement("red", class, requirement, lob) if err != nil { return err } } } if args.Requirements.General.Hours != 0 || args.Requirements.General.Lobbies != 0 { general := &models.Requirement{ LobbyID: lob.ID, Hours: args.Requirements.General.Hours, Lobbies: args.Requirements.General.Lobbies, Slot: -1, } general.Save() } } return chelpers.NewResponse( struct { ID uint `json:"id"` }{lob.ID}) }
func ServerInit(server *wsevent.Server, noAuthServer *wsevent.Server) { server.OnDisconnect = onDisconnect server.Extractor = getEvent noAuthServer.OnDisconnect = onDisconnect noAuthServer.Extractor = getEvent server.On("authenticationTest", func(server *wsevent.Server, so *wsevent.Client, data []byte) []byte { reqerr := chelpers.FilterRequest(so, 0, true) if reqerr != nil { bytes, _ := json.Marshal(reqerr) return bytes } bytes, _ := json.Marshal(struct { Message string `json:"message"` }{"authenticated"}) return bytes }) //Global Handlers server.Register(handler.Global{}) //Lobby Handlers server.Register(handler.Lobby{}) //server.On("lobbyCreate", handler.LobbyCreate) //Player Handlers server.Register(handler.Player{}) //Chat Handlers server.Register(handler.Chat{}) //Admin Handlers server.Register(handler.Admin{}) //Debugging handlers // if config.Constants.ServerMockUp { // server.On("debugLobbyFill", handler.DebugLobbyFill) // server.On("debugLobbyReady", handler.DebugLobbyReady) // server.On("debugUpdateStatsFilter", handler.DebugUpdateStatsFilter) // server.On("debugPlayerSub", handler.DebugPlayerSub) // } noAuthServer.On("lobbySpectatorJoin", func(s *wsevent.Server, so *wsevent.Client, data []byte) []byte { var args struct { Id *uint `json:"id"` } if err := chelpers.GetParams(data, &args); err != nil { return helpers.NewTPErrorFromError(err).Encode() } var lob *models.Lobby lob, tperr := models.GetLobbyById(*args.Id) if tperr != nil { return tperr.Encode() } chelpers.AfterLobbySpec(s, so, lob) bytes, _ := json.Marshal(models.DecorateLobbyData(lob, true)) so.EmitJSON(helpers.NewRequest("lobbyData", string(bytes))) return chelpers.EmptySuccessJS }) noAuthServer.On("getSocketInfo", (handler.Global{}).GetSocketInfo) noAuthServer.DefaultHandler = func(_ *wsevent.Server, so *wsevent.Client, data []byte) []byte { return helpers.NewTPError("Player isn't logged in.", -4).Encode() } }
func (Lobby) LobbyJoin(server *wsevent.Server, so *wsevent.Client, data []byte) []byte { reqerr := chelpers.FilterRequest(so, authority.AuthAction(0), true) if reqerr != nil { return reqerr.Encode() } var args struct { Id *uint `json:"id"` Class *string `json:"class"` Team *string `json:"team" valid:"red,blu"` } if err := chelpers.GetParams(data, &args); err != nil { return helpers.NewTPErrorFromError(err).Encode() } //helpers.Logger.Debug("id %d class %s team %s", *args.Id, *args.Class, *args.Team) player, tperr := models.GetPlayerBySteamId(chelpers.GetSteamId(so.Id())) if tperr != nil { return tperr.Encode() } lob, tperr := models.GetLobbyById(*args.Id) if tperr != nil { return tperr.Encode() } if lob.State == models.LobbyStateEnded { return helpers.NewTPError("Cannot join a closed lobby.", -1).Encode() } //Check if player is in the same lobby var sameLobby bool if id, err := player.GetLobbyId(); err == nil && id == *args.Id { sameLobby = true } slot, tperr := models.LobbyGetPlayerSlot(lob.Type, *args.Team, *args.Class) if tperr != nil { return tperr.Encode() } if prevId, err := player.GetLobbyId(); err != nil { server.RemoveClient(so.Id(), fmt.Sprintf("%d_public", prevId)) server.RemoveClient(so.Id(), fmt.Sprintf("%d_private", prevId)) } tperr = lob.AddPlayer(player, slot, *args.Team, *args.Class) if tperr != nil { return tperr.Encode() } if !sameLobby { chelpers.AfterLobbyJoin(server, so, lob, player) } if lob.IsFull() { lob.State = models.LobbyStateReadyingUp lob.ReadyUpTimestamp = time.Now().Unix() + 30 lob.Save() tick := time.After(time.Second * 30) id := lob.ID stop := make(chan struct{}) go func() { select { case <-tick: lobby := &models.Lobby{} db.DB.First(lobby, id) if lobby.State != models.LobbyStateInProgress { err := lobby.RemoveUnreadyPlayers() if err != nil { helpers.Logger.Error("RemoveUnreadyPlayers: ", err.Error()) err = nil } err = lobby.UnreadyAllPlayers() if err != nil { helpers.Logger.Error("UnreadyAllPlayers: ", err.Error()) } lobby.State = models.LobbyStateWaiting lobby.Save() } case <-stop: return } }() room := fmt.Sprintf("%s_private", chelpers.GetLobbyRoom(lob.ID)) broadcaster.SendMessageToRoom(room, "lobbyReadyUp", `{"timeout":30}`) models.BroadcastLobbyList() } err := models.AllowPlayer(*args.Id, player.SteamId, *args.Team+*args.Class) if err != nil { helpers.Logger.Error(err.Error()) } if lob.State == models.LobbyStateInProgress { bytes, _ := json.Marshal(models.DecorateLobbyConnect(lob, player.Name, *args.Class)) broadcaster.SendMessage(player.SteamId, "lobbyStart", string(bytes)) } return chelpers.EmptySuccessJS }
func (Lobby) LobbyCreate(_ *wsevent.Server, so *wsevent.Client, data []byte) []byte { reqerr := chelpers.FilterRequest(so, authority.AuthAction(0), true) if reqerr != nil { bytes, _ := json.Marshal(reqerr) return bytes } var args struct { Map *string `json:"map"` Type *string `json:"type" valid:"debug,6s,highlander,4v4,ultiduo,bball"` League *string `json:"league" valid:"ugc,etf2l,esea,asiafortress,ozfortress"` Server *string `json:"server"` RconPwd *string `json:"rconpwd"` WhitelistID *uint `json:"whitelistID"` Mumble *bool `json:"mumbleRequired"` } err := chelpers.GetParams(data, &args) if err != nil { return helpers.NewTPErrorFromError(err).Encode() } player, _ := models.GetPlayerBySteamId(chelpers.GetSteamId(so.Id())) var playermap = map[string]models.LobbyType{ "debug": models.LobbyTypeDebug, "6s": models.LobbyTypeSixes, "highlander": models.LobbyTypeHighlander, "ultiduo": models.LobbyTypeUltiduo, "bball": models.LobbyTypeBball, "4v4": models.LobbyTypeFours, } lobbyType := playermap[*args.Type] var count int db.DB.Table("server_records").Where("host = ?", *args.Server).Count(&count) if count != 0 { return helpers.NewTPError("A lobby is already using this server.", -1).Encode() } randBytes := make([]byte, 6) rand.Read(randBytes) serverPwd := base64.URLEncoding.EncodeToString(randBytes) //TODO what if playermap[lobbytype] is nil? info := models.ServerRecord{ Host: *args.Server, RconPassword: *args.RconPwd, ServerPassword: serverPwd} // err = models.VerifyInfo(info) // if err != nil { // bytes, _ := helpers.NewTPErrorFromError(err).Encode() // return string(bytes) // } lob := models.NewLobby(*args.Map, lobbyType, *args.League, info, int(*args.WhitelistID), *args.Mumble) lob.CreatedBySteamID = player.SteamId lob.RegionCode, lob.RegionName = chelpers.GetRegion(*args.Server) if (lob.RegionCode == "" || lob.RegionName == "") && config.Constants.GeoIP != "" { return helpers.NewTPError("Couldn't find region server.", 1).Encode() } lob.Save() err = lob.SetupServer() if err != nil { qerr := db.DB.Where("id = ?", lob.ID).Delete(&models.Lobby{}).Error if qerr != nil { helpers.Logger.Warning(qerr.Error()) } db.DB.Delete(&lob.ServerInfo) return helpers.NewTPErrorFromError(err).Encode() } lob.State = models.LobbyStateWaiting lob.Save() reply_str := struct { ID uint `json:"id"` }{lob.ID} models.FumbleLobbyCreated(lob) bytes, _ := chelpers.BuildSuccessJSON(reply_str).Encode() return bytes }