Which Maven bundle plugin should be used - bundle

Which maven plugin to be used to generate OSGi bundle and how is bnd-maven-plugin different from maven-bundle-plugin.

maven-bundle-plugin has been around for long time and that is why it most widely used.
bnd-maven-plugin was created not so long ago (mod 2015) to address some issues with maven-bundle-plugin. I suggest you read Neil Bartlett's post to understand the motivations.
The differences I'm aware of are:
maven-bundle-plugin replaces maven's default jar plugin (that is why you need the artifact type to be bundle and not jar) while bnd-maven-plugin does not. The formar causes issues in some cases (with some other maven plugins). The later basically means the packaging is done twice (first by BND and then by maven jar plugin)
maven-bundle-plugin can be configured directly in the pom or via bnd file. bnd-maven-plugin can only be configured via bnd file

Related

Maven plugin Tycho -> when to use it and when not to use it

What is the purpose to use Maven Tycho plugins. I read here tycho is used for building eclipse plugins and OSGI bundle.
Questions:- Can not we build eclipse plugins and OSGI bundle just by using the plain old maven POM.xml file[by not using tycho plugin].
What does maven need tycho plugin to help it build eclipse plugin and OSGI bundles?
Why should we use Maven tycho plugin to build eclipse plugins and OSGI bundles?
When using maven (or other command line build tools) manifest.mf) in combination with Eclipse (or another IDE) the classpath ends up being written down twice - once in the pom.xml and once in the Eclipse .classpath (or, for OSGi, in the target platform and manifest.mf). This violates the DRY principle.
There are various solutions to this problem. One is something like m2e, where you use the pom.xml to generate the Eclipse .classpath. Alternatively, you can go in the other direction and start by getting things compiling in Eclipse, and then use a maven plugin to convert that Eclipse setup to a maven build. This is what Tycho does, with the extra wrinkle that it works from a PDE manifest + target platform rather than directly from the .classpath.
Maven doesn't have a built-in packaging type for OSGi bundles and/or Eclipse plugins. So unless you want to use the jar packaging type and manually add OSGi specifics, you need a Maven plug-in to help you with this.
Tycho is one of the plugins that add support for building OSGi bundles.

What is the purpose of providing a downloaded pom.xml on mvnrepository.com

On mvnrepositry, when you search for a certain module, there's a link to download the binary. For some versions it has a pom.xml file available for download instead of the jar. What are you supposed to do with that pom.xml? It seems like if I specify a version that does not have a downloadable jar, but instead downloadable pom.xml, my maven build will fail. Is what I'm seeing correct?
Modules that only have pom files are maven modules with pom packaging. They are used to aggregate multiple modules into one unit. You can use such a module as a dependency for your maven project. Maven will download the pom file, analyze the dependencies included in that pom file and download those & add it to your automatically.
Even modules that have jars (jar packaging) have a pom file associated with them. This pom file defines the other dependencies that are required for using it. Maven will automatically process and fetch those dependencies (transitive dependencies).
This makes specifying and managing dependency for any project. You will specify the top level modules that your projects directly depends on and other things required will automatically figured out and downloaded. It also makes it easier when you have upgrade to a new version - all the transitive dependencies will get upgraded automatically.
One of the reason that cause this is because of licensing issue.
License for such JARs prohibit public redistribution in such approach. So someone provide only the POM so that you can get the JAR yourself and install it to your local maven repo/ internal repo, together with the POM provided.

Add multiple JARs and Javadoc to local Maven repository

