Skip to content

[GAZ-328] Migrate message-gateway to Java 21 / Spring Boot 3.4 / Camel 4 / Jakarta - #84

Open
GiulioRinalduzzi wants to merge 1 commit into
openMF:devfrom
GiulioRinalduzzi:migrate/sb34-jakarta-jdk21
Open

[GAZ-328] Migrate message-gateway to Java 21 / Spring Boot 3.4 / Camel 4 / Jakarta#84
GiulioRinalduzzi wants to merge 1 commit into
openMF:devfrom
GiulioRinalduzzi:migrate/sb34-jakarta-jdk21

Conversation

@GiulioRinalduzzi

@GiulioRinalduzzi GiulioRinalduzzi commented Aug 7, 2026

Copy link
Copy Markdown

Java 21 / Spring Boot 3.4.4 / Camel 4.4.1 / Jakarta EE 10, same recipe as the paymenthub-ee-* connectors: versions come from enforcedPlatform('org.mifos:paymenthub-ee-bom:2.0.0-SNAPSHOT'). Targets dev as requested. cc @tdaly61

Jakarta: only 8 of 79 source files needed it — javax.persistence (25), javax.xml.bind (2), javax.annotation (2). javax.sql.DataSource deliberately stays javax: it is JDK, not Jakarta EE. There is no Spring Security anywhere in this repo, which is normally the hard part of a Spring Boot 3 move.

Hibernate 6: two changes were needed to make the application start.

  • AbstractPersistableCustom used GenerationType.AUTO → now IDENTITY. Every table in db/migration declares its id AUTO_INCREMENT, which is what Hibernate 5 produced from AUTO on MySQL; Hibernate 6 turns it into a sequence table instead.
  • SmsOutboundMessageRepository.findByIdInAndTenantId took a String while OutboundMessages.tenantId is a Long. Hibernate 6 refuses to build the derived query. The method has no callers — happy to delete it instead if you prefer.

