private async Task _onuserupdateevent_(RequestResponseModel msg) { ulong user = Convert.ToUInt64(msg.Payload["user_id"]); string toonname = (string)msg.Payload["toon_name"]; UserJoinArgs args; //API doesn't reply with a lot of the data here despite being documented in spec doc try { List <string> flags = (List <string>)(msg.Payload["flags"]); Dictionary <string, string> attributes = (Dictionary <string, string>)(msg.Payload["attributes"]); string flag1 = flags[0]; string flag2 = flags[1]; string pid = attributes["ProgramId"]; string rate = attributes["Rate"]; string rank = attributes["Rank"]; string wins = attributes["Wins"]; args = new UserJoinArgs(user, toonname, flag1, flag2, pid, rate, rank, wins); } catch (Exception) { args = new UserJoinArgs(user, toonname, null, null, null, null, null, null); } Task t = Task.Run(() => OnUserJoin?.Invoke(this, args)); Debug.WriteLine($"[EVENT]User joined: {user}: {toonname}"); await t; }
private async Task _onchatdisconnectevent_(RequestResponseModel msg) { Task t = Task.Run(() => socket.Close()); Debug.WriteLine("[EVENT]Disconnected"); await t; }
private async Task _onuserleaveevent_(RequestResponseModel msg) { ulong user = Convert.ToUInt64(msg.Payload["user_id"]); UserLeaveArgs args = new UserLeaveArgs(user); Task t = Task.Run(() => OnUserLeave?.Invoke(this, args)); Debug.WriteLine($"[EVENT]User left: {user}"); await t; }
private async Task _onchatmessageevent_(RequestResponseModel msg) { ulong user = Convert.ToUInt64(msg.Payload["user_id"]); string message = (string)msg.Payload["message"]; string type = (string)msg.Payload["type"]; ChatMessageArgs args = new ChatMessageArgs(user, message, type); Task t = Task.Run(() => OnChatMessage?.Invoke(this, args)); Debug.WriteLine($"[EVENT]Chat message [{type}] from UID {user}: {message}"); await t; }
private async Task _onauthresponse_(RequestResponseModel msg) { //Step 2: Once auth accept response is received, attempt to connect to chat Debug.WriteLine("[RESPONSE]Authenticated! Attempting to enter chat..."); RequestResponseModel request = new RequestResponseModel() { Command = "Botapichat.ConnectRequest", RequestId = Interlocked.Exchange(ref requestID, requestID++) }; await Task.Run(() => socket.Send(JsonConvert.SerializeObject(request))); }
/// <summary> /// Disconnect from battle.net. /// Should only be called after a successful connection has been established (ie. OnChannelJoin is raised). /// Calling this function begins the disconnect handshake process, and does not necessarily mean the client is disconnected. /// The <see cref="OnDisconnect"/> event is raised when disconnected. /// </summary> /// <exception cref="InvalidOperationException">Attempting to disconnect before connecting</exception> public void Disconnect() { __ActiveConnectionCheck__(); RequestResponseModel request = new RequestResponseModel() { Command = "Botapichat.DisconnectRequest", RequestId = Interlocked.Exchange(ref requestID, requestID++) }; socket.Send(JsonConvert.SerializeObject(request)); Debug.WriteLine("[REQUEST]Disconnect"); }
private async Task _onchatconnectevent_(RequestResponseModel msg) { //Step 3: Recieving this response means login and connect is successful lock (mutex) { isReady = true; } string channelname = (string)msg.Payload["channel"]; ChannelJoinArgs c = new ChannelJoinArgs(channelname); Task t = Task.Run(() => OnChannelJoin?.Invoke(this, c)); Debug.WriteLine($"[EVENT]Entered channel: {channelname}"); await t; }
/// <summary> /// Sets a user to channel moderator. /// Note that there is currently no way to unmod a user. /// </summary> /// <param name="userid">User to mod</param> public void SetModerator(ulong userid) { __ActiveConnectionCheck__(); RequestResponseModel request = new RequestResponseModel() { Command = "Botapichat.SendSetModeratorRequest", RequestId = Interlocked.Exchange(ref requestID, requestID++), Payload = new Dictionary <string, object>() { { "user_id", userid } } }; socket.Send(JsonConvert.SerializeObject(request)); Debug.WriteLine($"[REQUEST]Set moderator: {userid}"); }
/// <summary> /// Sends an emoted message to the channel. /// </summary> /// <param name="emotemsg">Message to send</param> /// <returns></returns> public void SendEmote(string emotemsg) { __ActiveConnectionCheck__(); RequestResponseModel request = new RequestResponseModel() { Command = "Botapichat.SendEmoteRequest", RequestId = Interlocked.Exchange(ref requestID, requestID++), Payload = new Dictionary <string, object>() { { "message", emotemsg } } }; socket.Send(JsonConvert.SerializeObject(request)); Debug.WriteLine($"[REQUEST]Send emote: {emotemsg}"); }
/// <summary> /// Unbans a user from the channel. /// </summary> /// <param name="toonname">User to unban</param> public void UnbanUser(string toonname) { __ActiveConnectionCheck__(); RequestResponseModel request = new RequestResponseModel() { Command = "Botapichat.UnbanUserRequest", RequestId = Interlocked.Exchange(ref requestID, requestID++), Payload = new Dictionary <string, object>() { { "toon_name", toonname } } }; socket.Send(JsonConvert.SerializeObject(request)); Debug.WriteLine($"[REQUEST]Unban user: {toonname}"); }
private void __RequestResponseHelper__(RequestResponseModel msg) { ErrorArgs eargs = new ErrorArgs(msg.Status?.Code, msg.Status?.Area); OnError?.Invoke(this, eargs); }
private void __InitializeObjects__() { //Initializing commands to function mappings msgHandlers = new Dictionary <string, Func <RequestResponseModel, Task> >() { //Handshake and initialization related responses { "Botapiauth.AuthenticateResponse", _onauthresponse_ }, { "Botapichat.ConnectResponse", _onchatconnectresponse_ }, { "Botapichat.DisconnectResponse", _onchatdisconnectresponse_ }, //Async responses related to connection state { "Botapichat.ConnectEventRequest", _onchatconnectevent_ }, { "Botapichat.DisconnectEventRequest", _onchatdisconnectevent_ }, //General responses when server acknowledges a request { "Botapichat.SendMessageResponse", _onchatsendmessageresponse_ }, { "Botapichat.SendWhisperResponse", _onchatsendwhisperresponse_ }, { "Botapichat.BanUserResponse", _onbanuserresponse_ }, { "Botapichat.UnbanUserResponse", _onunbanuserresponse_ }, { "Botapichat.SendEmoteResponse", _onsendemoteresponse_ }, { "Botapichat.KickUserResponse", _onkickuserresponse_ }, { "Botapichat.SendSetModeratorResponse", _onsetmoderatorresponse_ }, //Server events that require client action { "Botapichat.MessageEventRequest", _onchatmessageevent_ }, { "Botapichat.UserUpdateEventRequest", _onuserupdateevent_ }, { "Botapichat.UserLeaveEventRequest", _onuserleaveevent_ } }; //Defining socket behaviour for listening socket.OnOpen += async(sender, args) => { //Step 1: Authenticate with server using API key Debug.WriteLine("[SOCKET]Connected! Attempting to authenticate..."); RequestResponseModel request = new RequestResponseModel() { Command = "Botapiauth.AuthenticateRequest", RequestId = Interlocked.Exchange(ref requestID, requestID++), Payload = new Dictionary <string, object>() { { "api_key", APIKey } } }; await Task.Run(() => socket.Send(JsonConvert.SerializeObject(request))); //Continued in _onauthresponse_() }; socket.OnMessage += async(sender, args) => { RequestResponseModel msg = JsonConvert.DeserializeObject <RequestResponseModel>(args.Data); if (msg.Command.IsNullOrEmpty() || !msgHandlers.ContainsKey(msg.Command)) { Debug.WriteLine($"[ERROR]Command {msg.Command} not recognized!"); Debug.WriteLine($"[ERROR]Message payload: {args.Data}"); } else { await msgHandlers[msg.Command].Invoke(msg); } }; socket.OnClose += async(sender, args) => { lock (mutex) { isConnected = false; isReady = false; } DisconnectArgs dargs = new DisconnectArgs(args.Code, args.Reason, args.WasClean); Task t = Task.Run(() => OnDisconnect?.Invoke(this, dargs)); Debug.WriteLine($"[SOCKET]Disconnected with code {args.Code}. Reason: {args.Reason}"); await t; }; socket.OnError += (sender, args) => { Debug.WriteLine($"[ERROR] {args.Message}"); if (args.Exception != null) { throw args.Exception; } }; }
private async Task _onkickuserresponse_(RequestResponseModel msg) { Debug.WriteLine("[RESPONSE]Kick user"); await Task.Run(() => __RequestResponseHelper__(msg)); }
private async Task _onsetmoderatorresponse_(RequestResponseModel msg) { Debug.WriteLine("[RESPONSE]Set Moderator"); await Task.Run(() => __RequestResponseHelper__(msg)); }
private async Task _onchatdisconnectresponse_(RequestResponseModel msg) { Debug.WriteLine("[RESPONSE]Disconnect"); await Task.Run(() => __RequestResponseHelper__(msg)); }
private async Task _onchatsendmessageresponse_(RequestResponseModel msg) { Debug.WriteLine("[RESPONSE]Message"); await Task.Run(() => __RequestResponseHelper__(msg)); }
private async Task _onsendemoteresponse_(RequestResponseModel msg) { Debug.WriteLine("[RESPONSE]Send Emote"); await Task.Run(() => __RequestResponseHelper__(msg)); }