I have a number of JAR files that comprise two different Java SDKs for BOXI R3.1: BusinessObjects Enterprise Java SDK and the Web Services Consumer Java SDK.
The BusinessObjects Enterprise Java SDK has a number of 'core' JARs:
biarengine.jar
biplugins.jar
cecore.jar
celib.jar
ceplugins_client.jar
ceplugins_core.jar
ceplugins_cr.jar
cereports.jar
cesession.jar
ceutils.jar
corbaidl.jar
ebus405.jar
flash.jar
SL_plugins.jar
logging.jar
pluginhelper.jar
xcelsius.jar
and a number of dependencies:
asn1.jar
backport-util-concurrent-2.2.jar
certj.jar
commons-logging.jar
derby.jar
freessl201.jar
jsafe.jar
log4j.jar
rascore.jar
sslj.jar
The Javadocs are available as a ZIP file.
The situation is similar for the web-services SDK, so I will omit the details.
Goal: package each SDK and its Javadoc as a local, Maven repository (it doesn't appear that SAP is providing a remote one).
Questions:
can one Maven repository contain multiple JAR files? The mvn deploy:deploy-file plugin seems to only work on a single file: How to add a jar, source and Javadoc to the local Maven repository?
should Javadocs be kept in ZIP format in a Maven repository?
if i choose to make to repos for a given SDK (i.e. core and dependencies), is specifying the linkage as easy as editing the core repos' configuration file?
rather than creating a repo for the dependencies, I'm assuming that it would be better to identify and reference existing Maven repos (e.g log4j.jar). Will this lead me to JAR hell?
Yes a maven repo can contain multiple files, you can execute mvn deploy:deploy-file on each one (using -Djavadoc and -Dsources as needed).
To specify dependencies for a jar, create a pom file for it (with dependencies) and use -DpomFile (and omit -DgeneratePom) in mvn deploy:deploy-file.
Yes you should not re-invent the wheel and deploy artifacts to your repository that are already in central. You can use tools like http://mvnrepository.com to search for your jars (look META-INF/MANIFEST.MF in your jars to find the version).
For more info see: http://maven.apache.org/plugins/maven-deploy-plugin/deploy-file-mojo.html.

Tycho resolves the wrong version of my own manifest-first artifacts

Consider the following scenario: My application has some dependencies on my own POM-first artifacts (built with pure Maven) and some dependencies on my own manifest-first artifacts (built with Tycho). For the POM-first artifacts, Tycho resolves the exact the version I specified in the POM. For the manifest-first artifacts, Tycho resolves the locally built units which may have a higher version.
In my concrete case, I specified a dependency in the pom.xml to the manifest-first artifact in version 1.2.0, but I get warning "The following locally built units have been used to resolve project dependencies" with version 1.3.0.2012xxx.
I have already found following bugs and discussions, but I don't understand why there is a difference in Tycho resolving POM-first and manifest-first dependencies.
https://bugs.eclipse.org/bugs/show_bug.cgi?id=355367
http://dev.eclipse.org/mhonarc/lists/tycho-user/msg01673.html
Dependency-resolution is a two-step process in Tycho:
First, Tycho computes the so-called target platform, which is
the set of artifacts that are considered for dependency resolution.
In this step, Tycho evaluates the POM dependencies according to the
Maven rules and adds the result to the target platform. Also, all
Tycho artifacts you have built locally with mvn install are added
to the target platform.
Then, Tycho resolves your project's dependencies (from the
MANIFEST.MF, feature.xml, etc.) according to the OSGi rules. Unlike
in Maven dependencies, OSGi dependencies are typically specified as
version ranges. So if you write
Require-Bundle: my.bundle;bundle-version="1.2.0"
you are saying that you want version 1.2.0 or later. You typically don't want to specify an exact version here, because this would have implications on the runtime. But you do want to control what happens at build time, which is why there are various ways to control the content of the target platform.
In your particular case, you have your POM-first artifacts in the target platform in the version specified in the POM. Then, you also seem to be specifying a POM dependency to your Tycho artifacts (which is uncommon, but okay), so you will have the Tycho artifacts in the specified version in the target platform. But since you have also built a newer version of the Tycho artifacts locally with mvn install, these will also be in the target platform. The dependency resolution (step 2) hence has a choice between two versions, an will typically pick the later version.
To prevent the locally built artifacts from being added to the target platform, you can delete the file ~/.m2/repository/.meta/p2-local-metadata.properties. (I'm assuming you already know this, but just to be sure. Bug 355367 will also bring a alternative, more convenient option in 0.16.0.)
And now I finally get to your question why the behaviour is different for POM-first artifacts compared to Tycho artifacts:
Assume multiple Tycho artifacts are built together in the same reactor. Then each artifact can use the other artifacts as dependencies without needing any specific target platform configuration, e.g. you don't need POM dependencies to the artifacts in the same reactor. (Or in other words: upstream artifacts from the same reactor are automatically part of a module's target platform.) So in order to support re-builds of parts of a Tycho reactor (after a mvn install of the full reactor), locally installed Tycho artifacts need to be added to every module's target platform. Tycho can't know if they were originally part of the same reactor, so it just adds them all.
For POM-first artifacts, the reference to the artifact is always there (through the Maven configuration inheritance), even if only a part of a Tycho reactor is built. Therefore there doesn't need to be any mechanism for picking up any version of the locally built POM-first artifacts, but Tycho can add the exactly specified version to the target platform.
For those interested to force tycho to ignore local artifacts when resolving the target platform, add the CLI tycho.localArtifacts=ignore as in e.g.
mvn clean install -Dtycho.localArtifacts=ignore
More details can be found on the Tycho-Target Eclipse Wiki

Javadoc creation with maven

We have created a new artifact to generate javadoc. We have 40 artifacts defined as dependencies. Task is to create javadoc.jar and html pages for the 40 dependency artifacts.
Whats the best approach to achieve this in maven?
This is very unusual. Javadoc works on sources, not compiled classes, whereas maven dependencies reference classes, not sources.
So to make this work you'll have to do all of this:
since this is a dedicated javadoc artifact, it won't have a main JAR artifact, so you'll probably want to set the packaging to POM
make sure all your referenced artifacts have attached sources
add <classifier>sources</classifier> to all your dependencies
unpack all dependencies to a common root folder using dependency:unpack-dependencies
run javadoc on that folder
create a jar using the maven-assembly-plugin
attach that jar to the build using the buildhelper plugin
On re-reading the question: I'm assuming that you want to create combined docs of all dependencies. If not, you'll need 40 separate executions each of the javadoc, assembly and buildhelper plugins. Good luck with that.
A slightly more automated approach than the answer above:
So to make this work you'll have to do all of this:
since this is a dedicated javadoc artifact, it won't have a main JAR artifact, so you'll probably want to set the packaging to POM
make sure all your referenced artifacts have attached sources
add <classifier>sources</classifier> to all your dependencies
unpack all dependencies to a common root folder using dependency:unpack-dependencies
Change your sources directory to where you unpacked all the dependencies
Use the source plugin to manage all the Javadoc generation and deployment

Resources