Dependencies

  • Flyway 6.4.0 → 10.x, forced by Spring Boot 3.4. Flyway 10 moved per-database support out of core, so flyway-mysql is now a separate dependency. This is the bit that overlaps with @kanishk Singh's postgres work — the swap should be flyway-mysqlflyway-database-postgresql plus the driver, and IDENTITY works on postgres too, so that part needs no further change.
  • mysql:mysql-connector-javacom.mysql:mysql-connector-j (BOM managed).
  • gson and okhttp are now declared explicitly. Both are imported directly by the code — gson in 8 files, okhttp in JasminSMSProvider and CallbackEventListner — but neither was declared: they only reached the classpath as transitives of com.infobip:infobip-api-java-client. Bumping or dropping an SMS vendor would have broken eight unrelated classes. gson now takes its version from the BOM, which moves it 2.8.9 → 2.11.0 (the old strictly/force pin is gone). okhttp keeps the 2.3.0 it already resolved to, so nothing changes at runtime — but note that is com.squareup.okhttp 2.x from 2015, and moving to okhttp3 is a source change worth its own ticket, especially as Jasmin is the provider you want for the integration test.
  • velocity dropped — nothing imports it, but it was quietly supplying commons-lang 2.x (last released 2011) to three helper classes. Declared commons-lang3 directly and switched those three imports.
  • retrofit dropped as a declared dependency. To be precise: retrofit 1.9.0 is still on the classpath, pulled in by the InfoBip SDK. Nothing in src/ references it, so only the declaration went away.
  • spring-kafka dropped — zero source references and zero configuration.
  • Removed the repository URL with a stray quote in it (.../fyn-libs-snapshot'); that JFrog no longer exists either.
  • Twilio / InfoBip / Telerivet SDKs keep explicit versions: the BOM does not manage them.

Build, Docker, CI

  • Gradle 7.3 → 8.10.2. profile-standalone.gradle and profile-deployable.gradle used jar.baseName / war.baseName, removed in Gradle 8 → archiveBaseName/archiveVersion.
  • Dockerfile: openjdk:11eclipse-temurin:21-jre, copies app.jar instead of the *.jar glob (which also matched the -plain.jar that has no Main-Class), and now exposes 5009 as well — the Camel REST port, which the delivery-report callbacks need. callbackconfig.port is outbound only, so it stays unexposed.
  • CircleCI: openjdk:17-buster-node-browsers-legacy → the shared PHEE template (cimg/openjdk:21.0.6, multi-arch, image name from CIRCLE_PROJECT_*).
  • application.yml: dropped spring.jpa.hibernate.use-new-id-generator-mappings, removed in Spring Boot 3.

Not touched, worth flagging

  • This repo has no tests at all — there is no src/test directory. Until there is one, CI proves only that it compiles. The Dummy-provider smoke test is the obvious first one to automate.
  • Camel has no routes. There is no RouteBuilder in the repo and the startup log says Routes startup (started:0); only CamelContext and Exchange are used, from ZeebeWorkers. So most of the five camel-* dependencies are dead weight. Left alone here, but worth a ticket.
  • application.yml has a hard-coded Telerivet API key and project id committed in the clear, and spring.datasource.url is jdbc:mysql:thin://, which is not a valid MySQL JDBC URL. Both pre-existing, but the key probably wants rotating.
  • The email path is still unimplemented: sendEmail is abstract on Provider with an empty body in all 7 providers.

@GiulioRinalduzzi
GiulioRinalduzzi force-pushed the migrate/sb34-jakarta-jdk21 branch from 0b09e29 to 881a662 Compare August 7, 2026 08:10
Same recipe as the paymenthub-ee-* connectors: versions come from
enforcedPlatform('org.mifos:paymenthub-ee-bom:2.0.0-SNAPSHOT'), no
hand-pinned versions except the SMS vendor SDKs and okhttp, which the BOM
does not manage.

Jakarta:
- javax.persistence / javax.xml.bind / javax.annotation -> jakarta.*
  (8 files). javax.sql.DataSource stays javax: it is JDK, not Jakarta EE.

Runtime fixes found by actually booting the app against MySQL, not by
compiling it:
- AbstractPersistableCustom used GenerationType.AUTO. Hibernate 5 turned
  that into AUTO_INCREMENT on MySQL, which is what every table in
  db/migration declares; Hibernate 6 turns it into a sequence table
  (m_tenants_seq, ...) that does not exist, so every insert failed.
  Now GenerationType.IDENTITY.
- SmsOutboundMessageRepository.findByIdInAndTenantId took a String while
  OutboundMessages.tenantId is a Long. Hibernate 5 allowed it, Hibernate 6
  refuses to build the query and the whole context fails to start. The
  method has no callers, so the type was never exercised.

Build:
- Spring Boot 2.5.6 -> 3.4.4, source/target 11 -> 21, Gradle 7.3 -> 8.10.2
- Flyway 6.4.0 -> 10.x (forced by Spring Boot 3.4); Flyway 10 moved MySQL
  support into flyway-mysql, added as a separate dependency
- mysql:mysql-connector-java -> com.mysql:mysql-connector-j (BOM managed)
- gson and okhttp are now declared. Both are imported directly by the code
  (gson in 8 files, okhttp in JasminSMSProvider and CallbackEventListner)
  but were only reaching the classpath as transitives of the InfoBip SDK,
  so bumping or dropping an SMS vendor would have broken unrelated
  classes. gson takes its version from the BOM (2.8.9 -> 2.11.0, the old
  strictly/force pin is gone); okhttp keeps the 2.3.0 it already resolved
  to, since moving to okhttp3 is a source change.
- velocity dropped: nothing imports it, but it was quietly supplying
  commons-lang 2.x (last released 2011) to three helper classes. Declared
  commons-lang3 directly and switched those three imports.
- retrofit dropped as a declared dependency; it is still on the classpath
  via the InfoBip SDK, but no source references it
- spring-kafka dropped: no source reference and no configuration
- removed the repository URL with a stray quote in it
  (jfrog.sandbox.fynarfin.io), which no longer exists either
- profile-standalone / profile-deployable used jar.baseName and
  war.baseName, removed in Gradle 8 -> archiveBaseName / archiveVersion
- useJUnitPlatform() and bootJar -> app.jar, as in the other repos

Docker and CI:
- Dockerfile: openjdk:11 -> eclipse-temurin:21-jre, and copy app.jar
  instead of the *.jar glob, which also matched the -plain.jar. Now also
  exposes 5009, the Camel REST port; callbackconfig.port is outbound only
  and stays unexposed.
- CircleCI: openjdk:17-buster-node-browsers-legacy -> the shared PHEE
  template on cimg/openjdk:21.0.6, multi-arch, image name from CIRCLE_*

application.yml: dropped spring.jpa.hibernate.use-new-id-generator-mappings,
removed in Spring Boot 3.
@GiulioRinalduzzi
GiulioRinalduzzi force-pushed the migrate/sb34-jakarta-jdk21 branch from 881a662 to 53ff22f Compare August 7, 2026 08:49
@GiulioRinalduzzi GiulioRinalduzzi changed the title [PHEE-370] Migrate to Java 21 / Spring Boot 3.4 / Camel 4 / Jakarta [GAZ-328] Migrate message-gateway to Java 21 / Spring Boot 3.4 / Camel 4 / Jakarta Aug 7, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant