WINK-388 - Applying patch from Gerhard Petracek that reworks cdi integration

git-svn-id: https://svn.apache.org/repos/asf/wink/trunk@1506382 13f79535-47bb-0310-9956-ffa450edef68
diff --git a/pom.xml b/pom.xml
index 9b2eb71..2d2e065 100644
--- a/pom.xml
+++ b/pom.xml
@@ -37,6 +37,11 @@
         <maven.compile.target>1.5</maven.compile.target>
         <!--WINK-330 Change slf4j api import to a range to make it more user friendly.-->
         <slf4j.osgi.import.instruction>org.slf4j.*;version="[1.5,1.7)"</slf4j.osgi.import.instruction>
+
+        <!-- for in-container tests -->
+        <tomee.version>1.5.2</tomee.version>
+        <arquillian.version>1.0.2.Final</arquillian.version>
+        <maven.surefire.plugin.version>2.11</maven.surefire.plugin.version>
     </properties>
     <modules>
         <module>wink-component-test-support</module>
@@ -113,6 +118,8 @@
                         <exclude>wink-json4j/src/test/resources/utf8_helloworld_ko.json</exclude>
                         <exclude>wink-json4j/src/test/resources/utf8_lowerchar.json</exclude>
                         <exclude>wink-json4j/src/test/resources/utf8_ordered.json</exclude>
+                        
+                        <exclude>wink-jcdi-server/src/main/resources/META-INF/services/javax.enterprise.inject.spi.Extension</exclude>
 
                         <exclude>wink-common/src/main/resources/META-INF/core/wink-providers</exclude>
                         <exclude>wink-server/src/main/resources/META-INF/server/wink-providers</exclude>
@@ -608,7 +615,7 @@
             <dependency>
                 <groupId>junit</groupId>
                 <artifactId>junit</artifactId>
-                <version>4.8.1</version>
+                <version>4.10</version>
                 <scope>test</scope>
             </dependency>
             <dependency>
@@ -747,6 +754,26 @@
                 <artifactId>guice</artifactId>
                 <version>2.0</version>
             </dependency>
+
+            <dependency>
+                <groupId>org.jboss.arquillian</groupId>
+                <artifactId>arquillian-bom</artifactId>
+                <version>${arquillian.version}</version>
+                <scope>import</scope>
+                <type>pom</type>
+            </dependency>
+            <dependency>
+                <groupId>org.jboss.shrinkwrap</groupId>
+                <artifactId>shrinkwrap-api</artifactId>
+                <version>1.0.1</version>
+                <scope>test</scope>
+            </dependency>
+            <dependency>
+                <groupId>org.apache.openejb</groupId>
+                <artifactId>arquillian-tomee-remote</artifactId>
+                <version>${tomee.version}</version>
+                <scope>test</scope>
+            </dependency>
         </dependencies>
     </dependencyManagement>
     <reporting>
diff --git a/wink-common/src/main/resources/org/apache/wink/common/internal/i18n/resource.properties b/wink-common/src/main/resources/org/apache/wink/common/internal/i18n/resource.properties
index 4953c7c..546ea15 100644
--- a/wink-common/src/main/resources/org/apache/wink/common/internal/i18n/resource.properties
+++ b/wink-common/src/main/resources/org/apache/wink/common/internal/i18n/resource.properties
@@ -152,7 +152,7 @@
 methodCallOutsideScopeOfRequestContext=A method call was made outside the scope of a request context.  Verify that the method is called within the context of a JAX-RS request.
 
 # JCDI
-jcdiSingletonObjectFactoryCannotInstantiateInstance=Cannot create an instance of the JCDI managed bean class {0}.  Verify that the bean is a singleton or is annotated with @javax.enterprise.context.ApplicationScoped. 
+#jcdiSingletonObjectFactoryCannotInstantiateInstance=Cannot create an instance of the JCDI managed bean class {0}.  Verify that the bean is a singleton or is annotated with @javax.enterprise.context.ApplicationScoped. 
 
 # others
 methodCannotHandleType=The system cannot determine the class of type {0}.
@@ -220,7 +220,7 @@
 saxParserConfigurationException=The system cannot configure the SAX parser with the given configuration parameter.
 badXMLReaderInitialStart=The XMLStreamReader instance has already been partially processed.
 exceptionDuringInjection=Exception encountered during JCDI injection
-couldNotFindBeanManager=Could not find BeanManager.
+#couldNotFindBeanManager=Could not find BeanManager.
 processingRequestTo=Processing {0} request to {1}, source content type is {2}, acceptable media types include {3}
 registeredResources=Registered JAX-RS resources: {0}
 followingProviders=The following JAX-RS providers are registered: {0}
diff --git a/wink-jcdi-server/pom.xml b/wink-jcdi-server/pom.xml
index 8365ecb..965d488 100644
--- a/wink-jcdi-server/pom.xml
+++ b/wink-jcdi-server/pom.xml
@@ -84,5 +84,87 @@
             <artifactId>slf4j-jdk14</artifactId>
             <scope>test</scope>
         </dependency>
+
+        <!-- test dependencies for in-container-tests -->
+        <dependency>
+            <groupId>org.apache.wink</groupId>
+            <artifactId>wink-client</artifactId>
+            <scope>test</scope>
+        </dependency>
+        <dependency>
+            <groupId>org.apache.wink</groupId>
+            <artifactId>wink-client-apache-httpclient</artifactId>
+            <scope>test</scope>
+        </dependency>
+
+        <dependency>
+            <groupId>org.apache.openejb</groupId>
+            <artifactId>arquillian-tomee-remote</artifactId>
+            <version>${tomee.version}</version>
+            <scope>test</scope>
+        </dependency>
+
+        <dependency>
+            <groupId>org.jboss.arquillian.junit</groupId>
+            <artifactId>arquillian-junit-container</artifactId>
+            <scope>test</scope>
+        </dependency>
+
+        <dependency>
+            <groupId>org.jboss.shrinkwrap</groupId>
+            <artifactId>shrinkwrap-api</artifactId>
+        </dependency>
     </dependencies>
+
+    <profiles>
+        <profile>
+            <!--
+             * arquillian-tomee-remote isn't a real remote connector for a running server-instance
+             *
+             * DEBUGGING:
+             * mvn test -Ptomee-build-managed -Dtest=UnitTestName -Dopenejb.server.debug=true
+             * then use remote debuggig at port 5005
+             *
+            -->
+            <id>tomee-build-managed</id>
+
+            <dependencies>
+                <dependency>
+                    <groupId>org.apache.openejb</groupId>
+                    <artifactId>tomee-embedded</artifactId>
+                    <version>${tomee.version}</version>
+                </dependency>
+                <dependency>
+                    <groupId>org.apache.openejb</groupId>
+                    <artifactId>arquillian-tomee-remote</artifactId>
+                </dependency>
+
+                <!-- needed by arquillian-tomee-remote -->
+                <dependency>
+                    <groupId>commons-logging</groupId>
+                    <artifactId>commons-logging</artifactId>
+                    <version>1.1.1</version>
+                    <scope>test</scope>
+                </dependency>
+            </dependencies>
+
+            <build>
+                <plugins>
+                    <plugin>
+                        <groupId>org.apache.maven.plugins</groupId>
+                        <artifactId>maven-surefire-plugin</artifactId>
+                        <version>${maven.surefire.plugin.version}</version>
+                        <configuration>
+                            <systemPropertyVariables>
+                                <tomee.version>${tomee.version}</tomee.version>
+                            </systemPropertyVariables>
+                            <systemProperties>
+                                <arquillian.launch>tomee</arquillian.launch>
+                            </systemProperties>
+                        </configuration>
+                    </plugin>
+                </plugins>
+            </build>
+        </profile>
+    </profiles>
 </project>
diff --git a/wink-jcdi-server/src/main/java/org/apache/wink/jcdi/server/internal/CdiAwareObjectFactory.java b/wink-jcdi-server/src/main/java/org/apache/wink/jcdi/server/internal/CdiAwareObjectFactory.java
new file mode 100644
index 0000000..3668af0
--- /dev/null
+++ b/wink-jcdi-server/src/main/java/org/apache/wink/jcdi/server/internal/CdiAwareObjectFactory.java
@@ -0,0 +1,102 @@
+/*
+ * 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.
+ */
+package org.apache.wink.jcdi.server.internal;
+
+import org.apache.wink.common.RuntimeContext;
+import org.apache.wink.common.internal.lifecycle.ObjectFactory;
+
+import javax.enterprise.context.Dependent;
+import javax.enterprise.context.spi.CreationalContext;
+import javax.enterprise.inject.spi.Bean;
+import javax.enterprise.inject.spi.BeanManager;
+import java.util.IdentityHashMap;
+import java.util.Map;
+
+public class CdiAwareObjectFactory<T> implements ObjectFactory<T> {
+    final private Class<T> clazz;
+    final private BeanManager beanManager;
+    private Bean<?> theBean;
+    private IdentityHashMap<T, CreationalContext<T>> dependentCreationalContextMap;
+
+    public CdiAwareObjectFactory(Class<T> c, BeanManager beanManager, Bean<T> bean) {
+        //TODO discuss the support of producer methods
+        this.clazz = c;
+        this.beanManager = beanManager;
+        theBean = bean;
+    }
+
+    @SuppressWarnings("unchecked")
+    public T getInstance(RuntimeContext context) {
+        CreationalContext<?> creationalContext = beanManager.createCreationalContext(theBean);
+        T instance = (T) beanManager.getReference(theBean, clazz, creationalContext);
+        //it's only allowed to manage the lifecycle of dependent-scoped beans manually
+        if (!theBean.getScope().equals(Dependent.class)) {
+            return instance; //contextual-reference
+        }
+
+        /*
+         * if there is a context, this is during a request. if context is null,
+         * this is during application scoped. store the CreationalContext to
+         * release it later.
+         */
+        if (context != null) {
+            context.setAttribute(CreationalContext.class, creationalContext);
+        } else {
+            /*
+             * be sure to synchronize on the off chance this is run concurrently
+             * (in normal operation, the application scoped instances are
+             * created sequentially but that could change
+             */
+            synchronized (this) {
+                if (dependentCreationalContextMap == null) {
+                    dependentCreationalContextMap = new IdentityHashMap<T, CreationalContext<T>>();
+                }
+                dependentCreationalContextMap.put(instance, (CreationalContext<T>) creationalContext);
+            }
+        }
+        return instance;
+    }
+
+    public Class<T> getInstanceClass() {
+        return clazz;
+    }
+
+    public void releaseAll(RuntimeContext context) {
+        synchronized (this) {
+            if (dependentCreationalContextMap != null) {
+                for (Map.Entry<T, CreationalContext<T>> dependentBeanEntry : dependentCreationalContextMap.entrySet()) {
+                    ((Bean<T>) theBean).destroy(dependentBeanEntry.getKey(), dependentBeanEntry.getValue());
+                }
+                dependentCreationalContextMap = null;
+            }
+        }
+    }
+
+    @SuppressWarnings("unchecked")
+    public void releaseInstance(T instance, RuntimeContext context) {
+        if (context != null) //mainly destroys dependent instances at the end of the request
+        {
+            CreationalContext<T> creationalContext =
+                    (CreationalContext<T>) context.getAttributes().remove(CreationalContext.class.getName());
+            if (creationalContext != null) {
+                ((Bean<T>) theBean).destroy(instance, creationalContext);
+            }
+        }
+    }
+}
diff --git a/wink-jcdi-server/src/main/java/org/apache/wink/jcdi/server/internal/CdiDeploymentConfiguration.java b/wink-jcdi-server/src/main/java/org/apache/wink/jcdi/server/internal/CdiDeploymentConfiguration.java
new file mode 100644
index 0000000..a649028
--- /dev/null
+++ b/wink-jcdi-server/src/main/java/org/apache/wink/jcdi/server/internal/CdiDeploymentConfiguration.java
@@ -0,0 +1,35 @@
+/*
+ * 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.
+ */
+package org.apache.wink.jcdi.server.internal;
+
+import org.apache.wink.common.internal.lifecycle.LifecycleManagersRegistry;
+import org.apache.wink.jcdi.server.spi.BeanManagerResolver;
+import org.apache.wink.server.internal.DeploymentConfiguration;
+
+public class CdiDeploymentConfiguration extends DeploymentConfiguration {
+    public CdiDeploymentConfiguration(BeanManagerResolver beanManagerResolver) {
+        if (beanManagerResolver == null) {
+            beanManagerResolver = new DefaultBeanManagerResolver();
+        }
+
+        LifecycleManagersRegistry lifecycleManagersRegistry = new LifecycleManagersRegistry();
+        setOfFactoryRegistry(lifecycleManagersRegistry);
+        lifecycleManagersRegistry.addFactoryFactory(new CdiLifecycleManager(beanManagerResolver));
+    }
+}
diff --git a/wink-jcdi-server/src/main/java/org/apache/wink/jcdi/server/internal/CdiLifecycleManager.java b/wink-jcdi-server/src/main/java/org/apache/wink/jcdi/server/internal/CdiLifecycleManager.java
new file mode 100644
index 0000000..5828491
--- /dev/null
+++ b/wink-jcdi-server/src/main/java/org/apache/wink/jcdi/server/internal/CdiLifecycleManager.java
@@ -0,0 +1,67 @@
+/*
+ * 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.
+ */
+package org.apache.wink.jcdi.server.internal;
+
+import org.apache.wink.common.internal.i18n.Messages;
+import org.apache.wink.common.internal.lifecycle.LifecycleManager;
+import org.apache.wink.common.internal.lifecycle.ObjectCreationException;
+import org.apache.wink.common.internal.lifecycle.ObjectFactory;
+import org.apache.wink.jcdi.server.internal.util.CdiUtils;
+import org.apache.wink.jcdi.server.spi.BeanManagerResolver;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+import javax.enterprise.inject.spi.Bean;
+
+public class CdiLifecycleManager<T> implements LifecycleManager<T> {
+    private static final Logger logger = LoggerFactory.getLogger(CdiLifecycleManager.class);
+
+    private final BeanManagerResolver beanManagerResolver;
+
+    public CdiLifecycleManager(BeanManagerResolver beanManagerResolver) {
+        this.beanManagerResolver = beanManagerResolver;
+        logger.trace("CdiLifecycleManager created");
+    }
+
+
+    public ObjectFactory<T> createObjectFactory(T object) throws ObjectCreationException {
+        logger.trace("createObjectFactory({}) entry", object);
+        if (object == null) {
+            throw new NullPointerException(Messages.getMessage("variableIsNull", "object")); //$NON-NLS-1$ //$NON-NLS-2$
+        }
+        logger.trace("createObjectFactory() exit returning null");
+        return null;
+    }
+
+    public ObjectFactory<T> createObjectFactory(Class<T> cls) throws ObjectCreationException {
+        logger.trace("createObjectFactory({}) entry", cls);
+        if (cls == null) {
+            throw new NullPointerException(Messages.getMessage("variableIsNull", "cls")); //$NON-NLS-1$ //$NON-NLS-2$
+        }
+
+        Bean<T> bean = CdiUtils.getBeanFor(cls, beanManagerResolver.get());
+
+        if (bean == null) {
+            return null; //needed to fall back to the default factory
+        }
+
+        return new CdiAwareObjectFactory<T>(cls, beanManagerResolver.get(), bean);
+    }
+}
+
diff --git a/wink-jcdi-server/src/main/java/org/apache/wink/jcdi/server/internal/DefaultBeanManagerResolver.java b/wink-jcdi-server/src/main/java/org/apache/wink/jcdi/server/internal/DefaultBeanManagerResolver.java
new file mode 100644
index 0000000..f478a48
--- /dev/null
+++ b/wink-jcdi-server/src/main/java/org/apache/wink/jcdi/server/internal/DefaultBeanManagerResolver.java
@@ -0,0 +1,67 @@
+/*
+ * 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.
+ */
+package org.apache.wink.jcdi.server.internal;
+
+import org.apache.wink.jcdi.server.internal.util.ClassUtils;
+import org.apache.wink.jcdi.server.spi.BeanManagerResolver;
+
+import javax.enterprise.inject.spi.BeanManager;
+import javax.naming.InitialContext;
+import javax.naming.NamingException;
+import java.util.Map;
+import java.util.concurrent.ConcurrentHashMap;
+
+public class DefaultBeanManagerResolver implements BeanManagerResolver {
+    private static Map<ClassLoader, BeanManager> beanManager = new ConcurrentHashMap<ClassLoader, BeanManager>();
+
+    //useful for OpenWebBeans which just has one BM which isn't bound to jndi with the minimal module-config
+    private static Map<ClassLoader, BeanManager> foundBeanManager = new ConcurrentHashMap<ClassLoader, BeanManager>();
+
+    public BeanManager get() {
+        BeanManager result = beanManager.get(ClassUtils.getClassLoader(null));
+        if (result == null) {
+            try {
+                result = (BeanManager) new InitialContext().lookup("java:comp/BeanManager");
+                beanManager.put(ClassUtils.getClassLoader(null), result);
+            } catch (NamingException e) {
+                result = foundBeanManager.get(ClassUtils.getClassLoader(null));
+
+                if (result != null) {
+                    beanManager.put(ClassUtils.getClassLoader(null), result);
+                } else {
+                    throw new IllegalStateException(e);
+                }
+            }
+        }
+
+        if (result == null) {
+            throw new IllegalStateException("no bean-manager found");
+        }
+
+        return result;
+    }
+
+    public static void setBeanManager(BeanManager beanManager) {
+        foundBeanManager.put(ClassUtils.getClassLoader(null), beanManager);
+    }
+
+    public static void reset() {
+        foundBeanManager.clear();
+    }
+}
diff --git a/wink-jcdi-server/src/main/java/org/apache/wink/jcdi/server/internal/JCDIRestServlet.java b/wink-jcdi-server/src/main/java/org/apache/wink/jcdi/server/internal/JCDIRestServlet.java
deleted file mode 100644
index 9b4ff67..0000000
--- a/wink-jcdi-server/src/main/java/org/apache/wink/jcdi/server/internal/JCDIRestServlet.java
+++ /dev/null
@@ -1,56 +0,0 @@
-/*
- * 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.    
- */
-
-package org.apache.wink.jcdi.server.internal;
-
-import org.apache.wink.common.internal.i18n.Messages;
-import org.apache.wink.common.internal.utils.ClassUtils;
-import org.apache.wink.jcdi.server.internal.extension.JCDIDeploymentConfiguration;
-import org.apache.wink.server.internal.DeploymentConfiguration;
-import org.apache.wink.server.internal.servlet.RestServlet;
-import org.slf4j.Logger;
-import org.slf4j.LoggerFactory;
-
-public class JCDIRestServlet extends RestServlet {
-
-    private static final String DEPLOYMENT_CONF_PARAM = "deploymentConfiguration";
-
-    private static final Logger logger               =
-                                                         LoggerFactory
-                                                             .getLogger(JCDIRestServlet.class);
-
-    private static final long   serialVersionUID     = -1920970727031271538L;
-
-    @Override
-    protected DeploymentConfiguration createDeploymentConfiguration()
-        throws ClassNotFoundException, InstantiationException, IllegalAccessException {
-        String initParameter = getInitParameter(DEPLOYMENT_CONF_PARAM);
-        if (initParameter != null) {
-            logger.info(Messages.getMessage("restServletUseDeploymentConfigurationParam",
-                        initParameter,
-                        DEPLOYMENT_CONF_PARAM));
-            // use ClassUtils.loadClass instead of Class.forName so we have
-            // classloader visibility into the Web module in J2EE environments
-            Class<?> confClass = ClassUtils.loadClass(initParameter);
-            return (DeploymentConfiguration)confClass.newInstance();
-        }
-        return new JCDIDeploymentConfiguration();
-    }
-
-}
diff --git a/wink-jcdi-server/src/main/java/org/apache/wink/jcdi/server/internal/extension/JAXRSJCDICustomInjectionTarget.java b/wink-jcdi-server/src/main/java/org/apache/wink/jcdi/server/internal/extension/JAXRSJCDICustomInjectionTarget.java
index 0ea7702..746819c 100644
--- a/wink-jcdi-server/src/main/java/org/apache/wink/jcdi/server/internal/extension/JAXRSJCDICustomInjectionTarget.java
+++ b/wink-jcdi-server/src/main/java/org/apache/wink/jcdi/server/internal/extension/JAXRSJCDICustomInjectionTarget.java
@@ -1,33 +1,23 @@
 /*
  * Licensed to the Apache Software Foundation (ASF) under one
- * or more contributor license agreements.  See the NOTICE file
+ * or more contributor license agreements. See the NOTICE file
  * distributed with this work for additional information
- * regarding copyright ownership.  The ASF licenses this file
+ * 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
- * 
+ * 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
+ * KIND, either express or implied. See the License for the
  * specific language governing permissions and limitations
- * under the License.    
+ * under the License.
  */
 package org.apache.wink.jcdi.server.internal.extension;
 
