PluralRichPresence/PluralRichPresnce/SimplyPlural/Socket.cs

122 lines
3.4 KiB
C#

using Newtonsoft.Json;
using PluralRichPresence.Api;
using System.Dynamic;
using System.Text;
namespace PluralRichPresence.SimplyPlural
{
public class Socket : ApiType
{
private AWebSocket? wSock;
public const int KEEPALIVE_INTERVAL = 10 * 1000;
public const string DEFAULT_WEBSOCKET_SERVER_URI = "wss://api.apparyllis.com/v1/socket";
public event EventHandler? FronterChanged;
Timer? keepAliveTimer = null;
private void onFronterChanged(dynamic fronterChangedEventData)
{
if(FronterChanged is not null)
{
FronterChanged(this, new EventArgs());
}
}
private void doUpdate(dynamic jsonData)
{
string target = jsonData.target;
switch (target)
{
case "frontHistory":
onFronterChanged(jsonData);
break;
}
}
private async Task reconnect()
{
while (true)
{
try
{
try
{
if (wSock is not null) wSock.Dispose();
wSock = null;
}
catch (Exception) { };
await connect();
await sendLogin();
this.keepAliveTimer = new Timer((TimerCallback) => { _ = sendKeepAlive(); }, null, KEEPALIVE_INTERVAL, 0);
}
catch (Exception) { Logger.Debug("failed to connect."); continue; }
break;
}
}
private async Task connect()
{
wSock = new AWebSocket(Config.GetEntry("SIMPLY_PLURAL_WEBSOCKET_URI", DEFAULT_WEBSOCKET_SERVER_URI));
await wSock.Connect();
wSock.TextReceived += wSockTextReceived;
wSock.Disconnected += wSockDisconnected;
}
private void wSockTextReceived(object? sender, TextReceivedEventArgs e)
{
string message = e.Text;
if (message == "pong") return;
try
{
dynamic? jsonData = JsonConvert.DeserializeObject(message);
if (jsonData is null) return;
string? type = jsonData.msg;
switch (type)
{
case "update":
doUpdate(jsonData);
break;
case null:
default:
break;
}
}
catch (Exception) { };
}
private void wSockDisconnected(object? sender, EventArgs e)
{
_ = reconnect();
}
private async Task sendKeepAlive()
{
if (wSock is not null) {
await wSock.SendText("ping");
}
if (keepAliveTimer is not null) keepAliveTimer.Change(KEEPALIVE_INTERVAL, 0);
}
private async Task sendLogin()
{
dynamic data = new ExpandoObject();
data.op = "authenticate";
data.token = token;
string authenticateJson = JsonConvert.SerializeObject(data);
if(wSock is not null)
await wSock.SendText(authenticateJson);
}
public Socket(string token) : base(token)
{
_ = reconnect();
}
}
}