I am adding IC integration with IBM SBT SDK (Java) into an existing project which still uses xerces 2.4.0 (as of March 2009).
Using IBM SBT SDK 1.0.x did not cause any problems here, but the XML serialization implementation of 1.1.0 completely relies on org.w3c.xml.ls.DOMImplementationLS and such stuff which was introduced after moving xerces to "xercesImpl" about 2004.
However the project contains much code working with XML based on xerces and xml-apis, and it looks dangerous to move too fast to "more current" versions of these libraries. Thus I want to move "no further than absolutely required".
Thanks to maven no one can directly see which version of any artifact is loaded if it is not directly referenced in the pom.xml. Thus my question:
Which version of xercesImpl is "really" required by IBM SBT SDK 1.1.0? 2.4.0 is not sufficient, as some methods used in the SBT SDK are not yet implemented there...
xerces version in the dependency would be 2.9.0; looking at the DOMUtil.java#loadDriver() class however there are workarounds to avoid the SBTK to use xerces altogether:
if your container allows to control the classpath tree, shadowing the xerces library from the toolkit will have it default to some other driver. In alternative you can provide your own XercesDriver class compatible with old xerces versions and leverage the classloader to have it loaded in place of ours.
if you are in a osgi container you can also make sure the host application manifest declares a dependency to a version <=2.4.0 and load both xerces versions letting the container fix the dependencies for you
anyway, to answer the question, using:
mvn dependency:list
I get version 2.9.0 for xerces:
The following files have been resolved:
com.ibm.sbt:com.ibm.commons:eclipse-plugin:9.0.0:provided
p2.eclipse-plugin:javax.servlet:jar:3.0.0.v201112011016:system
p2.eclipse-plugin:javax.xml:jar:1.3.4.v201005080400:system
p2.eclipse-plugin:org.apache.xalan:jar:2.7.1.v201005080400:system
p2.eclipse-plugin:org.apache.xerces:jar:2.9.0.v201101211617:system
p2.eclipse-plugin:org.apache.xml.resolver:jar:1.2.0.v201005080400:system
p2.eclipse-plugin:org.apache.xml.serializer:jar:2.7.1.v201005080400:system
p2.eclipse-plugin:org.eclipse.core.contenttype:jar:3.4.200.v20120523-2004:system
p2.eclipse-plugin:org.eclipse.core.jobs:jar:3.5.300.v20120912-155018:system
p2.eclipse-plugin:org.eclipse.core.runtime:jar:3.8.0.v20120912-155025:system
p2.eclipse-plugin:org.eclipse.equinox.app:jar:1.3.100.v20120522-1841:system
p2.eclipse-plugin:org.eclipse.equinox.common:jar:3.6.100.v20120522-1841:system
p2.eclipse-plugin:org.eclipse.equinox.preferences:jar:3.5.1.v20121031-182809:system
p2.eclipse-plugin:org.eclipse.equinox.registry:jar:3.5.200.v20120522-1841:system
p2.eclipse-plugin:org.eclipse.osgi:jar:3.8.2.v20130124-134944:system
Related
Clearly the com.sun.xml.bind:jaxb-impl artifact is labelled "Old JAXB Runtime module" in the maven repository (see link below), and yet both of these artifacts are still getting new releases:
https://mvnrepository.com/artifact/org.glassfish.jaxb/jaxb-runtime
https://mvnrepository.com/artifact/com.sun.xml.bind/jaxb-impl
This answer Which artifacts should I use for JAXB RI in my Maven project?
does not clarify the difference.
The accepted answer to both the above question and this one How to resolve java.lang.NoClassDefFoundError: javax/xml/bind/JAXBException conclude that for Java 9+ you should use: org.glassfish.jaxb:jaxb-runtime
But I have code using com.sun.xml.bind:jaxb-impl and it appears to be working fine. So what do I lose or gain by moving to jaxb-runtime?
Even the latest (3.0.2 at the time I write this) version is available for the "OLD" jaxb-impl module. If Oracle isn't doing this anymore, who makes the com.sun.xml.bind:jaxb-impl artifact? What is it for? Why doesn't it share the Maven group coordinates with jaxb-runtime?
Is there any central location that clearly documents what the current state of affairs is with JAXB?
There is just so much confusion with JAXB now.
P.S. I need to remain compatible with Java 8 for the time being - so I can't go to 3.x yet, and 2.4.x appears to be an abandoned attempt at fixing the modularity that they foolishly broke when it was split out of the JDK.
The only difference between jaxb-impl and jaxb-runtime is packaging: jaxb-impl bundles istack/txw2 inside the jar, whereas jaxb-runtime provides them via separate dependencies.
Version Compatibility and the JakartaEE Migration
I've been trying to make sense of this for the last day, and it's incredibly confusing. Particularly when you're trying to avoid the java.xml.bind to jakarta.xml.bind migration. There's out of date information everywhere and some broken releases in the jaxb-impl 2.3.x release line.
Best I can tell, GlassFish was providing the JAXB reference implementation. It's since moved to EE4J, but releases continue from that project against both sets of coordinates. Appears that com.sun.xml.bind:jaxb-ri is where the latest full bundles are released:
https://github.com/eclipse-ee4j/jaxb-ri/
Having figured out that piece of history, the real mess is that none of the artifacts reflect the javax.xml.bind to jakarta.xml.bind move in their artifact coordinates, only in the versions. This means if you're in ecosystem where you need both to exist, you're going to have a bad time.
For instance, the 2.3.3 release changed from depending on javax.xml.bind:jaxb-api to jakarta.xml.bind:jakarta.xml.bind-api because at 2.x, the jakarta artifacts provide the javax.xml.bind packages. At version 3.0.0 it provides jakarta.xml.bind.
The implementations are the same at 3.0.0 which means while the earlier versions could happily exist at runtime, you have no way of resolving them both in build tools and conflict resolution is going to break legacy uses of javax.xml.bind APIs.
Allow javax.xml.bind and jakarta.xml.bind to coexist
For projects that need both APIs to coexist without migrating the legacy code:
For javax.xml.bind use com.sun.xml.bind:jaxb-impl:2.3.6. Ignore the 3.0.0 and later releases. Add an explicit dependency on javax.xml.bind:jaxb-api:2.3.1 so that you have a package providing the javax.xml.bind API
For jakarta.xml.bind use the latest org.glassfish.jaxb:jaxb-runtime. Ignore the releases earlier than 3.0.0
Runtime compatibility with jakarta.xml.bind
Use the tomcat-jakartaee-migration tool to rewrite classes for deployment.
For Gradle projects, you can use the gradle-jakartaee-migration-plugin, and get the benefit of capabilities and transforms at development time too.
Migrate to jakarta.xml.bind
You can use either of the coordinates for the runtime based on your preferences for packaging:
com.sun.xml.bind:jaxb-impl:4.0.0
org.glassfish.jaxb:jaxb-runtime:4.0.0
Both depend on jakarta.xml.bind:jakarta.xml.bind-api with the jakarta.xml.bind package namespace.
In a setup like this:
Project
-ModuleA
implementation lib:1.1
implementation project(:ModuleB)
-ModuleB
api lib:1.2
-ExternalJar1
-lib1.3
-ExternalJar2
-lib1.4
How does Gradle determine what lib version to select? As per this SO answer, version 1.4 will be selected because it's the highest version and we have not specified "any specific constraints for transitive dependencies resolution". If that's correct, wouldn't ModuleA code break if it's not expecting a newer version? How can I fix that?
Do external libraries (imported jars) live in a closed sandbox - neither exposing their dependencies to project's classpath, nor using project dependencies in their classpath?
Assuming version 1.3 and 1.4 are not compatible, I can't even force one version as suggested in this SO post, what option do I have to fix this setup?
I have a legacy monolith application, which uses elasticsearch 1.X and now we need to run elasticsearch 7.X in the same application, so that same application index and query data in both version of elasticsearch.
In my project, there are multiple modules and they all have their own POM and parent POM, and my new module which uses elasticsearch 7.X depends on some module which uses 1.X.
Although I have excluded 1.X specific dependency in module which uses 7.X, Still it gives me below Error:
[76B7CCD2] java.lang.NoSuchFieldError: LATEST at
org.elasticsearch.Version.(Version.java:49) at
org.elasticsearch.common.io.stream.StreamInput.(StreamInput.java:114)
After doing a lot of research and using this and this link, As explained I excluded the elastic 1.x dependency but still looks like as my other sub-module still has ES 1.X and which is required as well, hence overall classpath of my application has both versions of org.elasticsearch.Version java class from the same package org.elasticsearch, which I feel is the root cause.
Now, How can I include the same class from the same package from two different versions of a same library.
You can't. You can only have one class with a given full qualified name (package + name).
You can try to shade one of the packages (i.e. rename it) with the Maven shade plugin (never tried that, actually), which might work.
Usually, you need to change code and fiddle around until you find a version of elasticsearch that works with all dependencies.
I am in a bit of a jam.
I am working on upgrading our software to have Kettle 6.1. Specifically, we need the feature of S3FileOutput. Meanwhile, our application was already using the aws-sdk for other things.
So I am running into a problem: Pentaho Kettle requires version 1.0.something of aws-sdk. Our application, on the otherhand needs 1.9.6 of the aws-sdk.
To give more details, the feature of Kettle we require is in the pentaho-big-data-legacy plugin. Even if I upgrade to the latest version of Kettle, pentaho-big-data-legacy still uses the old version of the aws-sdk.
I've read a bit about plugins having special classloaders, so one option I was considering is that maybe I am not downloading the right dependency. However, when I tried downloading pentaho-big-data-plugin instead of pentaho-big-data-legacy, I got weird errors, so I stopped going down this path.
I was wondering if there is any way I could put the Kettle Libs in one folder, and my application libs in another folder, and then set some sort of a PENTAHO environment variable to pick up the libraries from the alternative folder.
Another option is if I could somehow set the pentaho classloader, but I don't know if this is possible.
What are my options for having 2 versions of the aws-sdk in my application, with regards to Kettle?
Maven can do much more than download dependencies.
The Maven Shade plugin can help with your current predicament. During a build, it can rename packages.
You would make a project that builds a "fat jar" (or "uber jar") with Pentaho Kettle and its version of the aws-sdk re-packaged as appropriate. That dependency would be handled before your project is built, so you are free to use whatever version of aws-sdk you like since there is no longer a conflict on package names.
I am using AEM 6.1 with Maven to manage dependencies. I can see the bundle com.adobe.granite.poi version 2.0.0 being shipped along with the AEM instance. But I cant seem to find a maven dependency for the library in both Adobe public repository as well as Maven central repository.
I have checked the uber-jar dependency uber-jar-6.1.0-obfuscated-apis and could not locate it there as well.
I can find version 1.0.2 and 1.1.0 of com.adobe.granite.poi in the Adobe public nexus. I would prefer to avoid using a older version if possible. How would you manage this problem.
you can find granite poi 2.0.0 here - http://nexus.citytech.ctmsp.com/content/groups/public/com/adobe/granite/com.adobe.granite.poi/2.0.0/
BTW, I have had this experience with a couple of apis whose newer version are not available on adobe's maven repository, but they are shipped with AEM. what my understanding is that if its not available on adobe-public, its not (or not any longer) a public api and you are not supposed to use it. you may want to find an alternative.