From 78a7597689a878c55c1f385d30522ba3cd38d805 Mon Sep 17 00:00:00 2001 From: "Tim G. | SnapixLP" Date: Fri, 6 Jun 2025 11:56:37 +0200 Subject: [PATCH] fixed an error where get command cant serlialize employee --- Library/Server.cs | 15 +++- Server/Commands/CommandLibrary.cs | 109 +++++++++++++++++------------- TestClient/Program.cs | 48 ++++++++++++- 3 files changed, 124 insertions(+), 48 deletions(-) diff --git a/Library/Server.cs b/Library/Server.cs index 38981f8..fc4ee79 100644 --- a/Library/Server.cs +++ b/Library/Server.cs @@ -146,7 +146,8 @@ public class Server // Deserialize the command result to an Employee object try { - return Task.FromResult(Employee.FromJson(commandResult)); + var employee = Employee.FromJson(commandResult); + return Task.FromResult(employee); } catch (JsonException) { @@ -233,6 +234,18 @@ public class Server return Task.FromException(new Exception("Failed to clock break.")); } } + + public Task ClockHistory(string employeeCode) + { + var commandResult = ExecuteCommandAsync("fullClockHistory " + employeeCode).Result; + return Task.FromResult(commandResult); + } + + public Task FullClockHistory(int limit = 50) + { + var commandResult = ExecuteCommandAsync("fullClockHistory " + limit).Result; + return Task.FromResult(commandResult); + } } \ No newline at end of file diff --git a/Server/Commands/CommandLibrary.cs b/Server/Commands/CommandLibrary.cs index a558dfc..362bd22 100644 --- a/Server/Commands/CommandLibrary.cs +++ b/Server/Commands/CommandLibrary.cs @@ -344,8 +344,25 @@ public class CommandLibrary throw new CommandException("Employee not found."); // Return the first (and expected single) matching employee as JSON object - var firstEmp = dataArray[0]; - return firstEmp.GetRawText(); + var firstRow = dataArray[0]; + // 5) Deserialize it into an Employee object. + // This requires that Employee.Id is an int (matching the DB schema), + // or you map fields manually if Id remains a string. + Employee self; + try + { + string employeeJson = firstRow.GetRawText(); + self = JsonSerializer.Deserialize(employeeJson) + ?? throw new InvalidOperationException("Deserialized Employee was null."); + } + catch (Exception ex) + { + Program.messageSender.Error($"[GetSelfUser] Failed to deserialize Employee: {ex.Message}"); + throw new CommandException("Internal error while parsing user data."); + } + + // 6) Return the Employee’s JSON via the ToJson() helper you already wrote: + return self.ToJson(); } [Command("clockHistory")] @@ -396,58 +413,58 @@ public class CommandLibrary [Command("fullClockHistory")] public static string FullClockHistoryCommand(string[] args, TcpClient? client, TcpServer? socket) - { - // 1) Determine maxHistoryLength (default = 50) - int maxHistoryLength; - if (args.Length >= 1 && int.TryParse(args[0], out var parsed)) - { - maxHistoryLength = parsed; - } - else - { - maxHistoryLength = 50; - } +{ + // 1) Determine maxHistoryLength (default = 50) + int maxHistoryLength; + if (args.Length >= 1 && int.TryParse(args[0], out var parsed)) + { + maxHistoryLength = parsed; + } + else + { + maxHistoryLength = 50; + } - // 2) Verify client/socket - if (client == null || socket == null) - throw new CommandException("No client connection detected."); + // 2) Verify client/socket + if (client == null || socket == null) + throw new CommandException("No client connection detected."); - if (!socket.LoggedInClients.TryGetValue(client, out var employeeCode)) - throw new CommandException("User not logged in."); + if (!socket.LoggedInClients.TryGetValue(client, out var employeeCode)) + throw new CommandException("User not logged in."); - // 3) Look up the employee to get its Id - var empParams = new Dictionary { { "Code", employeeCode } }; - string empResultJson = Program.mySql.Get("employees", empParams); + // 3) Look up the employee to get its Id + var empParams = new Dictionary { { "Code", employeeCode } }; + string empResultJson = Program.mySql.Get("employees", empParams); - using var empDoc = JsonDocument.Parse(empResultJson); - bool empError = empDoc.RootElement.GetProperty("error").GetBoolean(); - if (empError) - { - string dbMsg = empDoc.RootElement.GetProperty("data").GetString() ?? "Unknown DB error"; - Program.messageSender.Error($"[FullClockHistory] DB error when looking up employee: {dbMsg}"); - throw new CommandException("Internal error while fetching user data."); - } + using var empDoc = JsonDocument.Parse(empResultJson); + bool empError = empDoc.RootElement.GetProperty("error").GetBoolean(); + if (empError) + { + string dbMsg = empDoc.RootElement.GetProperty("data").GetString() ?? "Unknown DB error"; + Program.messageSender.Error($"[FullClockHistory] DB error when looking up employee: {dbMsg}"); + throw new CommandException("Internal error while fetching user data."); + } - var empArray = empDoc.RootElement.GetProperty("data"); - if (empArray.GetArrayLength() == 0) - throw new CommandException("Logged-in user not found in database."); + var empArray = empDoc.RootElement.GetProperty("data"); + if (empArray.GetArrayLength() == 0) + throw new CommandException("Logged-in user not found in database."); - int employeeId = empArray[0].GetProperty("Id").GetInt32(); + int employeeId = empArray[0].GetProperty("Id").GetInt32(); - // 4) Query the history table for this employeeId, ordered by ChangeTime DESC, limited to maxHistoryLength - string sql = @" - SELECT `EmployeeId`, `NewState`, `ChangeTime` - FROM `employee_state_history` - WHERE `EmployeeId` = ? - ORDER BY `ChangeTime` DESC - LIMIT ? - "; - var values = new List { employeeId, maxHistoryLength }; - string historyJson = Program.mySql.Query(sql, null, values); + // 4) Query the history table for this employeeId, ordered by ChangeTime DESC, limited to maxHistoryLength + string sql = @" + SELECT `EmployeeId`, `NewState`, `ChangeTime` + FROM `employee_state_history` + ORDER BY `ChangeTime` DESC + LIMIT ? + "; + var values = new List {maxHistoryLength }; + // Pass an empty string ("") for 'types' so that parameters get bound correctly + string historyJson = Program.mySql.Query(sql, /*types:*/ "", /*values:*/ values); - // 5) Return the JSON from Query (the client will receive {"error":…, "data":[…]} ) - return historyJson; - } + // 5) Return the JSON from Query (the client will receive {"error":…, "data":[…]} ) + return historyJson; +} #endregion diff --git a/TestClient/Program.cs b/TestClient/Program.cs index f808900..4dd835a 100644 --- a/TestClient/Program.cs +++ b/TestClient/Program.cs @@ -36,6 +36,7 @@ public class Tester "clock in", "clock out", "clock break", + "clockhistory", "help" }; @@ -105,12 +106,46 @@ public class Tester var responseLines = response.Split("%break").ToList(); await messageBox.ShowAsync("Command Result: clock break", responseLines); } + else if (command == "clockhistory") + { + List history = new List(); + string historyString = server.FullClockHistory().Result; + ClockHistoryResponse historyResponse; + try + { + historyResponse = JsonSerializer.Deserialize(historyString); + } + catch (Exception e) + { + ms.Error(e.Message); + return; + } + Dictionary employees = new Dictionary(); + foreach (ClockEntry clockEntry in historyResponse.data) + { + if (!employees.ContainsKey(clockEntry.EmployeeId)) + { + Employee newEmployee = await server.GetEmployee(id: clockEntry.EmployeeId); + employees.Add(clockEntry.EmployeeId, newEmployee); + ms.Log(newEmployee.ToJson()); + } + + history.Add($"{clockEntry.EmployeeId}-{employees[clockEntry.EmployeeId].Code} - {clockEntry.NewState} - {clockEntry.ChangeTime}"); + //Console.WriteLine($"{clockEntry.EmployeeId}-{employees[clockEntry.EmployeeId].Code} - {clockEntry.NewState} - {clockEntry.ChangeTime}"); + } + ItemSelector selectorTemp = new ItemSelector(ms); + selectorTemp.SetTitle("Clock History"); + selectorTemp.SelectItemFromList(history.ToArray()); + //Console.ReadKey(); + } } catch (Exception ex) { await messageBox.ShowAsync("Error", new List { ex.Message }); } - + + + /* string input = ""; if (command.Contains("login")) @@ -140,4 +175,15 @@ public class Tester */ } } +} +public class ClockEntry +{ + public int EmployeeId { get; set; } + public int NewState { get; set; } + public DateTime ChangeTime { get; set; } +} +public class ClockHistoryResponse +{ + public bool error { get; set; } + public List data { get; set; } = new(); } \ No newline at end of file