SessionZero/SessionZeroClient/sessionzero/deleteme.txt
2025-03-31 22:38:25 -05:00

451 lines
14 KiB
Plaintext

using System;
using System.Collections.Generic;
using System.Net.Http;
using System.Text.Json;
using System.Threading;
using System.Threading.Tasks;
using Godot;
using HttpClient = System.Net.Http.HttpClient;
namespace SessionZeroClient.API;
public class ApiHandler : IApiHandler
{
private readonly HttpClient _httpClient;
public ApiHandler()
{
var handler = new HttpClientHandler
{
UseDefaultCredentials = true,
};
_httpClient = new HttpClient(handler)
{
Timeout = TimeSpan.FromSeconds(5),
};
}
/// <summary>
/// Returns true if the server URL is reachable valid, false otherwise.
/// </summary>
/// <param name="url"></param>
/// <returns></returns>
public async Task<bool> ValidateServerUrl(string url)
{
try
{
var apiString = $"{url}/api/Database/validate-server";
using var cts = new CancellationTokenSource(TimeSpan.FromSeconds(5));
var response = await _httpClient.GetAsync(apiString, cts.Token);
if (!response.IsSuccessStatusCode)
{
return false;
}
var responseString = await response.Content.ReadAsStringAsync(cts.Token);
var options = new JsonSerializerOptions { PropertyNameCaseInsensitive = true };
var validationResponse = JsonSerializer.Deserialize<ServerUrlValidationResponse>(responseString, options);
return validationResponse?.IsValid ?? false;
}
catch
{
throw new HttpRequestException($"Server {url} is invalid or not reachable.");
return false;
}
}
/// <summary>
/// Register a new user with the server.
/// </summary>
/// <param name="url"></param>
/// <param name="username"></param>
/// <param name="email"></param>
/// <param name="password"></param>
/// <returns></returns>
/// <exception cref="HttpRequestException"></exception>
public async Task<string> Register(string url, string username, string email, string password)
{
bool isValidServer = await ValidateServerUrl(url);
if (!isValidServer)
{
throw new HttpRequestException($"Could not Register User, Server {url} is invalid or not reachable.");
}
var apiString = $"{url}/api/Auth/register";
var requestBody = new Dictionary<string, string>
{
{"username", username},
{"email", email},
{"password", password}
};
var jsonBody = JsonSerializer.Serialize(requestBody);
var content = new StringContent(jsonBody, System.Text.Encoding.UTF8, "application/json");
var response = await _httpClient.PostAsync(apiString, content);
if (!response.IsSuccessStatusCode)
{
// throw new HttpRequestException($"Register failed: {response.StatusCode}");
}
var responseString = await response.Content.ReadAsStringAsync();
return responseString;
}
/// <summary>
/// Login to the server with the given username and password. Returns the JWT token if successful.
/// </summary>
/// <param name="url"></param>
/// <param name="username"></param>
/// <param name="password"></param>
/// <returns></returns>
/// <exception cref="HttpRequestException"></exception>
public async Task<string> Login(string url, string username, string password)
{
bool isValidServer = await ValidateServerUrl(url);
if (!isValidServer)
{
throw new HttpRequestException($"Could not Login, Server {url} is invalid or not reachable.");
}
var apiString = $"{url}/api/Auth/login";
var requestBody = new Dictionary<string, string>
{
{"username", username},
{"password", password}
};
var jsonBody = JsonSerializer.Serialize(requestBody);
var content = new StringContent(jsonBody, System.Text.Encoding.UTF8, "application/json");
var response = await _httpClient.PostAsync(apiString, content);
if (!response.IsSuccessStatusCode)
{
// throw new HttpRequestException($"Login failed: {response.StatusCode}");
}
var responseString = await response.Content.ReadAsStringAsync();
return responseString;
}
public class ServerUrlValidationResponse
{
public bool IsValid { get; set; }
public string Message { get; set; }
}
}
-----------------------------------------------------
using System.Threading.Tasks;
namespace SessionZeroClient.API;
public interface IApiHandler
{
Task<bool> ValidateServerUrl(string url);
Task<string> Register(string url, string username, string email, string password);
Task<string> Login(string url, string username, string password);
}
------------------------------------------------------
using Godot;
using System;
using System.Collections.Generic;
using System.Text.Json;
using System.Threading.Tasks;
using SessionZeroClient.API;
namespace SessionZeroClient;
public class AccountManager(IApiHandler apiHandler)
{
public string Username { get; private set; } = "";
public string Email { get; private set; } = "";
public string Jwt { get; private set; } = "";
private IApiHandler _apiHandler = apiHandler;
public async Task<bool> Register(string url, string username, string email, string password)
{
var response = await _apiHandler.Register(url, username, email, password);
if (!string.IsNullOrEmpty(response))
{
var responseData = JsonSerializer.Deserialize<Dictionary<string, string>>(response);
if (responseData != null && responseData.ContainsKey("message") && responseData["message"] == "User registered successfully")
{
return true;
}
}
return false;
}
public async Task<bool> Login(string url, string username, string password)
{
var response = await _apiHandler.Login(url, username, password);
if (!string.IsNullOrEmpty(response))
{
var responseData = JsonSerializer.Deserialize<Dictionary<string, string>>(response);
if (responseData != null && responseData.ContainsKey("token"))
{
Jwt = responseData["token"];
Username = username;
return true;
}
}
return false;
}
public void Logout()
{
Jwt = "";
Username = "";
Email = "";
}
}
-----------------------------------------------------------
using Godot;
using System;
using System.Threading.Tasks;
using SessionZeroClient;
using SessionZeroClient.API;
public partial class AccountScreenLogic : Node
{
[ExportGroup("UI Elements")]
// Selection Screen
[ExportSubgroup("Selection Screen")]
[Export] private VBoxContainer SelectionScreenVboxContainer { get; set; }
[Export] private Button RegisterSelectionButton { get; set; }
[Export] private Button LoginSelectionButton { get; set; }
[Export] private LineEdit UrlLineEdit { get; set; }
// Register Screen
[ExportSubgroup("Register Screen")]
[Export] private VBoxContainer RegisterScreenVboxContainer { get; set; }
[Export] private LineEdit RegisterUsernameLineEdit { get; set; }
[Export] private LineEdit RegisterEmailLineEdit { get; set; }
[Export] private LineEdit RegisterPasswordLineEdit { get; set; }
[Export] private Button RegisterButton { get; set; }
// Login Screen
[ExportSubgroup("Login Screen")]
[Export] private VBoxContainer LoginScreenVboxContainer { get; set; }
[Export] private LineEdit LoginUsernameLineEdit { get; set; }
[Export] private LineEdit LoginPasswordLineEdit { get; set; }
[Export] private Button LoginButton { get; set; }
// Account Screen
[ExportSubgroup("Account Screen")]
[Export] private VBoxContainer AccountScreenVboxContainer { get; set; }
[Export] private Label AccountScreenGreetingLabel { get; set; }
[Export] private Button LogoutButton { get; set; }
[Export] private Button OfflineModeButton { get; set; }
// Other
[ExportSubgroup("Other")]
[Export] Button BackButton { get; set; }
[Export] RichTextLabel StatusLabel { get; set; }
private IApiHandler _apiHandler;
private AccountManager _accountManager;
private string _url = "";
public void Init(IApiHandler apiHandler, AccountManager accountManager)
{
_apiHandler = apiHandler;
_accountManager = accountManager;
SetupSignals();
InitialState();
}
private void InitialState()
{
SelectionScreenVboxContainer.Visible = true;
RegisterScreenVboxContainer.Visible = false;
LoginScreenVboxContainer.Visible = false;
AccountScreenVboxContainer.Visible = false;
BackButton.Visible = false;
}
private void RegisterState()
{
SelectionScreenVboxContainer.Visible = false;
RegisterScreenVboxContainer.Visible = true;
LoginScreenVboxContainer.Visible = false;
AccountScreenVboxContainer.Visible = false;
BackButton.Visible = true;
}
private void LoginState()
{
SelectionScreenVboxContainer.Visible = false;
RegisterScreenVboxContainer.Visible = false;
LoginScreenVboxContainer.Visible = true;
AccountScreenVboxContainer.Visible = false;
BackButton.Visible = true;
}
private void AccountSuccessState()
{
SelectionScreenVboxContainer.Visible = false;
RegisterScreenVboxContainer.Visible = false;
LoginScreenVboxContainer.Visible = false;
AccountScreenVboxContainer.Visible = true;
BackButton.Visible = false;
AccountScreenGreetingLabel.Text = $"Welcome, {_accountManager.Username}!";
}
private void SetupSignals()
{
// Selection Screen
RegisterSelectionButton.Pressed += RegisterSelectionButtonPressed;
LoginSelectionButton.Pressed += LoginSelectionButtonPressed;
OfflineModeButton.Pressed += () => GD.Print("Offline mode not implemented yet.");
// Register Screen
RegisterButton.Pressed += RegisterButtonPressed;
// Login Screen
LoginButton.Pressed += LoginButtonPressed;
// Account Screen
LogoutButton.Pressed += Logout;
// Other
BackButton.Pressed += BackButtonPressed;
}
private async void RegisterSelectionButtonPressed()
{
bool isValidServer = await ValidateServerUrl(UrlLineEdit.Text);
if (isValidServer)
{
_url = UrlLineEdit.Text;
RegisterState();
}
}
private async void LoginSelectionButtonPressed()
{
bool isValidServer = await ValidateServerUrl(UrlLineEdit.Text);
if (isValidServer)
{
_url = UrlLineEdit.Text;
LoginState();
}
}
private async void RegisterButtonPressed()
{
var username = RegisterUsernameLineEdit.Text;
var email = RegisterEmailLineEdit.Text;
var password = RegisterPasswordLineEdit.Text;
var success = await _accountManager.Register(_url, username, email, password);
GD.Print($"Register success: {success}");
SetStatusLabel($"Register success: {success}", success ? Colors.Green : Colors.Red);
if (success)
{
var loginSuccess = await _accountManager.Login(_url, username, password);
GD.Print($"Login success: {loginSuccess}");
SetStatusLabel($"Login success: {loginSuccess}", loginSuccess ? Colors.Green : Colors.Red);
if (loginSuccess)
{
AccountSuccessState();
}
else
{
SetStatusLabel($"Login failed: {loginSuccess}", Colors.Red);
}
}
else
{
SetStatusLabel("Registration failed", Colors.Red);
}
}
private async void LoginButtonPressed()
{
var username = LoginUsernameLineEdit.Text;
var password = LoginPasswordLineEdit.Text;
var success = await _accountManager.Login(_url, username, password);
GD.Print($"Login success: {success}");
SetStatusLabel($"Login success: {success}", success ? Colors.Green : Colors.Red);
if (success)
{
AccountSuccessState();
}
else
{
SetStatusLabel("Login failed. Check Username and Password.", Colors.Red);
}
}
private async Task<bool> ValidateServerUrl(string url)
{
if (string.IsNullOrEmpty(url))
{
return false;
}
try
{
var isValid = await _apiHandler.ValidateServerUrl(url);
if (isValid)
{
GD.Print($"Server {url} is valid.");
SetStatusLabel($"Server {url} is valid.", Colors.Green);
}
return isValid;
}
catch (Exception ex)
{
GD.Print($"Server validation error: {ex.Message}");
SetStatusLabel($"Server validation error: {ex.Message}", Colors.Red);
return false;
}
}
private void Logout()
{
_accountManager.Logout();
GD.Print("Logged out");
SetStatusLabel("Logged out", Colors.Cyan);
InitialState();
}
private void BackButtonPressed()
{
InitialState();
}
private void SetStatusLabel(string message, Color color)
{
StatusLabel.Text = $"[color={color.ToHtml()}] {message} [/color]";
}
}