Hi all,
I have been experimenting a little bit more with the SPI Fly code. In
the directory spi-fly/contrib/pilot_using_weavinghook I've created a
bunch of new Eclipse projects which use the standard OSGi WeavingHook
to weave the code. Additionally I moved from AspectJ to ASM for the
bytecode weaving. I have been thinking about what we'd really want in
terms of behaviour.
For those who don't know about the SPI-Fly component in Aries, it's
aimed at making META-INF/services based providers and consumers work
in OSGi.
* Provider Registration *
Provider bundles opt-in using the
SPI-Provider: true
header.
Once opted in, SPI Fly simply registers any SPI it can find in the
bundle, by looking at the META-INF/services directory and registering
all the services it can find there in the Service Registry. At the
moment it sets one service property: spi.provider.url=<url pointing to
the relevant META-INF/services/... file>
That property could be useful in that it contains proof of where the
service came from and its simple existence shows that it's created
from a META-INF/services definition. However, I couldn't think of any
other property to add. Any suggestions here?
Also, is opting in like this is sufficient? Or do we want to support
more details in the SPI-Provider header, maybe the option to limit the
SPIs provided by the bundle?
* Consumers *
Consumers opt-in using the SPI-Consumer header. The main syntax the
code currently has is this:
SPI-Consumer: true
This means that any call made to ServiceLoader.load(SomeClass) is
wrapped with a ThreadContextClassLoader setting code that sets the
TCCL to a classloader that has visibility to *any* bundle that
provides the SomeClass service requested. This will make the
ServiceLoader.load() call work in general*.
There is a more specific variation to this, e.g.:
SPI-Consumer: java.util.ServiceLoader#load(java.lang.Class);bundle=impl2,...
Says that the ServiceLoader.load() call should only see services
provides by impl2.
Again, I'm trying to get an idea whether this would be enough. Do we
need more expressiveness here?
BTW currently I've only tested the this on Equinox, as it's the only
framework that I'm aware of that currently supports the Weaving Hooks,
as this is part of the OSGi 4.3 core spec I expect other frameworks to
start supporting this in the near term.
BTW2 I didn't really take 'legacy' service that don't use
ServiceLoader.load() yet. That's on the to-do list :)
Ideas welcome! Thanks!
David
* My test consumer looks like this, plain simple ServiceLoader.load() usage:
ServiceLoader<SPIProvider> ldr = ServiceLoader.load(SPIProvider.class);
for (SPIProvider spiObject : ldr) {
spiObject.doit(); // invoke the SPI object
}