diff --git a/pom.xml b/pom.xml index 8bd709f..5b48f90 100644 --- a/pom.xml +++ b/pom.xml @@ -4,7 +4,7 @@ 4.0.0 de.mbremer buerokalender - 1.0.1 + 1.1.0 3.8.1 true @@ -103,6 +103,11 @@ bootstrap-icons 1.5.0 + + org.webjars + popper.js + 2.9.2 + org.projectlombok lombok diff --git a/src/main/java/de/mbremer/extension/CommonExtensions.java b/src/main/java/de/mbremer/extension/CommonExtensions.java index 1ed6539..17c2a34 100644 --- a/src/main/java/de/mbremer/extension/CommonExtensions.java +++ b/src/main/java/de/mbremer/extension/CommonExtensions.java @@ -20,4 +20,8 @@ public class CommonExtensions { public static int plus(int a, int b) { return a + b; } + + public static String rightPad(String str, int length) { + return String.format("%1$-" + length + "s", str); + } } diff --git a/src/main/java/de/mbremer/kalender/Event.java b/src/main/java/de/mbremer/kalender/Event.java new file mode 100644 index 0000000..94fafe3 --- /dev/null +++ b/src/main/java/de/mbremer/kalender/Event.java @@ -0,0 +1,35 @@ +package de.mbremer.kalender; + +import lombok.Getter; + +import javax.validation.constraints.NotNull; +import java.time.LocalDate; +import java.time.LocalDateTime; +import java.time.format.DateTimeFormatter; +import java.util.UUID; + +@Getter +public class Event { + private final String created; + private final String dtStart; + private final String dtEnd; + private final String uid; + + public Event(@NotNull LocalDateTime created, LocalDate date) { + this.created = created.format(DateTimeFormatter.ISO_LOCAL_DATE_TIME) + .replaceAll("[-:]", "") + "Z"; + this.dtStart = date.format(DateTimeFormatter.ISO_LOCAL_DATE) + .replace("-", ""); + this.dtEnd = date.plusDays(1).format(DateTimeFormatter.ISO_LOCAL_DATE) + .replace("-", ""); + this.uid = UUID.randomUUID().toString() + "@buerokalender"; + } + + public String getLastModified() { + return created; + } + + public String getDtStamp() { + return created; + } +} diff --git a/src/main/java/de/mbremer/kalender/KalenderResource.java b/src/main/java/de/mbremer/kalender/KalenderResource.java index fa04acd..055d81c 100644 --- a/src/main/java/de/mbremer/kalender/KalenderResource.java +++ b/src/main/java/de/mbremer/kalender/KalenderResource.java @@ -1,6 +1,7 @@ package de.mbremer.kalender; import de.mbremer.secutity.User; +import io.quarkus.qute.Location; import io.quarkus.qute.Template; import io.quarkus.qute.TemplateInstance; import io.quarkus.security.identity.SecurityIdentity; @@ -14,6 +15,7 @@ import javax.transaction.Transactional; import javax.ws.rs.*; import javax.ws.rs.core.MediaType; import java.time.LocalDate; +import java.time.LocalDateTime; import java.util.List; import java.util.stream.Collectors; import java.util.stream.Stream; @@ -28,35 +30,32 @@ public class KalenderResource { SecurityIdentity identity; @Inject Template kalenderpage; + @Inject + @Location("export/textExport.txt") + Template textExport; + @Location("export/icsExport.ics") + Template icsExport; @Path("") @GET @Produces(MediaType.TEXT_HTML) - public TemplateInstance kalender() { - return kalenderWithOffset(0); - } - - @Path("offset/{weeks}") - @GET - @Produces(MediaType.TEXT_HTML) - public TemplateInstance kalenderWithOffset(@PathParam("weeks") int offsetInWeeks) { - User currentUser = User.find("username", identity.getPrincipal().getName()).singleResult(); - LocalDate today = LocalDate.now(); - - LocalDate montag = today.minusDays(today.getDayOfWeek().getValue() - 1).plusDays(7 * offsetInWeeks); - - List week = getWeek(currentUser, montag); + public TemplateInstance kalender(@QueryParam("offset") @DefaultValue("0") int offsetInWeeks) { + List week = getWeek(offsetInWeeks); return kalenderpage - .data("today", today) + .data("today", LocalDate.now()) .data("offset", offsetInWeeks) .data("week", week); } - private List getWeek(User currentUser, LocalDate start) { + private List getWeek(int offsetInWeeks) { + User currentUser = getCurrentUser(); + LocalDate today = LocalDate.now(); + LocalDate montag = today.minusDays(today.getDayOfWeek().getValue() - 1).plusDays(7 * offsetInWeeks); + return Stream.iterate(0, i -> i < 5, i -> ++i) .map(d -> { - LocalDate day = start.plusDays(d); + LocalDate day = montag.plusDays(d); KalenderTag tag = (KalenderTag) KalenderTag.find("day", day).singleResultOptional().orElse(new KalenderTag(day)); tag.setCurrentUserInOffice(currentUser.equals(tag.getInOffice())); tag.setToday(LocalDate.now().equals(day)); @@ -65,6 +64,14 @@ public class KalenderResource { .collect(Collectors.toList()); } + private List getEvents(int offsetInWeeks) { + List week = getWeek(offsetInWeeks); + return week.stream() + .filter(d -> d.isCurrentUserInOffice()) + .map(d-> new Event(LocalDateTime.now(), d.getDay())) + .collect(Collectors.toList()); + } + @POST @Transactional @Consumes(MediaType.MULTIPART_FORM_DATA) @@ -73,7 +80,7 @@ public class KalenderResource { @QueryParam("offset") int offsetInWeeks, @MultipartForm KalenderTagForm kalenderForm) { LocalDate dayParsed = LocalDate.parse(day); - User currentUser = User.find("username", identity.getPrincipal().getName()).singleResult(); + User currentUser = getCurrentUser(); try { KalenderTag tag = KalenderTag.find("day", dayParsed).singleResult(); if (kalenderForm.isInOffice() && tag.getInOffice() == null) { @@ -87,6 +94,24 @@ public class KalenderResource { tag.persist(); } - return kalenderWithOffset(offsetInWeeks); + return kalender(offsetInWeeks); + } + + private User getCurrentUser() { + return User.find("username", identity.getPrincipal().getName()).singleResult(); + } + + @GET + @Produces(MediaType.TEXT_PLAIN) + @Path("export/txt") + public TemplateInstance exportTxt(@QueryParam("offset") int offset) { + return textExport.data("week", getWeek(offset)); + } + + @GET + @Produces("text/calendar") + @Path("export/ics") + public TemplateInstance exportIcs(@QueryParam("offset") int offset) { + return icsExport.data("events", getEvents(offset)); } } diff --git a/src/main/resources/templates/base.html b/src/main/resources/templates/base.html index ea75a53..e359813 100644 --- a/src/main/resources/templates/base.html +++ b/src/main/resources/templates/base.html @@ -28,6 +28,7 @@ {#if info}{/if} {#insert contents}No contents!{/} + \ No newline at end of file diff --git a/src/main/resources/templates/export/icsExport.ics b/src/main/resources/templates/export/icsExport.ics new file mode 100644 index 0000000..92b6e3d --- /dev/null +++ b/src/main/resources/templates/export/icsExport.ics @@ -0,0 +1,19 @@ +BEGIN:VCALENDAR +VERSION:2.0 +METHOD:PUBLISH +PRODID:-//kalender.bremer.rocks//iCal Generator//DE +{#for event in events} +BEGIN:VEVENT +CREATED:{event.created} +LAST-MODIFIED:{event.lastModified} +DTSTAMP:{event.dtStamp} +SUMMARY:VIT +DTSTART;VALUE=DATE:{event.dtStart} +DTEND;VALUE=DATE:{event.dtEnd} +URL:https://kalender.bremer.rocks +DESCRIPTION:Arbeit im VIT-Buero +TRANSP:TRANSPARENT +UID:{event.uid} +END:VEVENT +{/for} +END:VCALENDAR \ No newline at end of file diff --git a/src/main/resources/templates/export/textExport.txt b/src/main/resources/templates/export/textExport.txt new file mode 100644 index 0000000..64cf8d7 --- /dev/null +++ b/src/main/resources/templates/export/textExport.txt @@ -0,0 +1,3 @@ +{#for day in week} +{day.day.formatCommon.rightPad(30)} {#if day.inOffice}{day.inOffice.username}{/if} +{/for} \ No newline at end of file diff --git a/src/main/resources/templates/kalenderpage.html b/src/main/resources/templates/kalenderpage.html index 8155233..46fb3db 100644 --- a/src/main/resources/templates/kalenderpage.html +++ b/src/main/resources/templates/kalenderpage.html @@ -6,17 +6,17 @@ Heute ist {today.formatCommon} -
+
-
+
@@ -57,5 +57,17 @@
+
+
+ + +
+
+ {/contents} {/include} \ No newline at end of file diff --git a/src/test/java/de/mbremer/extension/CommonExtensionsTest.java b/src/test/java/de/mbremer/extension/CommonExtensionsTest.java index 6ae2a96..9e65882 100644 --- a/src/test/java/de/mbremer/extension/CommonExtensionsTest.java +++ b/src/test/java/de/mbremer/extension/CommonExtensionsTest.java @@ -12,4 +12,9 @@ class CommonExtensionsTest { void testFormatCommon() { assertEquals("Sonntag, 4.7.2021", CommonExtensions.formatCommon(LocalDate.of(2021, 7, 4))); } + + @Test + void testRightPad() { + assertEquals("foo ", CommonExtensions.rightPad("foo", 5)); + } } \ No newline at end of file diff --git a/src/test/java/de/mbremer/kalender/EventTest.java b/src/test/java/de/mbremer/kalender/EventTest.java new file mode 100644 index 0000000..dff041b --- /dev/null +++ b/src/test/java/de/mbremer/kalender/EventTest.java @@ -0,0 +1,34 @@ +package de.mbremer.kalender; + +import org.junit.jupiter.api.Test; + +import java.time.LocalDate; +import java.time.LocalDateTime; + +import static org.junit.jupiter.api.Assertions.*; + +class EventTest { + @Test + void getCreated() { + Event event = new Event(LocalDateTime.of(2021, 7, 18, 14, 25, 45), LocalDate.of(2022, 1, 2)); + + assertEquals("20210718T142545Z", event.getCreated()); + assertEquals("20210718T142545Z", event.getLastModified()); + assertEquals("20210718T142545Z", event.getDtStamp()); + } + + @Test + void getDtstartEnd() { + Event event = new Event(LocalDateTime.of(2021, 7, 18, 14, 25, 45), LocalDate.of(2022, 1, 2)); + + assertEquals("20220102", event.getDtStart()); + assertEquals("20220103", event.getDtEnd()); + } + + @Test + void getUid() { + Event event = new Event(LocalDateTime.of(2021, 7, 18, 14, 25, 45), LocalDate.of(2022, 1, 2)); + + assertTrue(event.getUid().matches("([a-f0-9]{8}(-[a-f0-9]{4}){4}[a-f0-9]{8})@buerokalender")); + } +} \ No newline at end of file