using Shogi.Contracts.Api; using Shogi.Contracts.Types; using Shogi.UI.Pages.Home.Account; using System.Net; using System.Net.Http.Json; using System.Text.Json; namespace Shogi.UI.Pages.Home.Api { public class ShogiApi : IShogiApi { public const string GuestClientName = "Guest"; public const string MsalClientName = "Msal"; //public const string AnonymousClientName = "Anonymous"; private readonly JsonSerializerOptions serializerOptions; private readonly IHttpClientFactory clientFactory; private readonly AccountState accountState; public ShogiApi(IHttpClientFactory clientFactory, AccountState accountState) { serializerOptions = new JsonSerializerOptions(JsonSerializerDefaults.Web); this.clientFactory = clientFactory; this.accountState = accountState; } private HttpClient HttpClient => accountState.User?.WhichAccountPlatform switch { WhichAccountPlatform.Guest => clientFactory.CreateClient(GuestClientName), WhichAccountPlatform.Microsoft => clientFactory.CreateClient(MsalClientName), _ => throw new InvalidOperationException("AccountState.User must not be null during API call.") }; public async Task GuestLogout() { var response = await HttpClient.PutAsync(new Uri("User/GuestLogout", UriKind.Relative), null); response.EnsureSuccessStatusCode(); } public async Task GetSession(string name) { var response = await HttpClient.GetAsync(new Uri($"Sessions/{name}", UriKind.Relative)); if (response.IsSuccessStatusCode) { return (await response.Content.ReadFromJsonAsync(serializerOptions))?.Session; } return null; } public async Task GetSessionsPlayerCount() { var response = await HttpClient.GetAsync(RelativeUri("Sessions/PlayerCount")); if (response.IsSuccessStatusCode) { return await response.Content.ReadFromJsonAsync(serializerOptions); } return null; } /// /// Logs the user into the API and returns a token which can be used to request a socket connection. /// public async Task GetToken(WhichAccountPlatform whichAccountPlatform) { var httpClient = whichAccountPlatform == WhichAccountPlatform.Microsoft ? clientFactory.CreateClient(MsalClientName) : clientFactory.CreateClient(GuestClientName); var response = await httpClient.GetFromJsonAsync(RelativeUri("User/Token"), serializerOptions); return response; } public async Task Move(string sessionName, MovePieceCommand command) { await this.HttpClient.PatchAsync($"Sessions/{sessionName}/Move", JsonContent.Create(command)); } public async Task PostSession(string name, bool isPrivate) { var response = await HttpClient.PostAsJsonAsync(RelativeUri("Sessions"), new CreateSessionCommand { Name = name, }); return response.StatusCode; } public async Task PatchJoinGame(string name) { var response = await HttpClient.PatchAsync(RelativeUri($"Sessions/{name}/Join"), null); return response.StatusCode; } private static Uri RelativeUri(string path) => new Uri(path, UriKind.Relative); } }