/* * JBoss, Home of Professional Open Source. * Copyright 2009, Red Hat Middleware LLC, and individual contributors * as indicated by the @author tags. See the copyright.txt file in the * distribution for a full listing of individual contributors. * * This is free software; you can redistribute it and/or modify it * under the terms of the GNU Lesser General Public License as * published by the Free Software Foundation; either version 2.1 of * the License, or (at your option) any later version. * * This software is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * Lesser General Public License for more details. * * You should have received a copy of the GNU Lesser General Public * License along with this software; if not, write to the Free * Software Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA * 02110-1301 USA, or see the FSF site: http://www.fsf.org. */ package org.jboss.switchboard.mc.resource.provider; import java.util.ArrayList; import java.util.Collection; import java.util.HashMap; import java.util.Map; import org.jboss.deployers.structure.spi.DeploymentUnit; import org.jboss.logging.Logger; import org.jboss.switchboard.impl.resource.LinkRefResource; import org.jboss.switchboard.javaee.environment.ResourceEnvRefType; import org.jboss.switchboard.javaee.jboss.environment.JBossResourceEnvRefType; import org.jboss.switchboard.javaee.util.InjectionTargetUtil; import org.jboss.switchboard.mc.spi.MCBasedResourceProvider; import org.jboss.switchboard.spi.Resource; /** * ResourceEnvRefProvider * * @author Jaikiran Pai * @version $Revision: $ */ public class ResourceEnvRefProvider implements MCBasedResourceProvider { /** * Logger */ private static Logger logger = Logger.getLogger(ResourceEnvRefProvider.class); /** * Resource providers for various "types" of resource-env-ref entries. * The key of this map, is the type (for ex: javax.ejb.SessionContext) of the resource-env-ref and the value * is the ResourceProvider */ private Map> typedResourceEnvRefResourceProviders = new HashMap>(); /** * Resource providers, for resource-env-ref entries, which will be used to process resource-env-ref * entries, if the "type" based resource-env-ref providers cannot provide the resource. */ private Collection> fallbackResourceEnvRefResourceProviders = new ArrayList>(); private boolean warnOnMissingProvider; @Override public Class getEnvironmentEntryType() { return JBossResourceEnvRefType.class; } @Override public Resource provide(DeploymentUnit deploymentUnit, JBossResourceEnvRefType resEnvRef) { // Let's first check if there are any resource providers that have been // registered by a "type" of resource-env-ref String resourceType = this.getResourceEnvRefType(deploymentUnit.getClassLoader(), resEnvRef); if (resourceType != null) { resourceType = resourceType.trim(); } MCBasedResourceProvider resourceEnvRefProvider = this.typedResourceEnvRefResourceProviders.get(resourceType); // if available, process it if (resourceEnvRefProvider != null) { return resourceEnvRefProvider.provide(deploymentUnit, resEnvRef); } // No type based resource providers have been registered for this "type" of resource-env-ref. // so let's check if there's any explicit jndi/mapped/lookup name String lookupName = resEnvRef.getLookupName(); if (lookupName != null && !lookupName.trim().isEmpty()) { return new LinkRefResource(lookupName, null, resEnvRef.isIgnoreDependency()); } // now check mapped name String mappedName = resEnvRef.getMappedName(); if (mappedName != null && !mappedName.trim().isEmpty()) { return new LinkRefResource(mappedName, null, resEnvRef.isIgnoreDependency()); } // now check (JBoss specific) jndi name! String jndiName = resEnvRef.getJNDIName(); if (jndiName != null && !jndiName.trim().isEmpty()) { return new LinkRefResource(jndiName, null, resEnvRef.isIgnoreDependency()); } // fallback on the other resource-ref resource provider(s), if any. for (MCBasedResourceProvider provider : this.fallbackResourceEnvRefResourceProviders) { if (provider != null) { Resource resource = provider.provide(deploymentUnit, resEnvRef); if (resource != null) { return resource; } } } // No provider available and no mapped-name/lookup-name of jndi-name has been specified. String msg = "Neither any mapped-name/lookup/jndi-name specified nor any ResourceProvider could process resource-env-ref named " + resEnvRef.getName() + " of type " + resEnvRef.getResourceType(); if (warnOnMissingProvider) { logger.warn(msg); return null; } else { throw new RuntimeException(msg); } } public void setTypedResourceEnvRefResourceProviders(Map> providers) { if (providers == null) { throw new IllegalArgumentException("Cannot set null to typed resource-env-ref resource providers"); } this.typedResourceEnvRefResourceProviders = providers; } public void setFallbackResourceEnvRefResourceProviders(Collection> providers) { if (providers == null) { throw new IllegalArgumentException("Cannot set null to resource-env-ref resource providers"); } this.fallbackResourceEnvRefResourceProviders = providers; } /** * Returns the res-env-ref-type for the passed {@link ResourceEnvRefType}. *

* If the passed resource-env-ref has the res-type explicitly specified, then * that value is returned. Else, this method checks for the presence of any * injection targets for this resource-env-ref. If there's a injection target, then * the res-env-ref-type is deduced based on the field/method of the injection target. *

*

* This method returns null if the res-env-ref-type isn't explicitly specified and * if the res-type could not be deduced from the injection targets of this * resource-env-ref. *

* * @param cl The {@link ClassLoader} to be used during processing the metadata * @param resourceEnvRef The Java EE resource-env-ref * @return */ private String getResourceEnvRefType(ClassLoader cl, ResourceEnvRefType resourceEnvRef) { // first check whether the type is explicitly specified String explicitType = resourceEnvRef.getResourceType(); if (explicitType != null && !explicitType.isEmpty()) { return explicitType; } Class type = InjectionTargetUtil.getInjectionTargetPropertyType(cl, resourceEnvRef); return type == null ? null : type.getName(); } public void setWarnOnMissingProvider(boolean warn) { this.warnOnMissingProvider = warn; } public boolean isWarnOnMissingProvider() { return warnOnMissingProvider; } }