feat: sync all-day events for shifts without time (Frei, holidays, etc.)
Both Google Calendar and Nextcloud CalDAV now create all-day events for shifts that have no MorningTime or AfternoonTime configured, instead of silently skipping them. Fixes month-boundary crash on day 31 by using DateOnly.AddDays(1) for the end date. Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
This commit is contained in:
parent
0520ce3847
commit
d00f5ea8b7
2 changed files with 49 additions and 0 deletions
|
|
@ -84,7 +84,12 @@ public class GoogleCalendarService(IHttpContextAccessor httpContextAccessor, ICo
|
|||
var date = shiftWithTransport.Date;
|
||||
|
||||
if (string.IsNullOrEmpty(shift.MorningTime) && string.IsNullOrEmpty(shift.AfternoonTime))
|
||||
{
|
||||
var eventData = CalendarEventBuilder.BuildEventContent(shift, null);
|
||||
var allDayEvent = CreateAllDayGoogleEvent(eventData, DateOnly.FromDateTime(date));
|
||||
await CalendarEventBuilder.ExecuteWithRetryAsync(async () => await service.Events.Insert(allDayEvent, calendarId).ExecuteAsync());
|
||||
return;
|
||||
}
|
||||
|
||||
if (!string.IsNullOrEmpty(shift.MorningTime))
|
||||
{
|
||||
|
|
@ -103,6 +108,26 @@ public class GoogleCalendarService(IHttpContextAccessor httpContextAccessor, ICo
|
|||
}
|
||||
}
|
||||
|
||||
private static Event CreateAllDayGoogleEvent(CalendarEventData eventData, DateOnly date)
|
||||
{
|
||||
var dateStr = date.ToString("yyyy-MM-dd");
|
||||
var nextDateStr = date.AddDays(1).ToString("yyyy-MM-dd");
|
||||
return new Event
|
||||
{
|
||||
Summary = eventData.Summary,
|
||||
Start = new EventDateTime { Date = dateStr },
|
||||
End = new EventDateTime { Date = nextDateStr },
|
||||
ExtendedProperties = new Event.ExtendedPropertiesData
|
||||
{
|
||||
Private__ = new Dictionary<string, string>
|
||||
{
|
||||
["shiftSchedulerEvent"] = "true",
|
||||
["shiftName"] = eventData.Summary
|
||||
}
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
private static Event CreateGoogleEvent(CalendarEventData eventData, DateTimeOffset startTime, DateTimeOffset endTime)
|
||||
{
|
||||
return new Event
|
||||
|
|
|
|||
|
|
@ -162,7 +162,16 @@ public class NextcloudCalendarService(
|
|||
var date = shiftWithTransport.Date;
|
||||
|
||||
if (string.IsNullOrEmpty(shift.MorningTime) && string.IsNullOrEmpty(shift.AfternoonTime))
|
||||
{
|
||||
var uid = $"shift-{SanitizeForUid(shift.Name)}-{date:yyyyMMdd}-allday";
|
||||
var eventData = CalendarEventBuilder.BuildEventContent(shift, null);
|
||||
var icsContent = BuildAllDayIcsContent(uid, eventData, DateOnly.FromDateTime(date));
|
||||
var putRequest = CreateRequest(HttpMethod.Put, $"{calendarId}{Uri.EscapeDataString(uid)}.ics");
|
||||
putRequest.Content = new StringContent(icsContent, Encoding.UTF8, "text/calendar");
|
||||
(await client.SendAsync(putRequest)).EnsureSuccessStatusCode();
|
||||
await Task.Delay(300);
|
||||
continue;
|
||||
}
|
||||
|
||||
if (!string.IsNullOrEmpty(shift.MorningTime))
|
||||
{
|
||||
|
|
@ -194,6 +203,21 @@ public class NextcloudCalendarService(
|
|||
}
|
||||
}
|
||||
|
||||
private static string BuildAllDayIcsContent(string uid, CalendarEventData eventData, DateOnly date)
|
||||
{
|
||||
var calendar = new Calendar();
|
||||
var vevent = new CalendarEvent
|
||||
{
|
||||
Uid = uid,
|
||||
Summary = eventData.Summary,
|
||||
DtStart = new CalDateTime(date.Year, date.Month, date.Day),
|
||||
DtEnd = new CalDateTime(date.AddDays(1).Year, date.AddDays(1).Month, date.AddDays(1).Day)
|
||||
};
|
||||
vevent.Properties.Add(new Ical.Net.CalendarProperty("X-SHIFT-SCHEDULER", "TRUE"));
|
||||
calendar.Events.Add(vevent);
|
||||
return new CalendarSerializer().SerializeToString(calendar)!;
|
||||
}
|
||||
|
||||
private static string BuildIcsContent(string uid, CalendarEventData eventData, DateTimeOffset startTime, DateTimeOffset endTime)
|
||||
{
|
||||
var calendar = new Calendar();
|
||||
|
|
|
|||
Loading…
Reference in a new issue