From 51a9f9272e4df414b95a916172f6ed349bbe8b28 Mon Sep 17 00:00:00 2001 From: Stephan Richter Date: Tue, 28 Jul 2026 09:24:26 +0200 Subject: [PATCH] preparing to load events Signed-off-by: Stephan Richter --- .../umbrella/messagebus/events/TaskEvent.java | 4 ++ .../umbrella/core/api/UserService.java | 2 + .../umbrella/core/constants/Text.java | 1 + .../umbrella/journal/JournalDb.java | 6 +++ .../umbrella/journal/JournalModule.java | 38 ++++++++++++++++ .../srsoftware/umbrella/journal/SqliteDb.java | 43 ++++++++++++++++++- .../srsoftware/umbrella/user/UserModule.java | 12 ++++++ 7 files changed, 104 insertions(+), 2 deletions(-) diff --git a/bus/src/main/java/de/srsoftware/umbrella/messagebus/events/TaskEvent.java b/bus/src/main/java/de/srsoftware/umbrella/messagebus/events/TaskEvent.java index b6d5c008..f11e9b3b 100644 --- a/bus/src/main/java/de/srsoftware/umbrella/messagebus/events/TaskEvent.java +++ b/bus/src/main/java/de/srsoftware/umbrella/messagebus/events/TaskEvent.java @@ -10,6 +10,9 @@ import static de.srsoftware.umbrella.messagebus.events.Event.EventType.MEMBER_AD import de.srsoftware.umbrella.core.constants.Field; import de.srsoftware.umbrella.core.model.*; + +import java.sql.ResultSet; +import java.sql.SQLException; import java.util.Collection; import java.util.List; import java.util.Map; @@ -96,6 +99,7 @@ public class TaskEvent extends Event{ return t("You can view/edit this task at {base_url}/task/{id}/view",ID,payload().id()); } + @Override public Translatable subject() { return switch (eventType()){ diff --git a/core/src/main/java/de/srsoftware/umbrella/core/api/UserService.java b/core/src/main/java/de/srsoftware/umbrella/core/api/UserService.java index e8073262..09131fdd 100644 --- a/core/src/main/java/de/srsoftware/umbrella/core/api/UserService.java +++ b/core/src/main/java/de/srsoftware/umbrella/core/api/UserService.java @@ -8,6 +8,7 @@ import de.srsoftware.umbrella.core.model.Session; import de.srsoftware.umbrella.core.model.Token; import de.srsoftware.umbrella.core.model.UmbrellaUser; import java.util.Collection; +import java.util.HashMap; import java.util.Map; import java.util.Optional; @@ -15,6 +16,7 @@ public interface UserService { void dropSession(Token token) throws UmbrellaException; Session extend(Session session) throws UmbrellaException; Map list(Integer start, Integer limit, Collection ids) throws UmbrellaException; + HashMap loader(); Session load(Token token) throws UmbrellaException; UmbrellaUser load(Session session) throws UmbrellaException; Optional load(EmailAddress email) throws UmbrellaException; diff --git a/core/src/main/java/de/srsoftware/umbrella/core/constants/Text.java b/core/src/main/java/de/srsoftware/umbrella/core/constants/Text.java index 2e7fd581..5374a9aa 100644 --- a/core/src/main/java/de/srsoftware/umbrella/core/constants/Text.java +++ b/core/src/main/java/de/srsoftware/umbrella/core/constants/Text.java @@ -30,6 +30,7 @@ public class Text { public static final String EMAILS_FOR_RECEIVER = "emails for {email}"; public static final String EVALUATION = "evaluation"; + public static final String EVENT_LIST = "event list"; public static final String FILES = "files"; diff --git a/journal/src/main/java/de/srsoftware/umbrella/journal/JournalDb.java b/journal/src/main/java/de/srsoftware/umbrella/journal/JournalDb.java index 69a08f0e..6ba0f02f 100644 --- a/journal/src/main/java/de/srsoftware/umbrella/journal/JournalDb.java +++ b/journal/src/main/java/de/srsoftware/umbrella/journal/JournalDb.java @@ -1,8 +1,14 @@ /* © SRSoftware 2025 */ package de.srsoftware.umbrella.journal; +import de.srsoftware.umbrella.core.model.UmbrellaUser; import de.srsoftware.umbrella.messagebus.events.Event; +import java.util.HashMap; +import java.util.List; + public interface JournalDb { void logEvent(Event event); + + List> list(String module, long entityId, HashMap userLoader); } diff --git a/journal/src/main/java/de/srsoftware/umbrella/journal/JournalModule.java b/journal/src/main/java/de/srsoftware/umbrella/journal/JournalModule.java index 0f2d450e..8ee2ffe7 100644 --- a/journal/src/main/java/de/srsoftware/umbrella/journal/JournalModule.java +++ b/journal/src/main/java/de/srsoftware/umbrella/journal/JournalModule.java @@ -2,17 +2,33 @@ package de.srsoftware.umbrella.journal; import static de.srsoftware.umbrella.core.ConnectionProvider.connect; +import static de.srsoftware.umbrella.core.ModuleRegistry.userService; +import static de.srsoftware.umbrella.core.constants.Path.PARENT_CANDIDATES; +import static de.srsoftware.umbrella.core.constants.Path.TAGGED; +import static de.srsoftware.umbrella.core.exceptions.UmbrellaException.invalidField; import static de.srsoftware.umbrella.core.exceptions.UmbrellaException.missingField; import static de.srsoftware.umbrella.journal.Constants.CONFIG_DATABASE; import static de.srsoftware.umbrella.messagebus.MessageBus.messageBus; import static java.lang.System.Logger.Level.DEBUG; +import com.sun.net.httpserver.HttpExchange; import de.srsoftware.configuration.Configuration; +import de.srsoftware.tools.Path; +import de.srsoftware.tools.SessionToken; import de.srsoftware.umbrella.core.BaseHandler; import de.srsoftware.umbrella.core.ModuleRegistry; +import de.srsoftware.umbrella.core.constants.Field; +import de.srsoftware.umbrella.core.constants.Text; +import de.srsoftware.umbrella.core.exceptions.UmbrellaException; +import de.srsoftware.umbrella.core.model.Token; +import de.srsoftware.umbrella.core.model.UmbrellaUser; import de.srsoftware.umbrella.messagebus.EventListener; import de.srsoftware.umbrella.messagebus.events.Event; +import java.io.IOException; +import java.util.HashMap; +import java.util.Optional; + public class JournalModule extends BaseHandler implements EventListener { @@ -26,6 +42,28 @@ public class JournalModule extends BaseHandler implements EventListener { messageBus().register(this); } + @Override + public boolean doGet(Path path, HttpExchange ex) throws IOException { + addCors(ex); + try { + Optional token = SessionToken.from(ex).map(Token::of); + var user = userService().loadUser(token); + if (user.isEmpty()) return unauthorized(ex); + var module = path.pop(); + if (module == null) throw missingField(Field.MODULE); + var head = path.pop(); + if (head == null) throw missingField(Field.ENTITY_ID); + try { + var entityId = Long.parseLong(head); + journalDb.list(module, entityId, userService().loader()); + } catch (NumberFormatException e) { + throw invalidField(Field.ENTITY_ID, Text.NUMBER); + } + } catch (UmbrellaException e) { + return send(ex, e); + } + } + @Override public void onEvent(Event event) { LOG.log(DEBUG,"{0} @ {1} (by {2})",event.eventType(),event.module(),event.initiator().name()); diff --git a/journal/src/main/java/de/srsoftware/umbrella/journal/SqliteDb.java b/journal/src/main/java/de/srsoftware/umbrella/journal/SqliteDb.java index 785c0ce9..60481386 100644 --- a/journal/src/main/java/de/srsoftware/umbrella/journal/SqliteDb.java +++ b/journal/src/main/java/de/srsoftware/umbrella/journal/SqliteDb.java @@ -1,20 +1,32 @@ /* © SRSoftware 2025 */ package de.srsoftware.umbrella.journal; +import static de.srsoftware.tools.NotImplemented.notImplemented; +import static de.srsoftware.tools.jdbc.Condition.equal; +import static de.srsoftware.tools.jdbc.Query.SelectQuery.ALL; import static de.srsoftware.tools.jdbc.Query.insertInto; +import static de.srsoftware.tools.jdbc.Query.select; import static de.srsoftware.umbrella.core.constants.Field.*; -import static de.srsoftware.umbrella.core.exceptions.UmbrellaException.databaseException; -import static de.srsoftware.umbrella.core.exceptions.UmbrellaException.failedToCreateTable; +import static de.srsoftware.umbrella.core.exceptions.UmbrellaException.*; import static de.srsoftware.umbrella.journal.Constants.ERROR_WRITE_EVENT; import static de.srsoftware.umbrella.journal.Constants.TABLE_JOURNAL; import static java.text.MessageFormat.format; import de.srsoftware.umbrella.core.BaseDb; +import de.srsoftware.umbrella.core.constants.Field; +import de.srsoftware.umbrella.core.constants.Module; +import de.srsoftware.umbrella.core.constants.Text; +import de.srsoftware.umbrella.core.model.UmbrellaUser; import de.srsoftware.umbrella.messagebus.events.Event; +import de.srsoftware.umbrella.messagebus.events.TaskEvent; + import java.sql.Connection; import java.sql.SQLException; import java.time.LocalDateTime; import java.time.ZoneOffset; +import java.util.ArrayList; +import java.util.HashMap; +import java.util.List; public class SqliteDb extends BaseDb implements JournalDb{ public SqliteDb(Connection connection) { @@ -51,6 +63,33 @@ public class SqliteDb extends BaseDb implements JournalDb{ } } + @Override + public List> list(String module, long entityId, HashMap userLoader) { + try { + var rs = select(ALL).from(TABLE_JOURNAL).where(MODULE, equal(module)).where(ENTITY_ID,equal(entityId)).exec(db); + var list = new ArrayList>(); + + + while (rs.next()){ + var user = userLoader.get(rs.getLong(USER_ID)); + var id = rs.getLong(Field.ID); + var timestamp = rs.getLong(TIMESTAMP); + var action = rs.getString(ACTION); + var descr = rs.getString(DESCRIPTION); + + var event = switch (module){ + case Module.TASK -> new TaskEvent(user,) + default -> throw notImplemented("No handler for "+module+" events!"); + }; + list.add(event); + } + rs.close(); + return list; + } catch (SQLException e) { + throw failedToLoadObject(Text.EVENT_LIST); + }; + } + @Override public void logEvent(Event event) { try { diff --git a/user/src/main/java/de/srsoftware/umbrella/user/UserModule.java b/user/src/main/java/de/srsoftware/umbrella/user/UserModule.java index 2e895e95..4409bb22 100644 --- a/user/src/main/java/de/srsoftware/umbrella/user/UserModule.java +++ b/user/src/main/java/de/srsoftware/umbrella/user/UserModule.java @@ -6,6 +6,7 @@ import static de.srsoftware.tools.Optionals.*; import static de.srsoftware.tools.Strings.uuid; import static de.srsoftware.umbrella.core.ConnectionProvider.connect; import static de.srsoftware.umbrella.core.ModuleRegistry.postBox; +import static de.srsoftware.umbrella.core.ModuleRegistry.userService; import static de.srsoftware.umbrella.core.ResponseCode.*; import static de.srsoftware.umbrella.core.ResponseCode.HTTP_SERVER_ERROR; import static de.srsoftware.umbrella.core.Util.*; @@ -161,6 +162,17 @@ public class UserModule extends BaseHandler implements UserService { } } + @Override + public HashMap loader() { + return new HashMap(){ + public UmbrellaUser get(long id) { + var user = super.get(id); + if (user == null) put(id, user = loadUser(id)); + return user; + } + }; + } + @Override public UmbrellaUser loadUser(long userId) throws UmbrellaException { return users.load(userId);