using Elternbeirat.Contracts; using Elternbeirat.PocketBase; using Microsoft.AspNetCore.Components; namespace Elternbeirat.Web.Features.Embeds; public partial class EventsEmbed { // Number of upcoming events shown in the teaser; the full list is one link away. private const int TeaserCount = 3; [LoggerMessage( Level = LogLevel.Warning, Message = "Could not load events for an embed from PocketBase; the teaser is omitted.")] private static partial void LogSourceUnavailable( ILogger logger, Exception exception); [Inject] private PocketBaseClient PocketBase { get; set; } = null!; [Inject] private ILogger Logger { get; set; } = null!; [CascadingParameter] private HttpContext? HttpContext { get; set; } private IReadOnlyList _upcoming = []; protected override async Task OnInitializedAsync() { IReadOnlyList events; try { events = await PocketBase.GetEventsAsync(HttpContext?.RequestAborted ?? CancellationToken.None); } catch (PocketBaseUnavailableException exception) { // Only part of the page fails: omit the teaser, keep the page (and its // 200) intact. A missing teaser is degraded, not broken. LogSourceUnavailable(Logger, exception); return; } // Teaser: the soonest upcoming events, earliest first. An event earlier // today still counts as upcoming. var today = DateOnly.FromDateTime(DateTime.Today); _upcoming = [ .. events .Where(@event => DateOnly.FromDateTime(@event.Start) >= today) .OrderBy(@event => @event.Start) .Take(TeaserCount) ]; } }