From e6573f06b9ef26c4bf7b1042d13943414995544c Mon Sep 17 00:00:00 2001 From: Mateusz Nowak Date: Tue, 30 Sep 2025 16:31:18 +0200 Subject: [PATCH 1/5] add postgres to pom.xml --- pom.xml | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/pom.xml b/pom.xml index c8e0b36..8211368 100644 --- a/pom.xml +++ b/pom.xml @@ -12,6 +12,7 @@ 3.27.3 4.3.0 5.0.0-preview + 0.1.0 3.0 5.12.1 2.20.0 @@ -60,6 +61,11 @@ axon-server-connector ${axon.version} + + io.axoniq.framework + postgresql-core + ${axon-postgresql.version} + From 81f4670c41794b62f4219e207ef1275918021234 Mon Sep 17 00:00:00 2001 From: Mateusz Nowak Date: Tue, 30 Sep 2025 17:05:19 +0200 Subject: [PATCH 2/5] =?UTF-8?q?=F0=9F=97=83=EF=B8=8F=20db(postgres):=20add?= =?UTF-8?q?=20`PostgresEventStorageEngine`=20sample=20usage?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- docker-compose.yaml | 15 +++++++++-- pom.xml | 15 ++++++++++- .../university/ConfigurationProperties.java | 25 +++++++++++++------ .../university/UniversityAxonApplication.java | 25 ++++++++++++++++++- src/main/resources/application.properties | 4 ++- .../university/UniversityApplicationTest.java | 4 +-- .../faculty/FacultyAxonTestFixture.java | 6 ++--- src/test/resources/application.properties | 5 ++-- 8 files changed, 79 insertions(+), 20 deletions(-) diff --git a/docker-compose.yaml b/docker-compose.yaml index bb47f49..7097ad9 100644 --- a/docker-compose.yaml +++ b/docker-compose.yaml @@ -9,8 +9,19 @@ services: axoniq_axonserver_autocluster_first: axon-server axoniq_axonserver_autocluster_contexts: _admin volumes: - - data:/axonserver/data - - events:/axonserver/events + - ./volumes/axonserver-data:/axonserver/data + - ./volumes/axonserver-events:/axonserver/events + postgres: + image: postgres:18 + environment: + POSTGRES_DB: university_demo_db + POSTGRES_USER: university_demo_user + POSTGRES_PASSWORD: university_demo_password + ports: + - "5444:5444" + volumes: + - ./volumes/postgres-axon:/var/lib/postgresql/data + command: -p 5444 volumes: db: diff --git a/pom.xml b/pom.xml index 8211368..774e941 100644 --- a/pom.xml +++ b/pom.xml @@ -12,7 +12,6 @@ 3.27.3 4.3.0 5.0.0-preview - 0.1.0 3.0 5.12.1 2.20.0 @@ -22,6 +21,9 @@ 21 UTF-8 3.2.5 + 0.1.0 + 42.7.8 + 7.0.2 @@ -61,11 +63,22 @@ axon-server-connector ${axon.version} + io.axoniq.framework postgresql-core ${axon-postgresql.version} + + org.postgresql + postgresql + ${postgresql.version} + + + com.zaxxer + HikariCP + ${hikari-cp.version} + diff --git a/src/main/java/io/axoniq/demo/university/ConfigurationProperties.java b/src/main/java/io/axoniq/demo/university/ConfigurationProperties.java index 70b0502..09f19c8 100644 --- a/src/main/java/io/axoniq/demo/university/ConfigurationProperties.java +++ b/src/main/java/io/axoniq/demo/university/ConfigurationProperties.java @@ -9,7 +9,8 @@ public class ConfigurationProperties { private static final Logger logger = Logger.getLogger(ConfigurationProperties.class.getName()); - boolean axonServerEnabled = true; + // Possible values: "in-memory", "axonserver", "postgres" + private String eventStorageEngine = "axonserver"; public static ConfigurationProperties defaults() { return new ConfigurationProperties(); @@ -21,9 +22,9 @@ public static ConfigurationProperties load() { Properties properties = loadPropertiesFile("application.properties"); if (properties != null) { - String axonServerEnabled = properties.getProperty("axon.server.enabled"); - if (axonServerEnabled != null) { - props.axonServerEnabled = Boolean.parseBoolean(axonServerEnabled); + String engine = properties.getProperty("axon.event-storage.engine"); + if (engine != null && !engine.isBlank()) { + props.eventStorageEngine = engine.trim(); } } else { logger.info("No properties file found, using default configuration"); @@ -46,12 +47,20 @@ private static Properties loadPropertiesFile(String filename) { return null; } - public boolean axonServerEnabled() { - return axonServerEnabled; + public String eventStorageEngine() { + return eventStorageEngine; } - public ConfigurationProperties axonServerEnabled(boolean axonServerEnabled) { - this.axonServerEnabled = axonServerEnabled; + public ConfigurationProperties eventStorageEngine(String eventStorageEngine) { + this.eventStorageEngine = eventStorageEngine; return this; } + + public boolean isAxonServerEventStorageEngine() { + return "axonserver".equalsIgnoreCase(eventStorageEngine); + } + + public boolean isPostgresEventStorageEngine() { + return "postgres".equalsIgnoreCase(eventStorageEngine); + } } diff --git a/src/main/java/io/axoniq/demo/university/UniversityAxonApplication.java b/src/main/java/io/axoniq/demo/university/UniversityAxonApplication.java index 7391c7c..f314c1e 100644 --- a/src/main/java/io/axoniq/demo/university/UniversityAxonApplication.java +++ b/src/main/java/io/axoniq/demo/university/UniversityAxonApplication.java @@ -1,14 +1,20 @@ package io.axoniq.demo.university; +import com.zaxxer.hikari.HikariConfig; +import com.zaxxer.hikari.HikariDataSource; import io.axoniq.demo.university.faculty.FacultyModuleConfiguration; import io.axoniq.demo.university.shared.ids.CourseId; import io.axoniq.demo.university.faculty.write.createcourseplain.CreateCourse; import io.axoniq.demo.university.faculty.write.renamecourse.RenameCourse; +import io.axoniq.framework.postgresql.DataSourceConnectionExecutor; +import io.axoniq.framework.postgresql.PostgresqlEventStorageEngine; import org.axonframework.axonserver.connector.AxonServerConfiguration; import org.axonframework.axonserver.connector.AxonServerConfigurationEnhancer; import org.axonframework.commandhandling.gateway.CommandGateway; import org.axonframework.common.infra.FilesystemStyleComponentDescriptor; import org.axonframework.configuration.AxonConfiguration; +import org.axonframework.eventhandling.conversion.DelegatingEventConverter; +import org.axonframework.eventhandling.conversion.EventConverter; import org.axonframework.eventsourcing.configuration.EventSourcingConfigurer; import java.util.function.UnaryOperator; @@ -53,7 +59,7 @@ public EventSourcingConfigurer configurer( UnaryOperator customization ) { var configurer = EventSourcingConfigurer.create(); - if (configProps.axonServerEnabled) { + if (configProps.isAxonServerEventStorageEngine()) { configurer.componentRegistry(r -> r.registerComponent(AxonServerConfiguration.class, c -> { var axonServerConfig = new AxonServerConfiguration(); axonServerConfig.setContext(CONTEXT); @@ -62,6 +68,23 @@ public EventSourcingConfigurer configurer( } else { configurer.componentRegistry(r -> r.disableEnhancer(AxonServerConfigurationEnhancer.class)); } + if (configProps.isPostgresEventStorageEngine()) { + HikariConfig config = new HikariConfig(); + + config.setJdbcUrl("jdbc:postgresql://localhost:5444/university_demo_db"); + config.setUsername("university_demo_user"); + config.setPassword("university_demo_password"); +// config.setMaximumPoolSize(5); +// config.setMinimumIdle(1); +// config.setAutoCommit(false); + + configurer.registerEventStorageEngine(cr -> + new PostgresqlEventStorageEngine( + new DataSourceConnectionExecutor(new HikariDataSource(config)), + cr.getComponent(EventConverter.class) + ) + ); + } configurer = customization.apply(configurer); return configurer; } diff --git a/src/main/resources/application.properties b/src/main/resources/application.properties index 68495df..3966b44 100644 --- a/src/main/resources/application.properties +++ b/src/main/resources/application.properties @@ -1,2 +1,4 @@ # University Demo Application Configuration -axon.server.enabled=true + +# Options: in-memory / axonserver / postgres +axon.event-storage.engine=axonserver diff --git a/src/test/java/io/axoniq/demo/university/UniversityApplicationTest.java b/src/test/java/io/axoniq/demo/university/UniversityApplicationTest.java index a5c7d6e..1303798 100644 --- a/src/test/java/io/axoniq/demo/university/UniversityApplicationTest.java +++ b/src/test/java/io/axoniq/demo/university/UniversityApplicationTest.java @@ -32,8 +32,8 @@ void beforeEach() { } private static void purgeAxonServerIfEnabled(ConfigurationProperties configuration) { - boolean axonServerEnabled = configuration.axonServerEnabled(); - if (axonServerEnabled) { + boolean useAxonServer = configuration.isAxonServerEventStorageEngine(); + if (useAxonServer) { try { AxonServerContainerUtils.purgeEventsFromAxonServer("localhost", 8024, "university", true); } catch (IOException e) { diff --git a/src/test/java/io/axoniq/demo/university/faculty/FacultyAxonTestFixture.java b/src/test/java/io/axoniq/demo/university/faculty/FacultyAxonTestFixture.java index e33a8b1..e48ca3e 100644 --- a/src/test/java/io/axoniq/demo/university/faculty/FacultyAxonTestFixture.java +++ b/src/test/java/io/axoniq/demo/university/faculty/FacultyAxonTestFixture.java @@ -20,12 +20,12 @@ public static AxonTestFixture slice(UnaryOperator custo var configuration = ConfigurationProperties.load(); var configurer = application.configurer(configuration, customization); purgeAxonServerIfEnabled(configuration); - return AxonTestFixture.with(configurer, c -> configuration.axonServerEnabled() ? c : c.disableAxonServer()); + return AxonTestFixture.with(configurer, c -> configuration.isAxonServerEventStorageEngine() ? c : c.disableAxonServer()); } private static void purgeAxonServerIfEnabled(ConfigurationProperties configuration) { - boolean axonServerEnabled = configuration.axonServerEnabled(); - if (axonServerEnabled) { + boolean useAxonServer = configuration.isAxonServerEventStorageEngine(); + if (useAxonServer) { try { AxonServerContainerUtils.purgeEventsFromAxonServer("localhost", 8024, "university", true); } catch (IOException e) { diff --git a/src/test/resources/application.properties b/src/test/resources/application.properties index 107bd9a..55e209e 100644 --- a/src/test/resources/application.properties +++ b/src/test/resources/application.properties @@ -1,3 +1,4 @@ -# University Demo Test Configuration -axon.server.enabled=false +# University Demo Application Configuration +# Options: in-memory / axonserver / postgres +axon.event-storage.engine=in-memory From 6b19c11c1f25eef7e2995f773ccf272ffff37f3b Mon Sep 17 00:00:00 2001 From: Mateusz Nowak Date: Tue, 30 Sep 2025 18:28:24 +0200 Subject: [PATCH 3/5] =?UTF-8?q?=F0=9F=97=83=EF=B8=8F=20db(postgres):=20add?= =?UTF-8?q?=20`PostgresEventStorageEngine`=20sample=20usage?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- docker-compose.yaml | 2 +- .../axoniq/demo/university/UniversityAxonApplication.java | 6 +++--- src/main/resources/application.properties | 2 +- src/test/resources/application.properties | 2 +- 4 files changed, 6 insertions(+), 6 deletions(-) diff --git a/docker-compose.yaml b/docker-compose.yaml index 7097ad9..40f8748 100644 --- a/docker-compose.yaml +++ b/docker-compose.yaml @@ -20,7 +20,7 @@ services: ports: - "5444:5444" volumes: - - ./volumes/postgres-axon:/var/lib/postgresql/data + - ./volumes/postgres-axon:/var/lib/postgresql/18/docker command: -p 5444 volumes: diff --git a/src/main/java/io/axoniq/demo/university/UniversityAxonApplication.java b/src/main/java/io/axoniq/demo/university/UniversityAxonApplication.java index f314c1e..16043bd 100644 --- a/src/main/java/io/axoniq/demo/university/UniversityAxonApplication.java +++ b/src/main/java/io/axoniq/demo/university/UniversityAxonApplication.java @@ -74,9 +74,9 @@ public EventSourcingConfigurer configurer( config.setJdbcUrl("jdbc:postgresql://localhost:5444/university_demo_db"); config.setUsername("university_demo_user"); config.setPassword("university_demo_password"); -// config.setMaximumPoolSize(5); -// config.setMinimumIdle(1); -// config.setAutoCommit(false); + config.setAutoCommit(false); + config.setMaximumPoolSize(5); + config.setMinimumIdle(1); configurer.registerEventStorageEngine(cr -> new PostgresqlEventStorageEngine( diff --git a/src/main/resources/application.properties b/src/main/resources/application.properties index 3966b44..f66e07c 100644 --- a/src/main/resources/application.properties +++ b/src/main/resources/application.properties @@ -1,4 +1,4 @@ # University Demo Application Configuration # Options: in-memory / axonserver / postgres -axon.event-storage.engine=axonserver +axon.event-storage.engine=postgres diff --git a/src/test/resources/application.properties b/src/test/resources/application.properties index 55e209e..f66e07c 100644 --- a/src/test/resources/application.properties +++ b/src/test/resources/application.properties @@ -1,4 +1,4 @@ # University Demo Application Configuration # Options: in-memory / axonserver / postgres -axon.event-storage.engine=in-memory +axon.event-storage.engine=postgres From 48d6a0c2589ea26e5bc128b5ba96f222dbce4e64 Mon Sep 17 00:00:00 2001 From: Mateusz Nowak Date: Tue, 30 Sep 2025 22:21:06 +0200 Subject: [PATCH 4/5] =?UTF-8?q?=F0=9F=97=83=EF=B8=8F=20db(postgres):=20add?= =?UTF-8?q?=20`PostgresEventStorageEngine`=20sample=20usage?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../SubscribeStudentToCourseAxonFixtureTest.java | 1 + .../SubscribeStudentToCourseAxonFixtureTest.java | 1 + 2 files changed, 2 insertions(+) diff --git a/src/test/java/io/axoniq/demo/university/faculty/write/subscribestudent/SubscribeStudentToCourseAxonFixtureTest.java b/src/test/java/io/axoniq/demo/university/faculty/write/subscribestudent/SubscribeStudentToCourseAxonFixtureTest.java index 52163b3..d600adb 100644 --- a/src/test/java/io/axoniq/demo/university/faculty/write/subscribestudent/SubscribeStudentToCourseAxonFixtureTest.java +++ b/src/test/java/io/axoniq/demo/university/faculty/write/subscribestudent/SubscribeStudentToCourseAxonFixtureTest.java @@ -36,6 +36,7 @@ void successfulSubscription() { .when() .command(new SubscribeStudentToCourse(studentId, courseId)) .then() + .success() .events(new StudentSubscribedToCourse(studentId, courseId)); } diff --git a/src/test/java/io/axoniq/demo/university/faculty/write/subscribestudentmulti/SubscribeStudentToCourseAxonFixtureTest.java b/src/test/java/io/axoniq/demo/university/faculty/write/subscribestudentmulti/SubscribeStudentToCourseAxonFixtureTest.java index 1de5370..c4059c4 100644 --- a/src/test/java/io/axoniq/demo/university/faculty/write/subscribestudentmulti/SubscribeStudentToCourseAxonFixtureTest.java +++ b/src/test/java/io/axoniq/demo/university/faculty/write/subscribestudentmulti/SubscribeStudentToCourseAxonFixtureTest.java @@ -36,6 +36,7 @@ void successfulSubscription() { .when() .command(new SubscribeStudentToCourse(studentId, courseId)) .then() + .success() .events(new StudentSubscribedToCourse(studentId, courseId)); } From 2db260f4746e75f6a240c83d327d9bb968dcc7f1 Mon Sep 17 00:00:00 2001 From: Mateusz Nowak Date: Wed, 1 Oct 2025 23:55:13 +0200 Subject: [PATCH 5/5] =?UTF-8?q?=F0=9F=99=88=20chore(gitignore):=20add=20do?= =?UTF-8?q?cker=20volume=20and=20app=20logs?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .gitignore | 8 +++++++- src/main/resources/log4j2.xml | 37 +++++++++++++++++++++++++++++++++++ 2 files changed, 44 insertions(+), 1 deletion(-) create mode 100644 src/main/resources/log4j2.xml diff --git a/.gitignore b/.gitignore index b425f09..ae158e8 100644 --- a/.gitignore +++ b/.gitignore @@ -32,4 +32,10 @@ build/ .vscode/ ### Mac OS ### -.DS_Store \ No newline at end of file +.DS_Store + +### Docker ### +volumes + +### App ### +logs \ No newline at end of file diff --git a/src/main/resources/log4j2.xml b/src/main/resources/log4j2.xml new file mode 100644 index 0000000..f099382 --- /dev/null +++ b/src/main/resources/log4j2.xml @@ -0,0 +1,37 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + \ No newline at end of file