-import java.io.IOException;
-import java.security.AccessController;
-import java.security.PrivilegedActionException;
-import java.security.PrivilegedExceptionAction;
-import java.util.Set;
-
-import javax.enterprise.context.spi.CreationalContext;
-import javax.enterprise.inject.spi.InjectionPoint;
-import javax.enterprise.inject.spi.InjectionTarget;
-
 import org.apache.wink.common.internal.i18n.Messages;
 import org.apache.wink.common.internal.lifecycle.CreationUtils;
 import org.apache.wink.common.internal.registry.metadata.ApplicationMetadataCollector;
@@ -38,29 +28,23 @@
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
 
-public class JAXRSJCDICustomInjectionTarget<T> implements InjectionTarget<T> {
+import javax.enterprise.context.spi.CreationalContext;
+import javax.enterprise.inject.spi.InjectionPoint;
+import javax.enterprise.inject.spi.InjectionTarget;
+import java.io.IOException;
+import java.security.AccessController;
+import java.security.PrivilegedActionException;
+import java.security.PrivilegedExceptionAction;
+import java.util.Set;
 
-    private static final Logger      logger =
-                                                LoggerFactory
-                                                    .getLogger(JAXRSJCDICustomInjectionTarget.class);
+class WinkInjectionTarget<T> implements InjectionTarget<T> {
+    private static final Logger logger = LoggerFactory.getLogger(WinkInjectionTarget.class);
 
-    private ClassMetadata            classMetadata;
+    private ClassMetadata classMetadata;
 
-    final private InjectionTarget<T> delegate;
+    private final InjectionTarget<T> delegate;
 
-    static <T> ClassMetadata collectClassMetadata(final Class<T> cls) {
-        ClassMetadata classMetadata = null;
-        if (ProviderMetadataCollector.isProvider(cls)) {
-            classMetadata = ProviderMetadataCollector.collectMetadata(cls);
-        } else if (ResourceMetadataCollector.isResource(cls)) {
-            classMetadata = ResourceMetadataCollector.collectMetadata(cls);
-        } else if (ApplicationMetadataCollector.isApplication(cls)) {
-            classMetadata = ApplicationMetadataCollector.collectMetadata(cls);
-        }
-        return classMetadata;
-    }
-
-    public JAXRSJCDICustomInjectionTarget(InjectionTarget<T> delegate) {
+    WinkInjectionTarget(InjectionTarget<T> delegate) {
         logger.trace("constructor({}) entry", delegate);
         this.delegate = delegate;
         logger.trace("constructor() exit");
@@ -78,8 +62,7 @@
                     }
                     logger.trace("Calling CreationUtils.injectFields for instance");
                     try {
-                        CreationUtils.injectFields(instance, classMetadata, RuntimeContextTLS
-                            .getRuntimeContext());
+                        CreationUtils.injectFields(instance, classMetadata, RuntimeContextTLS.getRuntimeContext());
                     } catch (IOException e) {
                         throw new PrivilegedActionException(e);
                     }
@@ -114,4 +97,16 @@
     public T produce(CreationalContext<T> creationalContext) {
         return delegate.produce(creationalContext);
     }
+
+    private static <T> ClassMetadata collectClassMetadata(final Class<T> cls) {
+        ClassMetadata classMetadata = null;
+        if (ProviderMetadataCollector.isProvider(cls)) {
+            classMetadata = ProviderMetadataCollector.collectMetadata(cls);
+        } else if (ResourceMetadataCollector.isResource(cls)) {
+            classMetadata = ResourceMetadataCollector.collectMetadata(cls);
+        } else if (ApplicationMetadataCollector.isApplication(cls)) {
+            classMetadata = ApplicationMetadataCollector.collectMetadata(cls);
+        }
+        return classMetadata;
+    }
 }
diff --git a/wink-jcdi-server/src/main/java/org/apache/wink/jcdi/server/internal/extension/JCDIDeploymentConfiguration.java b/wink-jcdi-server/src/main/java/org/apache/wink/jcdi/server/internal/extension/JCDIDeploymentConfiguration.java
deleted file mode 100644
index 755c07f..0000000
--- a/wink-jcdi-server/src/main/java/org/apache/wink/jcdi/server/internal/extension/JCDIDeploymentConfiguration.java
+++ /dev/null
@@ -1,33 +0,0 @@
-/*
- * 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.    
- */
-package org.apache.wink.jcdi.server.internal.extension;
-
-import org.apache.wink.common.internal.lifecycle.LifecycleManagersRegistry;
-import org.apache.wink.jcdi.server.internal.lifecycle.JCDILifecycleManager;
-import org.apache.wink.server.internal.DeploymentConfiguration;
-
-public class JCDIDeploymentConfiguration extends DeploymentConfiguration {
-
-    @SuppressWarnings("unchecked")
-    public JCDIDeploymentConfiguration() {
-        LifecycleManagersRegistry lifecycleManagersRegistry = new LifecycleManagersRegistry();
-        setOfFactoryRegistry(lifecycleManagersRegistry);
-        lifecycleManagersRegistry.addFactoryFactory(new JCDILifecycleManager());
-    }
-}
diff --git a/wink-jcdi-server/src/main/java/org/apache/wink/jcdi/server/internal/extension/JCDIExtension.java b/wink-jcdi-server/src/main/java/org/apache/wink/jcdi/server/internal/extension/JCDIExtension.java
deleted file mode 100644
index 915c433..0000000
--- a/wink-jcdi-server/src/main/java/org/apache/wink/jcdi/server/internal/extension/JCDIExtension.java
+++ /dev/null
@@ -1,62 +0,0 @@
-/*
- * 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.    
- */
-package org.apache.wink.jcdi.server.internal.extension;
-
-import javax.enterprise.event.Observes;
-import javax.enterprise.inject.spi.Extension;
-import javax.enterprise.inject.spi.ProcessInjectionTarget;
-
-import org.apache.wink.common.internal.registry.metadata.ApplicationMetadataCollector;
-import org.apache.wink.common.internal.registry.metadata.ProviderMetadataCollector;
-import org.apache.wink.common.internal.registry.metadata.ResourceMetadataCollector;
-import org.slf4j.Logger;
-import org.slf4j.LoggerFactory;
-
-public class JCDIExtension implements Extension {
-
-    private static final Logger logger = LoggerFactory.getLogger(JCDIExtension.class);
-
-    public <T> void observeProcessInjectionTarget(@Observes ProcessInjectionTarget<T> pij) {
-        logger.trace("observeProcessInjectionTarget({}) entry", pij);
-        if (isJAXRSBean(pij.getAnnotatedType().getJavaClass())) {
-            logger.trace("Was JAX-RS annotated class so changing the injection target");
-            pij.setInjectionTarget(new JAXRSJCDICustomInjectionTarget<T>(pij.getInjectionTarget()));
-        }
-        logger.trace("observeProcessInjectionTarget() exit");
-    }
-
-    static boolean isJAXRSBean(final Class<?> cls) {
-        if (logger.isTraceEnabled()) {
-            logger.trace("isJAXRSBean({}) entry", cls.getName());
-        }
-        boolean result = false;
-        if (ProviderMetadataCollector.isProvider(cls)) {
-            result = true;
-        } else if (ResourceMetadataCollector.isResource(cls)) {
-            result = true;
-        } else if (ApplicationMetadataCollector.isApplication(cls)) {
-            result = true;
-        }
-        if (logger.isTraceEnabled()) {
-            logger.trace("isJAXRSBean({}) exit", result);
-        }
-        return result;
-    }
-
-}
diff --git a/wink-jcdi-server/src/main/java/org/apache/wink/jcdi/server/internal/extension/OptionalScopeAutoUpgradeExtension.java b/wink-jcdi-server/src/main/java/org/apache/wink/jcdi/server/internal/extension/OptionalScopeAutoUpgradeExtension.java
new file mode 100644
index 0000000..4d8522a
--- /dev/null
+++ b/wink-jcdi-server/src/main/java/org/apache/wink/jcdi/server/internal/extension/OptionalScopeAutoUpgradeExtension.java
@@ -0,0 +1,63 @@
+/*
+ * 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.
+ */
+package org.apache.wink.jcdi.server.internal.extension;
+
+import org.apache.wink.common.internal.registry.metadata.ApplicationMetadataCollector;
+import org.apache.wink.common.internal.registry.metadata.ProviderMetadataCollector;
+import org.apache.wink.common.internal.registry.metadata.ResourceMetadataCollector;
+import org.apache.wink.jcdi.server.internal.literal.ApplicationScopedLiteral;
+import org.apache.wink.jcdi.server.internal.literal.RequestScopedLiteral;
+import org.apache.wink.jcdi.server.internal.util.CdiUtils;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+import javax.enterprise.context.ApplicationScoped;
+import javax.enterprise.context.RequestScoped;
+import javax.enterprise.event.Observes;
+import javax.enterprise.inject.spi.BeanManager;
+import javax.enterprise.inject.spi.Extension;
+import javax.enterprise.inject.spi.ProcessAnnotatedType;
+import java.lang.annotation.Annotation;
+
+/**
+ * Adds scopes to CDI/JAX-RS beans, if they don't have one.
+ * Resource -> @RequestScoped
+ * Provider and Application -> @ApplicationScoped
+ */
+public class OptionalScopeAutoUpgradeExtension implements Extension {
+    private static final Logger logger = LoggerFactory.getLogger(OptionalScopeAutoUpgradeExtension.class);
+
+    @SuppressWarnings("UnusedDeclaration")
+    public void findProviderAndApplicationBeans(@Observes ProcessAnnotatedType<?> pat, BeanManager beanManager) {
+        Class<?> beanClass = pat.getAnnotatedType().getJavaClass();
+
+        Annotation[] annotations = pat.getAnnotatedType().getAnnotations()
+                .toArray(new Annotation[pat.getAnnotatedType().getAnnotations().size()]);
+
+        if (ResourceMetadataCollector.isResource(beanClass) && !CdiUtils.isBeanWithScope(annotations, beanManager)) {
+            logger.trace("{} upgraded to {} scoped bean.", beanClass.getName(), RequestScoped.class.getName());
+            pat.setAnnotatedType(new WinkAnnotatedTypeWrapper(pat.getAnnotatedType(), new RequestScopedLiteral()));
+        } else if ((ProviderMetadataCollector.isProvider(beanClass) ||
+                ApplicationMetadataCollector.isApplication(beanClass)) &&
+                !CdiUtils.isBeanWithScope(annotations, beanManager)) {
+            logger.trace("{} upgraded to {} scoped bean.", beanClass.getName(), ApplicationScoped.class.getName());
+            pat.setAnnotatedType(new WinkAnnotatedTypeWrapper(pat.getAnnotatedType(), new ApplicationScopedLiteral()));
+        }
+    }
+}
diff --git a/wink-jcdi-server/src/main/java/org/apache/wink/jcdi/server/internal/extension/WinkAnnotatedTypeWrapper.java b/wink-jcdi-server/src/main/java/org/apache/wink/jcdi/server/internal/extension/WinkAnnotatedTypeWrapper.java
new file mode 100644
index 0000000..e0e0273
--- /dev/null
+++ b/wink-jcdi-server/src/main/java/org/apache/wink/jcdi/server/internal/extension/WinkAnnotatedTypeWrapper.java
@@ -0,0 +1,92 @@
+/*
+ * 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.
+ */
+package org.apache.wink.jcdi.server.internal.extension;
+
+import javax.enterprise.inject.spi.AnnotatedConstructor;
+import javax.enterprise.inject.spi.AnnotatedField;
+import javax.enterprise.inject.spi.AnnotatedMethod;
+import javax.enterprise.inject.spi.AnnotatedType;
+import java.lang.annotation.Annotation;
+import java.lang.reflect.Type;
+import java.util.HashMap;
+import java.util.HashSet;
+import java.util.Map;
+import java.util.Set;
+
+class WinkAnnotatedTypeWrapper implements AnnotatedType {
+    private final AnnotatedType wrapped;
+
+    private Map<Class<? extends Annotation>, Annotation> annotations;
+    private Set<Annotation> annotationSet;
+
+    WinkAnnotatedTypeWrapper(AnnotatedType<?> wrapped, Annotation scopeAnnotation) {
+        this.wrapped = wrapped;
+
+        Set<Annotation> originalAnnotationSet = wrapped.getAnnotations();
+        this.annotations = new HashMap<Class<? extends Annotation>, Annotation>(originalAnnotationSet.size() + 1);
+
+        for (Annotation originalAnnotation : originalAnnotationSet) {
+            this.annotations.put(originalAnnotation.annotationType(), originalAnnotation);
+        }
+        this.annotations.put(scopeAnnotation.annotationType(), scopeAnnotation);
+
+        this.annotationSet = new HashSet<Annotation>(this.annotations.size());
+        this.annotationSet.addAll(this.annotations.values());
+    }
+
+    public boolean isAnnotationPresent(Class<? extends Annotation> annotationType) {
+        return this.annotations.containsKey(annotationType);
+    }
+
+    public Set<Annotation> getAnnotations() {
+        return this.annotationSet;
+    }
+
+    public <T extends Annotation> T getAnnotation(Class<T> annotationType) {
+        return (T) this.annotations.get(annotationType);
+    }
+
+    /*
+     * generated
+     */
+
+    public Class getJavaClass() {
+        return wrapped.getJavaClass();
+    }
+
+    public Set<AnnotatedConstructor> getConstructors() {
+        return wrapped.getConstructors();
+    }
+
+    public Set<AnnotatedMethod> getMethods() {
+        return wrapped.getMethods();
+    }
+
+    public Set<AnnotatedField> getFields() {
+        return wrapped.getFields();
+    }
+
+    public Type getBaseType() {
+        return wrapped.getBaseType();
+    }
+
+    public Set<Type> getTypeClosure() {
+        return wrapped.getTypeClosure();
+    }
+}
diff --git a/wink-jcdi-server/src/main/java/org/apache/wink/jcdi/server/internal/extension/WinkCdiExtension.java b/wink-jcdi-server/src/main/java/org/apache/wink/jcdi/server/internal/extension/WinkCdiExtension.java
new file mode 100644
index 0000000..3b02ef1
--- /dev/null
+++ b/wink-jcdi-server/src/main/java/org/apache/wink/jcdi/server/internal/extension/WinkCdiExtension.java
@@ -0,0 +1,143 @@
+/*
+ * 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.
+ */
+package org.apache.wink.jcdi.server.internal.extension;
+
+import org.apache.wink.common.internal.registry.metadata.ApplicationMetadataCollector;
+import org.apache.wink.common.internal.registry.metadata.ProviderMetadataCollector;
+import org.apache.wink.common.internal.registry.metadata.ResourceMetadataCollector;
+import org.apache.wink.jcdi.server.internal.DefaultBeanManagerResolver;
+import org.apache.wink.jcdi.server.internal.util.CdiUtils;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+import javax.enterprise.context.ApplicationScoped;
+import javax.enterprise.context.Dependent;
+import javax.enterprise.context.RequestScoped;
+import javax.enterprise.event.Observes;
+import javax.enterprise.inject.spi.*;
+import javax.inject.Singleton;
+import javax.ws.rs.core.Application;
+import javax.ws.rs.ext.Provider;
+import java.lang.annotation.Annotation;
+import java.util.ArrayList;
+import java.util.List;
+
+public class WinkCdiExtension implements Extension {
+    private static final Logger logger = LoggerFactory.getLogger(WinkCdiExtension.class);
+
+    //don't use a static list - an extension instance gets created per application
+    private List<Class> beanClassesToCheck = new ArrayList<Class>();
+
+    @SuppressWarnings("UnusedDeclaration")
+    public <T> void observeProcessInjectionTarget(@Observes ProcessInjectionTarget<T> pij) {
+        logger.trace("observeProcessInjectionTarget({}) entry", pij);
+
+        Annotation[] annotations = pij.getAnnotatedType().getAnnotations()
+                .toArray(new Annotation[pij.getAnnotatedType().getAnnotations().size()]);
+
+        if (isJAXRSBean(pij.getAnnotatedType().getJavaClass())) {
+            logger.trace("Was JAX-RS annotated class so changing the injection target");
+            pij.setInjectionTarget(new WinkInjectionTarget<T>(pij.getInjectionTarget()));
+        }
+        logger.trace("observeProcessInjectionTarget() exit");
+    }
+
+    @SuppressWarnings("UnusedDeclaration")
+    public void findJaxRsClasses(@Observes ProcessAnnotatedType<?> processAnnotatedType) {
+        Class<?> beanClass = processAnnotatedType.getAnnotatedType().getJavaClass();
+
+        if (ProviderMetadataCollector.isProvider(beanClass) || ApplicationMetadataCollector.isApplication(beanClass)
+                || ResourceMetadataCollector.isResource(beanClass)) {
+            beanClassesToCheck.add(beanClass);
+        }
+    }
+
+    @SuppressWarnings("UnusedDeclaration")
+    public void validateJaxRsCdiBeans(
+            @Observes AfterDeploymentValidation afterDeploymentValidation, BeanManager beanManager) {
+        DefaultBeanManagerResolver.setBeanManager(beanManager);
+
+        for (Class beanClass : beanClassesToCheck) {
+            Bean<?> bean = CdiUtils.getBeanFor(beanClass, beanManager);
+
+            if (bean == null) {
+                continue; //e.g. a vetoed bean
+            }
+
+            if (ResourceMetadataCollector.isResource(beanClass) && Dependent.class.equals(bean.getScope())) {
+                StringBuilder warning = new StringBuilder("{} gets processed as CDI bean, but uses {} ");
+
+                if (CdiUtils.isBeanWithScope(beanClass.getAnnotations(), beanManager)) {
+                    warning.append("explicitly. ");
+                } else {
+                    warning.append("implicitly. ");
+                }
+                warning.append("The suggested scope for this bean is {}. Alternatively use ");
+                warning.append(OptionalScopeAutoUpgradeExtension.class.getName());
+                Object[] parameters = new Object[]{
+                        beanClass.getName(), Dependent.class.getName(), RequestScoped.class.getName()};
+                logger.warn(warning.toString(), parameters);
+                continue;
+            }
+
+            //an extension can change the scope dynamically during bootstrapping -> check it at the end
+            if (!bean.getScope().equals(Singleton.class) && !beanManager.isNormalScope(bean.getScope())) {
+                StringBuilder warning = new StringBuilder();
+                if (ApplicationMetadataCollector.isApplication(beanClass)) {
+                    warning.append("Implementations of ").append(Application.class.getName());
+                } else {
+                    warning.append(Provider.class.getName()).append(" beans");
+                }
+                warning.append(" are only compatible with singletons. Please add ");
+                warning.append(OptionalScopeAutoUpgradeExtension.class.getName());
+                warning.append(" Or use ");
+                warning.append(ApplicationScoped.class.getName());
+                warning.append(" or ");
+                warning.append(Singleton.class.getName());
+                warning.append(" or a custom scope which keeps only one instance per class for the whole application.");
+                logger.warn(warning.toString());
+            }
+        }
+
+        beanClassesToCheck.clear();
+    }
+
+    @SuppressWarnings("UnusedDeclaration")
+    public void onShutdown(@Observes BeforeShutdown beforeShutdown) {
+        DefaultBeanManagerResolver.reset();
+    }
+
+    private static boolean isJAXRSBean(final Class<?> cls) {
+        if (logger.isTraceEnabled()) {
+            logger.trace("isJAXRSBean({}) entry", cls.getName());
+        }
+        boolean result = false;
+        if (ProviderMetadataCollector.isProvider(cls)) {
+            result = true;
+        } else if (ResourceMetadataCollector.isResource(cls)) {
+            result = true;
+        } else if (ApplicationMetadataCollector.isApplication(cls)) {
+            result = true;
+        }
+        if (logger.isTraceEnabled()) {
+            logger.trace("isJAXRSBean({}) exit", result);
+        }
+        return result;
+    }
+}
diff --git a/wink-jcdi-server/src/main/java/org/apache/wink/jcdi/server/internal/lifecycle/JCDIDefaultObjectFactory.java b/wink-jcdi-server/src/main/java/org/apache/wink/jcdi/server/internal/lifecycle/JCDIDefaultObjectFactory.java
deleted file mode 100644
index 6fa4d7c..0000000
--- a/wink-jcdi-server/src/main/java/org/apache/wink/jcdi/server/internal/lifecycle/JCDIDefaultObjectFactory.java
+++ /dev/null
@@ -1,136 +0,0 @@
-/*
- * 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.    
- */
-package org.apache.wink.jcdi.server.internal.lifecycle;
-
-import java.lang.annotation.Annotation;
-import java.util.ArrayList;
-import java.util.IdentityHashMap;
-import java.util.List;
-import java.util.Set;
-
-import javax.enterprise.context.spi.CreationalContext;
-import javax.enterprise.inject.spi.Bean;
-import javax.enterprise.inject.spi.BeanManager;
-
-import org.apache.wink.common.RuntimeContext;
-import org.apache.wink.common.internal.lifecycle.ObjectFactory;
-
-public class JCDIDefaultObjectFactory<T> implements ObjectFactory<T> {
-
-    final private Class<T>                           clazz;
-    final private BeanManager                        beanManager;
-    private Bean<?>                                  theBean;
-    private IdentityHashMap<T, CreationalContext<T>> creationalContextMap;
-
-    public JCDIDefaultObjectFactory(Class<T> c, BeanManager beanManager) {
-        this.clazz = c;
-        this.beanManager = beanManager;
-        // this.creationalContextMap = new IdentityHashMap<T,
-        // CreationalContext<T>>();
-        theBean = null;
-    }
-
-    /* package */IdentityHashMap<T, CreationalContext<T>> getCreationalContextMap() {
-        return creationalContextMap;
-    }
-
-    @SuppressWarnings("unchecked")
-    public T getInstance(RuntimeContext context) {
-        if (theBean == null) {
-            // cache the Bean object
-            Annotation[] annotations = clazz.getAnnotations();
-            List<Annotation> qualifierAnnotations = new ArrayList<Annotation>(1);
-            for (Annotation a : annotations) {
-                if (beanManager.isQualifier(a.annotationType())) {
-                    qualifierAnnotations.add(a);
-                }
-            }
-            Set<Bean<?>> beans =
-                beanManager.getBeans(clazz, qualifierAnnotations.toArray(new Annotation[0]));
-            theBean = beans.iterator().next();
-        }
-
-        /*
-         * need a new CreationalContext every "new" instance and use it to get
-         * the bean instance
-         */
-        CreationalContext<?> creationalContext = beanManager.createCreationalContext(theBean);
-        T instance = (T)beanManager.getReference(theBean, clazz, creationalContext);
-
-        /*
-         * if there is a context, this is during a request. if context is null,
-         * this is during application scoped. store the CreationalContext to
-         * release it later.
-         */
-        if (context != null) {
-            context.setAttribute(CreationalContext.class, creationalContext);
-        } else {
-            /*
-             * be sure to synchronize on the off chance this is run concurrently
-             * (in normal operation, the application scoped instances are
-             * created sequentially but that could change
-             */
-            synchronized (this) {
-                if (creationalContextMap == null) {
-                    creationalContextMap = new IdentityHashMap<T, CreationalContext<T>>();
-                }
-                creationalContextMap.put(instance, (CreationalContext<T>)creationalContext);
-            }
-        }
-        return instance;
-    }
-
-    public Class<T> getInstanceClass() {
-        return clazz;
-    }
-
-    public void releaseAll(RuntimeContext context) {
-        synchronized (this) {
-            if (creationalContextMap != null) {
-                for (CreationalContext<T> c : creationalContextMap.values()) {
-                    c.release();
-                }
-                creationalContextMap = null;
-            }
-        }
-    }
-
-    @SuppressWarnings("unchecked")
-    public void releaseInstance(T instance, RuntimeContext context) {
-        if (context != null) {
-            CreationalContext<T> creationalContext =
-                (CreationalContext<T>)context.getAttributes().remove(CreationalContext.class
-                    .getName());
-            if (creationalContext != null) {
-                creationalContext.release();
-            }
-        }
-// /* will this code ever run? */
-//        if (creationalContextMap != null) {
-//            synchronized (creationalContextMap) {
-//                CreationalContext<T> creationalContext =
-//                    (CreationalContext<T>)creationalContextMap.remove(instance);
-//                if (creationalContext != null) {
-//                    creationalContext.release();
-//                }
-//            }
-//        }
-    }
-
-}
diff --git a/wink-jcdi-server/src/main/java/org/apache/wink/jcdi/server/internal/lifecycle/JCDILifecycleManager.java b/wink-jcdi-server/src/main/java/org/apache/wink/jcdi/server/internal/lifecycle/JCDILifecycleManager.java
deleted file mode 100644
index d30cd11..0000000
--- a/wink-jcdi-server/src/main/java/org/apache/wink/jcdi/server/internal/lifecycle/JCDILifecycleManager.java
+++ /dev/null
@@ -1,134 +0,0 @@
-/*
- * 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.    
- */
-package org.apache.wink.jcdi.server.internal.lifecycle;
-
-import java.lang.annotation.Annotation;
-import java.util.ArrayList;
-import java.util.List;
-import java.util.Set;
-
-import javax.enterprise.inject.spi.Bean;
-import javax.enterprise.inject.spi.BeanManager;
-import javax.naming.InitialContext;
-import javax.naming.NamingException;
-
-import org.apache.wink.common.internal.i18n.Messages;
-import org.apache.wink.common.internal.lifecycle.LifecycleManager;
-import org.apache.wink.common.internal.lifecycle.ObjectCreationException;
-import org.apache.wink.common.internal.lifecycle.ObjectFactory;
-import org.apache.wink.common.internal.registry.metadata.ApplicationMetadataCollector;
-import org.apache.wink.common.internal.registry.metadata.ProviderMetadataCollector;
-import org.slf4j.Logger;
-import org.slf4j.LoggerFactory;
-
-public class JCDILifecycleManager<T> implements LifecycleManager<T> {
-
-    public JCDILifecycleManager() {
-        logger.trace("JCDILifecycleManager created");
-    }
-
-    private static final Logger logger      = LoggerFactory.getLogger(JCDILifecycleManager.class);
-
-    private BeanManager         beanManager = null;
-
-    void setBeanManager(BeanManager beanManager) {
-        this.beanManager = beanManager;
-    }
-
-    BeanManager getBeanManager() {
-        if (beanManager == null) {
-            try {
-                InitialContext initialContext = new InitialContext();
-                beanManager = (BeanManager)initialContext.lookup("java:comp/BeanManager");
-            } catch (NamingException e) {
-                logger.warn(Messages.getMessage("couldNotFindBeanManager"), e);
-            }
-        }
-        return beanManager;
-    }
-
-    public ObjectFactory<T> createObjectFactory(T object) throws ObjectCreationException {
-        logger.trace("createObjectFactory({}) entry", object);
-        if (object == null) {
-            throw new NullPointerException(Messages.getMessage("variableIsNull", "object")); //$NON-NLS-1$ //$NON-NLS-2$
-        }
-        logger.trace("createObjectFactory() exit returning null");
-        return null;
-    }
-
-    public ObjectFactory<T> createObjectFactory(Class<T> cls) throws ObjectCreationException {
-        logger.trace("createObjectFactory({}) entry", cls);
-        if (cls == null) {
-            throw new NullPointerException(Messages.getMessage("variableIsNull", "cls")); //$NON-NLS-1$ //$NON-NLS-2$
-        }
-
-        BeanManager beanManager = getBeanManager();
-        if (isJCDIManagedBean(cls, beanManager)) {
-            if (ProviderMetadataCollector.isProvider(cls) || ApplicationMetadataCollector
-                .isApplication(cls)) {
-                /*
-                 * for providers and application sub-classes, they must be
-                 * singletons, so use a special caching singleton object factory
-                 * for them. also allows error messages to be handled.
-                 */
-                logger.trace("createObjectFactory() returning JCDISingletonObjectFactory");
-                return new JCDISingletonObjectFactory<T>(cls, beanManager);
-            }
-            logger.trace("createObjectFactory() returning JCDIDefaultObjectFactory");
-            return new JCDIDefaultObjectFactory<T>(cls, beanManager);
-        }
-
-        logger.trace("createObjectFactory() returning null");
-        return null;
-    }
-
-    /**
-     * Determines if a class is a JCDI managed bean or not.
-     * 
-     * @param <T>
-     * @param cls
-     * @return true if the class is a JCDI managed bean, false if not
-     */
-    static <T> boolean isJCDIManagedBean(Class<T> cls, BeanManager beanManager) {
-        logger.trace("isJCDIManagedBean({}, {}) entry", cls, beanManager);
-        Annotation[] annotations = cls.getAnnotations();
-        List<Annotation> qualifierAnnotations = new ArrayList<Annotation>(1);
-        for (Annotation a : annotations) {
-            if (beanManager.isQualifier(a.annotationType())) {
-                qualifierAnnotations.add(a);
-            }
-        }
-        logger.trace("Qualifier annotations are {}", qualifierAnnotations);
-        Set<Bean<?>> beans =
-            beanManager.getBeans(cls, qualifierAnnotations.toArray(new Annotation[0]));
-        logger.trace("Beans are {}", beans);
-        if (beans == null || beans.isEmpty()) {
-            logger
-                .debug("{} is NOT a JCDI managed bean.",
-                       cls);
-            logger.trace("isJCDIManagedBean() returning false");
-            return false;
-        }
-        logger.debug("{} is a JCDI managed bean.", cls);
-
-        logger.trace("isJCDIManagedBean() returning true");
-        return true;
-    }
-
-}
diff --git a/wink-jcdi-server/src/main/java/org/apache/wink/jcdi/server/internal/lifecycle/JCDISingletonObjectFactory.java b/wink-jcdi-server/src/main/java/org/apache/wink/jcdi/server/internal/lifecycle/JCDISingletonObjectFactory.java
deleted file mode 100644
index e1ad23f..0000000
--- a/wink-jcdi-server/src/main/java/org/apache/wink/jcdi/server/internal/lifecycle/JCDISingletonObjectFactory.java
+++ /dev/null
@@ -1,101 +0,0 @@
-/*
- * 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.
- *  
- */
-package org.apache.wink.jcdi.server.internal.lifecycle;
-
-import java.lang.annotation.Annotation;
-import java.util.ArrayList;
-import java.util.List;
-import java.util.Set;
-
-import javax.enterprise.context.spi.CreationalContext;
-import javax.enterprise.inject.spi.Bean;
-import javax.enterprise.inject.spi.BeanManager;
-
-import org.apache.wink.common.RuntimeContext;
-import org.apache.wink.common.internal.i18n.Messages;
-import org.apache.wink.common.internal.lifecycle.ObjectCreationException;
-import org.apache.wink.common.internal.lifecycle.ObjectFactory;
-import org.slf4j.Logger;
-import org.slf4j.LoggerFactory;
-
-public class JCDISingletonObjectFactory<T> implements ObjectFactory<T> {
-
-    private final Logger               logger     =
-                                                      LoggerFactory
-                                                          .getLogger(JCDISingletonObjectFactory.class);
-
-    final private T                    instance;
-
-    final private CreationalContext<?> creationalContext;
-
-    private boolean                    isReleased = false;
-
-    @SuppressWarnings("unchecked")
-    public JCDISingletonObjectFactory(Class<T> clazz, BeanManager beanManager) {
-        Annotation[] annotations = clazz.getAnnotations();
-        List<Annotation> qualifierAnnotations = new ArrayList<Annotation>(1);
-        for (Annotation a : annotations) {
-            if (beanManager.isQualifier(a.annotationType())) {
-                qualifierAnnotations.add(a);
-            }
-        }
-        Set<Bean<?>> beans =
-            beanManager.getBeans(clazz, qualifierAnnotations.toArray(new Annotation[0]));
-        Bean theBean = beans.iterator().next();
-
-        creationalContext = beanManager.createCreationalContext(theBean);
-        try {
-            instance = (T)beanManager.getReference(theBean, clazz, creationalContext);
-        } catch (Exception e) {
-            if (logger.isErrorEnabled()) {
-                logger.error(Messages
-                    .getMessage("jcdiSingletonObjectFactoryCannotInstantiateInstance", clazz
-                        .getName()), e);
-            }
-            throw new ObjectCreationException(e);
-        }
-    }
-
-    public T getInstance(RuntimeContext context) {
-        return instance;
-    }
-
-    @SuppressWarnings("unchecked")
-    public Class<T> getInstanceClass() {
-        return (Class<T>)instance.getClass();
-    }
-
-    public void releaseAll(RuntimeContext context) {
-        if (isReleased) {
-            /* already released so return */
-            return;
-        }
-        isReleased = true;
-        if (creationalContext != null) {
-            creationalContext.release();
-
-        }
-    }
-
-    public void releaseInstance(T instance, RuntimeContext context) {
-        /* do nothing */
-    }
-
-}
diff --git a/wink-jcdi-server/src/main/java/org/apache/wink/jcdi/server/internal/literal/ApplicationScopedLiteral.java b/wink-jcdi-server/src/main/java/org/apache/wink/jcdi/server/internal/literal/ApplicationScopedLiteral.java
new file mode 100644
index 0000000..3e6b6ee
--- /dev/null
+++ b/wink-jcdi-server/src/main/java/org/apache/wink/jcdi/server/internal/literal/ApplicationScopedLiteral.java
@@ -0,0 +1,29 @@
+/*
+ * 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.
+ */
+package org.apache.wink.jcdi.server.internal.literal;
+
+import javax.enterprise.context.ApplicationScoped;
+import javax.enterprise.util.AnnotationLiteral;
+
+/**
+ * Literal for {@link javax.enterprise.context.ApplicationScoped}
+ */
+public class ApplicationScopedLiteral extends AnnotationLiteral<ApplicationScoped> implements ApplicationScoped {
+    private static final long serialVersionUID = -6967350738539832411L;
+}
diff --git a/wink-jcdi-server/src/main/java/org/apache/wink/jcdi/server/internal/literal/RequestScopedLiteral.java b/wink-jcdi-server/src/main/java/org/apache/wink/jcdi/server/internal/literal/RequestScopedLiteral.java
new file mode 100644
index 0000000..566c0f7
--- /dev/null
+++ b/wink-jcdi-server/src/main/java/org/apache/wink/jcdi/server/internal/literal/RequestScopedLiteral.java
@@ -0,0 +1,29 @@
+/*
+ * 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.
+ */
+package org.apache.wink.jcdi.server.internal.literal;
+
+import javax.enterprise.context.RequestScoped;
+import javax.enterprise.util.AnnotationLiteral;
+
+/**
+ * Literal for {@link javax.enterprise.context.RequestScoped}
+ */
+public class RequestScopedLiteral extends AnnotationLiteral<RequestScoped> implements RequestScoped {
+    private static final long serialVersionUID = -6967350738539832411L;
+}
diff --git a/wink-jcdi-server/src/main/java/org/apache/wink/jcdi/server/internal/servlet/CdiRestServlet.java b/wink-jcdi-server/src/main/java/org/apache/wink/jcdi/server/internal/servlet/CdiRestServlet.java
new file mode 100644
index 0000000..873815a
--- /dev/null
+++ b/wink-jcdi-server/src/main/java/org/apache/wink/jcdi/server/internal/servlet/CdiRestServlet.java
@@ -0,0 +1,47 @@
+/*
+ * 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.
+ */
+package org.apache.wink.jcdi.server.internal.servlet;
+
+import org.apache.wink.common.internal.i18n.Messages;
+import org.apache.wink.common.internal.utils.ClassUtils;
+import org.apache.wink.jcdi.server.internal.CdiDeploymentConfiguration;
+import org.apache.wink.server.internal.DeploymentConfiguration;
+import org.apache.wink.server.internal.servlet.RestServlet;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+//TODO discuss: use service-loader instead (or owb fallback for 1.5)
+public class CdiRestServlet extends RestServlet {
+    private static final long serialVersionUID = 5701130677376976607L;
+    private static final Logger logger = LoggerFactory.getLogger(CdiRestServlet.class);
+    private static final String DEPLOYMENT_CONF_PARAM = "deploymentConfiguration";
+
+    @Override
+    protected DeploymentConfiguration createDeploymentConfiguration()
+            throws ClassNotFoundException, InstantiationException, IllegalAccessException {
+        String initParameter = getInitParameter(DEPLOYMENT_CONF_PARAM);
+        if (initParameter != null) {
+            logger.info(Messages.getMessage(
+                    "restServletUseDeploymentConfigurationParam", initParameter, DEPLOYMENT_CONF_PARAM));
+            Class<?> confClass = ClassUtils.loadClass(initParameter);
+            return (DeploymentConfiguration) confClass.newInstance();
+        }
+        return new CdiDeploymentConfiguration(null /*see TODO*/);
+    }
+}
diff --git a/wink-jcdi-server/src/main/java/org/apache/wink/jcdi/server/internal/util/CdiUtils.java b/wink-jcdi-server/src/main/java/org/apache/wink/jcdi/server/internal/util/CdiUtils.java
new file mode 100644
index 0000000..853d09c
--- /dev/null
+++ b/wink-jcdi-server/src/main/java/org/apache/wink/jcdi/server/internal/util/CdiUtils.java
@@ -0,0 +1,96 @@
+/*
+ * 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.
+ */
+package org.apache.wink.jcdi.server.internal.util;
+
+import javax.enterprise.inject.AmbiguousResolutionException;
+import javax.enterprise.inject.Specializes;
+import javax.enterprise.inject.spi.Bean;
+import javax.enterprise.inject.spi.BeanManager;
+import java.lang.annotation.Annotation;
+import java.util.*;
+
+//abstract class won't end up as cdi-bean
+public abstract class CdiUtils {
+    private CdiUtils() {
+        // prevent instantiation
+    }
+
+    public static <T> Bean<T> getBeanFor(Class<T> beanClass, BeanManager beanManager) {
+        Annotation[] qualifiers = getClassLevelQualifiers(beanClass, beanManager); //producers aren't supported currently
+        Set<Bean<?>> beans = beanManager.getBeans(beanClass, qualifiers);
+
+        if (beans == null || beans.isEmpty()) {
+            return null;
+        }
+
+        Bean<?> result;
+
+        try {
+            result = beanManager.resolve(beans);
+        } catch (AmbiguousResolutionException e) {
+            //try it again with concrete class in case of resource-sub-classes
+            beans = new HashSet<Bean<?>>(beans);
+            Iterator<Bean<?>> beanIterator = beans.iterator();
+
+            while (beanIterator.hasNext()) {
+                Bean<?> bean = beanIterator.next();
+
+                if (bean.isAlternative()) {
+                    continue; //don't drop alternatives
+                }
+
+                if (bean.getBeanClass().isAnnotationPresent(Specializes.class)) {
+                    continue; //don't drop specialized beans
+                }
+
+                if (beanClass.equals(bean.getBeanClass())) {
+                    //in case of a prev. AmbiguousResolutionException we have to find the same class
+                    beanIterator.remove();
+                }
+            }
+            result = beanManager.resolve(beans);
+        }
+        return (Bean<T>) result;
+    }
+
+    public static <T> Annotation[] getClassLevelQualifiers(Class<T> beanClass, BeanManager beanManager) {
+        List<Annotation> result = new ArrayList<Annotation>();
+        for (Annotation annotation : beanClass.getAnnotations()) {
+            if (beanManager.isQualifier(annotation.annotationType())) {
+                result.add(annotation);
+            }
+        }
+        return result.toArray(new Annotation[result.size()]);
+    }
+
+    public static boolean isBeanWithScope(Annotation[] annotations, BeanManager beanManager) {
+        for (Annotation annotation : annotations) {
+            if (beanManager.isScope(annotation.annotationType())) {
+                return true;
+            }
+
+            if (beanManager.isStereotype(annotation.annotationType())) {
+                if (isBeanWithScope(annotation.annotationType().getAnnotations(), beanManager)) {
+                    return true;
+                }
+            }
+        }
+        return false;
+    }
+}
diff --git a/wink-jcdi-server/src/main/java/org/apache/wink/jcdi/server/internal/util/ClassUtils.java b/wink-jcdi-server/src/main/java/org/apache/wink/jcdi/server/internal/util/ClassUtils.java
new file mode 100644
index 0000000..ed6620e
--- /dev/null
+++ b/wink-jcdi-server/src/main/java/org/apache/wink/jcdi/server/internal/util/ClassUtils.java
@@ -0,0 +1,71 @@
+/*
+ * 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.
+ */
+package org.apache.wink.jcdi.server.internal.util;
+
+import java.security.AccessController;
+import java.security.PrivilegedAction;
+
+//abstract class won't end up as cdi-bean
+//see org.apache.deltaspike.core.util.ClassUtils
+public abstract class ClassUtils {
+    /**
+     * Constructor which prevents the instantiation of this class
+     */
+    private ClassUtils() {
+        // prevent instantiation
+    }
+
+    public static ClassLoader getClassLoader(Object o) {
+        if (System.getSecurityManager() != null) {
+            return AccessController.doPrivileged(new GetClassLoaderAction(o));
+        } else {
+            return getClassLoaderInternal(o);
+        }
+    }
+
+    static class GetClassLoaderAction implements PrivilegedAction<ClassLoader> {
+        private Object object;
+
+        GetClassLoaderAction(Object object) {
+            this.object = object;
+        }
+
+        public ClassLoader run() {
+            try {
+                return getClassLoaderInternal(object);
+            } catch (Exception e) {
+                return null;
+            }
+        }
+    }
+
+    private static ClassLoader getClassLoaderInternal(Object o) {
+        ClassLoader loader = Thread.currentThread().getContextClassLoader();
+
+        if (loader == null && o != null) {
+            loader = o.getClass().getClassLoader();
+        }
+
+        if (loader == null) {
+            loader = ClassUtils.class.getClassLoader();
+        }
+
+        return loader;
+    }
+}
diff --git a/wink-jcdi-server/src/main/java/org/apache/wink/jcdi/server/spi/BeanManagerResolver.java b/wink-jcdi-server/src/main/java/org/apache/wink/jcdi/server/spi/BeanManagerResolver.java
new file mode 100644
index 0000000..e355b9d
--- /dev/null
+++ b/wink-jcdi-server/src/main/java/org/apache/wink/jcdi/server/spi/BeanManagerResolver.java
@@ -0,0 +1,29 @@
+/*
+ * 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.
+ */
+package org.apache.wink.jcdi.server.spi;
+
+import javax.enterprise.inject.spi.BeanManager;
+
+/**
+ * Allows to provide a custom resolver.
+ * E.g. one which delegates to org.apache.deltaspike.core.api.provider.BeanManagerProvider
+ */
+public interface BeanManagerResolver {
+    BeanManager get();
+}
diff --git a/wink-jcdi-server/src/main/resources/META-INF/services/javax.enterprise.inject.spi.Extension b/wink-jcdi-server/src/main/resources/META-INF/services/javax.enterprise.inject.spi.Extension
index 072d127..ba8be6b 100644
--- a/wink-jcdi-server/src/main/resources/META-INF/services/javax.enterprise.inject.spi.Extension
+++ b/wink-jcdi-server/src/main/resources/META-INF/services/javax.enterprise.inject.spi.Extension
@@ -1 +1,19 @@
-org.apache.wink.jcdi.server.internal.extension.JCDIExtension
+# 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.
+
+org.apache.wink.jcdi.server.internal.extension.WinkCdiExtension
+#org.apache.wink.jcdi.server.internal.extension.OptionalScopeAutoUpgradeExtension
diff --git a/wink-jcdi-server/src/test/java/org/apache/wink/jcdi/server/internal/extension/JAXRSJCDICustomInjectionTargetTest.java b/wink-jcdi-server/src/test/java/org/apache/wink/jcdi/server/internal/extension/JAXRSJCDICustomInjectionTargetTest.java
deleted file mode 100644
index 842a760..0000000
--- a/wink-jcdi-server/src/test/java/org/apache/wink/jcdi/server/internal/extension/JAXRSJCDICustomInjectionTargetTest.java
+++ /dev/null
@@ -1,228 +0,0 @@
-/*
- * 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.    
- */
-package org.apache.wink.jcdi.server.internal.extension;
-
-import java.io.IOException;
-import java.io.InputStream;
-import java.lang.annotation.Annotation;
-import java.lang.reflect.Type;
-import java.util.HashSet;
-import java.util.Set;
-
-import javax.enterprise.context.spi.CreationalContext;
-import javax.enterprise.inject.spi.InjectionPoint;
-import javax.enterprise.inject.spi.InjectionTarget;
-import javax.ws.rs.Path;
-import javax.ws.rs.core.Application;
-import javax.ws.rs.core.Context;
-import javax.ws.rs.core.HttpHeaders;
-import javax.ws.rs.core.MediaType;
-import javax.ws.rs.core.MultivaluedMap;
-import javax.ws.rs.core.Request;
-import javax.ws.rs.ext.MessageBodyReader;
-import javax.ws.rs.ext.Provider;
-
-import junit.framework.TestCase;
-
-import org.jmock.Expectations;
-import org.jmock.Mockery;
-
-@SuppressWarnings("unchecked")
-public class JAXRSJCDICustomInjectionTargetTest extends TestCase {
-
-    private Mockery                                mockContext       = new Mockery();
-    private InjectionTarget<Object>                it                =
-                                                                         mockContext
-                                                                             .mock(InjectionTarget.class);
-    private JAXRSJCDICustomInjectionTarget<Object> jaxrsIT;
-
-    private CreationalContext<Object>              creationalContext =
-                                                                         mockContext
-                                                                             .mock(CreationalContext.class);
-
-    static class JAXRSApplicationClass extends Application {
-        @Context
-        public Request      request;
-
-        private HttpHeaders http;
-
-        @Context
-        public void setHeaders(HttpHeaders headers) {
-            http = headers;
-        }
-
-        public HttpHeaders getHttp() {
-            return http;
-        }
-    }
-
-    @Provider
-    static class JAXRSProviderClass implements MessageBodyReader<Object> {
-
-        @Context
-        public Request      request;
-
-        private HttpHeaders http;
-
-        @Context
-        public void setHeaders(HttpHeaders headers) {
-            http = headers;
-        }
-
-        public HttpHeaders getHttp() {
-            return http;
-        }
-
-        public boolean isReadable(Class<?> type,
-                                  Type genericType,
-                                  Annotation[] annotations,
-                                  MediaType mediaType) {
-            return false;
-        }
-
-        public Object readFrom(Class<Object> type,
-                               Type genericType,
-                               Annotation[] annotations,
-                               MediaType mediaType,
-                               MultivaluedMap<String, String> httpHeaders,
-                               InputStream entityStream) throws IOException {
-            return null;
-        }
-    }
-
-    @Path("/hello")
-    static class JAXRSResourceClass {
-
-        @Context
-        public Request      request;
-
-        private HttpHeaders http;
-
-        @Context
-        public void setHeaders(HttpHeaders headers) {
-            http = headers;
-        }
-
-        public HttpHeaders getHttp() {
-            return http;
-        }
-    }
-
-    public void setUp() {
-        jaxrsIT = new JAXRSJCDICustomInjectionTarget<Object>(it);
-    }
-
-    public void testInjectJAXRSApplication() {
-        final JAXRSApplicationClass jaxrsObj = new JAXRSApplicationClass();
-        mockContext.checking(new Expectations() {
-            {
-                oneOf(it).inject(jaxrsObj, creationalContext);
-            }
-        });
-        jaxrsIT.inject(jaxrsObj, creationalContext);
-        assertNotNull(jaxrsObj.getHttp());
-        assertNotNull(jaxrsObj.request);
-        mockContext.assertIsSatisfied();
-    }
-
-    public void testInjectJAXRSProvider() {
-        final JAXRSProviderClass jaxrsObj = new JAXRSProviderClass();
-        mockContext.checking(new Expectations() {
-            {
-                oneOf(it).inject(jaxrsObj, creationalContext);
-            }
-        });
-        jaxrsIT.inject(jaxrsObj, creationalContext);
-        assertNotNull(jaxrsObj.getHttp());
-        assertNotNull(jaxrsObj.request);
-        mockContext.assertIsSatisfied();
-    }
-
-    public void testInjectJAXRSResource() {
-        final JAXRSResourceClass jaxrsObj = new JAXRSResourceClass();
-        mockContext.checking(new Expectations() {
-            {
-                oneOf(it).inject(jaxrsObj, creationalContext);
-            }
-        });
-        jaxrsIT.inject(jaxrsObj, creationalContext);
-        assertNotNull(jaxrsObj.getHttp());
-        assertNotNull(jaxrsObj.request);
-        mockContext.assertIsSatisfied();
-    }
-
-    public void testPostConstruct() {
-        final Object instance = new Object();
-        mockContext.checking(new Expectations() {
-            {
-                oneOf(it).postConstruct(instance);
-            }
-        });
-        jaxrsIT.postConstruct(instance);
-        mockContext.assertIsSatisfied();
-    }
-
-    public void testPreDestroy() {
-        final Object instance = new Object();
-        mockContext.checking(new Expectations() {
-            {
-                oneOf(it).preDestroy(instance);
-            }
-        });
-        jaxrsIT.preDestroy(instance);
-        mockContext.assertIsSatisfied();
-    }
-
-    public void testDispose() {
-        final Object instance = new Object();
-        mockContext.checking(new Expectations() {
-            {
-                oneOf(it).dispose(instance);
-            }
-        });
-        jaxrsIT.dispose(instance);
-        mockContext.assertIsSatisfied();
-    }
-
-    public void testGetInjectionPoints() {
-        final Set<InjectionPoint> expectedIPSet = new HashSet<InjectionPoint>();
-        mockContext.checking(new Expectations() {
-            {
-                oneOf(it).getInjectionPoints();
-                will(returnValue(expectedIPSet));
-            }
-        });
-        Set<InjectionPoint> actualIPSet = jaxrsIT.getInjectionPoints();
-        assertEquals(expectedIPSet, actualIPSet);
-        mockContext.assertIsSatisfied();
-    }
-
-    public void testProduce() {
-        final Object expectedProducedInstance = new Object();
-        mockContext.checking(new Expectations() {
-            {
-                oneOf(it).produce(creationalContext);
-                will(returnValue(expectedProducedInstance));
-            }
-        });
-        Object retValue = jaxrsIT.produce(creationalContext);
-        assertEquals(expectedProducedInstance, retValue);
-        mockContext.assertIsSatisfied();
-    }
-}
diff --git a/wink-jcdi-server/src/test/java/org/apache/wink/jcdi/server/internal/extension/JAXRSJCDIExtensionTest.java b/wink-jcdi-server/src/test/java/org/apache/wink/jcdi/server/internal/extension/JAXRSJCDIExtensionTest.java
deleted file mode 100644
index ee3b50f..0000000
--- a/wink-jcdi-server/src/test/java/org/apache/wink/jcdi/server/internal/extension/JAXRSJCDIExtensionTest.java
+++ /dev/null
@@ -1,165 +0,0 @@
-/*
- * 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.    
- */
-package org.apache.wink.jcdi.server.internal.extension;
-
-import java.io.IOException;
-import java.io.InputStream;
-import java.lang.annotation.Annotation;
-import java.lang.reflect.Type;
-
-import javax.enterprise.inject.spi.AnnotatedType;
-import javax.enterprise.inject.spi.InjectionTarget;
-import javax.enterprise.inject.spi.ProcessInjectionTarget;
-import javax.ws.rs.Path;
-import javax.ws.rs.core.Application;
-import javax.ws.rs.core.MediaType;
-import javax.ws.rs.core.MultivaluedMap;
-import javax.ws.rs.ext.MessageBodyReader;
-import javax.ws.rs.ext.Provider;
-
-import junit.framework.TestCase;
-
-import org.jmock.Expectations;
-import org.jmock.Mockery;
-
-public class JAXRSJCDIExtensionTest extends TestCase {
-
-    private Mockery                   mockContext     = new Mockery();
-
-    private ProcessInjectionTarget<?> pij             =
-                                                          mockContext
-                                                              .mock(ProcessInjectionTarget.class);
-
-    private InjectionTarget<?>        injectionTarget = mockContext.mock(InjectionTarget.class);
-
-    private AnnotatedType<?>          aType           = mockContext.mock(AnnotatedType.class);
-
-    private JCDIExtension             jcdiExtension   = new JCDIExtension();
-
-    static class JAXRSApplicationClass extends Application {
-    }
-
-    @Provider
-    static class JAXRSProviderClass implements MessageBodyReader<Object> {
-
-        public boolean isReadable(Class<?> type,
-                                  Type genericType,
-                                  Annotation[] annotations,
-                                  MediaType mediaType) {
-            return false;
-        }
-
-        public Object readFrom(Class<Object> type,
-                               Type genericType,
-                               Annotation[] annotations,
-                               MediaType mediaType,
-                               MultivaluedMap<String, String> httpHeaders,
-                               InputStream entityStream) throws IOException {
-            return null;
-        }
-    }
-
-    @Path("/hello")
-    static class JAXRSResourceClass {
-
-    }
-
-    public void testIsJAXRSBean() {
-        assertFalse(JCDIExtension.isJAXRSBean(Object.class));
-        assertFalse(JCDIExtension.isJAXRSBean(JCDIExtension.class));
-
-        assertTrue(JCDIExtension.isJAXRSBean(JAXRSResourceClass.class));
-        assertTrue(JCDIExtension.isJAXRSBean(JAXRSProviderClass.class));
-        assertTrue(JCDIExtension.isJAXRSBean(JAXRSApplicationClass.class));
-    }
-
-    public void testObserveNonJAXRSProcessInjectionTarget() {
-        mockContext.checking(new Expectations() {
-            {
-                oneOf(pij).getAnnotatedType();
-                will(returnValue(aType));
-
-                oneOf(aType).getJavaClass();
-                will(returnValue(Object.class));
-            }
-        });
-        jcdiExtension.observeProcessInjectionTarget(pij);
-        mockContext.assertIsSatisfied();
-    }
-
-    @SuppressWarnings("unchecked")
-    public void testObserveJAXRSProcessInjectionTargetForApplicationSubclasses() {
-        mockContext.checking(new Expectations() {
-            {
-                oneOf(pij).getAnnotatedType();
-                will(returnValue(aType));
-
-                oneOf(aType).getJavaClass();
-                will(returnValue(JAXRSApplicationClass.class));
-
-                oneOf(pij).getInjectionTarget();
-                will(returnValue(injectionTarget));
-
-                oneOf(pij).setInjectionTarget(with(any(JAXRSJCDICustomInjectionTarget.class)));
-            }
-        });
-        jcdiExtension.observeProcessInjectionTarget(pij);
-        mockContext.assertIsSatisfied();
-    }
-
-    @SuppressWarnings("unchecked")
-    public void testObserveJAXRSProcessInjectionTargetForResourceClasses() {
-        mockContext.checking(new Expectations() {
-            {
-                oneOf(pij).getAnnotatedType();
-                will(returnValue(aType));
-
-                oneOf(aType).getJavaClass();
-                will(returnValue(JAXRSResourceClass.class));
-
-                oneOf(pij).getInjectionTarget();
-                will(returnValue(injectionTarget));
-
-                oneOf(pij).setInjectionTarget(with(any(JAXRSJCDICustomInjectionTarget.class)));
-            }
-        });
-        jcdiExtension.observeProcessInjectionTarget(pij);
-        mockContext.assertIsSatisfied();
-    }
-
-    @SuppressWarnings("unchecked")
-    public void testObserveJAXRSProcessInjectionTargetForProviderClasses() {
-        mockContext.checking(new Expectations() {
-            {
-                oneOf(pij).getAnnotatedType();
-                will(returnValue(aType));
-
-                oneOf(aType).getJavaClass();
-                will(returnValue(JAXRSProviderClass.class));
-
-                oneOf(pij).getInjectionTarget();
-                will(returnValue(injectionTarget));
-
-                oneOf(pij).setInjectionTarget(with(any(JAXRSJCDICustomInjectionTarget.class)));
-            }
-        });
-        jcdiExtension.observeProcessInjectionTarget(pij);
-        mockContext.assertIsSatisfied();
-    }
-}
diff --git a/wink-jcdi-server/src/test/java/org/apache/wink/jcdi/server/internal/lifecycle/JCDIDefaultObjectFactoryTest.java b/wink-jcdi-server/src/test/java/org/apache/wink/jcdi/server/internal/lifecycle/JCDIDefaultObjectFactoryTest.java
deleted file mode 100644
index 525e244..0000000
--- a/wink-jcdi-server/src/test/java/org/apache/wink/jcdi/server/internal/lifecycle/JCDIDefaultObjectFactoryTest.java
+++ /dev/null
@@ -1,247 +0,0 @@
-/*
- * 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.    
- */
-
-package org.apache.wink.jcdi.server.internal.lifecycle;
-
-import java.lang.annotation.Annotation;
-import java.util.Collections;
-import java.util.Map;
-
-import javax.enterprise.context.ApplicationScoped;
-import javax.enterprise.context.spi.CreationalContext;
-import javax.enterprise.inject.spi.Bean;
-import javax.enterprise.inject.spi.BeanManager;
-import javax.ws.rs.Path;
-import javax.ws.rs.core.Context;
-import javax.ws.rs.core.HttpHeaders;
-import javax.ws.rs.core.Request;
-
-import junit.framework.TestCase;
-
-import org.apache.wink.common.RuntimeContext;
-import org.jmock.Expectations;
-import org.jmock.Mockery;
-
-public class JCDIDefaultObjectFactoryTest extends TestCase {
-
-    @Path("/hello")
-    static class JAXRSResourceClass {
-
-        @Context
-        public Request      request;
-
-        private HttpHeaders http;
-
-        @Context
-        public void setHeaders(HttpHeaders headers) {
-            http = headers;
-        }
-
-        public HttpHeaders getHttp() {
-            return http;
-        }
-    }
-
-    private Mockery              mockContext           = new Mockery();
-
-    private BeanManager          beanManagerMock       = mockContext.mock(BeanManager.class);
-
-    private RuntimeContext       runtimeContextMock    = mockContext.mock(RuntimeContext.class);
-
-    private Bean<?>              beanMock              = mockContext.mock(Bean.class);
-
-    private CreationalContext<?> creationalContextMock = mockContext.mock(CreationalContext.class);
-
-    private Map<?, ?>            attributeMap          = mockContext.mock(Map.class);
-
-    public void testInit() {
-        JCDIDefaultObjectFactory<JAXRSResourceClass> objFactory =
-            new JCDIDefaultObjectFactory<JAXRSResourceClass>(JAXRSResourceClass.class, beanManagerMock);
-        assertEquals(JAXRSResourceClass.class, objFactory.getInstanceClass());
-        assertNull(objFactory.getCreationalContextMap());
-        mockContext.assertIsSatisfied();
-    }
-
-    public void testGetInstanceWithNullRuntimeContext() {
-        final JAXRSResourceClass resourceInstance = new JAXRSResourceClass();
-        mockContext.checking(new Expectations() {
-            {
-                oneOf(beanManagerMock).isQualifier(Path.class);
-                will(returnValue(false));
-
-                oneOf(beanManagerMock).getBeans(JAXRSResourceClass.class, new Annotation[0]);
-                will(returnValue(Collections.singleton(beanMock)));
-
-                oneOf(beanManagerMock).createCreationalContext(beanMock);
-                will(returnValue(creationalContextMock));
-
-                oneOf(beanManagerMock).getReference(beanMock,
-                                                    JAXRSResourceClass.class,
-                                                    creationalContextMock);
-                will(returnValue(resourceInstance));
-            }
-        });
-
-        JCDIDefaultObjectFactory<JAXRSResourceClass> objFactory =
-            new JCDIDefaultObjectFactory<JAXRSResourceClass>(JAXRSResourceClass.class, beanManagerMock);
-        assertSame(resourceInstance, objFactory.getInstance(null));
-        assertNotNull(objFactory.getCreationalContextMap());
-        assertSame(creationalContextMock, objFactory.getCreationalContextMap()
-            .get(resourceInstance));
-        mockContext.assertIsSatisfied();
-
-        /*
-         * now test a releaseInstance; this should never occur in practice
-         * because the getInstance was passed a null RuntimeContext (so it is a
-         * global/ApplicationScoped object) but testing it
-         */
-
-        mockContext.checking(new Expectations() {
-            {
-                oneOf(runtimeContextMock).getAttributes();
-                will(returnValue(attributeMap));
-
-                oneOf(attributeMap).remove(CreationalContext.class.getName());
-                will(returnValue(null));
-            }
-        });
-
-        objFactory.releaseInstance(resourceInstance, runtimeContextMock);
-        assertNotNull(objFactory.getCreationalContextMap());
-        mockContext.assertIsSatisfied();
-
-        /* now test the releaseAll */
-
-        mockContext.checking(new Expectations() {
-            {
-                oneOf(creationalContextMock).release();
-            }
-        });
-
-        objFactory.releaseAll(null);
-        assertNull(objFactory.getCreationalContextMap());
-        mockContext.assertIsSatisfied();
-    }
-
-    public void testGetInstanceWithRuntimeContext() {
-        final JAXRSResourceClass resourceInstance = new JAXRSResourceClass();
-        mockContext.checking(new Expectations() {
-            {
-                oneOf(beanManagerMock).isQualifier(Path.class);
-                will(returnValue(false));
-
-                oneOf(beanManagerMock).getBeans(JAXRSResourceClass.class, new Annotation[0]);
-                will(returnValue(Collections.singleton(beanMock)));
-
-                oneOf(beanManagerMock).createCreationalContext(beanMock);
-                will(returnValue(creationalContextMock));
-
-                oneOf(beanManagerMock).getReference(beanMock,
-                                                    JAXRSResourceClass.class,
-                                                    creationalContextMock);
-                will(returnValue(resourceInstance));
-
-                oneOf(runtimeContextMock).setAttribute(CreationalContext.class,
-                                                       creationalContextMock);
-            }
-        });
-
-        JCDIDefaultObjectFactory<JAXRSResourceClass> objFactory =
-            new JCDIDefaultObjectFactory<JAXRSResourceClass>(JAXRSResourceClass.class, beanManagerMock);
-        assertSame(resourceInstance, objFactory.getInstance(runtimeContextMock));
-        assertNull(objFactory.getCreationalContextMap());
-        mockContext.assertIsSatisfied();
-
-        /* now test the release */
-
-        mockContext.checking(new Expectations() {
-            {
-                oneOf(creationalContextMock).release();
-
-                oneOf(runtimeContextMock).getAttributes();
-                will(returnValue(attributeMap));
-
-                oneOf(attributeMap).remove(CreationalContext.class.getName());
-                will(returnValue(creationalContextMock));
-            }
-        });
-
-        objFactory.releaseInstance(resourceInstance, runtimeContextMock);
-        assertNull(objFactory.getCreationalContextMap());
-
-        mockContext.assertIsSatisfied();
-    }
-
-    public void testReleaseInstanceNull() {
-        JCDIDefaultObjectFactory<JAXRSResourceClass> objFactory =
-            new JCDIDefaultObjectFactory<JAXRSResourceClass>(JAXRSResourceClass.class, beanManagerMock);
-        assertNull(objFactory.getCreationalContextMap());
-        objFactory.releaseInstance(null, null);
-        assertNull(objFactory.getCreationalContextMap());
-
-        mockContext.assertIsSatisfied();
-    }
-
-    public void testReleaseInstanceRuntimeContextNoCreationalContext() {
-        JCDIDefaultObjectFactory<JAXRSResourceClass> objFactory =
-            new JCDIDefaultObjectFactory<JAXRSResourceClass>(JAXRSResourceClass.class, beanManagerMock);
-        assertNull(objFactory.getCreationalContextMap());
-        objFactory.releaseInstance(new JAXRSResourceClass(), null);
-        assertNull(objFactory.getCreationalContextMap());
-        mockContext.assertIsSatisfied();
-
-        mockContext.checking(new Expectations() {
-            {
-                oneOf(runtimeContextMock).getAttributes();
-                will(returnValue(attributeMap));
-
-                oneOf(attributeMap).remove(CreationalContext.class.getName());
-                will(returnValue(null));
-            }
-        });
-
-        assertNull(objFactory.getCreationalContextMap());
-        objFactory.releaseInstance(null, runtimeContextMock);
-        assertNull(objFactory.getCreationalContextMap());
-
-        mockContext.assertIsSatisfied();
-    }
-
-    public void testReleaseAllNull() {
-        JCDIDefaultObjectFactory<JAXRSResourceClass> objFactory =
-            new JCDIDefaultObjectFactory<JAXRSResourceClass>(JAXRSResourceClass.class, beanManagerMock);
-        assertNull(objFactory.getCreationalContextMap());
-        objFactory.releaseAll(null);
-        assertNull(objFactory.getCreationalContextMap());
-
-        mockContext.assertIsSatisfied();
-    }
-
-    public void testReleaseAllNoApplicationScopedObjects() {
-        JCDIDefaultObjectFactory<JAXRSResourceClass> objFactory =
-            new JCDIDefaultObjectFactory<JAXRSResourceClass>(JAXRSResourceClass.class, beanManagerMock);
-        assertNull(objFactory.getCreationalContextMap());
-        objFactory.releaseAll(runtimeContextMock);
-        assertNull(objFactory.getCreationalContextMap());
-
-        mockContext.assertIsSatisfied();
-    }
-    
-    /* TODO need to test multiple runs */
-}
diff --git a/wink-jcdi-server/src/test/java/org/apache/wink/jcdi/server/internal/lifecycle/JCDILifecycleManagerTest.java b/wink-jcdi-server/src/test/java/org/apache/wink/jcdi/server/internal/lifecycle/JCDILifecycleManagerTest.java
deleted file mode 100644
index ca2980d..0000000
--- a/wink-jcdi-server/src/test/java/org/apache/wink/jcdi/server/internal/lifecycle/JCDILifecycleManagerTest.java
+++ /dev/null
@@ -1,328 +0,0 @@
-/*
- * 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.    
- */
-package org.apache.wink.jcdi.server.internal.lifecycle;
-
-import static org.hamcrest.Matchers.anyOf;
-
-import java.io.IOException;
-import java.io.InputStream;
-import java.lang.annotation.Annotation;
-import java.lang.annotation.Retention;
-import java.lang.annotation.RetentionPolicy;
-import java.lang.reflect.Type;
-import java.util.Collections;
-
-import javax.enterprise.inject.spi.Bean;
-import javax.enterprise.inject.spi.BeanManager;
-import javax.inject.Named;
-import javax.inject.Qualifier;
-import javax.ws.rs.Path;
-import javax.ws.rs.core.Application;
-import javax.ws.rs.core.Context;
-import javax.ws.rs.core.HttpHeaders;
-import javax.ws.rs.core.MediaType;
-import javax.ws.rs.core.MultivaluedMap;
-import javax.ws.rs.core.Request;
-import javax.ws.rs.ext.MessageBodyReader;
-import javax.ws.rs.ext.Provider;
-
-import junit.framework.TestCase;
-
-import org.jmock.Expectations;
-import org.jmock.Mockery;
-
-public class JCDILifecycleManagerTest extends TestCase {
-
-    private Mockery     mockContext      = new Mockery();
-
-    private BeanManager beanManagerMock  = mockContext.mock(BeanManager.class);
-
-    private BeanManager beanManager2Mock = mockContext.mock(BeanManager.class, "beanManager2Mock");
-
-    private Bean<?>     beanMock         = mockContext.mock(Bean.class);
-
-    static class JAXRSApplicationClass extends Application {
-        @Context
-        public Request      request;
-
-        private HttpHeaders http;
-
-        @Context
-        public void setHeaders(HttpHeaders headers) {
-            http = headers;
-        }
-
-        public HttpHeaders getHttp() {
-            return http;
-        }
-    }
-
-    @Provider
-    static class JAXRSProviderClass implements MessageBodyReader<Object> {
-
-        @Context
-        public Request      request;
-
-        private HttpHeaders http;
-
-        @Context
-        public void setHeaders(HttpHeaders headers) {
-            http = headers;
-        }
-
-        public HttpHeaders getHttp() {
-            return http;
-        }
-
-        public boolean isReadable(Class<?> type,
-                                  Type genericType,
-                                  Annotation[] annotations,
-                                  MediaType mediaType) {
-            return false;
-        }
-
-        public Object readFrom(Class<Object> type,
-                               Type genericType,
-                               Annotation[] annotations,
-                               MediaType mediaType,
-                               MultivaluedMap<String, String> httpHeaders,
-                               InputStream entityStream) throws IOException {
-            return null;
-        }
-    }
-
-    @Path("/hello")
-    static class JAXRSResourceClass {
-
-        @Context
-        public Request      request;
-
-        private HttpHeaders http;
-
-        @Context
-        public void setHeaders(HttpHeaders headers) {
-            http = headers;
-        }
-
-        public HttpHeaders getHttp() {
-            return http;
-        }
-    }
-
-    @Named("myJAXRSResourceClassName")
-    @Path("/hello")
-    static class JAXRSResourceClassWithQualifier {
-
-    }
-
-    @Qualifier
-    @Retention(value = RetentionPolicy.RUNTIME)
-    public @interface MyQualifierAnnotation {
-    }
-
-    @Named("myJAXRSResourceClassName")
-    @MyQualifierAnnotation
-    @Path("/hello")
-    static class JAXRSResourceClassWithMultipleQualifiers {
-
-    }
-
-    public void testIsJCDIManagedBeanResourceClass() {
-        mockContext.checking(new Expectations() {
-            {
-                oneOf(beanManagerMock).isQualifier(Path.class);
-                will(returnValue(false));
-
-                oneOf(beanManagerMock).getBeans(JAXRSResourceClass.class, new Annotation[0]);
-                will(returnValue(Collections.singleton(beanMock)));
-            }
-        });
-        assertTrue(JCDILifecycleManager
-            .isJCDIManagedBean(JAXRSResourceClass.class, beanManagerMock));
-        mockContext.assertIsSatisfied();
-    }
-
-    public void testIsJCDIManagedBeanResourceClassWithQualifier() {
-        mockContext.checking(new Expectations() {
-            {
-                oneOf(beanManagerMock).isQualifier(Path.class);
-                will(returnValue(false));
-
-                oneOf(beanManagerMock).isQualifier(Named.class);
-                will(returnValue(true));
-
-                oneOf(beanManagerMock)
-                    .getBeans(JAXRSResourceClassWithQualifier.class,
-                              new Annotation[] {JAXRSResourceClassWithQualifier.class
-                                  .getAnnotation(Named.class)});
-                will(returnValue(Collections.singleton(beanMock)));
-            }
-        });
-        assertTrue(JCDILifecycleManager.isJCDIManagedBean(JAXRSResourceClassWithQualifier.class,
-                                                          beanManagerMock));
-        mockContext.assertIsSatisfied();
-    }
-
-    @SuppressWarnings("unchecked")
-    public void testIsJCDIManagedBeanResourceClassWithMultipleQualifiers() {
-        mockContext.checking(new Expectations() {
-            {
-                oneOf(beanManagerMock).isQualifier(Path.class);
-                will(returnValue(false));
-
-                oneOf(beanManagerMock).isQualifier(Named.class);
-                will(returnValue(true));
-
-                oneOf(beanManagerMock).isQualifier(MyQualifierAnnotation.class);
-                will(returnValue(true));
-
-                oneOf(beanManagerMock)
-                    .getBeans(with(same(JAXRSResourceClassWithMultipleQualifiers.class)),
-                              with(anyOf(
-
-                              equal(new Annotation[] {
-                                  JAXRSResourceClassWithMultipleQualifiers.class
-                                      .getAnnotation(Named.class),
-                                  JAXRSResourceClassWithMultipleQualifiers.class
-                                      .getAnnotation(MyQualifierAnnotation.class)}),
-
-                              equal(new Annotation[] {
-                                  JAXRSResourceClassWithMultipleQualifiers.class
-                                      .getAnnotation(MyQualifierAnnotation.class),
-                                  JAXRSResourceClassWithMultipleQualifiers.class
-                                      .getAnnotation(Named.class)})
-
-                              )));
-                will(returnValue(Collections.singleton(beanMock)));
-            }
-        });
-        assertTrue(JCDILifecycleManager
-            .isJCDIManagedBean(JAXRSResourceClassWithMultipleQualifiers.class, beanManagerMock));
-        mockContext.assertIsSatisfied();
-    }
-
-    public void testIsJCDIManagedBeanResourceClassReturnsFalseDueToEmptySet() {
-        mockContext.checking(new Expectations() {
-            {
-                oneOf(beanManagerMock).isQualifier(Path.class);
-                will(returnValue(false));
-
-                oneOf(beanManagerMock).getBeans(JAXRSResourceClass.class, new Annotation[0]);
-                will(returnValue(Collections.emptySet()));
-            }
-        });
-        assertFalse(JCDILifecycleManager.isJCDIManagedBean(JAXRSResourceClass.class,
-                                                           beanManagerMock));
-        mockContext.assertIsSatisfied();
-    }
-
-    public void testIsJCDIManagedBeanResourceClassReturnsFalseDueToNull() {
-        mockContext.checking(new Expectations() {
-            {
-                oneOf(beanManagerMock).isQualifier(Path.class);
-                will(returnValue(false));
-
-                oneOf(beanManagerMock).getBeans(JAXRSResourceClass.class, new Annotation[0]);
-                will(returnValue(null));
-            }
-        });
-        assertFalse(JCDILifecycleManager.isJCDIManagedBean(JAXRSResourceClass.class,
-                                                           beanManagerMock));
-        mockContext.assertIsSatisfied();
-    }
-
-    public void testSetGetBeanManager() {
-        JCDILifecycleManager<Object> manager = new JCDILifecycleManager<Object>();
-
-        // should not be able to lookup via JNDI
-        assertNull(manager.getBeanManager());
-
-        manager.setBeanManager(beanManagerMock);
-        assertSame(beanManagerMock, manager.getBeanManager());
-
-        manager.setBeanManager(beanManager2Mock);
-        assertSame(beanManager2Mock, manager.getBeanManager());
-
-        mockContext.assertIsSatisfied();
-    }
-
-    public void testCreateSingletonObjectFactory() {
-        JCDILifecycleManager<Object> manager = new JCDILifecycleManager<Object>();
-        try {
-            manager.createObjectFactory(null);
-            fail("Expected NPE");
-        } catch (NullPointerException e) {
-            // expected
-        }
-        assertNull(manager.createObjectFactory(new Object()));
-        assertNull(manager.createObjectFactory(new JAXRSResourceClass()));
-        assertNull(manager.createObjectFactory(new JAXRSApplicationClass()));
-        assertNull(manager.createObjectFactory(new JAXRSProviderClass()));
-        assertNull(manager.createObjectFactory(new JAXRSResourceClassWithQualifier()));
-        assertNull(manager.createObjectFactory(new JAXRSResourceClassWithMultipleQualifiers()));
-        mockContext.assertIsSatisfied();
-    }
-
-    public void testCreateClassObjectFactoryNull() {
-        JCDILifecycleManager<JAXRSResourceClass> manager =
-            new JCDILifecycleManager<JAXRSResourceClass>();
-        try {
-            Class<JAXRSResourceClass> c = null;
-            manager.createObjectFactory(c);
-            fail("Expected NPE");
-        } catch (NullPointerException e) {
-            // expected
-        }
-        mockContext.assertIsSatisfied();
-    }
-
-    public void testCreateClassObjectFactoryButNotManagedBean() {
-        mockContext.checking(new Expectations() {
-            {
-                oneOf(beanManagerMock).isQualifier(Path.class);
-                will(returnValue(false));
-
-                oneOf(beanManagerMock).getBeans(JAXRSResourceClass.class, new Annotation[0]);
-                will(returnValue(null));
-            }
-        });
-        JCDILifecycleManager<JAXRSResourceClass> manager =
-            new JCDILifecycleManager<JAXRSResourceClass>();
-        manager.setBeanManager(beanManagerMock);
-        assertNull(manager.createObjectFactory(JAXRSResourceClass.class));
-        mockContext.assertIsSatisfied();
-    }
-
-    public void testCreateClassObjectFactoryWithResourceManagedBean() {
-        mockContext.checking(new Expectations() {
-            {
-                oneOf(beanManagerMock).isQualifier(Path.class);
-                will(returnValue(false));
-
-                oneOf(beanManagerMock).getBeans(JAXRSResourceClass.class, new Annotation[0]);
-                will(returnValue(Collections.singleton(beanMock)));
-            }
-        });
-        JCDILifecycleManager<JAXRSResourceClass> manager =
-            new JCDILifecycleManager<JAXRSResourceClass>();
-        manager.setBeanManager(beanManagerMock);
-        assertNotNull(manager.createObjectFactory(JAXRSResourceClass.class));
-        mockContext.assertIsSatisfied();
-    }
-}
diff --git a/wink-jcdi-server/src/test/java/org/apache/wink/jcdi/server/internal/lifecycle/JCDISingletonObjectFactoryTest.java b/wink-jcdi-server/src/test/java/org/apache/wink/jcdi/server/internal/lifecycle/JCDISingletonObjectFactoryTest.java
deleted file mode 100644
index 3f489ff..0000000
--- a/wink-jcdi-server/src/test/java/org/apache/wink/jcdi/server/internal/lifecycle/JCDISingletonObjectFactoryTest.java
+++ /dev/null
@@ -1,353 +0,0 @@
-/*
- * 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.
- *  
- */
-
-package org.apache.wink.jcdi.server.internal.lifecycle;
-
-import java.io.IOException;
-import java.io.InputStream;
-import java.lang.annotation.Annotation;
-import java.lang.reflect.Type;
-import java.util.Collections;
-
-import javax.enterprise.context.spi.CreationalContext;
-import javax.enterprise.inject.spi.Bean;
-import javax.enterprise.inject.spi.BeanManager;
-import javax.ws.rs.core.MediaType;
-import javax.ws.rs.core.MultivaluedMap;
-import javax.ws.rs.ext.MessageBodyReader;
-import javax.ws.rs.ext.Provider;
-
-import junit.framework.TestCase;
-
-import org.apache.wink.common.RuntimeContext;
-import org.jmock.Expectations;
-import org.jmock.Mockery;
-
-public class JCDISingletonObjectFactoryTest extends TestCase {
-
-    private Mockery              mockContext           = new Mockery();
-
-    private BeanManager          beanManagerMock       = mockContext.mock(BeanManager.class);
-
-    private RuntimeContext       runtimeContextMock    = mockContext.mock(RuntimeContext.class);
-
-    private Bean<?>              beanMock              = mockContext.mock(Bean.class);
-
-    private CreationalContext<?> creationalContextMock = mockContext.mock(CreationalContext.class);
-
-    private final JAXRSProvider  providerInstance      = new JAXRSProvider();
-
-    @Provider
-    static class JAXRSProvider implements MessageBodyReader<Object> {
-
-        public boolean isReadable(Class<?> type,
-                                  Type genericType,
-                                  Annotation[] annotations,
-                                  MediaType mediaType) {
-            throw new UnsupportedOperationException();
-        }
-
-        public Object readFrom(Class<Object> type,
-                               Type genericType,
-                               Annotation[] annotations,
-                               MediaType mediaType,
-                               MultivaluedMap<String, String> httpHeaders,
-                               InputStream entityStream) throws IOException {
-            throw new UnsupportedOperationException();
-        }
-    }
-
-    public void testInit() {
-        mockContext.checking(new Expectations() {
-            {
-                oneOf(beanManagerMock).isQualifier(Provider.class);
-                will(returnValue(false));
-
-                oneOf(beanManagerMock).getBeans(JAXRSProvider.class, new Annotation[0]);
-                will(returnValue(Collections.singleton(beanMock)));
-
-                oneOf(beanManagerMock).createCreationalContext(beanMock);
-                will(returnValue(creationalContextMock));
-
-                oneOf(beanManagerMock).getReference(beanMock,
-                                                    JAXRSProvider.class,
-                                                    creationalContextMock);
-                will(returnValue(providerInstance));
-            }
-        });
-        new JCDISingletonObjectFactory<JAXRSProvider>(JAXRSProvider.class, beanManagerMock);
-        mockContext.assertIsSatisfied();
-    }
-
-    public void testGetInstanceClass() {
-        mockContext.checking(new Expectations() {
-            {
-                oneOf(beanManagerMock).isQualifier(Provider.class);
-                will(returnValue(false));
-
-                oneOf(beanManagerMock).getBeans(JAXRSProvider.class, new Annotation[0]);
-                will(returnValue(Collections.singleton(beanMock)));
-
-                oneOf(beanManagerMock).createCreationalContext(beanMock);
-                will(returnValue(creationalContextMock));
-
-                oneOf(beanManagerMock).getReference(beanMock,
-                                                    JAXRSProvider.class,
-                                                    creationalContextMock);
-                will(returnValue(providerInstance));
-            }
-        });
-        JCDISingletonObjectFactory<JAXRSProvider> objFactory =
-            new JCDISingletonObjectFactory<JAXRSProvider>(JAXRSProvider.class, beanManagerMock);
-        assertEquals(JAXRSProvider.class, objFactory.getInstanceClass());
-        mockContext.assertIsSatisfied();
-    }
-
-    public void testGetInstance() {
-        mockContext.checking(new Expectations() {
-            {
-                oneOf(beanManagerMock).isQualifier(Provider.class);
-                will(returnValue(false));
-
-                oneOf(beanManagerMock).getBeans(JAXRSProvider.class, new Annotation[0]);
-                will(returnValue(Collections.singleton(beanMock)));
-
-                oneOf(beanManagerMock).createCreationalContext(beanMock);
-                will(returnValue(creationalContextMock));
-
-                oneOf(beanManagerMock).getReference(beanMock,
-                                                    JAXRSProvider.class,
-                                                    creationalContextMock);
-                will(returnValue(providerInstance));
-            }
-        });
-        JCDISingletonObjectFactory<JAXRSProvider> objFactory =
-            new JCDISingletonObjectFactory<JAXRSProvider>(JAXRSProvider.class, beanManagerMock);
-
-        JAXRSProvider provider = objFactory.getInstance(null);
-        assertSame(providerInstance, provider);
-
-        JAXRSProvider provider2 = objFactory.getInstance(null);
-        assertSame(provider, provider2);
-
-        JAXRSProvider provider3 = objFactory.getInstance(runtimeContextMock);
-        assertSame(provider, provider3);
-
-        mockContext.assertIsSatisfied();
-    }
-
-    public void testReleaseInstance() {
-        mockContext.checking(new Expectations() {
-            {
-                oneOf(beanManagerMock).isQualifier(Provider.class);
-                will(returnValue(false));
-
-                oneOf(beanManagerMock).getBeans(JAXRSProvider.class, new Annotation[0]);
-                will(returnValue(Collections.singleton(beanMock)));
-
-                oneOf(beanManagerMock).createCreationalContext(beanMock);
-                will(returnValue(creationalContextMock));
-
-                oneOf(beanManagerMock).getReference(beanMock,
-                                                    JAXRSProvider.class,
-                                                    creationalContextMock);
-                will(returnValue(providerInstance));
-            }
-        });
-        JCDISingletonObjectFactory<JAXRSProvider> objFactory =
-            new JCDISingletonObjectFactory<JAXRSProvider>(JAXRSProvider.class, beanManagerMock);
-        /* this should do absolutely nothing */
-        objFactory.releaseInstance(providerInstance, runtimeContextMock);
-        objFactory.releaseInstance(providerInstance, null);
-        objFactory.releaseInstance(null, runtimeContextMock);
-        objFactory.releaseInstance(null, null);
-        mockContext.assertIsSatisfied();
-    }
-
-    public void testReleaseAllInstance() {
-        mockContext.checking(new Expectations() {
-            {
-                oneOf(beanManagerMock).isQualifier(Provider.class);
-                will(returnValue(false));
-
-                oneOf(beanManagerMock).getBeans(JAXRSProvider.class, new Annotation[0]);
-                will(returnValue(Collections.singleton(beanMock)));
-
-                oneOf(beanManagerMock).createCreationalContext(beanMock);
-                will(returnValue(creationalContextMock));
-
-                oneOf(beanManagerMock).getReference(beanMock,
-                                                    JAXRSProvider.class,
-                                                    creationalContextMock);
-                will(returnValue(providerInstance));
-            }
-        });
-        JCDISingletonObjectFactory<JAXRSProvider> objFactory =
-            new JCDISingletonObjectFactory<JAXRSProvider>(JAXRSProvider.class, beanManagerMock);
-
-        mockContext.checking(new Expectations() {
-            {
-                oneOf(creationalContextMock).release();
-            }
-        });
-        objFactory.releaseAll(runtimeContextMock);
-        objFactory.releaseAll(null);
-        mockContext.assertIsSatisfied();
-    }
-
-    public void testReleaseAllWithNoGetInstance() {
-        mockContext.checking(new Expectations() {
-            {
-                oneOf(beanManagerMock).isQualifier(Provider.class);
-                will(returnValue(false));
-
-                oneOf(beanManagerMock).getBeans(JAXRSProvider.class, new Annotation[0]);
-                will(returnValue(Collections.singleton(beanMock)));
-
-                oneOf(beanManagerMock).createCreationalContext(beanMock);
-                will(returnValue(creationalContextMock));
-
-                oneOf(beanManagerMock).getReference(beanMock,
-                                                    JAXRSProvider.class,
-                                                    creationalContextMock);
-                will(returnValue(providerInstance));
-            }
-        });
-        JCDISingletonObjectFactory<JAXRSProvider> objFactory =
-            new JCDISingletonObjectFactory<JAXRSProvider>(JAXRSProvider.class, beanManagerMock);
-
-        mockContext.checking(new Expectations() {
-            {
-                oneOf(creationalContextMock).release();
-            }
-        });
-        objFactory.releaseAll(null);
-        objFactory.releaseAll(runtimeContextMock);
-        mockContext.assertIsSatisfied();
-    }
-
-    public void testReleaseAllAfterGetInstance() {
-        mockContext.checking(new Expectations() {
-            {
-                oneOf(beanManagerMock).isQualifier(Provider.class);
-                will(returnValue(false));
-
-                oneOf(beanManagerMock).getBeans(JAXRSProvider.class, new Annotation[0]);
-                will(returnValue(Collections.singleton(beanMock)));
-
-                oneOf(beanManagerMock).createCreationalContext(beanMock);
-                will(returnValue(creationalContextMock));
-
-                oneOf(beanManagerMock).getReference(beanMock,
-                                                    JAXRSProvider.class,
-                                                    creationalContextMock);
-                will(returnValue(providerInstance));
-            }
-        });
-        JCDISingletonObjectFactory<JAXRSProvider> objFactory =
-            new JCDISingletonObjectFactory<JAXRSProvider>(JAXRSProvider.class, beanManagerMock);
-
-        JAXRSProvider provider = objFactory.getInstance(null);
-        assertSame(providerInstance, provider);
-
-        mockContext.checking(new Expectations() {
-            {
-                oneOf(creationalContextMock).release();
-            }
-        });
-        objFactory.releaseAll(null);
-
-        /* called again for nefarious reasons; should never happen in production */
-        objFactory.releaseAll(null);
-
-        mockContext.assertIsSatisfied();
-    }
-
-    public void testReleaseAllAfterGetInstanceWithRuntimeContext() {
-        mockContext.checking(new Expectations() {
-            {
-                oneOf(beanManagerMock).isQualifier(Provider.class);
-                will(returnValue(false));
-
-                oneOf(beanManagerMock).getBeans(JAXRSProvider.class, new Annotation[0]);
-                will(returnValue(Collections.singleton(beanMock)));
-
-                oneOf(beanManagerMock).createCreationalContext(beanMock);
-                will(returnValue(creationalContextMock));
-
-                oneOf(beanManagerMock).getReference(beanMock,
-                                                    JAXRSProvider.class,
-                                                    creationalContextMock);
-                will(returnValue(providerInstance));
-            }
-        });
-
-        JCDISingletonObjectFactory<JAXRSProvider> objFactory =
-            new JCDISingletonObjectFactory<JAXRSProvider>(JAXRSProvider.class, beanManagerMock);
-
-        JAXRSProvider provider = objFactory.getInstance(null);
-        assertSame(providerInstance, provider);
-
-        mockContext.checking(new Expectations() {
-            {
-                oneOf(creationalContextMock).release();
-            }
-        });
-        objFactory.releaseAll(runtimeContextMock);
-
-        /* called again for nefarious reasons; should never happen in production */
-        objFactory.releaseAll(runtimeContextMock);
-
-        mockContext.assertIsSatisfied();
-    }
-
-    public void testReleaseInstanceAfterGetInstance() {
-        mockContext.checking(new Expectations() {
-            {
-                oneOf(beanManagerMock).isQualifier(Provider.class);
-                will(returnValue(false));
-
-                oneOf(beanManagerMock).getBeans(JAXRSProvider.class, new Annotation[0]);
-                will(returnValue(Collections.singleton(beanMock)));
-
-                oneOf(beanManagerMock).createCreationalContext(beanMock);
-                will(returnValue(creationalContextMock));
-
-                oneOf(beanManagerMock).getReference(beanMock,
-                                                    JAXRSProvider.class,
-                                                    creationalContextMock);
-                will(returnValue(providerInstance));
-            }
-        });
-
-        JCDISingletonObjectFactory<JAXRSProvider> objFactory =
-            new JCDISingletonObjectFactory<JAXRSProvider>(JAXRSProvider.class, beanManagerMock);
-
-        JAXRSProvider provider = objFactory.getInstance(null);
-        assertSame(providerInstance, provider);
-
-        objFactory.releaseInstance(provider, runtimeContextMock);
-        objFactory.releaseInstance(null, runtimeContextMock);
-        objFactory.releaseInstance(provider, null);
-
-        mockContext.assertIsSatisfied();
-    }
-
-}
diff --git a/wink-jcdi-server/src/test/java/org/apache/wink/jcdi/server/test/WinkCdiTest.java b/wink-jcdi-server/src/test/java/org/apache/wink/jcdi/server/test/WinkCdiTest.java
new file mode 100644
index 0000000..1e68d41
--- /dev/null
+++ b/wink-jcdi-server/src/test/java/org/apache/wink/jcdi/server/test/WinkCdiTest.java
@@ -0,0 +1,110 @@
+/*
+* 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.
+*/
+package org.apache.wink.jcdi.server.test;
+
+
+import org.apache.wink.client.ClientConfig;
+import org.apache.wink.client.Resource;
+import org.apache.wink.client.RestClient;
+import org.apache.wink.common.model.synd.SyndFeed;
+import org.apache.wink.jcdi.server.internal.servlet.CdiRestServlet;
+import org.apache.wink.jcdi.server.test.controller.TestController;
+import org.apache.wink.jcdi.server.test.service.SimpleTestService;
+import org.apache.wink.jcdi.server.test.util.ArchiveUtils;
+import org.jboss.arquillian.container.test.api.Deployment;
+import org.jboss.arquillian.container.test.api.RunAsClient;
+import org.jboss.arquillian.junit.Arquillian;
+import org.jboss.arquillian.test.api.ArquillianResource;
+import org.jboss.shrinkwrap.api.ShrinkWrap;
+import org.jboss.shrinkwrap.api.asset.Asset;
+import org.jboss.shrinkwrap.api.asset.EmptyAsset;
+import org.jboss.shrinkwrap.api.asset.StringAsset;
+import org.jboss.shrinkwrap.api.spec.JavaArchive;
+import org.jboss.shrinkwrap.api.spec.WebArchive;
+import org.junit.Assert;
+import org.junit.Test;
+import org.junit.runner.RunWith;
+
+import java.net.MalformedURLException;
+import java.net.URISyntaxException;
+import java.net.URL;
+
+@RunWith(Arquillian.class)
+public class WinkCdiTest {
+    private final static String TEST_NAME = "restTests";
+    private final static String TEST_SERVLET_PATH = "wink-test";
+    private final static String TEST_APPLICATION_FILE_NAME = "test-application";
+
+    //creating a WebArchive is only a workaround because JavaArchive cannot contain other archives.
+    @Deployment
+    public static WebArchive deploy() {
+        JavaArchive testJar = ShrinkWrap.create(JavaArchive.class, TEST_NAME + ".jar")
+                .addPackage(WinkCdiTest.class.getPackage())
+                .addPackage(TestController.class.getPackage())
+                .addPackage(SimpleTestService.class.getPackage())
+                .addAsManifestResource(EmptyAsset.INSTANCE, "beans.xml");
+
+        Asset webXmlAsset = new StringAsset("<web-app xmlns=\"http://java.sun.com/xml/ns/javaee\"\n" +
+                "         xmlns:xsi=\"http://www.w3.org/2001/XMLSchema-instance\"\n" +
+                "         xsi:schemaLocation=\"http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-app_3_0.xsd\"\n" +
+                "         version=\"3.0\">\n" +
+                "    <servlet>\n" +
+                "        <servlet-name>wink-test</servlet-name>\n" +
+                "        <servlet-class>" + CdiRestServlet.class.getName() + "</servlet-class>\n" +
+                "        <init-param>\n" +
+                "            <param-name>applicationConfigLocation</param-name>\n" +
+                "            <param-value>/WEB-INF/" + TEST_APPLICATION_FILE_NAME + "</param-value>\n" +
+                "        </init-param>\n" +
+                "    </servlet>\n" +
+                "    <servlet-mapping>\n" +
+                "        <servlet-name>wink-test</servlet-name>\n" +
+                "        <url-pattern>/" + TEST_SERVLET_PATH + "/*</url-pattern>\n" +
+                "    </servlet-mapping>\n" +
+                "</web-app>");
+
+        Asset applicationAsset = new StringAsset(TestController.class.getName());
+
+        return ShrinkWrap.create(WebArchive.class, TEST_NAME + ".war")
+                .addAsLibraries(ArchiveUtils.getWinkCoreServerArchive())
+                .addAsLibraries(ArchiveUtils.getWinkCdiServerArchive())
+                .addAsLibraries(ArchiveUtils.getWinkCommonArchive())
+                .addAsLibraries(testJar)
+                .addAsWebInfResource(EmptyAsset.INSTANCE, "beans.xml")
+                .addAsWebInfResource(webXmlAsset, "web.xml")
+                .addAsWebInfResource(applicationAsset, TEST_APPLICATION_FILE_NAME);
+    }
+
+    @ArquillianResource
+    private URL url;
+
+    @Test
+    @RunAsClient
+    public void simpleClientToServerCall() throws URISyntaxException, MalformedURLException {
+        Assert.assertNotNull(url);
+        String resourcePath = TEST_SERVLET_PATH + TestController.PATH;
+
+        RestClient restClient = new RestClient(new ClientConfig());
+
+        URL resourceURL = new URL(url.toExternalForm() + resourcePath);
+        Resource resource = restClient.resource(resourceURL.toURI());
+
+        // invoke GET on the resource and check the result
+        Assert.assertEquals("Hello CDI", resource.get(SyndFeed.class).getTitle().getValue());
+    }
+}
diff --git a/wink-jcdi-server/src/test/java/org/apache/wink/jcdi/server/test/controller/TestController.java b/wink-jcdi-server/src/test/java/org/apache/wink/jcdi/server/test/controller/TestController.java
new file mode 100644
index 0000000..7241925
--- /dev/null
+++ b/wink-jcdi-server/src/test/java/org/apache/wink/jcdi/server/test/controller/TestController.java
@@ -0,0 +1,50 @@
+/*
+ * 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.
+ */
+package org.apache.wink.jcdi.server.test.controller;
+
+import org.apache.wink.common.model.synd.SyndEntry;
+import org.apache.wink.common.model.synd.SyndText;
+import org.apache.wink.jcdi.server.test.service.SimpleTestService;
+
+import javax.inject.Inject;
+import javax.ws.rs.GET;
+import javax.ws.rs.Path;
+import javax.ws.rs.Produces;
+import javax.ws.rs.core.Context;
+import javax.ws.rs.core.MediaType;
+import javax.ws.rs.core.UriInfo;
+import java.util.Date;
+
+@Path(TestController.PATH)
+public class TestController {
+    public static final String PATH = "/hello";
+
+    @Inject
+    private SimpleTestService simpleTestService;
+
+    @Context
+    private UriInfo uriInfo;
+
+    @GET
+    @Produces(MediaType.APPLICATION_ATOM_XML)
+    public SyndEntry getGreeting() {
+        String text = this.simpleTestService.createGreeting("CDI");
+        return new SyndEntry(new SyndText(text), "hello-cdi:1", new Date());
+    }
+}
diff --git a/wink-jcdi-server/src/test/java/org/apache/wink/jcdi/server/test/service/SimpleTestService.java b/wink-jcdi-server/src/test/java/org/apache/wink/jcdi/server/test/service/SimpleTestService.java
new file mode 100644
index 0000000..283589b
--- /dev/null
+++ b/wink-jcdi-server/src/test/java/org/apache/wink/jcdi/server/test/service/SimpleTestService.java
@@ -0,0 +1,28 @@
+/*
+ * 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.
+*/
+package org.apache.wink.jcdi.server.test.service;
+
+import javax.enterprise.context.ApplicationScoped;
+
+@ApplicationScoped
+public class SimpleTestService {
+    public String createGreeting(String name) {
+        return "Hello " + name;
+    }
+}
diff --git a/wink-jcdi-server/src/test/java/org/apache/wink/jcdi/server/test/util/ArchiveUtils.java b/wink-jcdi-server/src/test/java/org/apache/wink/jcdi/server/test/util/ArchiveUtils.java
new file mode 100644
index 0000000..6d8da35
--- /dev/null
+++ b/wink-jcdi-server/src/test/java/org/apache/wink/jcdi/server/test/util/ArchiveUtils.java
@@ -0,0 +1,38 @@
+/*
+ * 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.
+ */
+package org.apache.wink.jcdi.server.test.util;
+
+import org.jboss.shrinkwrap.api.spec.JavaArchive;
+
+public abstract class ArchiveUtils {
+    public static JavaArchive[] getWinkCoreServerArchive() {
+        String[] excludedFiles = new String[]{};
+        return ShrinkWrapArchiveUtil.getArchives("META-INF/server/wink-providers", new String[]{"org.apache.wink.server"}, excludedFiles, "wink-core");
+    }
+
+    public static JavaArchive[] getWinkCdiServerArchive() {
+        String[] excludedFiles = new String[]{"org.apache.wink.jcdi.server.test"};
+        return ShrinkWrapArchiveUtil.getArchives("META-INF/services/javax.enterprise.inject.spi.Extension", new String[]{"org.apache.wink.jcdi.server"}, excludedFiles, "wink-cdi");
+    }
+
+    public static JavaArchive[] getWinkCommonArchive() {
+        String[] excludedFiles = new String[]{};
+        return ShrinkWrapArchiveUtil.getArchives("META-INF/core/wink-providers", new String[]{"org.apache.wink.common"}, excludedFiles, "wink-common");
+    }
+}
diff --git a/wink-jcdi-server/src/test/java/org/apache/wink/jcdi/server/test/util/ShrinkWrapArchiveUtil.java b/wink-jcdi-server/src/test/java/org/apache/wink/jcdi/server/test/util/ShrinkWrapArchiveUtil.java
new file mode 100644
index 0000000..9e6626d
--- /dev/null
+++ b/wink-jcdi-server/src/test/java/org/apache/wink/jcdi/server/test/util/ShrinkWrapArchiveUtil.java
@@ -0,0 +1,226 @@
+/*
+ * 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.
+ */
+package org.apache.wink.jcdi.server.test.util;
+
+
+import org.jboss.shrinkwrap.api.ShrinkWrap;
+import org.jboss.shrinkwrap.api.spec.JavaArchive;
+
+import java.io.File;
+import java.io.IOException;
+import java.net.URI;
+import java.net.URL;
+import java.util.*;
+
+//based on org.apache.deltaspike.test.utils.ShrinkWrapArchiveUtil
+public abstract class ShrinkWrapArchiveUtil {
+    public static JavaArchive[] getArchives(String markerFile,
+                                            String[] includeIfPackageExists,
+                                            String[] excludeIfPackageExists,
+                                            String archiveName) {
+        ClassLoader classLoader = ShrinkWrapArchiveUtil.class.getClassLoader();
+
+        try {
+            Enumeration<URL> foundFiles = classLoader.getResources(markerFile);
+
+            List<JavaArchive> archives = new ArrayList<JavaArchive>();
+
+            while (foundFiles.hasMoreElements()) {
+                URL foundFile = foundFiles.nextElement();
+
+                JavaArchive archive
+                        = createArchive(foundFile, markerFile, includeIfPackageExists, excludeIfPackageExists, archiveName);
+                if (archive != null) {
+                    archives.add(archive);
+                }
+            }
+
+            return archives.toArray(new JavaArchive[archives.size()]);
+        } catch (IOException ioe) {
+            throw new RuntimeException(ioe);
+        }
+    }
+
+    private static JavaArchive createArchive(URL foundFile, String markerFile,
+                                             String[] includeIfPackageExists,
+                                             String[] excludeIfPackageExists,
+                                             String archiveName)
+            throws IOException {
+        String urlString = foundFile.toString();
+        int idx = urlString.lastIndexOf(markerFile);
+        urlString = urlString.substring(0, idx);
+
+        String jarUrlPath = isJarUrl(urlString);
+        if (jarUrlPath != null) {
+            JavaArchive foundJar = ShrinkWrap.createFromZipFile(JavaArchive.class, new File(URI.create(jarUrlPath)));
+
+            if (excludeIfPackageExists != null) {
+                for (String excludePackage : excludeIfPackageExists) {
+                    if (foundJar.contains(excludePackage.replaceAll("\\.", "\\/"))) {
+                        return null;
+                    }
+                }
+            }
+            if (includeIfPackageExists != null) {
+                for (String includePackage : includeIfPackageExists) {
+                    if (foundJar.contains(includePackage.replaceAll("\\.", "\\/"))) {
+                        return foundJar;
+                    }
+                }
+            }
+            return null; // couldn't find any jar
+        } else {
+            File f = new File((new URL(ensureCorrectUrlFormat(urlString))).getFile());
+            if (!f.exists()) {
+                // try a fallback if the URL contains %20 -> spaces
+                if (urlString.contains("%20")) {
+                    urlString = urlString.replaceAll("%20", " ");
+                    f = new File((new URL(ensureCorrectUrlFormat(urlString))).getFile());
+                }
+
+            }
+
+            return addFileArchive(f, includeIfPackageExists, excludeIfPackageExists, archiveName);
+        }
+    }
+
+    private static JavaArchive addFileArchive(File archiveBasePath,
+                                              String[] includeIfPackageExists,
+                                              String[] excludeIfPackageExists,
+                                              String archiveName)
+            throws IOException {
+        if (!archiveBasePath.exists()) {
+            return null;
+        }
+
+        JavaArchive ret = null;
+
+        if (archiveName == null) {
+            archiveName = UUID.randomUUID().toString();
+        } else {
+            archiveName += "_" + UUID.randomUUID().toString();
+        }
+        JavaArchive javaArchive = ShrinkWrap.create(JavaArchive.class, archiveName + ".jar");
+
+        if (includeIfPackageExists == null) {
+            // no include rule, thus add it immediately
+            ret = javaArchive;
+        }
+
+        int basePathLength = archiveBasePath.getAbsolutePath().length() + 1;
+
+        for (File archiveEntry : collectArchiveEntries(archiveBasePath)) {
+            String entryName = archiveEntry.getAbsolutePath().substring(basePathLength);
+
+            // exclude rule
+            if (excludeIfPackageExists(entryName, excludeIfPackageExists)) {
+                continue;
+            }
+
+            // include rule
+            if (ret == null && includeIfPackageExists(entryName, includeIfPackageExists)) {
+                ret = javaArchive;
+            }
+
+            if (entryName.endsWith(".class")) {
+                String className
+                        = pathToClassName(entryName.substring(0, entryName.length() - (".class".length())));
+
+                javaArchive.addClass(className);
+            } else {
+                javaArchive.addAsResource(archiveEntry, entryName.replace('\\', '/'));
+            }
+        }
+
+        return ret;
+    }
+
+    private static List<File> collectArchiveEntries(File archiveBasePath) {
+        if (archiveBasePath.isDirectory()) {
+            List<File> archiveEntries = new ArrayList<File>();
+            File[] files = archiveBasePath.listFiles();
+
+            if (files != null) {
+                for (File file : files) {
+                    if (file.isDirectory()) {
+                        archiveEntries.addAll(collectArchiveEntries(file));
+                    } else {
+                        archiveEntries.add(file);
+                    }
+                }
+            }
+
+            return archiveEntries;
+        }
+
+        return Collections.emptyList();
+    }
+
+    private static boolean excludeIfPackageExists(String jarEntryName, String[] excludeOnPackages) {
+        if (excludeOnPackages != null) {
+            String packageName = pathToClassName(jarEntryName);
+
+            for (String excludeOnPackage : excludeOnPackages) {
+                if (packageName.startsWith(excludeOnPackage)) {
+                    return true;
+                }
+            }
+        }
+
+        return false;
+    }
+
+    private static boolean includeIfPackageExists(String jarEntryName, String[] includeOnPackages) {
+        if (includeOnPackages == null) {
+            return true;
+        }
+
+        String packageName = pathToClassName(jarEntryName);
+
+        for (String includeOnPackage : includeOnPackages) {
+            if (packageName.startsWith(includeOnPackage)) {
+                return true;
+            }
+        }
+
+        return false;
+    }
+
+    private static String isJarUrl(String urlPath) {
+        final int jarColon = urlPath.indexOf(':');
+        if (urlPath.endsWith("!/") && jarColon > 0) {
+            urlPath = urlPath.substring(jarColon + 1, urlPath.length() - 2);
+            return urlPath;
+        }
+
+        return null;
+    }
+
+    private static String ensureCorrectUrlFormat(String url) {
+        //fix for wls
+        if (!url.startsWith("file:/")) {
+            url = "file:/" + url;
+        }
+        return url;
+    }
+
+    private static String pathToClassName(String pathName) {
+        return pathName.replace('/', '.').replace('\\', '.');   // replace unix and windows separators
+    }
+}
diff --git a/wink-jcdi-server/src/test/resources/META-INF/beans.xml b/wink-jcdi-server/src/test/resources/META-INF/beans.xml
new file mode 100644
index 0000000..4070730
--- /dev/null
+++ b/wink-jcdi-server/src/test/resources/META-INF/beans.xml
@@ -0,0 +1,23 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!--
+    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.
+-->
+<beans xmlns="http://java.sun.com/xml/ns/javaee"
+       xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+       xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/beans_1_0.xsd">
+</beans>
diff --git a/wink-jcdi-server/src/test/resources/arquillian.xml b/wink-jcdi-server/src/test/resources/arquillian.xml
new file mode 100644
index 0000000..6aae51e
--- /dev/null
+++ b/wink-jcdi-server/src/test/resources/arquillian.xml
@@ -0,0 +1,44 @@
+<!--
+    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.
+-->
+
+<arquillian xmlns="http://jboss.org/schema/arquillian" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+            xsi:schemaLocation="http://jboss.org/schema/arquillian http://jboss.org/schema/arquillian/arquillian_1_0.xsd">
+
+    <!--Uncomment to have test archives exported to the file system for inspection -->
+    <!--
+    <engine>
+        <property name="deploymentExportPath">target/</property>
+    </engine>
+    -->
+    <container qualifier="tomee">
+        <configuration>
+            <!-- tomee gets copied to this directory during the build -->
+            <property name="dir">target/tomee</property>
+
+            <property name="portRange">20001-25000</property>
+            <property name="httpPort">-1</property><!-- for using a free port-->
+            <property name="ajpPort">-1</property>
+            <property name="stopPort">-1</property>
+            <property name="appWorkingDir">target/arquillian-test-working-dir</property>
+            <property name="cleanOnStartUp">true</property>
+            <property name="debug">true</property>
+            <property name="debugPort">5005</property>
+        </configuration>
+    </container>
+</arquillian>