Hi,
I am trying to use javax.xml.stream.XMLInputFactory and javax.xml.stream.XMLOutputFactory inside an OSGi framework. These use ServiceLoader internally to locate concrete XMLInputFactory and XMLOutputFactory classes, i.e. by invoking javax.xml.stream.FactoryFinder. However, FactoryFinder is part of the JDK and so has no osgi.serviceloader metadata.
The only way I know to add extra requirements to Bnd is:
-runrequires: \
osgi.serviceloader;filter:='(osgi.serviceloader=javax.xml.stream.XMLInputFactory)';osgi.serviceloader='javax.xml.stream.XMLInputFactory',\
osgi.serviceloader;filter:='(osgi.serviceloader=javax.xml.stream.XMLOutputFactory)';osgi.serviceloader='javax.xml.stream.XMLOutputFactory',\
However, I still get this exception at runtime:
=> javax.xml.stream.FactoryConfigurationError: Provider for javax.xml.stream.XMLInputFactory cannot be found
java.xml/javax.xml.stream.FactoryFinder.find(FactoryFinder.java:320)
java.xml/javax.xml.stream.XMLInputFactory.newFactory(XMLInputFactory.java:323)
com.fasterxml.jackson.dataformat.xml.XmlFactory.<init>(XmlFactory.java:120)
com.fasterxml.jackson.dataformat.xml.XmlFactory.<init>(XmlFactory.java:106)
com.fasterxml.jackson.dataformat.xml.XmlFactory.<init>(XmlFactory.java:90)
com.fasterxml.jackson.dataformat.xml.XmlMapper.<init>(XmlMapper.java:129)
com.fasterxml.jackson.dataformat.xml.XmlMapper.builder(XmlMapper.java:220)
...
FWIW, this is happening with a locally-patched 2.14.0-SNAPSHOT version of Jackson where I have added these Bnd annotations:
package com.fasterxml.jackson.dataformat.xml;
@ServiceProvider(JsonFactory.class)
@ServiceConsumer(XMLInputFactory.class)
@ServiceConsumer(XMLOutputFactory.class)
public class XmlFactory extends JsonFactory
However, it occurs to me that it is the system bundle which is the actual “consumer” here, and so maybe that is where the requirement should be. But there is no obvious equivalent of -runsystemcapabilities for requirements other than -runrequires.
For reference, my -runbundles does contain:
org.apache.aries.spifly.dynamic.bundle;version='[1.3.2,1.3.3)',\
Can anyone help me sort my .bndrun file out please?
Thanks,
Chris
Edit: From the POV of a TestOSGi Gradle task, this test fails:
@ServiceConsumer(XMLInputFactory.class)
class ServiceLoaderTest {
private static final Logger logger = LoggerFactory.getLogger(ServiceLoader.class);
@Test
void loadXMLInputFactoryByClassLoader() {
final XMLInputFactory inputFactory = XMLInputFactory.newFactory(XMLInputFactory.class.getName(), getClass().getClassLoader());
assertNotNull(inputFactory);
logger.info("FOUND: {}", inputFactory);
}
}
but this succeeds:
@ServiceConsumer(XMLInputFactory.class)
class ServiceLoaderTest {
private static final Logger logger = LoggerFactory.getLogger(ServiceLoader.class);
@Test
void serviceLoadXMLInputFactory() {
final ServiceLoader<XMLInputFactory> inputFactoriesLoader = ServiceLoader.load(XMLInputFactory.class, getClass().getClassLoader());
final List<XMLInputFactory> inputFactories = inputFactoriesLoader.stream().map(ServiceLoader.Provider::get).collect(toList());
assertThat(inputFactories).isNotEmpty();
inputFactories.forEach(input -> logger.info("FOUND: {}", input));
}
}