I'm finally getting back to this discussion...
Comments below.
Raymond Auge wrote on 11/30/18 08:55
AM:
Let's work through the mechanics.
1) Jakarta will add module names to spec APIs at some point,
some already have them.
2) Developers will implement modules against the spec API
modules and their modules will require spec API by module
name.
This means that at runtime, the module name of the spec API
MUST be identical to match their "require <api>;".
Any impl that also provides the API, in order to work
against the application code MUST NOT ONLY provide the same
packages, it MUST use the module name of the spec API.
This is different from the past because in the past the only
contract was the packages exported by the API and imported
by the impl. It did not matter where the packages came from
on the classpath.
However, in JPMS module exported packages are fundamentally
tied to the module name of the API, they are sealed unit.
To recap, any module that provides both the API and an IMPL
MUST use the spec module name. Is that what we are looking
for?
I agree with the above.
To me this clearly adds some key constraints going
forward:
- API modules have to be assumed to be re-usable at runtime.
If you mean that API modules must be reusable at runtime by
multiple implementations of that API, I disagree.
Different implementations of the API, using (e.g.) different Maven
coordinates, could supply exactly the same API (using different
source code) and exactly the same module name. A developer
assembling an application would require the module by name but
choose the desired implementation using the Maven coordinates.
- Implementations that package the API MUST adopt the
module name of the spec API, AND they must NOT remove any
part of the spec's defined module-info, they can only add,
otherwise they break the module's contract. Is that what
jakarta expects implementors to do?
I think it's more subtle than that.
There's attributes of a module that are clearly part of its
"interface", such as the packages that it exports. Other attributes
are part of the implementation of the module, such as the packages
it requires but does not re-export.
- The only way for implementations to provide
distinguishing modules providing their own modules names is
if they never package the API inside the module.
If they package the spec-required classes without the spec-required
module name, they would clearly not be meeting the requirements of
the spec.
If they package the spec-required classes with the
spec-required module name, they might meet the requirements of the
spec. If the spec requires that only the spec-defined
classes are exported from the spec-defined module, then the
implementation module would not be able to export any
implementation-specific APIs.
(I wish JPMS allowed multiple modules to be co-packaged in a single
jar file.)
I'm not sure if the JPMS spec has defined exactly what constitutes
the interface to a module, and what the corresponding source and
binary compatibility requirements are, but that's where we should
start. It definitely should not be "just use exactly this
module-info.java".
|