From 7dafac3155320b58e48331232b2440a8fc1473e8 Mon Sep 17 00:00:00 2001 From: Thomas Gran Date: Thu, 15 Oct 2026 19:36:55 +0200 Subject: [PATCH 01/11] feat!: add JPMS module descriptor and replace NamespacePrefixMapper overloads Add module-info.java (open module org.entur.siri) exporting the handwritten and generated packages. BREAKING CHANGE: SiriXml.toXml(Siri, NamespacePrefixMapper[, OutputStream]) in both org.entur.siri21.util and org.rutebanken.siri20.util now take a Consumer customizer instead. The JAXBNamespacePrefixMapper dependency, which shares a package with the JAXB RI and cannot coexist with it on the module path, is removed. Callers set their own JAXB implementation's namespace prefix mapper property on the Marshaller. --- pom.xml | 5 ----- src/main/java/module-info.java | 21 +++++++++++++++++++ .../java/org/entur/siri21/util/SiriXml.java | 14 ++++++------- .../org/rutebanken/siri20/util/SiriXml.java | 14 ++++++------- 4 files changed, 35 insertions(+), 19 deletions(-) create mode 100644 src/main/java/module-info.java diff --git a/pom.xml b/pom.xml index eb78e0a..4ffe9be 100644 --- a/pom.xml +++ b/pom.xml @@ -71,11 +71,6 @@ - - com.googlecode.jaxb-namespaceprefixmapper-interfaces - JAXBNamespacePrefixMapper - 6.1.0 - com.fasterxml.jackson.core jackson-databind diff --git a/src/main/java/module-info.java b/src/main/java/module-info.java new file mode 100644 index 0000000..ee94c57 --- /dev/null +++ b/src/main/java/module-info.java @@ -0,0 +1,21 @@ +open module org.entur.siri { + requires transitive jakarta.xml.bind; + requires com.fasterxml.jackson.databind; + requires com.fasterxml.jackson.module.jakarta.xmlbind; + + exports org.entur.siri; + exports org.entur.siri.adapter; + exports org.entur.siri.validator; + exports org.entur.siri21.util; + exports org.rutebanken.siri20.util; + exports eu.datex2.siri20.schema._2_0rc1._2_0; + exports eu.datex2.siri21.schema._2_0rc1._2_0; + exports net.opengis.gml.siri; + exports org.w3._2001.xmlschema; + exports uk.org.acbs.siri20; + exports uk.org.acbs.siri21; + exports uk.org.ifopt.siri20; + exports uk.org.ifopt.siri21; + exports uk.org.siri.siri20; + exports uk.org.siri.siri21; +} diff --git a/src/main/java/org/entur/siri21/util/SiriXml.java b/src/main/java/org/entur/siri21/util/SiriXml.java index 41c3f46..58db958 100644 --- a/src/main/java/org/entur/siri21/util/SiriXml.java +++ b/src/main/java/org/entur/siri21/util/SiriXml.java @@ -15,7 +15,6 @@ package org.entur.siri21.util; -import com.sun.xml.bind.marshaller.NamespacePrefixMapper; import org.entur.siri.XmlInputFactoryProvider; import uk.org.siri.siri21.Siri; @@ -31,6 +30,7 @@ import java.io.OutputStream; import java.io.StringReader; import java.io.StringWriter; +import java.util.function.Consumer; public class SiriXml { @@ -71,12 +71,12 @@ public static String toXml(Siri siri) throws JAXBException { return toXml(siri, null); } - public static String toXml(Siri siri, NamespacePrefixMapper customNamespacePrefixMapper) throws JAXBException { + public static String toXml(Siri siri, Consumer marshallerCustomizer) throws JAXBException { Marshaller jaxbMarshaller = jaxbContext.createMarshaller(); - if (customNamespacePrefixMapper != null) { - jaxbMarshaller.setProperty("com.sun.xml.bind.namespacePrefixMapper", customNamespacePrefixMapper); + if (marshallerCustomizer != null) { + marshallerCustomizer.accept(jaxbMarshaller); } StringWriter sw = new StringWriter(); jaxbMarshaller.marshal(siri, sw); @@ -84,11 +84,11 @@ public static String toXml(Siri siri, NamespacePrefixMapper customNamespacePrefi return sw.toString(); } - public static void toXml(Siri siri, NamespacePrefixMapper customNamespacePrefixMapper, OutputStream out) throws JAXBException, IOException { + public static void toXml(Siri siri, Consumer marshallerCustomizer, OutputStream out) throws JAXBException, IOException { Marshaller jaxbMarshaller = jaxbContext.createMarshaller(); - if (customNamespacePrefixMapper != null) { - jaxbMarshaller.setProperty("com.sun.xml.bind.namespacePrefixMapper", customNamespacePrefixMapper); + if (marshallerCustomizer != null) { + marshallerCustomizer.accept(jaxbMarshaller); } jaxbMarshaller.marshal(siri, out); } diff --git a/src/main/java/org/rutebanken/siri20/util/SiriXml.java b/src/main/java/org/rutebanken/siri20/util/SiriXml.java index 538529f..9933633 100644 --- a/src/main/java/org/rutebanken/siri20/util/SiriXml.java +++ b/src/main/java/org/rutebanken/siri20/util/SiriXml.java @@ -20,6 +20,7 @@ import java.io.OutputStream; import java.io.StringReader; import java.io.StringWriter; +import java.util.function.Consumer; import jakarta.xml.bind.JAXBContext; import jakarta.xml.bind.JAXBException; @@ -29,7 +30,6 @@ import javax.xml.stream.XMLStreamException; import javax.xml.stream.XMLStreamReader; -import com.sun.xml.bind.marshaller.NamespacePrefixMapper; import org.entur.siri.XmlInputFactoryProvider; import uk.org.siri.siri20.Siri; @@ -73,12 +73,12 @@ public static String toXml(Siri siri) throws JAXBException { return toXml(siri, null); } - public static String toXml(Siri siri, NamespacePrefixMapper customNamespacePrefixMapper) throws JAXBException { + public static String toXml(Siri siri, Consumer marshallerCustomizer) throws JAXBException { Marshaller jaxbMarshaller = jaxbContext.createMarshaller(); - if (customNamespacePrefixMapper != null) { - jaxbMarshaller.setProperty("com.sun.xml.bind.namespacePrefixMapper", customNamespacePrefixMapper); + if (marshallerCustomizer != null) { + marshallerCustomizer.accept(jaxbMarshaller); } StringWriter sw = new StringWriter(); jaxbMarshaller.marshal(siri, sw); @@ -86,11 +86,11 @@ public static String toXml(Siri siri, NamespacePrefixMapper customNamespacePrefi return sw.toString(); } - public static void toXml(Siri siri, NamespacePrefixMapper customNamespacePrefixMapper, OutputStream out) throws JAXBException, IOException { + public static void toXml(Siri siri, Consumer marshallerCustomizer, OutputStream out) throws JAXBException, IOException { Marshaller jaxbMarshaller = jaxbContext.createMarshaller(); - if (customNamespacePrefixMapper != null) { - jaxbMarshaller.setProperty("com.sun.xml.bind.namespacePrefixMapper", customNamespacePrefixMapper); + if (marshallerCustomizer != null) { + marshallerCustomizer.accept(jaxbMarshaller); } jaxbMarshaller.marshal(siri, out); } From 05d7e172c313d660ea3986537ff8a9f9615b03de Mon Sep 17 00:00:00 2001 From: Thomas Gran Date: Thu, 15 Oct 2026 19:40:41 +0200 Subject: [PATCH 02/11] test: cover SiriXml.toXml Consumer overloads Add tests for both the SIRI 2.0 and 2.1 SiriXml classes: customizer is applied to the marshaller, null customizer matches the default output, the OutputStream overload applies the customizer, and a customizer does not leak into later calls. --- .../util/SiriXmlMarshallerCustomizerTest.java | 92 +++++++++++++++++++ .../util/SiriXmlMarshallerCustomizerTest.java | 92 +++++++++++++++++++ 2 files changed, 184 insertions(+) create mode 100644 src/test/java/org/entur/siri21/util/SiriXmlMarshallerCustomizerTest.java create mode 100644 src/test/java/org/rutebanken/siri20/util/SiriXmlMarshallerCustomizerTest.java diff --git a/src/test/java/org/entur/siri21/util/SiriXmlMarshallerCustomizerTest.java b/src/test/java/org/entur/siri21/util/SiriXmlMarshallerCustomizerTest.java new file mode 100644 index 0000000..47c8254 --- /dev/null +++ b/src/test/java/org/entur/siri21/util/SiriXmlMarshallerCustomizerTest.java @@ -0,0 +1,92 @@ + /* + * Licensed under the EUPL, Version 1.2 or – as soon they will be approved by + * the European Commission - subsequent versions of the EUPL (the "Licence"); + * You may not use this work except in compliance with the Licence. + * You may obtain a copy of the Licence at: + * + * https://joinup.ec.europa.eu/software/page/eupl + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the Licence is distributed on an "AS IS" basis, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the Licence for the specific language governing permissions and + * limitations under the Licence. + */ + +package org.entur.siri21.util; + +import jakarta.xml.bind.Marshaller; +import org.junit.BeforeClass; +import org.junit.Test; +import uk.org.siri.siri21.Siri; + +import java.io.ByteArrayOutputStream; +import java.io.IOException; +import java.nio.charset.StandardCharsets; +import java.nio.file.Files; +import java.nio.file.Paths; +import java.util.concurrent.atomic.AtomicInteger; + +import static org.entur.siri21.util.SiriXml.parseXml; +import static org.entur.siri21.util.SiriXml.toXml; +import static org.junit.Assert.assertEquals; +import static org.junit.Assert.assertFalse; +import static org.junit.Assert.assertTrue; + +public class SiriXmlMarshallerCustomizerTest { + + private static Siri siri; + + @BeforeClass + public static void init() throws Exception { + String xml = new String(Files.readAllBytes(Paths.get("src/test/resources/et-2_1.xml")), StandardCharsets.UTF_8); + siri = parseXml(xml); + } + + @Test + public void testCustomizerIsAppliedToMarshaller() throws Exception { + AtomicInteger calls = new AtomicInteger(); + + String formatted = toXml(siri, marshaller -> { + calls.incrementAndGet(); + setFormattedOutput(marshaller); + }); + + assertEquals(1, calls.get()); + assertTrue("Expected indented output", isIndented(formatted)); + } + + @Test + public void testNullCustomizerGivesSameOutputAsDefault() throws Exception { + assertEquals(toXml(siri), toXml(siri, null)); + } + + @Test + public void testCustomizerIsAppliedWhenWritingToOutputStream() throws Exception { + ByteArrayOutputStream out = new ByteArrayOutputStream(); + + SiriXml.toXml(siri, SiriXmlMarshallerCustomizerTest::setFormattedOutput, out); + + String formatted = new String(out.toByteArray(), StandardCharsets.UTF_8); + assertTrue("Expected indented output", isIndented(formatted)); + } + + @Test + public void testCustomizerDoesNotLeakIntoLaterCalls() throws Exception { + toXml(siri, SiriXmlMarshallerCustomizerTest::setFormattedOutput); + + assertFalse("Customizer must only affect its own marshaller", isIndented(toXml(siri))); + } + + private static boolean isIndented(String xml) { + return xml.split("\n").length > 5; + } + + private static void setFormattedOutput(Marshaller marshaller) { + try { + marshaller.setProperty(Marshaller.JAXB_FORMATTED_OUTPUT, true); + } catch (Exception e) { + throw new IllegalStateException(e); + } + } +} diff --git a/src/test/java/org/rutebanken/siri20/util/SiriXmlMarshallerCustomizerTest.java b/src/test/java/org/rutebanken/siri20/util/SiriXmlMarshallerCustomizerTest.java new file mode 100644 index 0000000..17d33b9 --- /dev/null +++ b/src/test/java/org/rutebanken/siri20/util/SiriXmlMarshallerCustomizerTest.java @@ -0,0 +1,92 @@ +/* + * Licensed under the EUPL, Version 1.2 or – as soon they will be approved by + * the European Commission - subsequent versions of the EUPL (the "Licence"); + * You may not use this work except in compliance with the Licence. + * You may obtain a copy of the Licence at: + * + * https://joinup.ec.europa.eu/software/page/eupl + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the Licence is distributed on an "AS IS" basis, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the Licence for the specific language governing permissions and + * limitations under the Licence. + */ + +package org.rutebanken.siri20.util; + +import jakarta.xml.bind.Marshaller; +import org.junit.BeforeClass; +import org.junit.Test; +import uk.org.siri.siri20.Siri; + +import java.io.ByteArrayOutputStream; +import java.io.IOException; +import java.nio.charset.StandardCharsets; +import java.nio.file.Files; +import java.nio.file.Paths; +import java.util.concurrent.atomic.AtomicInteger; + +import static org.rutebanken.siri20.util.SiriXml.parseXml; +import static org.rutebanken.siri20.util.SiriXml.toXml; +import static org.junit.Assert.assertEquals; +import static org.junit.Assert.assertFalse; +import static org.junit.Assert.assertTrue; + +public class SiriXmlMarshallerCustomizerTest { + + private static Siri siri; + + @BeforeClass + public static void init() throws Exception { + String xml = new String(Files.readAllBytes(Paths.get("src/test/resources/et.xml")), StandardCharsets.UTF_8); + siri = parseXml(xml); + } + + @Test + public void testCustomizerIsAppliedToMarshaller() throws Exception { + AtomicInteger calls = new AtomicInteger(); + + String formatted = toXml(siri, marshaller -> { + calls.incrementAndGet(); + setFormattedOutput(marshaller); + }); + + assertEquals(1, calls.get()); + assertTrue("Expected indented output", isIndented(formatted)); + } + + @Test + public void testNullCustomizerGivesSameOutputAsDefault() throws Exception { + assertEquals(toXml(siri), toXml(siri, null)); + } + + @Test + public void testCustomizerIsAppliedWhenWritingToOutputStream() throws Exception { + ByteArrayOutputStream out = new ByteArrayOutputStream(); + + SiriXml.toXml(siri, SiriXmlMarshallerCustomizerTest::setFormattedOutput, out); + + String formatted = new String(out.toByteArray(), StandardCharsets.UTF_8); + assertTrue("Expected indented output", isIndented(formatted)); + } + + @Test + public void testCustomizerDoesNotLeakIntoLaterCalls() throws Exception { + toXml(siri, SiriXmlMarshallerCustomizerTest::setFormattedOutput); + + assertFalse("Customizer must only affect its own marshaller", isIndented(toXml(siri))); + } + + private static boolean isIndented(String xml) { + return xml.split("\n").length > 5; + } + + private static void setFormattedOutput(Marshaller marshaller) { + try { + marshaller.setProperty(Marshaller.JAXB_FORMATTED_OUTPUT, true); + } catch (Exception e) { + throw new IllegalStateException(e); + } + } +} From 0465ebb1a3276be12f1c42273658842d95f7d6fe Mon Sep 17 00:00:00 2001 From: Thomas Gran Date: Thu, 15 Oct 2026 19:46:56 +0200 Subject: [PATCH 03/11] build: use compiler release flag and drop unused slf4j dependencies - Use instead of / so builds on newer JDKs cannot use APIs newer than Java 11. - Remove slf4j-api and slf4j-simple. Nothing in the project uses slf4j. - Remove the now-unused (and previously duplicated) slf4j.version property. --- pom.xml | 13 ------------- 1 file changed, 13 deletions(-) diff --git a/pom.xml b/pom.xml index 4ffe9be..f75f817 100644 --- a/pom.xml +++ b/pom.xml @@ -24,9 +24,7 @@ UTF-8 11 - 2.0.9 2.18.11 - 2.0.7 1.18.0 4.2.0 3.11.2 @@ -109,11 +107,6 @@ test 2.1.0 - - org.slf4j - slf4j-api - ${slf4j.version} - junit @@ -121,12 +114,6 @@ 4.13.2 test - - org.slf4j - slf4j-simple - ${slf4j.version} - test - From d77207efd75446acf1eb1c0d5c12207a9fd241a4 Mon Sep 17 00:00:00 2001 From: Thomas Gran Date: Thu, 15 Oct 2026 19:46:56 +0200 Subject: [PATCH 04/11] fix: require jackson-annotations in module descriptor SiriJson imports com.fasterxml.jackson.annotation.JsonInclude directly, so the module must require com.fasterxml.jackson.annotation. This only surfaced when compiling with --release. --- src/main/java/module-info.java | 1 + 1 file changed, 1 insertion(+) diff --git a/src/main/java/module-info.java b/src/main/java/module-info.java index ee94c57..3fd761f 100644 --- a/src/main/java/module-info.java +++ b/src/main/java/module-info.java @@ -1,5 +1,6 @@ open module org.entur.siri { requires transitive jakarta.xml.bind; + requires com.fasterxml.jackson.annotation; requires com.fasterxml.jackson.databind; requires com.fasterxml.jackson.module.jakarta.xmlbind; From 79785017cb11d02fe4895424099429f590e577a4 Mon Sep 17 00:00:00 2001 From: Thomas Gran Date: Thu, 15 Oct 2026 19:52:44 +0200 Subject: [PATCH 05/11] build: remove duplicate jakarta.activation module from dependencies jackson-module-jakarta-xmlbind-annotations pulled in jakarta.activation-api 2.1.0 while jakarta.xml.bind-api pulled in com.sun.activation:jakarta.activation 2.0.1. Both declare the module name jakarta.activation, which made surefire log "Module 'jakarta.activation' is already on the module path". Exclude the API jar from the Jackson module and drop the test-scope pin of the same jar. --- pom.xml | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/pom.xml b/pom.xml index f75f817..df5e6f5 100644 --- a/pom.xml +++ b/pom.xml @@ -83,6 +83,12 @@ com.fasterxml.jackson.module jackson-module-jakarta-xmlbind-annotations ${jackson.version} + + + jakarta.activation + jakarta.activation-api + + jakarta.xml.bind @@ -101,12 +107,6 @@ 3.0.2 test - - jakarta.activation - jakarta.activation-api - test - 2.1.0 - junit From cef8dd07acba875d839ea5e2049e97cb498e9196 Mon Sep 17 00:00:00 2001 From: Thomas Gran Date: Thu, 15 Oct 2026 19:52:44 +0200 Subject: [PATCH 06/11] test: verify JAXB RI NamespacePrefixMapper works through the customizer --- .../util/SiriXmlMarshallerCustomizerTest.java | 22 +++++++++++++++++++ 1 file changed, 22 insertions(+) diff --git a/src/test/java/org/entur/siri21/util/SiriXmlMarshallerCustomizerTest.java b/src/test/java/org/entur/siri21/util/SiriXmlMarshallerCustomizerTest.java index 47c8254..7aa7a0a 100644 --- a/src/test/java/org/entur/siri21/util/SiriXmlMarshallerCustomizerTest.java +++ b/src/test/java/org/entur/siri21/util/SiriXmlMarshallerCustomizerTest.java @@ -16,6 +16,7 @@ package org.entur.siri21.util; import jakarta.xml.bind.Marshaller; +import org.glassfish.jaxb.runtime.marshaller.NamespacePrefixMapper; import org.junit.BeforeClass; import org.junit.Test; import uk.org.siri.siri21.Siri; @@ -56,6 +57,27 @@ public void testCustomizerIsAppliedToMarshaller() throws Exception { assertTrue("Expected indented output", isIndented(formatted)); } + @Test + public void testJaxbRiNamespacePrefixMapperCanBeSetThroughCustomizer() throws Exception { + NamespacePrefixMapper mapper = new NamespacePrefixMapper() { + @Override + public String getPreferredPrefix(String namespaceUri, String suggestion, boolean requirePrefix) { + return "http://www.siri.org.uk/siri".equals(namespaceUri) ? "siri" : suggestion; + } + }; + + String xml = toXml(siri, marshaller -> { + try { + marshaller.setProperty("org.glassfish.jaxb.namespacePrefixMapper", mapper); + } catch (Exception e) { + throw new IllegalStateException(e); + } + }); + + assertTrue("Expected siri: prefix", xml.contains(" Date: Thu, 15 Oct 2026 19:52:44 +0200 Subject: [PATCH 07/11] docs: document JPMS module and the NamespacePrefixMapper migration Add a README section on the org.entur.siri module and an "Upgrading to 3.0" note with a before/after example. Update CLAUDE.md for module-info.java, the release flag, the Consumer API and the JDK 11 build requirement. --- CLAUDE.md | 7 ++++++- README.md | 39 ++++++++++++++++++++++++++++++++++++++- 2 files changed, 44 insertions(+), 2 deletions(-) diff --git a/CLAUDE.md b/CLAUDE.md index 75ec8a6..4e57677 100644 --- a/CLAUDE.md +++ b/CLAUDE.md @@ -27,6 +27,8 @@ mvn generate-sources **Note:** Tests run with `-Duser.timezone=Europe/Oslo` (configured in surefire plugin). +**Note:** Surefire runs tests on the module path because `module-info.java` exists. + ## Architecture ### Code Generation (bulk of the codebase) @@ -37,7 +39,7 @@ The `cxf-xjc-plugin` generates ~1,900 Java classes from XSD schemas during `gene Generated sources land in `target/generated-sources`. JAXB binding customizations are in `src/main/resources/siri-{2.0,2.1}/xjb/jaxb-bindings.xml` — these map `xsd:dateTime`/`xsd:time` to `java.time.ZonedDateTime` and `xsd:duration` to `java.time.Duration`. -### Handwritten Code (~9 files) +### Handwritten Code (~10 files) | Package | Class | Purpose | |---------|-------|---------| @@ -49,11 +51,14 @@ Generated sources land in `target/generated-sources`. JAXB binding customization | `org.entur.siri21.util` | `SiriJson` | SIRI 2.1 JSON conversion (Jackson + Jakarta XML Bind) | | `org.rutebanken.siri20.util` | `SiriXml` | SIRI 2.0 XML marshalling/unmarshalling (legacy package) | | `org.entur.siri` | `UnsupportedSiriVersionException` | Exception for unsupported SIRI versions | +| (module root) | `module-info.java` | JPMS descriptor: `open module org.entur.siri` | ### Key Design Decisions - **Jakarta EE**: Uses `jakarta.xml.bind` (3.0+), not legacy `javax.xml.bind`. - **Java 11** target (source and bytecode) via `` in the compiler plugin; CI builds on JDK 25, and any JDK from 11 to 25 works locally. +- **JPMS**: `src/main/java/module-info.java` declares `open module org.entur.siri` (open because the consumer's JAXB runtime needs reflective access). When you add a generated or handwritten package, add an `exports` line for it. +- **No `NamespacePrefixMapper` in the API**: `SiriXml.toXml` takes a `Consumer` customizer. The `JAXBNamespacePrefixMapper` stub shares a package with the JAXB RI, so it cannot be used on the module path. - **JUnit 4** for tests. - **JSON support exists only for SIRI 2.1** (`SiriJson`), not 2.0. - **SIRI 2.0 utility lives in legacy package** `org.rutebanken.siri20.util` (historical). diff --git a/README.md b/README.md index 9f45435..feace6e 100644 --- a/README.md +++ b/README.md @@ -11,4 +11,41 @@ Source 1.0 - 1.4 http://user47094.vs.easily.co.uk/siri/ Source 2.0 -> https://www.vdv.de/siri.aspx -Also provides XML-validation through method `SiriValidator.validate`. \ No newline at end of file +Also provides XML-validation through method `SiriValidator.validate`. + +## Java modules (JPMS) + +The jar is a named module, `org.entur.siri`. It is an `open module`, because the JAXB runtime that you supply needs reflective access to the generated classes. It requires `jakarta.xml.bind` and Jackson. You must also provide a JAXB implementation, for example `com.sun.xml.bind:jaxb-impl`. + +```java +module my.app { + requires org.entur.siri; +} +``` + +## Upgrading to 3.0 + +**Breaking change: `NamespacePrefixMapper` is removed from `SiriXml`.** +The overloads `toXml(Siri, NamespacePrefixMapper)` and `toXml(Siri, NamespacePrefixMapper, OutputStream)` in `org.entur.siri21.util.SiriXml` and `org.rutebanken.siri20.util.SiriXml` now take a `Consumer` instead. The `JAXBNamespacePrefixMapper` dependency is removed, because it shares a package with the JAXB reference implementation and cannot be used on the module path. + +Before: + +```java +SiriXml.toXml(siri, myNamespacePrefixMapper); +``` + +After: set the property of your own JAXB implementation on the marshaller. + +```java +SiriXml.toXml(siri, marshaller -> { + try { + marshaller.setProperty("org.glassfish.jaxb.namespacePrefixMapper", myNamespacePrefixMapper); + } catch (PropertyException e) { + throw new IllegalStateException(e); + } +}); +``` + +The property name depends on your JAXB implementation. Use the one that your implementation documents. If your own code imports `com.sun.xml.bind.marshaller.NamespacePrefixMapper`, add the dependency that provides it yourself. This library no longer brings it in. + +The module name is now explicit (`org.entur.siri`). It was derived from the jar file name (`siri.java.model`) before. From f7385d4f92c5f8738c40c489851a10ca5bda17ba Mon Sep 17 00:00:00 2001 From: Thomas Gran Date: Thu, 15 Oct 2026 20:04:34 +0200 Subject: [PATCH 08/11] refactor!: Move SIRI 2.0 util classes from org.rutebanken.siri20.util to org.entur.siri20.util (git-mv) --- src/main/java/org/{rutebanken => entur}/siri20/util/SiriJson.java | 0 src/main/java/org/{rutebanken => entur}/siri20/util/SiriXml.java | 0 .../siri20/util/SiriXmlMarshallerCustomizerTest.java | 0 3 files changed, 0 insertions(+), 0 deletions(-) rename src/main/java/org/{rutebanken => entur}/siri20/util/SiriJson.java (100%) rename src/main/java/org/{rutebanken => entur}/siri20/util/SiriXml.java (100%) rename src/test/java/org/{rutebanken => entur}/siri20/util/SiriXmlMarshallerCustomizerTest.java (100%) diff --git a/src/main/java/org/rutebanken/siri20/util/SiriJson.java b/src/main/java/org/entur/siri20/util/SiriJson.java similarity index 100% rename from src/main/java/org/rutebanken/siri20/util/SiriJson.java rename to src/main/java/org/entur/siri20/util/SiriJson.java diff --git a/src/main/java/org/rutebanken/siri20/util/SiriXml.java b/src/main/java/org/entur/siri20/util/SiriXml.java similarity index 100% rename from src/main/java/org/rutebanken/siri20/util/SiriXml.java rename to src/main/java/org/entur/siri20/util/SiriXml.java diff --git a/src/test/java/org/rutebanken/siri20/util/SiriXmlMarshallerCustomizerTest.java b/src/test/java/org/entur/siri20/util/SiriXmlMarshallerCustomizerTest.java similarity index 100% rename from src/test/java/org/rutebanken/siri20/util/SiriXmlMarshallerCustomizerTest.java rename to src/test/java/org/entur/siri20/util/SiriXmlMarshallerCustomizerTest.java From 7ce41774bb59debba8a4225b484b02e1b62fff87 Mon Sep 17 00:00:00 2001 From: Thomas Gran Date: Thu, 15 Oct 2026 20:04:34 +0200 Subject: [PATCH 09/11] refactor!: Move SIRI 2.0 util classes from org.rutebanken.siri20.util to org.entur.siri20.util (code) BREAKING CHANGE: org.rutebanken.siri20.util.SiriXml and SiriJson are now in org.entur.siri20.util, matching org.entur.siri21.util. There are no forwarders in the old package. --- CLAUDE.md | 7 +++---- README.md | 5 ++++- src/main/java/module-info.java | 2 +- src/main/java/org/entur/siri20/util/SiriJson.java | 2 +- src/main/java/org/entur/siri20/util/SiriXml.java | 2 +- .../java/org/entur/siri/XmlInputFactoryProviderTest.java | 2 +- .../entur/siri20/util/SiriXmlMarshallerCustomizerTest.java | 6 +++--- 7 files changed, 14 insertions(+), 12 deletions(-) diff --git a/CLAUDE.md b/CLAUDE.md index 4e57677..6999808 100644 --- a/CLAUDE.md +++ b/CLAUDE.md @@ -39,7 +39,7 @@ The `cxf-xjc-plugin` generates ~1,900 Java classes from XSD schemas during `gene Generated sources land in `target/generated-sources`. JAXB binding customizations are in `src/main/resources/siri-{2.0,2.1}/xjb/jaxb-bindings.xml` — these map `xsd:dateTime`/`xsd:time` to `java.time.ZonedDateTime` and `xsd:duration` to `java.time.Duration`. -### Handwritten Code (~10 files) +### Handwritten Code (~11 files) | Package | Class | Purpose | |---------|-------|---------| @@ -49,7 +49,8 @@ Generated sources land in `target/generated-sources`. JAXB binding customization | `org.entur.siri.validator` | `SiriValidationEventHandler` | Collects validation errors | | `org.entur.siri21.util` | `SiriXml` | SIRI 2.1 XML marshalling/unmarshalling (JAXB) | | `org.entur.siri21.util` | `SiriJson` | SIRI 2.1 JSON conversion (Jackson + Jakarta XML Bind) | -| `org.rutebanken.siri20.util` | `SiriXml` | SIRI 2.0 XML marshalling/unmarshalling (legacy package) | +| `org.entur.siri20.util` | `SiriXml` | SIRI 2.0 XML marshalling/unmarshalling | +| `org.entur.siri20.util` | `SiriJson` | SIRI 2.0 JSON conversion (Jackson + Jakarta XML Bind) | | `org.entur.siri` | `UnsupportedSiriVersionException` | Exception for unsupported SIRI versions | | (module root) | `module-info.java` | JPMS descriptor: `open module org.entur.siri` | @@ -60,8 +61,6 @@ Generated sources land in `target/generated-sources`. JAXB binding customization - **JPMS**: `src/main/java/module-info.java` declares `open module org.entur.siri` (open because the consumer's JAXB runtime needs reflective access). When you add a generated or handwritten package, add an `exports` line for it. - **No `NamespacePrefixMapper` in the API**: `SiriXml.toXml` takes a `Consumer` customizer. The `JAXBNamespacePrefixMapper` stub shares a package with the JAXB RI, so it cannot be used on the module path. - **JUnit 4** for tests. -- **JSON support exists only for SIRI 2.1** (`SiriJson`), not 2.0. -- **SIRI 2.0 utility lives in legacy package** `org.rutebanken.siri20.util` (historical). ### Test Data diff --git a/README.md b/README.md index feace6e..c338e15 100644 --- a/README.md +++ b/README.md @@ -26,7 +26,7 @@ module my.app { ## Upgrading to 3.0 **Breaking change: `NamespacePrefixMapper` is removed from `SiriXml`.** -The overloads `toXml(Siri, NamespacePrefixMapper)` and `toXml(Siri, NamespacePrefixMapper, OutputStream)` in `org.entur.siri21.util.SiriXml` and `org.rutebanken.siri20.util.SiriXml` now take a `Consumer` instead. The `JAXBNamespacePrefixMapper` dependency is removed, because it shares a package with the JAXB reference implementation and cannot be used on the module path. +The overloads `toXml(Siri, NamespacePrefixMapper)` and `toXml(Siri, NamespacePrefixMapper, OutputStream)` in `org.entur.siri21.util.SiriXml` and `org.entur.siri20.util.SiriXml` now take a `Consumer` instead. The `JAXBNamespacePrefixMapper` dependency is removed, because it shares a package with the JAXB reference implementation and cannot be used on the module path. Before: @@ -48,4 +48,7 @@ SiriXml.toXml(siri, marshaller -> { The property name depends on your JAXB implementation. Use the one that your implementation documents. If your own code imports `com.sun.xml.bind.marshaller.NamespacePrefixMapper`, add the dependency that provides it yourself. This library no longer brings it in. +**Breaking change: the SIRI 2.0 utility package is renamed.** +`org.rutebanken.siri20.util` (`SiriXml`, `SiriJson`) is now `org.entur.siri20.util`, which matches `org.entur.siri21.util`. Update your imports. There are no deprecated forwarders in the old package. + The module name is now explicit (`org.entur.siri`). It was derived from the jar file name (`siri.java.model`) before. diff --git a/src/main/java/module-info.java b/src/main/java/module-info.java index 3fd761f..58fabca 100644 --- a/src/main/java/module-info.java +++ b/src/main/java/module-info.java @@ -8,7 +8,7 @@ exports org.entur.siri.adapter; exports org.entur.siri.validator; exports org.entur.siri21.util; - exports org.rutebanken.siri20.util; + exports org.entur.siri20.util; exports eu.datex2.siri20.schema._2_0rc1._2_0; exports eu.datex2.siri21.schema._2_0rc1._2_0; exports net.opengis.gml.siri; diff --git a/src/main/java/org/entur/siri20/util/SiriJson.java b/src/main/java/org/entur/siri20/util/SiriJson.java index 9127181..262e02d 100644 --- a/src/main/java/org/entur/siri20/util/SiriJson.java +++ b/src/main/java/org/entur/siri20/util/SiriJson.java @@ -13,7 +13,7 @@ * limitations under the Licence. */ -package org.rutebanken.siri20.util; +package org.entur.siri20.util; import com.fasterxml.jackson.annotation.JsonInclude; import com.fasterxml.jackson.databind.DeserializationFeature; diff --git a/src/main/java/org/entur/siri20/util/SiriXml.java b/src/main/java/org/entur/siri20/util/SiriXml.java index 9933633..fabad67 100644 --- a/src/main/java/org/entur/siri20/util/SiriXml.java +++ b/src/main/java/org/entur/siri20/util/SiriXml.java @@ -13,7 +13,7 @@ * limitations under the Licence. */ -package org.rutebanken.siri20.util; +package org.entur.siri20.util; import java.io.IOException; import java.io.InputStream; diff --git a/src/test/java/org/entur/siri/XmlInputFactoryProviderTest.java b/src/test/java/org/entur/siri/XmlInputFactoryProviderTest.java index 08d7ed0..f632ff9 100644 --- a/src/test/java/org/entur/siri/XmlInputFactoryProviderTest.java +++ b/src/test/java/org/entur/siri/XmlInputFactoryProviderTest.java @@ -42,7 +42,7 @@ public class XmlInputFactoryProviderTest { @Test(expected = Exception.class) public void testXxeBlockedSiri20() throws Exception { - org.rutebanken.siri20.util.SiriXml.parseXml(XXE_XML); + org.entur.siri20.util.SiriXml.parseXml(XXE_XML); } @Test(expected = Exception.class) diff --git a/src/test/java/org/entur/siri20/util/SiriXmlMarshallerCustomizerTest.java b/src/test/java/org/entur/siri20/util/SiriXmlMarshallerCustomizerTest.java index 17d33b9..9833cbc 100644 --- a/src/test/java/org/entur/siri20/util/SiriXmlMarshallerCustomizerTest.java +++ b/src/test/java/org/entur/siri20/util/SiriXmlMarshallerCustomizerTest.java @@ -13,7 +13,7 @@ * limitations under the Licence. */ -package org.rutebanken.siri20.util; +package org.entur.siri20.util; import jakarta.xml.bind.Marshaller; import org.junit.BeforeClass; @@ -27,8 +27,8 @@ import java.nio.file.Paths; import java.util.concurrent.atomic.AtomicInteger; -import static org.rutebanken.siri20.util.SiriXml.parseXml; -import static org.rutebanken.siri20.util.SiriXml.toXml; +import static org.entur.siri20.util.SiriXml.parseXml; +import static org.entur.siri20.util.SiriXml.toXml; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertFalse; import static org.junit.Assert.assertTrue; From 0a3657aa4587ea835314c3714fad35891e640b66 Mon Sep 17 00:00:00 2001 From: Thomas Gran Date: Thu, 15 Oct 2026 21:20:26 +0200 Subject: [PATCH 10/11] refactor!: Move generated SIRI types to org.entur.siri.schema.v20/v21 BREAKING CHANGE: generated packages are renamed. XML namespaces and the wire format are unchanged. uk.org.siri.siri2x -> org.entur.siri.schema.v2x.siri uk.org.ifopt.siri2x -> org.entur.siri.schema.v2x.ifopt uk.org.acbs.siri2x -> org.entur.siri.schema.v2x.acsb eu.datex2.siri2x.schema._2_0rc1._2_0 -> org.entur.siri.schema.v2x.datex2 net.opengis.gml.siri -> org.entur.siri.schema.v21.gml Everything now lives under the module root, so it cannot form a split package with other generated models (netex-java-model, ojp-java-model). XJC no longer generates adapters into org.w3._2001.xmlschema. The dateTime/time bindings use the hand-written ZonedDateTimeXmlAdapter and ZonedTimeXmlAdapter instead. module-info.java exports the new packages. --- CLAUDE.md | 4 ++-- src/main/java/module-info.java | 19 ++++++++-------- .../ZonedDateTimeDateTimeXmlAdapter.java | 0 .../adapter/ZonedDateTimeTimeXmlAdapter.java | 0 .../siri/adapter/ZonedDateTimeXmlAdapter.java | 22 +++++++++++++++++++ .../siri/adapter/ZonedTimeXmlAdapter.java | 22 +++++++++++++++++++ .../entur/siri/validator/SiriValidator.java | 4 ++-- .../java/org/entur/siri20/util/SiriJson.java | 2 +- .../java/org/entur/siri20/util/SiriXml.java | 2 +- .../java/org/entur/siri21/util/SiriJson.java | 2 +- .../java/org/entur/siri21/util/SiriXml.java | 2 +- .../resources/siri-2.0/xjb/jaxb-bindings.xml | 16 +++++--------- .../resources/siri-2.1/xjb/jaxb-bindings.xml | 18 ++++++--------- .../util/SiriXmlMarshallerCustomizerTest.java | 2 +- .../entur/siri21/util/MarshallingTest.java | 2 +- .../org/entur/siri21/util/SiriJsonTest.java | 2 +- .../util/SiriXmlMarshallerCustomizerTest.java | 2 +- .../org/entur/siri21/util/SiriXmlTest.java | 2 +- 18 files changed, 79 insertions(+), 44 deletions(-) create mode 100644 src/main/java/org/entur/siri/adapter/ZonedDateTimeDateTimeXmlAdapter.java create mode 100644 src/main/java/org/entur/siri/adapter/ZonedDateTimeTimeXmlAdapter.java create mode 100644 src/main/java/org/entur/siri/adapter/ZonedDateTimeXmlAdapter.java create mode 100644 src/main/java/org/entur/siri/adapter/ZonedTimeXmlAdapter.java diff --git a/CLAUDE.md b/CLAUDE.md index 6999808..4d373b0 100644 --- a/CLAUDE.md +++ b/CLAUDE.md @@ -34,8 +34,8 @@ mvn generate-sources ### Code Generation (bulk of the codebase) The `cxf-xjc-plugin` generates ~1,900 Java classes from XSD schemas during `generate-sources`: -- **SIRI 2.0** XSDs → `uk.org.siri.siri20.*` (plus `uk.org.ifopt.siri20`, `uk.org.acbs.siri20`, `eu.datex2.siri20`) -- **SIRI 2.1** XSDs → `uk.org.siri.siri21.*` (plus `uk.org.ifopt.siri21`, `uk.org.acbs.siri21`, `eu.datex2.siri21`) +- **SIRI 2.0** XSDs → `org.entur.siri.schema.v20.siri` (plus `.ifopt`, `.acsb`, `.datex2`) +- **SIRI 2.1** XSDs → `org.entur.siri.schema.v21.siri` (plus `.ifopt`, `.acsb`, `.datex2`, `.gml`) Generated sources land in `target/generated-sources`. JAXB binding customizations are in `src/main/resources/siri-{2.0,2.1}/xjb/jaxb-bindings.xml` — these map `xsd:dateTime`/`xsd:time` to `java.time.ZonedDateTime` and `xsd:duration` to `java.time.Duration`. diff --git a/src/main/java/module-info.java b/src/main/java/module-info.java index 58fabca..4f144d3 100644 --- a/src/main/java/module-info.java +++ b/src/main/java/module-info.java @@ -9,14 +9,13 @@ exports org.entur.siri.validator; exports org.entur.siri21.util; exports org.entur.siri20.util; - exports eu.datex2.siri20.schema._2_0rc1._2_0; - exports eu.datex2.siri21.schema._2_0rc1._2_0; - exports net.opengis.gml.siri; - exports org.w3._2001.xmlschema; - exports uk.org.acbs.siri20; - exports uk.org.acbs.siri21; - exports uk.org.ifopt.siri20; - exports uk.org.ifopt.siri21; - exports uk.org.siri.siri20; - exports uk.org.siri.siri21; + exports org.entur.siri.schema.v20.acsb; + exports org.entur.siri.schema.v20.datex2; + exports org.entur.siri.schema.v20.ifopt; + exports org.entur.siri.schema.v20.siri; + exports org.entur.siri.schema.v21.acsb; + exports org.entur.siri.schema.v21.datex2; + exports org.entur.siri.schema.v21.gml; + exports org.entur.siri.schema.v21.ifopt; + exports org.entur.siri.schema.v21.siri; } diff --git a/src/main/java/org/entur/siri/adapter/ZonedDateTimeDateTimeXmlAdapter.java b/src/main/java/org/entur/siri/adapter/ZonedDateTimeDateTimeXmlAdapter.java new file mode 100644 index 0000000..e69de29 diff --git a/src/main/java/org/entur/siri/adapter/ZonedDateTimeTimeXmlAdapter.java b/src/main/java/org/entur/siri/adapter/ZonedDateTimeTimeXmlAdapter.java new file mode 100644 index 0000000..e69de29 diff --git a/src/main/java/org/entur/siri/adapter/ZonedDateTimeXmlAdapter.java b/src/main/java/org/entur/siri/adapter/ZonedDateTimeXmlAdapter.java new file mode 100644 index 0000000..878facd --- /dev/null +++ b/src/main/java/org/entur/siri/adapter/ZonedDateTimeXmlAdapter.java @@ -0,0 +1,22 @@ +package org.entur.siri.adapter; + +import jakarta.xml.bind.annotation.adapters.XmlAdapter; +import java.time.ZonedDateTime; +import java.time.format.DateTimeFormatter; + +/** + * JAXB adapter for {@code xsd:dateTime} bound to {@link ZonedDateTime}. Written by hand so that XJC does not + * generate an adapter class into the {@code org.w3._2001.xmlschema} package, which would be a split package. + */ +public class ZonedDateTimeXmlAdapter extends XmlAdapter { + + @Override + public ZonedDateTime unmarshal(String value) { + return ZonedDateTimeAdapter.parse(value); + } + + @Override + public String marshal(ZonedDateTime value) { + return DateTimeFormatter.ISO_OFFSET_DATE_TIME.format(value); + } +} diff --git a/src/main/java/org/entur/siri/adapter/ZonedTimeXmlAdapter.java b/src/main/java/org/entur/siri/adapter/ZonedTimeXmlAdapter.java new file mode 100644 index 0000000..a318f6c --- /dev/null +++ b/src/main/java/org/entur/siri/adapter/ZonedTimeXmlAdapter.java @@ -0,0 +1,22 @@ +package org.entur.siri.adapter; + +import jakarta.xml.bind.annotation.adapters.XmlAdapter; +import java.time.ZonedDateTime; +import java.time.format.DateTimeFormatter; + +/** + * JAXB adapter for {@code xsd:time} bound to {@link ZonedDateTime}. Written by hand so that XJC does not + * generate an adapter class into the {@code org.w3._2001.xmlschema} package, which would be a split package. + */ +public class ZonedTimeXmlAdapter extends XmlAdapter { + + @Override + public ZonedDateTime unmarshal(String value) { + return ZonedDateTimeAdapter.parse(value); + } + + @Override + public String marshal(ZonedDateTime value) { + return DateTimeFormatter.ISO_OFFSET_TIME.format(value); + } +} diff --git a/src/main/java/org/entur/siri/validator/SiriValidator.java b/src/main/java/org/entur/siri/validator/SiriValidator.java index 42d1fc1..bece60e 100644 --- a/src/main/java/org/entur/siri/validator/SiriValidator.java +++ b/src/main/java/org/entur/siri/validator/SiriValidator.java @@ -51,10 +51,10 @@ public class SiriValidator { private static void init() throws JAXBException { if (siri20jaxbContext == null) { - siri20jaxbContext = JAXBContext.newInstance(uk.org.siri.siri20.Siri.class); + siri20jaxbContext = JAXBContext.newInstance(org.entur.siri.schema.v20.siri.Siri.class); } if (siri21jaxbContext == null) { - siri21jaxbContext = JAXBContext.newInstance(uk.org.siri.siri21.Siri.class); + siri21jaxbContext = JAXBContext.newInstance(org.entur.siri.schema.v21.siri.Siri.class); } } /** diff --git a/src/main/java/org/entur/siri20/util/SiriJson.java b/src/main/java/org/entur/siri20/util/SiriJson.java index 262e02d..d2b0304 100644 --- a/src/main/java/org/entur/siri20/util/SiriJson.java +++ b/src/main/java/org/entur/siri20/util/SiriJson.java @@ -23,7 +23,7 @@ import com.fasterxml.jackson.databind.type.TypeFactory; import com.fasterxml.jackson.databind.util.StdDateFormat; import com.fasterxml.jackson.module.jakarta.xmlbind.JakartaXmlBindAnnotationIntrospector; -import uk.org.siri.siri20.Siri; +import org.entur.siri.schema.v20.siri.Siri; import java.io.IOException; import java.io.OutputStream; diff --git a/src/main/java/org/entur/siri20/util/SiriXml.java b/src/main/java/org/entur/siri20/util/SiriXml.java index fabad67..dc54d94 100644 --- a/src/main/java/org/entur/siri20/util/SiriXml.java +++ b/src/main/java/org/entur/siri20/util/SiriXml.java @@ -32,7 +32,7 @@ import org.entur.siri.XmlInputFactoryProvider; -import uk.org.siri.siri20.Siri; +import org.entur.siri.schema.v20.siri.Siri; public class SiriXml { diff --git a/src/main/java/org/entur/siri21/util/SiriJson.java b/src/main/java/org/entur/siri21/util/SiriJson.java index 23ff35d..eda3976 100644 --- a/src/main/java/org/entur/siri21/util/SiriJson.java +++ b/src/main/java/org/entur/siri21/util/SiriJson.java @@ -23,7 +23,7 @@ import com.fasterxml.jackson.databind.type.TypeFactory; import com.fasterxml.jackson.databind.util.StdDateFormat; import com.fasterxml.jackson.module.jakarta.xmlbind.JakartaXmlBindAnnotationIntrospector; -import uk.org.siri.siri21.Siri; +import org.entur.siri.schema.v21.siri.Siri; import java.io.IOException; import java.io.OutputStream; diff --git a/src/main/java/org/entur/siri21/util/SiriXml.java b/src/main/java/org/entur/siri21/util/SiriXml.java index 58db958..92293ca 100644 --- a/src/main/java/org/entur/siri21/util/SiriXml.java +++ b/src/main/java/org/entur/siri21/util/SiriXml.java @@ -16,7 +16,7 @@ package org.entur.siri21.util; import org.entur.siri.XmlInputFactoryProvider; -import uk.org.siri.siri21.Siri; +import org.entur.siri.schema.v21.siri.Siri; import jakarta.xml.bind.JAXBContext; import jakarta.xml.bind.JAXBException; diff --git a/src/main/resources/siri-2.0/xjb/jaxb-bindings.xml b/src/main/resources/siri-2.0/xjb/jaxb-bindings.xml index 4c9fa1f..c69c758 100644 --- a/src/main/resources/siri-2.0/xjb/jaxb-bindings.xml +++ b/src/main/resources/siri-2.0/xjb/jaxb-bindings.xml @@ -20,12 +20,8 @@ - - + + @@ -33,25 +29,25 @@ - + - + - + - + diff --git a/src/main/resources/siri-2.1/xjb/jaxb-bindings.xml b/src/main/resources/siri-2.1/xjb/jaxb-bindings.xml index c375d52..b549ec9 100644 --- a/src/main/resources/siri-2.1/xjb/jaxb-bindings.xml +++ b/src/main/resources/siri-2.1/xjb/jaxb-bindings.xml @@ -20,12 +20,8 @@ - - + + @@ -33,30 +29,30 @@ - + - + - + - + - + diff --git a/src/test/java/org/entur/siri20/util/SiriXmlMarshallerCustomizerTest.java b/src/test/java/org/entur/siri20/util/SiriXmlMarshallerCustomizerTest.java index 9833cbc..f916095 100644 --- a/src/test/java/org/entur/siri20/util/SiriXmlMarshallerCustomizerTest.java +++ b/src/test/java/org/entur/siri20/util/SiriXmlMarshallerCustomizerTest.java @@ -18,7 +18,7 @@ import jakarta.xml.bind.Marshaller; import org.junit.BeforeClass; import org.junit.Test; -import uk.org.siri.siri20.Siri; +import org.entur.siri.schema.v20.siri.Siri; import java.io.ByteArrayOutputStream; import java.io.IOException; diff --git a/src/test/java/org/entur/siri21/util/MarshallingTest.java b/src/test/java/org/entur/siri21/util/MarshallingTest.java index 107c4ce..00eb8f1 100644 --- a/src/test/java/org/entur/siri21/util/MarshallingTest.java +++ b/src/test/java/org/entur/siri21/util/MarshallingTest.java @@ -17,7 +17,7 @@ import org.junit.BeforeClass; import org.junit.Test; -import uk.org.siri.siri21.Siri; +import org.entur.siri.schema.v21.siri.Siri; import java.io.IOException; import java.io.RandomAccessFile; diff --git a/src/test/java/org/entur/siri21/util/SiriJsonTest.java b/src/test/java/org/entur/siri21/util/SiriJsonTest.java index 3722a15..316d138 100644 --- a/src/test/java/org/entur/siri21/util/SiriJsonTest.java +++ b/src/test/java/org/entur/siri21/util/SiriJsonTest.java @@ -17,7 +17,7 @@ import org.junit.BeforeClass; import org.junit.Test; -import uk.org.siri.siri21.Siri; +import org.entur.siri.schema.v21.siri.Siri; import java.io.ByteArrayOutputStream; import java.io.IOException; diff --git a/src/test/java/org/entur/siri21/util/SiriXmlMarshallerCustomizerTest.java b/src/test/java/org/entur/siri21/util/SiriXmlMarshallerCustomizerTest.java index 7aa7a0a..73abcfe 100644 --- a/src/test/java/org/entur/siri21/util/SiriXmlMarshallerCustomizerTest.java +++ b/src/test/java/org/entur/siri21/util/SiriXmlMarshallerCustomizerTest.java @@ -19,7 +19,7 @@ import org.glassfish.jaxb.runtime.marshaller.NamespacePrefixMapper; import org.junit.BeforeClass; import org.junit.Test; -import uk.org.siri.siri21.Siri; +import org.entur.siri.schema.v21.siri.Siri; import java.io.ByteArrayOutputStream; import java.io.IOException; diff --git a/src/test/java/org/entur/siri21/util/SiriXmlTest.java b/src/test/java/org/entur/siri21/util/SiriXmlTest.java index ec215d0..46c28b8 100644 --- a/src/test/java/org/entur/siri21/util/SiriXmlTest.java +++ b/src/test/java/org/entur/siri21/util/SiriXmlTest.java @@ -18,7 +18,7 @@ import org.entur.siri.validator.SiriValidator; import org.junit.BeforeClass; import org.junit.Test; -import uk.org.siri.siri21.Siri; +import org.entur.siri.schema.v21.siri.Siri; import java.io.IOException; import java.io.RandomAccessFile; From 3fd241efd5eba1ac313fd727623992a33f30ae4e Mon Sep 17 00:00:00 2001 From: Thomas Gran Date: Thu, 15 Oct 2026 21:23:06 +0200 Subject: [PATCH 11/11] docs: document the generated package rename in the README --- README.md | 12 ++++++++++++ 1 file changed, 12 insertions(+) diff --git a/README.md b/README.md index c338e15..c74afc6 100644 --- a/README.md +++ b/README.md @@ -25,6 +25,18 @@ module my.app { ## Upgrading to 3.0 +**Breaking change: the generated packages are renamed.** +The XML namespaces and the wire format are unchanged. Update your imports: + +| Before | After | +|---|---| +| `uk.org.siri.siri20` / `siri21` | `org.entur.siri.schema.v20.siri` / `v21.siri` | +| `uk.org.ifopt.siri20` / `siri21` | `org.entur.siri.schema.v20.ifopt` / `v21.ifopt` | +| `uk.org.acbs.siri20` / `siri21` | `org.entur.siri.schema.v20.acsb` / `v21.acsb` | +| `eu.datex2.siri20.schema._2_0rc1._2_0` / `siri21...` | `org.entur.siri.schema.v20.datex2` / `v21.datex2` | +| `net.opengis.gml.siri` | `org.entur.siri.schema.v21.gml` | + + **Breaking change: `NamespacePrefixMapper` is removed from `SiriXml`.** The overloads `toXml(Siri, NamespacePrefixMapper)` and `toXml(Siri, NamespacePrefixMapper, OutputStream)` in `org.entur.siri21.util.SiriXml` and `org.entur.siri20.util.SiriXml` now take a `Consumer` instead. The `JAXBNamespacePrefixMapper` dependency is removed, because it shares a package with the JAXB reference implementation and cannot be used on the module path.