This closes #10
diff --git a/jaxp-api-1.4/src/main/java/javax/xml/xpath/XPathFactoryFinder.java b/jaxp-api-1.4/src/main/java/javax/xml/xpath/XPathFactoryFinder.java
index cef620f..a690712 100644
--- a/jaxp-api-1.4/src/main/java/javax/xml/xpath/XPathFactoryFinder.java
+++ b/jaxp-api-1.4/src/main/java/javax/xml/xpath/XPathFactoryFinder.java
@@ -262,7 +262,7 @@
* @return null
* if it fails. Error messages will be printed by this method.
*/
- private XPathFactory createInstance( String className ) {
+ XPathFactory createInstance( String className ) {
try {
if (debug) debugPrintln("instanciating "+className);
Class clazz;
diff --git a/jaxrs-api-2.1/pom.xml b/jaxrs-api-2.1/pom.xml
new file mode 100644
index 0000000..99aeac9
--- /dev/null
+++ b/jaxrs-api-2.1/pom.xml
@@ -0,0 +1,205 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
+
+ <!--
+
+ Licensed to the Apache Software Foundation (ASF) under one or more
+ contributor license agreements. See the NOTICE file distributed with
+ this work for additional information regarding copyright ownership.
+ The ASF licenses this file to You under the Apache License, Version 2.0
+ (the "License"); you may not use this file except in compliance with
+ the License. You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+ -->
+
+ <modelVersion>4.0.0</modelVersion>
+
+ <parent>
+ <groupId>org.apache.servicemix.specs</groupId>
+ <artifactId>specs</artifactId>
+ <version>2.10-SNAPSHOT</version>
+ </parent>
+
+ <groupId>org.apache.servicemix.specs</groupId>
+ <artifactId>org.apache.servicemix.specs.jaxrs-api-2.1</artifactId>
+ <packaging>bundle</packaging>
+ <version>2.10-SNAPSHOT</version>
+ <name>Apache ServiceMix :: Specs :: JAX-RS API 2.1</name>
+
+ <dependencies>
+ <dependency>
+ <groupId>javax.ws.rs</groupId>
+ <artifactId>javax.ws.rs-api</artifactId>
+ <version>2.1</version>
+ </dependency>
+ <dependency>
+ <groupId>org.apache.servicemix.specs</groupId>
+ <artifactId>org.apache.servicemix.specs.locator</artifactId>
+ <version>${project.parent.version}</version>
+ </dependency>
+ </dependencies>
+
+ <build>
+ <plugins>
+ <plugin>
+ <groupId>org.codehaus.mojo</groupId>
+ <artifactId>build-helper-maven-plugin</artifactId>
+ <version>3.0.0</version>
+ <executions>
+ <execution>
+ <phase>prepare-package</phase>
+ <goals>
+ <goal>add-source</goal>
+ </goals>
+ <configuration>
+ <sources>
+ <source>${project.build.directory}/sources</source>
+ </sources>
+ </configuration>
+ </execution>
+ </executions>
+ </plugin>
+ <plugin>
+ <groupId>org.apache.felix</groupId>
+ <artifactId>maven-bundle-plugin</artifactId>
+ <version>3.4.0</version>
+ <configuration>
+ <instructions>
+ <Bundle-SymbolicName>${project.artifactId}</Bundle-SymbolicName>
+ <Bundle-Description>${project.name}</Bundle-Description>
+ <Bundle-License>CDDL-1.1;link="https://spdx.org/licenses/CDDL-1.1.html"</Bundle-License>
+ <Export-Package>
+ javax.ws.rs*;version=2.1.0;-split-package:=merge-first,
+ javax.ws.rs;version=2.1.0,
+ javax.ws.rs.core;version=2.1.0,
+ javax.ws.rs.ext;version=2.1.0,
+ javax.ws.rs;version=2.1.0,
+ javax.ws.rs.core;version=2.1.0,
+ javax.ws.rs.ext;version=2.1.0
+ </Export-Package>
+ <Import-Package>
+ !javax.ws.rs*,
+ javax.annotation;version=1.2,
+ *
+ </Import-Package>
+ <_nouses>true</_nouses>
+ <Private-Package>org.apache.servicemix.specs.locator;-split-package:=merge-first;-noimport:=true</Private-Package>
+ <Bundle-Activator>org.apache.servicemix.specs.locator.Activator</Bundle-Activator>
+ <Implementation-Title>Apache ServiceMix</Implementation-Title>
+ <Implementation-Version>${project.version}</Implementation-Version>
+ <Provide-Capability>osgi.contract;osgi.contract=JavaJAXRS;uses:="javax.ws.rs,javax.ws.rs.client,javax.ws.rs.container,javax.ws.rs.core,javax.ws.rs.ext,javax.ws.rs.sse";version:List<Version>="2.1,2,1.1"</Provide-Capability>
+ </instructions>
+ <unpackBundle>true</unpackBundle>
+ </configuration>
+ </plugin>
+ <plugin>
+ <groupId>org.apache.maven.plugins</groupId>
+ <artifactId>maven-shade-plugin</artifactId>
+ <executions>
+ <execution>
+ <phase>package</phase>
+ <goals>
+ <goal>shade</goal>
+ </goals>
+ <configuration>
+ <artifactSet>
+ <includes>
+ <include>javax.ws.rs:javax.ws.rs-api</include>
+ <include>org.apache.servicemix.specs:org.apache.servicemix.specs.locator</include>
+ </includes>
+ </artifactSet>
+ <filters>
+ <filter>
+ <artifact>javax.ws.rs:javax.ws.rs-api</artifact>
+ <excludes>
+ <exclude>javax/**</exclude>
+ </excludes>
+ </filter>
+ <filter>
+ <artifact>org.apache.servicemix.specs:org.apache.servicemix.specs.locator</artifact>
+ <excludes>
+ <exclude>org/**</exclude>
+ </excludes>
+ </filter>
+ </filters>
+ <createSourcesJar>${createSourcesJar}</createSourcesJar>
+ <promoteTransitiveDependencies>true</promoteTransitiveDependencies>
+ <createDependencyReducedPom>true</createDependencyReducedPom>
+ </configuration>
+ </execution>
+ </executions>
+ </plugin>
+ </plugins>
+ </build>
+
+ <profiles>
+ <profile>
+ <id>deploy</id>
+ <properties>
+ <createSourcesJar>true</createSourcesJar>
+ </properties>
+ <build>
+ <plugins>
+ <plugin>
+ <groupId>org.apache.maven.plugins</groupId>
+ <artifactId>maven-dependency-plugin</artifactId>
+ <executions>
+ <execution>
+ <id>unpack-sources</id>
+ <phase>generate-sources</phase>
+ <goals>
+ <goal>unpack</goal>
+ </goals>
+ <configuration>
+ <artifactItems>
+ <artifactItem>
+ <groupId>javax.ws.rs</groupId>
+ <artifactId>javax.ws.rs-api</artifactId>
+ <classifier>sources</classifier>
+ </artifactItem>
+ <artifactItem>
+ <groupId>org.apache.servicemix.specs</groupId>
+ <artifactId>org.apache.servicemix.specs.locator</artifactId>
+ <classifier>sources</classifier>
+ </artifactItem>
+ </artifactItems>
+ <outputDirectory>${project.build.directory}/sources</outputDirectory>
+ </configuration>
+ </execution>
+ </executions>
+ </plugin>
+
+ <plugin>
+ <groupId>org.apache.maven.plugins</groupId>
+ <artifactId>maven-javadoc-plugin</artifactId>
+ <executions>
+ <execution>
+ <id>package</id>
+ <phase>package</phase>
+ <goals>
+ <goal>jar</goal>
+ </goals>
+ </execution>
+ </executions>
+ <configuration>
+ <additionalparam>-Xdoclint:none</additionalparam>
+ <sourceFileExcludes>
+ <exclude>**/module-info.java</exclude>
+ </sourceFileExcludes>
+ <minmemory>128m</minmemory>
+ <maxmemory>512m</maxmemory>
+ <sourcepath>${project.build.directory}/sources</sourcepath>
+ </configuration>
+ </plugin>
+ </plugins>
+ </build>
+ </profile>
+ </profiles>
+</project>
diff --git a/jaxrs-api-2.1/src/main/java/javax/ws/rs/client/FactoryFinder.java b/jaxrs-api-2.1/src/main/java/javax/ws/rs/client/FactoryFinder.java
new file mode 100644
index 0000000..fd597f5
--- /dev/null
+++ b/jaxrs-api-2.1/src/main/java/javax/ws/rs/client/FactoryFinder.java
@@ -0,0 +1,252 @@
+/*
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
+ *
+ * Copyright (c) 2010-2013 Oracle and/or its affiliates. All rights reserved.
+ *
+ * The contents of this file are subject to the terms of either the GNU
+ * General Public License Version 2 only ("GPL") or the Common Development
+ * and Distribution License("CDDL") (collectively, the "License"). You
+ * may not use this file except in compliance with the License. You can
+ * obtain a copy of the License at
+ * http://glassfish.java.net/public/CDDL+GPL_1_1.html
+ * or packager/legal/LICENSE.txt. See the License for the specific
+ * language governing permissions and limitations under the License.
+ *
+ * When distributing the software, include this License Header Notice in each
+ * file and include the License file at packager/legal/LICENSE.txt.
+ *
+ * GPL Classpath Exception:
+ * Oracle designates this particular file as subject to the "Classpath"
+ * exception as provided by Oracle in the GPL Version 2 section of the License
+ * file that accompanied this code.
+ *
+ * Modifications:
+ * If applicable, add the following below the License Header, with the fields
+ * enclosed by brackets [] replaced by your own identifying information:
+ * "Portions Copyright [year] [name of copyright owner]"
+ *
+ * Contributor(s):
+ * If you wish your version of this file to be governed by only the CDDL or
+ * only the GPL Version 2, indicate your decision by adding "[Contributor]
+ * elects to include this software in this distribution under the [CDDL or GPL
+ * Version 2] license." If you don't indicate a single choice of license, a
+ * recipient has the option to distribute your version of this file under
+ * either the CDDL, the GPL Version 2 or to extend the choice of license to
+ * its licensees as provided above. However, if you add GPL Version 2 code
+ * and therefore, elected the GPL Version 2 license, then the option applies
+ * only if the new code is made subject to such option by the copyright
+ * holder.
+ */
+package javax.ws.rs.client;
+
+import java.io.BufferedReader;
+import java.io.File;
+import java.io.FileInputStream;
+import java.io.InputStream;
+import java.io.InputStreamReader;
+import java.security.AccessController;
+import java.security.PrivilegedAction;
+import java.util.Properties;
+import java.util.logging.Level;
+import java.util.logging.Logger;
+
+/**
+ * Factory finder utility class.
+ *
+ * @author Paul Sandoz
+ * @author Marc Hadley
+ * @since 1.0
+ */
+final class FactoryFinder {
+
+ private static final Logger LOGGER = Logger.getLogger(FactoryFinder.class.getName());
+
+ private FactoryFinder() {
+ // prevents instantiation
+ }
+
+ static ClassLoader getContextClassLoader() {
+ return AccessController.doPrivileged(
+ new PrivilegedAction<ClassLoader>() {
+
+ @Override
+ public ClassLoader run() {
+ ClassLoader cl = null;
+ try {
+ cl = Thread.currentThread().getContextClassLoader();
+ } catch (SecurityException ex) {
+ LOGGER.log(
+ Level.WARNING,
+ "Unable to get context classloader instance.",
+ ex);
+ }
+ return cl;
+ }
+ });
+ }
+
+ /**
+ * Creates an instance of the specified class using the specified
+ * <code>ClassLoader</code> object.
+ *
+ * @param className name of the class to be instantiated.
+ * @param classLoader class loader to be used.
+ * @return instance of the specified class.
+ * @throws ClassNotFoundException if the given class could not be found
+ * or could not be instantiated
+ */
+ private static Object newInstance(final String className, final ClassLoader classLoader) throws ClassNotFoundException {
+ try {
+ Class spiClass;
+ if (classLoader == null) {
+ spiClass = Class.forName(className);
+ } else {
+ try {
+ spiClass = Class.forName(className, false, classLoader);
+ } catch (ClassNotFoundException ex) {
+ LOGGER.log(
+ Level.FINE,
+ "Unable to load provider class " + className
+ + " using custom classloader " + classLoader.getClass().getName()
+ + " trying again with current classloader.",
+ ex);
+ spiClass = Class.forName(className);
+ }
+ }
+ return spiClass.newInstance();
+ } catch (ClassNotFoundException x) {
+ throw x;
+ } catch (Exception x) {
+ throw new ClassNotFoundException("Provider " + className + " could not be instantiated: " + x, x);
+ }
+ }
+
+ /**
+ * Finds the implementation <code>Class</code> object for the given
+ * factory name, or if that fails, finds the <code>Class</code> object
+ * for the given fallback class name. The arguments supplied MUST be
+ * used in order. If using the first argument is successful, the second
+ * one will not be used.
+ * <P>
+ * This method is package private so that this code can be shared.
+ *
+ * @param factoryId the name of the factory to find, which is
+ * a system property
+ * @param fallbackClassName the implementation class name, which is
+ * to be used only if nothing else
+ * is found; <code>null</code> to indicate that
+ * there is no fallback class name
+ * @return the <code>Class</code> object of the specified message factory;
+ * may not be <code>null</code>
+ * @throws ClassNotFoundException if the given class could not be found
+ * or could not be instantiated
+ */
+ static Object find(final String factoryId, final String fallbackClassName) throws ClassNotFoundException {
+ return find(factoryId, fallbackClassName, null);
+ }
+ /**
+ * Finds the implementation <code>Class</code> object for the given
+ * factory name, or if that fails, finds the <code>Class</code> object
+ * for the given fallback class name. The arguments supplied MUST be
+ * used in order. If using the first argument is successful, the second
+ * one will not be used.
+ * <P>
+ * This method is package private so that this code can be shared.
+ *
+ * @param factoryId the name of the factory to find, which is
+ * a system property
+ * @param fallbackClassName the implementation class name, which is
+ * to be used only if nothing else
+ * is found; <code>null</code> to indicate that
+ * there is no fallback class name
+ * @param service The interface class of the service
+ * @return the <code>Class</code> object of the specified message factory;
+ * may not be <code>null</code>
+ * @throws ClassNotFoundException if the given class could not be found
+ * or could not be instantiated
+ */
+ static <T> Object find(final String factoryId, final String fallbackClassName, Class<T> service) throws ClassNotFoundException {
+
+ try {
+ // If we are deployed into an OSGi environment, leverage it
+ Class factoryClass = null;
+ try {
+ factoryClass = FactoryFinder.class.getClassLoader().loadClass(factoryId);
+ } catch (Throwable t) {
+ if (service != null) {
+ factoryClass = service;
+ } else {
+ throw t;
+ }
+ }
+ Class spiClass = org.apache.servicemix.specs.locator.OsgiLocator.locate(factoryClass, factoryId);
+ if (spiClass != null) {
+ return spiClass.newInstance();
+ }
+ } catch (Throwable e) {
+ }
+
+ ClassLoader classLoader = getContextClassLoader();
+
+ String serviceId = "META-INF/services/" + factoryId;
+ // try to find services in CLASSPATH
+ try {
+ InputStream is;
+ if (classLoader == null) {
+ is = ClassLoader.getSystemResourceAsStream(serviceId);
+ } else {
+ is = classLoader.getResourceAsStream(serviceId);
+ }
+
+ if (is != null) {
+ BufferedReader rd = new BufferedReader(new InputStreamReader(is, "UTF-8"));
+
+ String factoryClassName = rd.readLine();
+ rd.close();
+
+ if (factoryClassName != null && !"".equals(factoryClassName)) {
+ return newInstance(factoryClassName, classLoader);
+ }
+ }
+ } catch (Exception ex) {
+ LOGGER.log(Level.FINER, "Failed to load service " + factoryId + " from " + serviceId, ex);
+ }
+
+
+ // try to read from $java.home/lib/jaxrs.properties
+ try {
+ String javah = System.getProperty("java.home");
+ String configFile = javah + File.separator
+ + "lib" + File.separator + "jaxrs.properties";
+ File f = new File(configFile);
+ if (f.exists()) {
+ Properties props = new Properties();
+ props.load(new FileInputStream(f));
+ String factoryClassName = props.getProperty(factoryId);
+ return newInstance(factoryClassName, classLoader);
+ }
+ } catch (Exception ex) {
+ LOGGER.log(Level.FINER, "Failed to load service " + factoryId
+ + " from $java.home/lib/jaxrs.properties", ex);
+ }
+
+
+ // Use the system property
+ try {
+ String systemProp = System.getProperty(factoryId);
+ if (systemProp != null) {
+ return newInstance(systemProp, classLoader);
+ }
+ } catch (SecurityException se) {
+ LOGGER.log(Level.FINER, "Failed to load service " + factoryId
+ + " from a system property", se);
+ }
+
+ if (fallbackClassName == null) {
+ throw new ClassNotFoundException(
+ "Provider for " + factoryId + " cannot be found", null);
+ }
+
+ return newInstance(fallbackClassName, classLoader);
+ }
+}
diff --git a/jaxrs-api-2.1/src/main/java/javax/ws/rs/ext/FactoryFinder.java b/jaxrs-api-2.1/src/main/java/javax/ws/rs/ext/FactoryFinder.java
new file mode 100644
index 0000000..ffa4965
--- /dev/null
+++ b/jaxrs-api-2.1/src/main/java/javax/ws/rs/ext/FactoryFinder.java
@@ -0,0 +1,181 @@
+/*
+ * The contents of this file are subject to the terms
+ * of the Common Development and Distribution License
+ * (the "License"). You may not use this file except
+ * in compliance with the License.
+ *
+ * You can obtain a copy of the license at
+ * http://www.opensource.org/licenses/cddl1.php
+ * See the License for the specific language governing
+ * permissions and limitations under the License.
+ */
+package javax.ws.rs.ext;
+
+import java.io.BufferedReader;
+import java.io.File;
+import java.io.FileInputStream;
+import java.io.InputStream;
+import java.io.InputStreamReader;
+import java.util.Properties;
+
+public class FactoryFinder {
+
+ /**
+ * Creates an instance of the specified class using the specified
+ * <code>ClassLoader</code> object.
+ *
+ * @throws ClassNotFoundException if the given class could not be found
+ * or could not be instantiated
+ */
+ private static Object newInstance(String className,
+ ClassLoader classLoader) throws ClassNotFoundException {
+ try {
+ Class spiClass;
+ if (classLoader == null) {
+ spiClass = Class.forName(className);
+ } else {
+ spiClass = classLoader.loadClass(className);
+ }
+ return spiClass.newInstance();
+ } catch (ClassNotFoundException x) {
+ throw x;
+ } catch (Exception x) {
+ throw new ClassNotFoundException(
+ "Provider " + className + " could not be instantiated: " + x,
+ x);
+ }
+ }
+
+ /**
+ * Finds the implementation <code>Class</code> object for the given
+ * factory name, or if that fails, finds the <code>Class</code> object
+ * for the given fallback class name. The arguments supplied MUST be
+ * used in order. If using the first argument is successful, the second
+ * one will not be used.
+ * <p/>
+ * This method is package private so that this code can be shared.
+ *
+ * @param factoryId the name of the factory to find, which is
+ * a system property
+ * @param fallbackClassName the implementation class name, which is
+ * to be used only if nothing else
+ * is found; <code>null</code> to indicate that
+ * there is no fallback class name
+ * @return the <code>Class</code> object of the specified message factory;
+ * may not be <code>null</code>
+ * @throws WebServiceException if there is an error
+ */
+ static Object find(final String factoryId, final String fallbackClassName) throws ClassNotFoundException {
+ return find(factoryId, fallbackClassName, null);
+ }
+
+ /**
+ * Finds the implementation <code>Class</code> object for the given
+ * factory name, or if that fails, finds the <code>Class</code> object
+ * for the given fallback class name. The arguments supplied MUST be
+ * used in order. If using the first argument is successful, the second
+ * one will not be used.
+ * <P>
+ * This method is package private so that this code can be shared.
+ *
+ * @param factoryId the name of the factory to find, which is
+ * a system property
+ * @param fallbackClassName the implementation class name, which is
+ * to be used only if nothing else
+ * is found; <code>null</code> to indicate that
+ * there is no fallback class name
+ * @param service The interface class of the service
+ * @return the <code>Class</code> object of the specified message factory;
+ * may not be <code>null</code>
+ * @throws ClassNotFoundException if the given class could not be found
+ * or could not be instantiated
+ */
+ static <T> Object find(final String factoryId, final String fallbackClassName, Class<T> service) throws ClassNotFoundException {
+
+ try {
+ // If we are deployed into an OSGi environment, leverage it
+ Class factoryClass = null;
+ try {
+ factoryClass = FactoryFinder.class.getClassLoader().loadClass(factoryId);
+ } catch (Throwable t) {
+ if (service != null) {
+ factoryClass = service;
+ } else {
+ throw t;
+ }
+ }
+ Class spiClass = org.apache.servicemix.specs.locator.OsgiLocator.locate(factoryClass, factoryId);
+ if (spiClass != null) {
+ return spiClass.newInstance();
+ }
+ } catch (Throwable e) {
+ }
+
+ ClassLoader classLoader;
+ try {
+ classLoader = Thread.currentThread().getContextClassLoader();
+ } catch (Exception x) {
+ throw new ClassNotFoundException(x.toString(), x);
+ }
+
+ String serviceId = "META-INF/services/" + factoryId;
+ // try to find services in CLASSPATH
+ try {
+ InputStream is;
+ if (classLoader == null) {
+ is = ClassLoader.getSystemResourceAsStream(serviceId);
+ } else {
+ is = classLoader.getResourceAsStream(serviceId);
+ }
+
+ if (is != null) {
+ BufferedReader rd =
+ new BufferedReader(new InputStreamReader(is, "UTF-8"));
+
+ String factoryClassName = rd.readLine();
+ rd.close();
+
+ if (factoryClassName != null &&
+ !"".equals(factoryClassName)) {
+ return newInstance(factoryClassName, classLoader);
+ }
+ }
+ } catch (Exception ex) {
+ }
+
+
+ // try to read from $java.home/lib/jaxrs.properties
+ try {
+ String javah = System.getProperty("java.home");
+ String configFile = javah + File.separator +
+ "lib" + File.separator + "jaxrs.properties";
+ File f = new File(configFile);
+ if (f.exists()) {
+ Properties props = new Properties();
+ props.load(new FileInputStream(f));
+ String factoryClassName = props.getProperty(factoryId);
+ return newInstance(factoryClassName, classLoader);
+ }
+ } catch (Exception ex) {
+ }
+
+
+ // Use the system property
+ try {
+ String systemProp =
+ System.getProperty(factoryId);
+ if (systemProp != null) {
+ return newInstance(systemProp, classLoader);
+ }
+ } catch (SecurityException se) {
+ }
+
+ if (fallbackClassName == null) {
+ throw new ClassNotFoundException(
+ "Provider for " + factoryId + " cannot be found", null);
+ }
+
+ return newInstance(fallbackClassName, classLoader);
+ }
+
+}
diff --git a/pom.xml b/pom.xml
index e46f515..433d1bf 100644
--- a/pom.xml
+++ b/pom.xml
@@ -74,7 +74,8 @@
<module>jsr370-api-m1</module>
<module>jsr370-api-m4</module>
<module>jsr370-api-m5</module>
- <module>json-api-1.1</module>
+ <module>jaxrs-api-2.1</module>
+ <module>json-api-1.1</module>
<module>assembly</module>
</modules>
@@ -280,6 +281,19 @@
</execution>
</executions>
</plugin>
+ <plugin>
+ <groupId>org.apache.maven.plugins</groupId>
+ <artifactId>maven-source-plugin</artifactId>
+ <version>3.0.1</version>
+ <executions>
+ <execution>
+ <id>attach-sources</id>
+ <goals>
+ <goal>jar</goal>
+ </goals>
+ </execution>
+ </executions>
+ </plugin>
</plugins>
</build>