bnd, Bndtools, Maven, Gradle, and baselining
bnd is the core tool for creating and analyzing OSGi artifacts. Bndtools adds an Eclipse workspace and runtime experience; Maven and Gradle plugins integrate the same analysis into ordinary builds.
Build by analysis
bnd reads compiled bytecode, determines referenced packages, calculates imports, applies export instructions, generates DS/Metatype descriptors, and verifies metadata.
Bundle-SymbolicName: com.acme.charging.core
Export-Package: com.acme.charging.api;version=1.4.0
-dsannotations: *
-metatypeannotations: *
-reproducible: true
Avoid Import-Package: * as a thoughtless handwritten
manifest. In bnd, a final * instruction means “include
remaining calculated imports” and is often appropriate after intentional
overrides.
Resolution
Use .bndrun requirements plus repositories to calculate
-runbundles. Commit or reproduce the resolution and fail CI
when the declared runtime no longer resolves.
Semantic versioning and baselining
bnd compares a new API with a previous bundle:
- compatible addition usually increments minor;
- breaking API change increments major;
- implementation-only fix increments micro.
Provider and consumer interface roles affect compatibility advice. Baselining turns version discipline into build evidence.
Maven and Gradle
Use current bnd plugins, pin versions, keep generated manifests inspectable, and run integration tests against the produced JAR—not just IDE output. Maven coordinates are repository identity; they do not replace OSGi metadata.
Reproducibility
Pin repositories, plugin versions, execution environment, framework, and runtime closure. Sign releases, generate an SBOM, and compare the deployed digest to CI output.
Feynman check
bnd does not “make a JAR modular” by magic. It discovers bytecode relationships and writes a contract. You still decide the public API and acceptable ranges.