using cwebplusApp.Shared.Models; using Microsoft.JSInterop; using Newtonsoft.Json; using System; using System.Collections.Generic; using System.Threading.Tasks; namespace cwebplusApp.Shared.Services { public sealed class ReportRepositoryService { private const string KeyNameFoundReports = "foundReportRepository"; private const string KeyNameMissingReports = "missingReportRepository"; private readonly IJSRuntime jsRuntime; private bool initialized; public event EventHandler Changed; public ReportRepositoryService(IJSRuntime jsRuntime) { this.jsRuntime = jsRuntime; } public async Task SaveReport(ReportRepositoryItem reportRepositoryItem) { if (reportRepositoryItem is FoundReportRepositoryItem fItem) { await SaveFoundReport(fItem); } else if (reportRepositoryItem is MissingReportRepositoryItem mItem) { await SaveMissingReport(mItem); } } public async ValueTask> GetFoundReports() { // Register the Storage event handler. This handler calls OnStorageUpdated when the storage changed. // This way, you can reload the settings when another instance of the application (tab / window) save the settings if (!initialized) { // Create a reference to the current object, so the JS function can call the public method "OnStorageUpdated" var reference = DotNetObjectReference.Create(this); await this.jsRuntime.InvokeVoidAsync("BlazorRegisterStorageEvent", reference); this.initialized = true; } // Read the JSON string that contains the data from the local storage List result; var str = await this.jsRuntime.InvokeAsync("BlazorGetLocalStorage", KeyNameFoundReports); if (str != null) { result = JsonConvert.DeserializeObject>(str) ?? new(); } else { result = new(); } return result; } public async ValueTask> GetPendingFoundReports() { List pendingFoundReps = new(); List foundReps = await GetFoundReports(); foreach (FoundReportRepositoryItem report in foundReps) { if (!report.Transmitted) { pendingFoundReps.Add(report); } } return pendingFoundReps; } public async ValueTask> GetMissingReports() { // Register the Storage event handler. This handler calls OnStorageUpdated when the storage changed. // This way, you can reload the settings when another instance of the application (tab / window) save the settings if (!initialized) { // Create a reference to the current object, so the JS function can call the public method "OnStorageUpdated" var reference = DotNetObjectReference.Create(this); await this.jsRuntime.InvokeVoidAsync("BlazorRegisterStorageEvent", reference); this.initialized = true; } // Read the JSON string that contains the data from the local storage List result; var str = await this.jsRuntime.InvokeAsync("BlazorGetLocalStorage", KeyNameMissingReports); if (str != null) { result = JsonConvert.DeserializeObject>(str) ?? new(); } else { result = new(); } return result; } public async ValueTask> GetPendingMissingReports() { List pendingMissingReps = new(); List missingReps = await GetMissingReports(); foreach (MissingReportRepositoryItem report in missingReps) { if (!report.Transmitted) { pendingMissingReps.Add(report); } } return pendingMissingReps; } public async Task SaveFoundReport(FoundReportRepositoryItem foundReportRepositoryItem) { List foundReps = await GetFoundReports(); foundReps.Remove(foundReportRepositoryItem); foundReps.Add(foundReportRepositoryItem); var json = JsonConvert.SerializeObject(foundReps); await jsRuntime.InvokeVoidAsync("BlazorSetLocalStorage", KeyNameFoundReports, json); } public async Task SaveMissingReport(MissingReportRepositoryItem missingReportRepositoryItem) { List missingReps = await GetMissingReports(); missingReps.Remove(missingReportRepositoryItem); missingReps.Add(missingReportRepositoryItem); var json = JsonConvert.SerializeObject(missingReps); await jsRuntime.InvokeVoidAsync("BlazorSetLocalStorage", KeyNameMissingReports, json); } public async ValueTask GetNbrOfPendingReports() { List foundReportRepositoryItems = await GetPendingFoundReports(); List missingReportRepositoryItems = await GetPendingMissingReports(); return foundReportRepositoryItems.Count + missingReportRepositoryItems.Count; } // This method is called from BlazorRegisterStorageEvent when the storage changed [JSInvokable] public void OnStorageUpdated(string key) { if (key == KeyNameMissingReports || key == KeyNameFoundReports) { // Reset the settings. The next call to Get will reload the data Changed?.Invoke(this, EventArgs.Empty); } } public static long GetCurrentTimeInMillis() { return DateTime.Now.Ticks / TimeSpan.TicksPerMillisecond; } public static string GetCurrentDateTimeFromMillis(long millis) { TimeSpan time = TimeSpan.FromMilliseconds(millis); DateTime date = new DateTime() + time; return date.ToString("dd.MM.yyyy HH:mm:ss"); } } }