You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@camel.apache.org by cm...@apache.org on 2012/02/06 12:08:45 UTC
svn commit: r1240976 - in /camel/trunk/components/camel-cdi: ./
src/main/java/org/apache/camel/component/cdi/
src/main/java/org/apache/camel/component/cdi/util/
src/main/resources/META-INF/ src/main/resources/META-INF/services/
src/test/java/org/apache...
Author: cmoulliard
Date: Mon Feb 6 11:08:44 2012
New Revision: 1240976
URL: http://svn.apache.org/viewvc?rev=1240976&view=rev
Log:
Add BeanManagerProvider and services (javax.enterprise.inject.spi.extension)
Added:
camel/trunk/components/camel-cdi/src/main/java/org/apache/camel/component/cdi/util/
camel/trunk/components/camel-cdi/src/main/java/org/apache/camel/component/cdi/util/AnyLiteral.java
camel/trunk/components/camel-cdi/src/main/java/org/apache/camel/component/cdi/util/BeanManagerProvider.java
camel/trunk/components/camel-cdi/src/main/java/org/apache/camel/component/cdi/util/BeanProvider.java
camel/trunk/components/camel-cdi/src/main/java/org/apache/camel/component/cdi/util/package-info.java
camel/trunk/components/camel-cdi/src/main/resources/META-INF/beans.xml
- copied unchanged from r1233921, camel/trunk/components/camel-cdi/src/test/resources/META-INF/beans.xml
camel/trunk/components/camel-cdi/src/main/resources/META-INF/services/
camel/trunk/components/camel-cdi/src/main/resources/META-INF/services/javax.enterprise.inject.spi.Extension
Modified:
camel/trunk/components/camel-cdi/pom.xml
camel/trunk/components/camel-cdi/src/main/java/org/apache/camel/component/cdi/CdiBeanRegistry.java
camel/trunk/components/camel-cdi/src/test/java/org/apache/camel/cdi/CdiContainerBeanManagerTest.java
Modified: camel/trunk/components/camel-cdi/pom.xml
URL: http://svn.apache.org/viewvc/camel/trunk/components/camel-cdi/pom.xml?rev=1240976&r1=1240975&r2=1240976&view=diff
==============================================================================
--- camel/trunk/components/camel-cdi/pom.xml (original)
+++ camel/trunk/components/camel-cdi/pom.xml Mon Feb 6 11:08:44 2012
@@ -41,6 +41,7 @@
${camel.osgi.import.defaults},
*
</camel.osgi.import.pkg>
+ <openwebbeans.version>1.1.4-SNAPSHOT</openwebbeans.version>
</properties>
<dependencies>
@@ -48,20 +49,24 @@
<groupId>org.apache.camel</groupId>
<artifactId>camel-core</artifactId>
</dependency>
+ <dependency>
+ <groupId>org.apache.camel</groupId>
+ <artifactId>camel-spring</artifactId>
+ </dependency>
<!-- JSR-299 Impl -->
<dependency>
<groupId>org.apache.openwebbeans</groupId>
<artifactId>openwebbeans-impl</artifactId>
- <version>${openwebbeans-version}</version>
- <scope>compile</scope>
+ <version>${openwebbeans.version}</version>
+ <scope>test</scope>
</dependency>
<!-- SPI API -->
<dependency>
<groupId>org.apache.openwebbeans</groupId>
<artifactId>openwebbeans-spi</artifactId>
- <version>${openwebbeans-version}</version>
+ <version>${openwebbeans.version}</version>
<scope>compile</scope>
</dependency>
@@ -76,7 +81,7 @@
<dependency>
<groupId>org.apache.openwebbeans</groupId>
<artifactId>openwebbeans-el10</artifactId>
- <version>${openwebbeans-version}</version>
+ <version>${openwebbeans.version}</version>
<scope>compile</scope>
</dependency>
@@ -85,6 +90,7 @@
<groupId>org.apache.geronimo.specs</groupId>
<artifactId>geronimo-jcdi_1.0_spec</artifactId>
<version>1.0</version>
+ <scope>provided</scope>
</dependency>
<!-- JSR-330 API -->
@@ -92,6 +98,7 @@
<groupId>org.apache.geronimo.specs</groupId>
<artifactId>geronimo-atinject_1.0_spec</artifactId>
<version>1.0</version>
+ <scope>provided</scope>
</dependency>
<!-- logging -->
@@ -112,13 +119,13 @@
<dependency>
<groupId>org.apache.openwebbeans.test</groupId>
<artifactId>cditest</artifactId>
- <version>${openwebbeans-version}</version>
+ <version>${openwebbeans.version}</version>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.apache.openwebbeans.test</groupId>
<artifactId>cditest-owb</artifactId>
- <version>${openwebbeans-version}</version>
+ <version>${openwebbeans.version}</version>
<scope>test</scope>
</dependency>
<dependency>
@@ -139,5 +146,8 @@
</dependency>
</dependencies>
-
+
+ <build>
+ <defaultGoal>install</defaultGoal>
+ </build>
</project>
Modified: camel/trunk/components/camel-cdi/src/main/java/org/apache/camel/component/cdi/CdiBeanRegistry.java
URL: http://svn.apache.org/viewvc/camel/trunk/components/camel-cdi/src/main/java/org/apache/camel/component/cdi/CdiBeanRegistry.java?rev=1240976&r1=1240975&r2=1240976&view=diff
==============================================================================
--- camel/trunk/components/camel-cdi/src/main/java/org/apache/camel/component/cdi/CdiBeanRegistry.java (original)
+++ camel/trunk/components/camel-cdi/src/main/java/org/apache/camel/component/cdi/CdiBeanRegistry.java Mon Feb 6 11:08:44 2012
@@ -16,19 +16,18 @@
*/
package org.apache.camel.component.cdi;
-import java.util.Collections;
-import java.util.HashMap;
-import java.util.Map;
-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.camel.spi.Registry;
-import org.apache.camel.util.ObjectHelper;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
+import java.util.Map;
+
+import static org.apache.camel.component.cdi.util.BeanProvider.getContextualNamesReferences;
+import static org.apache.camel.component.cdi.util.BeanProvider.getContextualReference;
+import static org.apache.camel.util.ObjectHelper.notEmpty;
+import static org.apache.camel.util.ObjectHelper.notNull;
+
+
/**
* CdiBeanRegistry used by Camel to perform lookup into the
* Cdi BeanManager. The BeanManager must be passed as argument
@@ -36,72 +35,34 @@ import org.slf4j.LoggerFactory;
*/
public class CdiBeanRegistry implements Registry {
- private static final Logger LOG = LoggerFactory.getLogger(CdiBeanRegistry.class);
- private final BeanManager delegate;
-
- public CdiBeanRegistry(final BeanManager delegate) throws IllegalArgumentException {
- ObjectHelper.notNull(delegate, "delegate");
- this.delegate = delegate;
- }
+ private final Logger log = LoggerFactory.getLogger(getClass());
+ /**
+ * @see org.apache.camel.spi.Registry#lookup(java.lang.String)
+ */
@Override
public Object lookup(final String name) {
- ObjectHelper.notEmpty(name, "name");
- LOG.trace("Looking up bean using name = [{}] in CDI registry.", name);
-
- final Set<Bean<?>> beans = getDelegate().getBeans(name);
- if (beans.isEmpty()) {
- LOG.debug("Found no bean matching name = [{}] in CDI registry.", name);
- return null;
- }
- if (beans.size() > 1) {
- throw new IllegalStateException("Expected to find exactly one bean having name [" + name + "], but got [" + beans.size() + "]");
- }
- final Bean<?> bean = beans.iterator().next();
- LOG.debug("Found bean [{}] matching name = [{}] in CDI registry.", bean, name);
+ notEmpty(name, "name");
+ log.trace("Looking up bean using name = [{}] in CDI registry ...", name);
- final CreationalContext<?> context = getDelegate().createCreationalContext(null);
- return getDelegate().getReference(bean, bean.getBeanClass(), context);
+ return getContextualReference(name, true);
}
- @Override
- public <T> T lookup(final String name, final Class<T> type) {
- ObjectHelper.notEmpty(name, "name");
- ObjectHelper.notNull(type, "type");
- LOG.trace("Looking up bean using name = [{}] having expected type = [{}] in CDI registry.", name, type.getName());
-
- return type.cast(lookup(name));
- }
-
- @Override
- public <T> Map<String, T> lookupByType(final Class<T> type) {
- ObjectHelper.notNull(type, "type");
- LOG.trace("Looking up all beans having expected type = [{}] in CDI registry.", type.getName());
-
- final Set<Bean<?>> beans = getDelegate().getBeans(type);
- if (beans.isEmpty()) {
- LOG.debug("Found no beans having expected type = [{}] in CDI registry.", type.getName());
- return Collections.emptyMap();
- }
-
- LOG.debug("Found [{}] beans having expected type = [{}] in CDI registry.", Integer.valueOf(beans.size()), type.getName());
-
- final Map<String, T> beansByName = new HashMap<String, T>(beans.size());
- final CreationalContext<?> context = getDelegate().createCreationalContext(null);
-
- for (final Bean<?> bean : beans) {
- beansByName.put(bean.getName(), type.cast(getDelegate().getReference(bean, type, context)));
- }
-
- return beansByName;
- }
-
- @Override
- public String toString() {
- return "CdiRegistry[" + this.delegate + "]";
- }
-
- private BeanManager getDelegate() {
- return this.delegate;
- }
+ @Override
+ public <T> T lookup(final String name, final Class<T> type) {
+ notEmpty(name, "name");
+ notNull(type, "type");
+ return type.cast(lookup(name));
+ }
+
+ @Override
+ public <T> Map<String, T> lookupByType(final Class<T> type) {
+ notNull(type, "type");
+ return getContextualNamesReferences(type, true, true);
+ }
+
+ @Override
+ public String toString() {
+ return "CdiRegistry[" + System.identityHashCode(this) + "]";
+ }
}
Added: camel/trunk/components/camel-cdi/src/main/java/org/apache/camel/component/cdi/util/AnyLiteral.java
URL: http://svn.apache.org/viewvc/camel/trunk/components/camel-cdi/src/main/java/org/apache/camel/component/cdi/util/AnyLiteral.java?rev=1240976&view=auto
==============================================================================
--- camel/trunk/components/camel-cdi/src/main/java/org/apache/camel/component/cdi/util/AnyLiteral.java (added)
+++ camel/trunk/components/camel-cdi/src/main/java/org/apache/camel/component/cdi/util/AnyLiteral.java Mon Feb 6 11:08:44 2012
@@ -0,0 +1,7 @@
+package org.apache.camel.component.cdi.util;
+
+import javax.enterprise.inject.Any;
+import javax.enterprise.util.AnnotationLiteral;
+
+public class AnyLiteral extends AnnotationLiteral<Any> implements Any {
+}
Added: camel/trunk/components/camel-cdi/src/main/java/org/apache/camel/component/cdi/util/BeanManagerProvider.java
URL: http://svn.apache.org/viewvc/camel/trunk/components/camel-cdi/src/main/java/org/apache/camel/component/cdi/util/BeanManagerProvider.java?rev=1240976&view=auto
==============================================================================
--- camel/trunk/components/camel-cdi/src/main/java/org/apache/camel/component/cdi/util/BeanManagerProvider.java (added)
+++ camel/trunk/components/camel-cdi/src/main/java/org/apache/camel/component/cdi/util/BeanManagerProvider.java Mon Feb 6 11:08:44 2012
@@ -0,0 +1,193 @@
+/*
+ * 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.camel.component.cdi.util;
+
+import javax.enterprise.event.Observes;
+import javax.enterprise.inject.spi.AfterBeanDiscovery;
+import javax.enterprise.inject.spi.BeanManager;
+import javax.enterprise.inject.spi.BeforeShutdown;
+import javax.enterprise.inject.spi.Extension;
+import javax.naming.InitialContext;
+import javax.naming.NamingException;
+import java.security.AccessController;
+import java.security.PrivilegedAction;
+import java.util.Map;
+import java.util.concurrent.ConcurrentHashMap;
+
+
+/**
+ * <p>This class provides access to the {@link BeanManager}
+ * by registering the current {@link BeanManager} in an extension and
+ * making it available via a singleton factory for the current application.</p>
+ * <p>This is really handy if you like to access CDI functionality
+ * from places where no injection is available.</p>
+ * <p>If a simple but manual bean-lookup is needed, it's easier to use the {@link BeanProvider}.</p>
+ * <p/>
+ * <p>As soon as an application shuts down, the reference to the {@link BeanManager} will be removed.<p>
+ * <p/>
+ * <p>Usage:<p/>
+ * <pre>
+ * BeanManager bm = BeanManagerProvider.getInstance().getBeanManager();
+ * </pre>
+ */
+public class BeanManagerProvider implements Extension {
+ private static BeanManagerProvider bmp = null;
+
+ private volatile Map<ClassLoader, BeanManager> bms = new ConcurrentHashMap<ClassLoader, BeanManager>();
+
+ /**
+ * Returns if the {@link BeanManagerProvider} has been initialized.
+ * Usually it isn't needed to call this method in application code.
+ * It's e.g. useful for other frameworks to check if DeltaSpike and the CDI container in general have been started.
+ *
+ * @return true if the bean-manager-provider is ready to be used
+ */
+ public static boolean isActive() {
+ return bmp != null;
+ }
+
+ /**
+ * Allows to get the current provider instance which provides access to the current {@link BeanManager}
+ *
+ * @return the singleton BeanManagerProvider
+ * @throws IllegalStateException if the {@link BeanManagerProvider} isn't ready to be used.
+ * That's the case if the environment isn't configured properly and therefore the {@link AfterBeanDiscovery}
+ * hasn't be called before this method gets called.
+ */
+ public static BeanManagerProvider getInstance() {
+ if (bmp == null) {
+ //X TODO Java-EE5 support needs to be discussed
+ // workaround for some Java-EE5 environments in combination with a special
+ // StartupBroadcaster for bootstrapping CDI
+
+ // CodiStartupBroadcaster.broadcastStartup();
+ // here bmp might not be null (depends on the broadcasters)
+ }
+ if (bmp == null) {
+ throw new IllegalStateException("No " + BeanManagerProvider.class.getName() + " in place! " +
+ "Please ensure that you configured the CDI implementation of your choice properly. " +
+ "If your setup is correct, please clear all caches and compiled artifacts.");
+ }
+ return bmp;
+ }
+
+
+ /**
+ * The active {@link BeanManager} for the current application (/{@link ClassLoader})
+ *
+ * @return the current bean-manager
+ */
+ public BeanManager getBeanManager() {
+ ClassLoader classLoader = getClassLoader();
+
+ BeanManager result = bms.get(classLoader);
+
+ if (result == null) {
+ result = resolveBeanManagerViaJndi();
+
+ if (result != null) {
+ bms.put(classLoader, result);
+ }
+ }
+ return result;
+ }
+
+ public static ClassLoader getClassLoader() {
+ ClassLoader loader = AccessController.doPrivileged(new PrivilegedAction<ClassLoader>() {
+ /**
+ * {@inheritDoc}
+ */
+ @Override
+ public ClassLoader run() {
+ try {
+ return Thread.currentThread().getContextClassLoader();
+ } catch (Exception e) {
+ return null;
+ }
+ }
+ }
+ );
+
+ if (loader == null) {
+ loader = BeanManagerProvider.class.getClassLoader();
+ }
+
+ return loader;
+ }
+
+ /**
+ * It basically doesn't matter which of the system events we use,
+ * but basically we use the {@link AfterBeanDiscovery} event since it allows to use the
+ * {@link BeanManagerProvider} for all events which occur after the {@link AfterBeanDiscovery} event.
+ *
+ * @param afterBeanDiscovery event which we don't actually use ;)
+ * @param beanManager the BeanManager we store and make available.
+ */
+ protected void setBeanManager(@Observes AfterBeanDiscovery afterBeanDiscovery, BeanManager beanManager) {
+ BeanManagerProvider bmpFirst = setBeanManagerProvider(this);
+
+ ClassLoader cl = getClassLoader();
+ bmpFirst.bms.put(cl, beanManager);
+
+ //X TODO Java-EE5 support needs to be discussed
+ //CodiStartupBroadcaster.broadcastStartup();
+ }
+
+ /**
+ * Cleanup on container shutdown
+ *
+ * @param beforeShutdown cdi shutdown event
+ */
+ protected void cleanupStoredBeanManagerOnShutdown(@Observes BeforeShutdown beforeShutdown) {
+ bms.remove(getClassLoader());
+ }
+
+ /**
+ * Get the BeanManager from the JNDI registry.
+ * <p/>
+ * Workaround for JBossAS 6 (see EXTCDI-74)
+ * {@link #setBeanManager(javax.enterprise.inject.spi.AfterBeanDiscovery, javax.enterprise.inject.spi.BeanManager)}
+ * is called in context of a different {@link ClassLoader}
+ *
+ * @return current {@link javax.enterprise.inject.spi.BeanManager} which is provided via JNDI
+ */
+ private BeanManager resolveBeanManagerViaJndi() {
+ try {
+ return (BeanManager) new InitialContext().lookup("java:comp/BeanManager");
+ } catch (NamingException e) {
+ //workaround didn't work -> force NPE
+ return null;
+ }
+ }
+
+ /**
+ * This function exists to prevent findbugs to complain about
+ * setting a static member from a non-static function.
+ *
+ * @param beanManagerProvider the bean-manager-provider which should be used if there isn't an existing provider
+ * @return the first BeanManagerProvider
+ */
+ private static BeanManagerProvider setBeanManagerProvider(BeanManagerProvider beanManagerProvider) {
+ if (bmp == null) {
+ bmp = beanManagerProvider;
+ }
+
+ return bmp;
+ }
+}
Added: camel/trunk/components/camel-cdi/src/main/java/org/apache/camel/component/cdi/util/BeanProvider.java
URL: http://svn.apache.org/viewvc/camel/trunk/components/camel-cdi/src/main/java/org/apache/camel/component/cdi/util/BeanProvider.java?rev=1240976&view=auto
==============================================================================
--- camel/trunk/components/camel-cdi/src/main/java/org/apache/camel/component/cdi/util/BeanProvider.java (added)
+++ camel/trunk/components/camel-cdi/src/main/java/org/apache/camel/component/cdi/util/BeanProvider.java Mon Feb 6 11:08:44 2012
@@ -0,0 +1,267 @@
+/*
+ * 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.camel.component.cdi.util;
+
+import javax.enterprise.context.Dependent;
+import javax.enterprise.context.spi.CreationalContext;
+import javax.enterprise.inject.Typed;
+import javax.enterprise.inject.spi.Bean;
+import javax.enterprise.inject.spi.BeanManager;
+import java.lang.annotation.Annotation;
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.Collection;
+import java.util.Collections;
+import java.util.HashMap;
+import java.util.HashSet;
+import java.util.Iterator;
+import java.util.List;
+import java.util.Map;
+import java.util.Set;
+
+/**
+ * This class contains utility methods to resolve contextual references
+ * in situations where no injection is available.
+ *
+ * @see BeanManagerProvider
+ */
+@Typed
+public final class BeanProvider {
+
+ private BeanProvider() {
+ // this is a utility class which doesn't get instantiated.
+ }
+
+ /**
+ * <p></p>Get a Contextual Reference by it's type and annotation (qualifier).
+ * You can use this method to get contextual references of a given type.
+ * A 'Contextual Reference' is a proxy which will automatically resolve
+ * the correct contextual instance when you access any method.</p>
+ * <p/>
+ * <p><b>Attention:</b> You shall not use this method to manually resolve a
+ * @Dependent bean! The reason is that this contextual instances do usually
+ * live in the well defined lifecycle of their injection point (the bean they got
+ * injected into). But if we manually resolve a @Dependent bean, then it does <b>not</b>
+ * belong to such a well defined lifecycle (because @Dependent it is not
+ * @NormalScoped) and thus will not automatically be
+ * destroyed at the end of the lifecycle. You need to manually destroy this contextual instance via
+ * {@link javax.enterprise.context.spi.Contextual#destroy(Object, javax.enterprise.context.spi.CreationalContext)}.
+ * Thus you also need to manually store the CreationalContext and the Bean you
+ * used to create the contextual instance which this method will not provide.</p>
+ *
+ * @param type the type of the bean in question
+ * @param optional if <code>true</code> it will return <code>null</code> if no bean could be found or created.
+ * Otherwise it will throw an {@code IllegalStateException}
+ * @param qualifiers additional qualifiers which further distinct the resolved bean
+ * @param <T> target type
+ * @return the resolved Contextual Reference
+ */
+ public static <T> T getContextualReference(Class<T> type, boolean optional, Annotation... qualifiers) {
+ BeanManager beanManager = getBeanManager();
+ Set<Bean<?>> beans = beanManager.getBeans(type, qualifiers);
+
+ if (beans == null || beans.isEmpty()) {
+ if (optional) {
+ return null;
+ }
+
+ throw new IllegalStateException("Could not find beans for Type=" + type
+ + " and qualifiers:" + Arrays.toString(qualifiers));
+ }
+
+ return getContextualReference(type, beanManager, beans);
+ }
+
+ /**
+ * <p>Get a Contextual Reference by it's EL Name.
+ * This only works for beans with the @Named annotation.</p>
+ * <p/>
+ * <p><b>Attention:</b> please see the notes on manually resolving @Dependent bean
+ * in {@link #getContextualReference(Class, boolean, java.lang.annotation.Annotation...)}!</p>
+ *
+ * @param name the EL name of the bean
+ * @param optional if <code>true</code> it will return <code>null</code> if no bean could be found or created.
+ * Otherwise it will throw an {@code IllegalStateException}
+ * @return the resolved Contextual Reference
+ */
+ public static Object getContextualReference(String name, boolean optional) {
+ return getContextualReference(name, optional, Object.class);
+ }
+
+ /**
+ * <p>Get a Contextual Reference by it's EL Name.
+ * This only works for beans with the @Named annotation.</p>
+ * <p/>
+ * <p><b>Attention:</b> please see the notes on manually resolving @Dependent bean
+ * in {@link #getContextualReference(Class, boolean, java.lang.annotation.Annotation...)}!</p>
+ *
+ * @param name the EL name of the bean
+ * @param optional if <code>true</code> it will return <code>null</code> if no bean could be found or created.
+ * Otherwise it will throw an {@code IllegalStateException}
+ * @param type the type of the bean in question - use {@link #getContextualReference(String, boolean)}
+ * if the type is unknown e.g. in dyn. use-cases
+ * @param <T> target type
+ * @return the resolved Contextual Reference
+ */
+ public static <T> T getContextualReference(String name, boolean optional, Class<T> type) {
+ BeanManager beanManager = getBeanManager();
+ Set<Bean<?>> beans = beanManager.getBeans(name);
+
+ if (beans == null || beans.isEmpty()) {
+ if (optional) {
+ return null;
+ }
+
+ throw new IllegalStateException("Could not find beans for Type=" + type
+ + " and name:" + name);
+ }
+
+ return getContextualReference(type, beanManager, beans);
+ }
+
+ /**
+ * <p>Get a list of Contextual References by it's type independent of the qualifier
+ * (including dependent scoped beans).
+ * <p/>
+ * You can use this method to get all contextual references of a given type.
+ * A 'Contextual Reference' is a proxy which will automatically resolve
+ * the correct contextual instance when you access any method.</p>
+ * <p/>
+ * <p><b>Attention:</b> please see the notes on manually resolving @Dependent bean
+ * in {@link #getContextualReference(Class, boolean, java.lang.annotation.Annotation...)}!</p>
+ *
+ * @param type the type of the bean in question
+ * @param optional if <code>true</code> it will return an empty list if no bean could be found or created.
+ * Otherwise it will throw an {@code IllegalStateException}
+ * @param <T> target type
+ * @return the resolved list of Contextual Reference or an empty-list if optional is true
+ */
+ public static <T> List<T> getContextualReferences(Class<T> type,
+ boolean optional) {
+ return getContextualReferences(type, optional, true);
+ }
+
+ /**
+ * <p>Get a list of Contextual References by it's type independent of the qualifier.
+ * <p/>
+ * Further details are available at {@link #getContextualReferences(Class, boolean)}
+ *
+ * @param type the type of the bean in question
+ * @param optional if <code>true</code> it will return an empty list if no bean could be found or created.
+ * Otherwise it will throw an {@code IllegalStateException}
+ * @param includeDefaultScopedBeans specifies if dependent scoped beans should be included in the in the result
+ * @param <T> target type
+ * @return the resolved list of Contextual Reference or an empty-list if optional is true
+ */
+ public static <T> List<T> getContextualReferences(Class<T> type,
+ boolean optional,
+ boolean includeDefaultScopedBeans) {
+ BeanManager beanManager = getBeanManager();
+ Set<Bean<?>> beans = beanManager.getBeans(type, new AnyLiteral());
+
+ if (beans == null || beans.isEmpty()) {
+ if (optional) {
+ return Collections.emptyList();
+ }
+
+ throw new IllegalStateException("Could not find beans for Type=" + type);
+ }
+
+ if (!includeDefaultScopedBeans) {
+ beans = filterDefaultScopedBeans(beans);
+ }
+
+ List<T> result = new ArrayList<T>(beans.size());
+
+ for (Bean<?> bean : beans) {
+ result.add(getContextualReference(type, beanManager,
+ new HashSet<Bean<?>>((Collection) Arrays.asList(new Object[]{bean}))));
+ }
+ return result;
+ }
+
+ public static <T> Map<String, T> getContextualNamesReferences(Class<T> type,
+ boolean optional,
+ boolean includeDefaultScopedBeans) {
+ BeanManager beanManager = getBeanManager();
+ Set<Bean<?>> beans = beanManager.getBeans(type, new AnyLiteral());
+
+ if (beans == null || beans.isEmpty()) {
+ if (optional) {
+ return Collections.emptyMap();
+ }
+
+ throw new IllegalStateException("Could not find beans for Type=" + type);
+ }
+
+ if (!includeDefaultScopedBeans) {
+ beans = filterDefaultScopedBeans(beans);
+ }
+
+ Map<String, T> result = new HashMap<String, T>(beans.size());
+
+ for (Bean<?> bean : beans) {
+ result.put(bean.getName(), getContextualReference(type, beanManager,
+ new HashSet<Bean<?>>((Collection) Arrays.asList(new Object[]{bean}))));
+ }
+ return result;
+ }
+
+ private static Set<Bean<?>> filterDefaultScopedBeans(Set<Bean<?>> beans) {
+ Set<Bean<?>> result = new HashSet<Bean<?>>(beans.size());
+
+ Iterator<Bean<?>> beanIterator = beans.iterator();
+
+ Bean<?> currentBean;
+ while (beanIterator.hasNext()) {
+ currentBean = beanIterator.next();
+
+ if (!Dependent.class.isAssignableFrom(currentBean.getScope())) {
+ result.add(currentBean);
+ }
+ }
+ return result;
+ }
+
+ /**
+ * Internal helper method to resolve the right bean and resolve the contextual reference.
+ *
+ * @param type the type of the bean in question
+ * @param beanManager current bean-manager
+ * @param beans beans in question
+ * @param <T> target type
+ * @return the contextual reference
+ */
+ private static <T> T getContextualReference(Class<T> type, BeanManager beanManager, Set<Bean<?>> beans) {
+ Bean<?> bean = beanManager.resolve(beans);
+
+ CreationalContext<?> creationalContext = beanManager.createCreationalContext(bean);
+
+ @SuppressWarnings({"unchecked", "UnnecessaryLocalVariable"})
+ T result = (T) beanManager.getReference(bean, type, creationalContext);
+ return result;
+ }
+
+ /**
+ * Internal method to resolve the BeanManager via the {@link BeanManagerProvider}
+ */
+ private static BeanManager getBeanManager() {
+ return BeanManagerProvider.getInstance().getBeanManager();
+ }
+}
Added: camel/trunk/components/camel-cdi/src/main/java/org/apache/camel/component/cdi/util/package-info.java
URL: http://svn.apache.org/viewvc/camel/trunk/components/camel-cdi/src/main/java/org/apache/camel/component/cdi/util/package-info.java?rev=1240976&view=auto
==============================================================================
--- camel/trunk/components/camel-cdi/src/main/java/org/apache/camel/component/cdi/util/package-info.java (added)
+++ camel/trunk/components/camel-cdi/src/main/java/org/apache/camel/component/cdi/util/package-info.java Mon Feb 6 11:08:44 2012
@@ -0,0 +1,5 @@
+/**
+ * mainly copied from deltaspike to avoid to bring to whole
+ * package when only 2 classes are useful.
+ */
+package org.apache.camel.component.cdi.util;
Added: camel/trunk/components/camel-cdi/src/main/resources/META-INF/services/javax.enterprise.inject.spi.Extension
URL: http://svn.apache.org/viewvc/camel/trunk/components/camel-cdi/src/main/resources/META-INF/services/javax.enterprise.inject.spi.Extension?rev=1240976&view=auto
==============================================================================
--- camel/trunk/components/camel-cdi/src/main/resources/META-INF/services/javax.enterprise.inject.spi.Extension (added)
+++ camel/trunk/components/camel-cdi/src/main/resources/META-INF/services/javax.enterprise.inject.spi.Extension Mon Feb 6 11:08:44 2012
@@ -0,0 +1,17 @@
+#
+# 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.camel.component.cdi.util.BeanManagerProvider
Modified: camel/trunk/components/camel-cdi/src/test/java/org/apache/camel/cdi/CdiContainerBeanManagerTest.java
URL: http://svn.apache.org/viewvc/camel/trunk/components/camel-cdi/src/test/java/org/apache/camel/cdi/CdiContainerBeanManagerTest.java?rev=1240976&r1=1240975&r2=1240976&view=diff
==============================================================================
--- camel/trunk/components/camel-cdi/src/test/java/org/apache/camel/cdi/CdiContainerBeanManagerTest.java (original)
+++ camel/trunk/components/camel-cdi/src/test/java/org/apache/camel/cdi/CdiContainerBeanManagerTest.java Mon Feb 6 11:08:44 2012
@@ -1,28 +1,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.
- */
package org.apache.camel.cdi;
-import java.util.ArrayList;
-import java.util.List;
-import javax.enterprise.inject.spi.BeanManager;
-import javax.inject.Inject;
-
import org.apache.camel.CamelContext;
import org.apache.camel.Exchange;
+import org.apache.camel.ProducerTemplate;
import org.apache.camel.builder.RouteBuilder;
import org.apache.camel.cdi.store.Item;
import org.apache.camel.cdi.store.ShoppingBean;
@@ -36,27 +16,38 @@ import org.junit.After;
import org.junit.Before;
import org.junit.Test;
+import javax.inject.Inject;
+import java.util.ArrayList;
+import java.util.List;
+
public class CdiContainerBeanManagerTest extends CamelTestSupport {
- private CdiTestContainer cdiContainer;
+ private MockEndpoint resultEndpoint;
+
+ private ProducerTemplate template;
+
+ CdiTestContainer cdiContainer;
+ CamelContext camelContext;
@Inject
- private ShoppingBean shoppingBean;
+ ShoppingBean shoppingBean;
@Before
public void setUp() throws Exception {
cdiContainer = CdiTestContainerLoader.getCdiContainer();
cdiContainer.bootContainer();
- cdiContainer.startContexts();
- super.setUp();
- }
+ System.out.println(">> Container started and bean manager instantiated !");
- @Override
- protected CamelContext createCamelContext() throws Exception {
- BeanManager beanManager = cdiContainer.getBeanManager();
- context = new DefaultCamelContext(new CdiBeanRegistry(beanManager));
- return context;
+ // Camel
+ context = new DefaultCamelContext(new CdiBeanRegistry());
+ context.addRoutes(createRouteBuilder());
+ context.setTracing(true);
+ context.start();
+ resultEndpoint = context.getEndpoint("mock:result", MockEndpoint.class);
+ template = context.createProducerTemplate();
+
+ System.out.println(">> Camel started !");
}
@After
@@ -66,25 +57,22 @@ public class CdiContainerBeanManagerTest
}
@Test
- @SuppressWarnings("unchecked")
public void testInjection() throws InterruptedException {
- MockEndpoint mock = getMockEndpoint("mock:result");
- mock.expectedMessageCount(1);
-
+ resultEndpoint.expectedMessageCount(1);
template.sendBody("direct:inject", "hello");
assertMockEndpointsSatisfied();
- Exchange exchange = mock.getExchanges().get(0);
+ Exchange exchange = resultEndpoint.getExchanges().get(0);
List<Item> results = (List<Item>) exchange.getIn().getBody();
- Object[] items = results.toArray();
- Object[] itemsExpected = itemsExpected().toArray();
- for (int i = 0; i < items.length; ++i) {
- Item itemExpected = (Item) items[i];
- Item itemReceived = (Item) itemsExpected[i];
- assertEquals(itemExpected.getName(), itemReceived.getName());
- assertEquals(itemExpected.getPrice(), itemReceived.getPrice());
+ Object[] items = (Object[]) results.toArray();
+ Object[] itemsExpected = (Object[]) itemsExpected().toArray();
+ for(int i=0; i< items.length; ++i) {
+ Item itemExpected = (Item)items[i];
+ Item itemReceived = (Item)itemsExpected[i];
+ assertEquals(itemExpected.getName(), itemReceived.getName());
+ assertEquals(itemExpected.getPrice(), itemReceived.getPrice());
}
assertNotNull(results);
@@ -109,11 +97,15 @@ public class CdiContainerBeanManagerTest
return new RouteBuilder() {
@Override
public void configure() throws Exception {
+
from("direct:inject")
.beanRef("shoppingBean", "listAllProducts")
.to("mock:result");
+
}
+
};
}
+
}