From 656d39f43e8eebe8128c2b9bdbc2c2c58ed5bf82 Mon Sep 17 00:00:00 2001 From: Daniel Pichler Date: Thu, 25 Dec 2025 11:39:44 +0100 Subject: [PATCH] Less requests to get Data faster Load settings with `GetEntryWithSettingsAsync`, update `Hours` and `ViewModels`. --- .../Interfaces/IHoursService.cs | 1 + Jugenddienst Stunden/Services/HoursService.cs | 9 ++++ Jugenddienst Stunden/Types/BaseResponse.cs | 5 ++- Jugenddienst Stunden/Types/Hours.cs | 41 ++++++++++++++----- .../ViewModels/StundeViewModel.cs | 35 ++++++++++------ .../ViewModels/StundenViewModel.cs | 6 +-- 6 files changed, 69 insertions(+), 28 deletions(-) diff --git a/Jugenddienst Stunden/Interfaces/IHoursService.cs b/Jugenddienst Stunden/Interfaces/IHoursService.cs index 7f72f91..1b8424e 100644 --- a/Jugenddienst Stunden/Interfaces/IHoursService.cs +++ b/Jugenddienst Stunden/Interfaces/IHoursService.cs @@ -13,4 +13,5 @@ public interface IHoursService { Task GetEntryAsync(int id); Task SaveEntryAsync(DayTime stunde); Task DeleteEntryAsync(DayTime stunde); + Task<(DayTime dayTime, Settings settings, List existingDayTimes)> GetEntryWithSettingsAsync(int id); } \ No newline at end of file diff --git a/Jugenddienst Stunden/Services/HoursService.cs b/Jugenddienst Stunden/Services/HoursService.cs index 5885789..aba2755 100644 --- a/Jugenddienst Stunden/Services/HoursService.cs +++ b/Jugenddienst Stunden/Services/HoursService.cs @@ -48,6 +48,15 @@ internal class HoursService : IHoursService { public async Task GetEntryAsync(int id) => await _repo.LoadEntry(id); + public async Task<(DayTime dayTime, Settings settings, List existingDayTimes)> GetEntryWithSettingsAsync(int id) { + //var stunde = await _repo.LoadEntry(id); + //var (existingDayTimes, settings) = await GetDayWithSettingsAsync(stunde.Day); + //return (stunde, settings, existingDayTimes); + string q = $"id={id}"; + var baseRes = await _repo.LoadBase(q); + return (baseRes.daytime ?? new DayTime(), baseRes.settings, baseRes.daytimes ?? new List()); + } + public async Task SaveEntryAsync(DayTime stunde) { var settings = await _repo.LoadSettings(); _validator.Validate(stunde, settings); diff --git a/Jugenddienst Stunden/Types/BaseResponse.cs b/Jugenddienst Stunden/Types/BaseResponse.cs index 6b97982..c57398f 100644 --- a/Jugenddienst Stunden/Types/BaseResponse.cs +++ b/Jugenddienst Stunden/Types/BaseResponse.cs @@ -1,4 +1,5 @@ using Jugenddienst_Stunden.Models; +using Jugenddienst_Stunden.Types; namespace Jugenddienst_Stunden.Types; @@ -8,12 +9,12 @@ internal class BaseResponse { /// /// Monatsübersicht /// - public Hours hour { get; set; } + public Types.Hours hour { get; set; } /// /// Stundenliste ... für die Katz? /// - public List hours { get; set; } + public List hours { get; set; } /// /// Liste der Stundeneinträge diff --git a/Jugenddienst Stunden/Types/Hours.cs b/Jugenddienst Stunden/Types/Hours.cs index 69d64d8..a211b10 100644 --- a/Jugenddienst Stunden/Types/Hours.cs +++ b/Jugenddienst Stunden/Types/Hours.cs @@ -4,24 +4,45 @@ using System.Collections.ObjectModel; namespace Jugenddienst_Stunden.Types; public partial class Hours : ObservableObject { - public double? Zeit; + /// + /// Total time in seconds for the current context. + /// "zeit" is used by the API to represent the current recorded time value. + /// + public int zeit; - public double? Nominal; + /// + /// Nominal working time expectation (e.g. seconds per day or month depending on API semantics). + /// Represents the expected amount of time to be worked. + /// + public int nominal; - //public Dictionary nominal_day_api; + /// + /// List of nominal day records returned by the API. + /// May be null when the API does not provide per-day nominal data. + /// public List? Nominal_day_api; - //public Dictionary nominal_week_api; + /// + /// List of nominal week records returned by the API. + /// May be null when the API does not provide per-week nominal data. + /// public List? Nominal_week_api; - //public List time_line; - public double? Zeit_total; - - //https://stackoverflow.com/questions/29449641/deserialize-json-when-a-value-can-be-an-object-or-an-empty-array/29450279#29450279 - //[JsonConverter(typeof(JsonSingleOrEmptyArrayConverter))] - //public Dictionary zeit_total_daily; + /// + /// Total time in seconds reported by the API for the current period. Nullable if not provided. + /// + public double? zeit_total; + /// + /// Daily total time values returned by the API. + /// Each entry represents a day with its associated time value. + /// public List zeit_total_daily_api; + + /// + /// Collection of daytime entries representing individual recorded time slots or events. + /// Nullable when the API returns no detailed daytime information. + /// public List? daytime; //public List wochensumme; diff --git a/Jugenddienst Stunden/ViewModels/StundeViewModel.cs b/Jugenddienst Stunden/ViewModels/StundeViewModel.cs index 54b90b2..c99e1f4 100644 --- a/Jugenddienst Stunden/ViewModels/StundeViewModel.cs +++ b/Jugenddienst Stunden/ViewModels/StundeViewModel.cs @@ -86,7 +86,7 @@ public partial class StundeViewModel : ObservableObject, IQueryAttributable { alertService.AlertRaised += (s, msg) => AlertEvent?.Invoke(this, msg); } - LoadSettingsAsync(); + //LoadSettingsAsync(); } private async void LoadSettingsAsync() { @@ -105,6 +105,16 @@ public partial class StundeViewModel : ObservableObject, IQueryAttributable { } } + private async void UpdateSettingsAsync(Settings settings) { + GlobalVar.Settings = settings; + OptionsGemeinde = settings.Gemeinden; + OptionsProjekt = settings.Projekte; + OptionsFreistellung = settings.Freistellungen; + + GemeindeAktivSet = settings.GemeindeAktivSet; + ProjektAktivSet = settings.ProjektAktivSet; + } + async Task Save() { bool exceptionOccurred = false; bool proceed = true; @@ -185,7 +195,9 @@ public partial class StundeViewModel : ObservableObject, IQueryAttributable { if (query.ContainsKey("load")) { //DateTime heute = DateTime.Now; try { - var entry = await _hoursService.GetEntryAsync(Convert.ToInt32(query["load"])); + //var entry = await _hoursService.GetEntryAsync(Convert.ToInt32(query["load"])); + var (entry, settings, daytimes) = await _hoursService.GetEntryWithSettingsAsync(Convert.ToInt32(query["load"])); + UpdateSettingsAsync(settings); DayTime = entry; DayTime.TimeSpanVon = entry.Begin.ToTimeSpan(); @@ -208,13 +220,16 @@ public partial class StundeViewModel : ObservableObject, IQueryAttributable { OnPropertyChanged(nameof(SubTitle)); FreistellungEnabled = !DayTime.Approved; + + DayTimes = daytimes; + OnPropertyChanged(nameof(DayTimes)); } catch (Exception e) { AlertEvent?.Invoke(this, e.Message); } finally { //Evtl. noch die anderen Zeiten des gleichen Tages holen - var day = await _hoursService.GetDayWithSettingsAsync(DayTime.Day); - DayTimes = day.dayTimes; - OnPropertyChanged(nameof(DayTimes)); + //var day = await _hoursService.GetDayWithSettingsAsync(DayTime.Day); + //DayTimes = day.dayTimes; + //OnPropertyChanged(nameof(DayTimes)); } //OnPropertyChanged(nameof(DayTime)); @@ -227,15 +242,9 @@ public partial class StundeViewModel : ObservableObject, IQueryAttributable { //Bei neuem Eintrag die vorhandenen des gleichen Tages anzeigen try { var (list, settings) = await _hoursService.GetDayWithSettingsAsync(_date); - GlobalVar.Settings = settings; + UpdateSettingsAsync(settings); DayTimes = list; - - OptionsGemeinde = settings.Gemeinden; - OptionsProjekt = settings.Projekte; - OptionsFreistellung = settings.Freistellungen; - - GemeindeAktivSet = settings.GemeindeAktivSet; - ProjektAktivSet = settings.ProjektAktivSet; + } catch (Exception) { //Ein Tag ohne Einträge gibt eine Fehlermeldung, //die soll aber ignoriert werden, weil beim Neueintrag ist das ja Wurscht diff --git a/Jugenddienst Stunden/ViewModels/StundenViewModel.cs b/Jugenddienst Stunden/ViewModels/StundenViewModel.cs index b394fa3..bb8b4ef 100644 --- a/Jugenddienst Stunden/ViewModels/StundenViewModel.cs +++ b/Jugenddienst Stunden/ViewModels/StundenViewModel.cs @@ -101,14 +101,14 @@ public partial class StundenViewModel : ObservableObject, IQueryAttributable, IN /// Monatsübersicht: Geleistete Stunden /// public double? ZeitCalculated { - get => Hours.Zeit_total; + get => Hours.zeit_total; } /// /// Monatsübersicht: Sollstunden /// public double? Nominal { - get => Hours.Nominal; + get => Hours.nominal; } /// @@ -287,7 +287,7 @@ public partial class StundenViewModel : ObservableObject, IQueryAttributable, IN //Nach der Tagessumme die anderen Tage anhängen if (DayTimes != null) { - var more = await _hoursService.GetDayRangeAsync(date, date.AddDays(3)); + var more = await _hoursService.GetDayRangeAsync(date.AddDays(1), date.AddDays(3)); if (more != null && more.Count > 0) { await MainThread.InvokeOnMainThreadAsync(() =>