Return-Path: Delivered-To: apmail-geronimo-scm-archive@www.apache.org Received: (qmail 36257 invoked from network); 27 Oct 2009 23:04:23 -0000 Received: from hermes.apache.org (HELO mail.apache.org) (140.211.11.3) by minotaur.apache.org with SMTP; 27 Oct 2009 23:04:23 -0000 Received: (qmail 34977 invoked by uid 500); 27 Oct 2009 21:17:43 -0000 Delivered-To: apmail-geronimo-scm-archive@geronimo.apache.org Received: (qmail 34927 invoked by uid 500); 27 Oct 2009 21:17:43 -0000 Mailing-List: contact scm-help@geronimo.apache.org; run by ezmlm Precedence: bulk list-help: list-unsubscribe: List-Post: Reply-To: dev@geronimo.apache.org List-Id: Delivered-To: mailing list scm@geronimo.apache.org Received: (qmail 34917 invoked by uid 99); 27 Oct 2009 21:17:43 -0000 Received: from athena.apache.org (HELO athena.apache.org) (140.211.11.136) by apache.org (qpsmtpd/0.29) with ESMTP; Tue, 27 Oct 2009 21:17:43 +0000 X-ASF-Spam-Status: No, hits=-5.1 required=5.0 tests=AWL,BAYES_00 X-Spam-Check-By: apache.org Received: from [140.211.11.4] (HELO eris.apache.org) (140.211.11.4) by apache.org (qpsmtpd/0.29) with ESMTP; Tue, 27 Oct 2009 21:17:39 +0000 Received: by eris.apache.org (Postfix, from userid 65534) id AAA6D238888E; Tue, 27 Oct 2009 21:17:19 +0000 (UTC) Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit Subject: svn commit: r830343 - in /geronimo/server/branches/2.2/plugins/openejb: geronimo-openejb-builder/src/main/java/org/apache/geronimo/openejb/deployment/ geronimo-openejb/src/main/java/org/apache/geronimo/openejb/ geronimo-openejb/src/test/java/org/apache... Date: Tue, 27 Oct 2009 21:17:19 -0000 To: scm@geronimo.apache.org From: dblevins@apache.org X-Mailer: svnmailer-1.0.8 Message-Id: <20091027211719.AAA6D238888E@eris.apache.org> Author: dblevins Date: Tue Oct 27 21:17:18 2009 New Revision: 830343 URL: http://svn.apache.org/viewvc?rev=830343&view=rev Log: Reworked bean initialization to essentially be lazy. Though the effect is that the decoupling allows it to happen as soon as Container.deploy(*) is called in the OpenEJB code. This should fix both GERONIMO-4918 and GERONIMO-3780. Modified: geronimo/server/branches/2.2/plugins/openejb/geronimo-openejb-builder/src/main/java/org/apache/geronimo/openejb/deployment/EjbDeploymentBuilder.java geronimo/server/branches/2.2/plugins/openejb/geronimo-openejb-builder/src/main/java/org/apache/geronimo/openejb/deployment/EjbModuleBuilder.java geronimo/server/branches/2.2/plugins/openejb/geronimo-openejb/src/main/java/org/apache/geronimo/openejb/EjbDeployment.java geronimo/server/branches/2.2/plugins/openejb/geronimo-openejb/src/main/java/org/apache/geronimo/openejb/EjbDeploymentGBean.java geronimo/server/branches/2.2/plugins/openejb/geronimo-openejb/src/main/java/org/apache/geronimo/openejb/EjbModuleImpl.java geronimo/server/branches/2.2/plugins/openejb/geronimo-openejb/src/main/java/org/apache/geronimo/openejb/GeronimoThreadContextListener.java geronimo/server/branches/2.2/plugins/openejb/geronimo-openejb/src/test/java/org/apache/geronimo/openejb/GBeanTest.java Modified: geronimo/server/branches/2.2/plugins/openejb/geronimo-openejb-builder/src/main/java/org/apache/geronimo/openejb/deployment/EjbDeploymentBuilder.java URL: http://svn.apache.org/viewvc/geronimo/server/branches/2.2/plugins/openejb/geronimo-openejb-builder/src/main/java/org/apache/geronimo/openejb/deployment/EjbDeploymentBuilder.java?rev=830343&r1=830342&r2=830343&view=diff ============================================================================== --- geronimo/server/branches/2.2/plugins/openejb/geronimo-openejb-builder/src/main/java/org/apache/geronimo/openejb/deployment/EjbDeploymentBuilder.java (original) +++ geronimo/server/branches/2.2/plugins/openejb/geronimo-openejb-builder/src/main/java/org/apache/geronimo/openejb/deployment/EjbDeploymentBuilder.java Tue Oct 27 21:17:18 2009 @@ -170,9 +170,9 @@ } - public void addEjbModuleDependency(AbstractName ejbModuleName) { + public void addEjbModuleDependency(GBeanData ejbModule) { for (GBeanData gbean : gbeans.values()) { - gbean.addDependency(ejbModuleName); + ejbModule.addDependency(gbean.getAbstractName()); } } Modified: geronimo/server/branches/2.2/plugins/openejb/geronimo-openejb-builder/src/main/java/org/apache/geronimo/openejb/deployment/EjbModuleBuilder.java URL: http://svn.apache.org/viewvc/geronimo/server/branches/2.2/plugins/openejb/geronimo-openejb-builder/src/main/java/org/apache/geronimo/openejb/deployment/EjbModuleBuilder.java?rev=830343&r1=830342&r2=830343&view=diff ============================================================================== --- geronimo/server/branches/2.2/plugins/openejb/geronimo-openejb-builder/src/main/java/org/apache/geronimo/openejb/deployment/EjbModuleBuilder.java (original) +++ geronimo/server/branches/2.2/plugins/openejb/geronimo-openejb-builder/src/main/java/org/apache/geronimo/openejb/deployment/EjbModuleBuilder.java Tue Oct 27 21:17:18 2009 @@ -39,9 +39,6 @@ import javax.ejb.TimerService; import javax.xml.namespace.QName; import javax.xml.ws.WebServiceContext; - -import org.slf4j.Logger; -import org.slf4j.LoggerFactory; import org.apache.geronimo.common.DeploymentException; import org.apache.geronimo.connector.ResourceAdapterWrapperGBean; import org.apache.geronimo.deployment.ClassPathList; @@ -50,7 +47,6 @@ import org.apache.geronimo.deployment.NamespaceDrivenBuilder; import org.apache.geronimo.deployment.NamespaceDrivenBuilderCollection; import org.apache.geronimo.deployment.service.EnvironmentBuilder; -import org.apache.geronimo.deployment.service.GBeanBuilder; import org.apache.geronimo.deployment.util.DeploymentUtil; import org.apache.geronimo.deployment.xmlbeans.XmlBeansUtil; import org.apache.geronimo.gbean.AbstractName; @@ -58,8 +54,8 @@ import org.apache.geronimo.gbean.GBeanData; import org.apache.geronimo.gbean.GBeanInfo; import org.apache.geronimo.gbean.GBeanInfoBuilder; -import org.apache.geronimo.gbean.ReferencePatterns; import org.apache.geronimo.gbean.GBeanLifecycle; +import org.apache.geronimo.gbean.ReferencePatterns; import org.apache.geronimo.j2ee.deployment.EARContext; import org.apache.geronimo.j2ee.deployment.Module; import org.apache.geronimo.j2ee.deployment.ModuleBuilder; @@ -78,15 +74,13 @@ import org.apache.geronimo.naming.deployment.ResourceEnvironmentSetter; import org.apache.geronimo.openejb.EjbContainer; import org.apache.geronimo.openejb.EjbDeployment; -import org.apache.geronimo.openejb.EjbModuleImplGBean; +import org.apache.geronimo.openejb.EjbModuleImpl; import org.apache.geronimo.openejb.OpenEjbSystem; import org.apache.geronimo.openejb.xbeans.ejbjar.OpenejbGeronimoEjbJarType; +import org.apache.geronimo.persistence.PersistenceUnitGBean; import org.apache.geronimo.security.jacc.ComponentPermissions; -import org.apache.geronimo.xbeans.geronimo.j2ee.GerSecurityDocument; import org.apache.geronimo.xbeans.javaee.EjbJarType; -import org.apache.geronimo.persistence.PersistenceUnitGBean; import org.apache.openejb.OpenEJBException; -import org.apache.openejb.util.LinkResolver; import org.apache.openejb.assembler.classic.AppInfo; import org.apache.openejb.assembler.classic.CmpJarBuilder; import org.apache.openejb.assembler.classic.ContainerInfo; @@ -97,14 +91,8 @@ import org.apache.openejb.assembler.classic.MdbContainerInfo; import org.apache.openejb.assembler.classic.MessageDrivenBeanInfo; import org.apache.openejb.assembler.classic.OpenEjbConfiguration; -import org.apache.openejb.assembler.classic.StatefulBeanInfo; import org.apache.openejb.assembler.classic.PersistenceContextReferenceInfo; -import org.apache.openejb.assembler.classic.StatelessSessionContainerInfo; -import org.apache.openejb.assembler.classic.StatefulSessionContainerInfo; -import org.apache.openejb.assembler.classic.SingletonSessionContainerInfo; -import org.apache.openejb.assembler.classic.BmpEntityContainerInfo; -import org.apache.openejb.assembler.classic.CmpEntityContainerInfo; -import org.apache.openejb.util.UniqueDefaultLinkResolver; +import org.apache.openejb.assembler.classic.StatefulBeanInfo; import org.apache.openejb.config.AppModule; import org.apache.openejb.config.ConfigurationFactory; import org.apache.openejb.config.DeploymentLoader; @@ -114,7 +102,6 @@ import org.apache.openejb.config.ValidationError; import org.apache.openejb.config.ValidationFailedException; import org.apache.openejb.config.ValidationFailure; -import org.apache.openejb.config.ConfigurationFactory.Chain; import org.apache.openejb.jee.EjbJar; import org.apache.openejb.jee.EjbRef; import org.apache.openejb.jee.EnterpriseBean; @@ -134,8 +121,12 @@ import org.apache.openejb.jee.oejb2.PatternType; import org.apache.openejb.jee.oejb2.ResourceLocatorType; import org.apache.openejb.loader.SystemInstance; +import org.apache.openejb.util.LinkResolver; +import org.apache.openejb.util.UniqueDefaultLinkResolver; import org.apache.xmlbeans.XmlCursor; import org.apache.xmlbeans.XmlObject; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; /** * Master builder for processing EJB JAR deployments and creating the @@ -789,7 +780,7 @@ } } // Add JSR77 EJBModule GBean - GBeanData ejbModuleGBeanData = new GBeanData(ejbModule.getModuleName(), EjbModuleImplGBean.GBEAN_INFO); + GBeanData ejbModuleGBeanData = new GBeanData(ejbModule.getModuleName(), EjbModuleImpl.class); try { ejbModuleGBeanData.setReferencePattern("J2EEServer", earContext.getServerName()); if (!ejbModule.isStandAlone()) { @@ -812,7 +803,7 @@ } // add a depdendency on the ejb module object - ejbDeploymentBuilder.addEjbModuleDependency(ejbModuleGBeanData.getAbstractName()); + ejbDeploymentBuilder.addEjbModuleDependency(ejbModuleGBeanData); // add the Jacc permissions to the ear ComponentPermissions componentPermissions = ejbDeploymentBuilder.buildComponentPermissions(); Modified: geronimo/server/branches/2.2/plugins/openejb/geronimo-openejb/src/main/java/org/apache/geronimo/openejb/EjbDeployment.java URL: http://svn.apache.org/viewvc/geronimo/server/branches/2.2/plugins/openejb/geronimo-openejb/src/main/java/org/apache/geronimo/openejb/EjbDeployment.java?rev=830343&r1=830342&r2=830343&view=diff ============================================================================== --- geronimo/server/branches/2.2/plugins/openejb/geronimo-openejb/src/main/java/org/apache/geronimo/openejb/EjbDeployment.java (original) +++ geronimo/server/branches/2.2/plugins/openejb/geronimo-openejb/src/main/java/org/apache/geronimo/openejb/EjbDeployment.java Tue Oct 27 21:17:18 2009 @@ -19,11 +19,13 @@ import java.lang.reflect.Method; import java.util.Set; +import java.util.concurrent.atomic.AtomicReference; import javax.ejb.EJBHome; import javax.ejb.EJBLocalHome; import javax.ejb.EJBObject; import javax.naming.Context; +import javax.naming.NamingException; import javax.security.auth.Subject; import javax.security.auth.login.LoginException; @@ -63,7 +65,7 @@ protected final OpenEjbSystem openEjbSystem; - protected CoreDeploymentInfo deploymentInfo; + protected AtomicReference deploymentInfo = new AtomicReference(); private Context javaCompSubContext; @@ -115,7 +117,7 @@ } public CoreDeploymentInfo getDeploymentInfo() { - return deploymentInfo; + return deploymentInfo.get(); } public String getDeploymentId() { @@ -183,75 +185,75 @@ } public EJBHome getEJBHome() { - return deploymentInfo.getEJBHome(); + return getDeploymentInfo().getEJBHome(); } public EJBLocalHome getEJBLocalHome() { - return deploymentInfo.getEJBLocalHome(); + return getDeploymentInfo().getEJBLocalHome(); } public Object getBusinessLocalHome() { - return deploymentInfo.getBusinessLocalHome(); + return getDeploymentInfo().getBusinessLocalHome(); } public Object getBusinessRemoteHome() { - return deploymentInfo.getBusinessRemoteHome(); + return getDeploymentInfo().getBusinessRemoteHome(); } public EJBObject getEjbObject(Object primaryKey) { - return (EJBObject) EjbObjectProxyHandler.createProxy(deploymentInfo, primaryKey, InterfaceType.EJB_HOME); + return (EJBObject) EjbObjectProxyHandler.createProxy(getDeploymentInfo(), primaryKey, InterfaceType.EJB_HOME); } public Class getHomeInterface() { - return deploymentInfo.getHomeInterface(); + return getDeploymentInfo().getHomeInterface(); } public Class getRemoteInterface() { - return deploymentInfo.getRemoteInterface(); + return getDeploymentInfo().getRemoteInterface(); } public Class getLocalHomeInterface() { - return deploymentInfo.getLocalHomeInterface(); + return getDeploymentInfo().getLocalHomeInterface(); } public Class getLocalInterface() { - return deploymentInfo.getLocalInterface(); + return getDeploymentInfo().getLocalInterface(); } public Class getBeanClass() { - return deploymentInfo.getBeanClass(); + return getDeploymentInfo().getBeanClass(); } public Class getBusinessLocalInterface() { - return deploymentInfo.getBusinessLocalInterface(); + return getDeploymentInfo().getBusinessLocalInterface(); } public Class getBusinessRemoteInterface() { - return deploymentInfo.getBusinessRemoteInterface(); + return getDeploymentInfo().getBusinessRemoteInterface(); } public Class getMdbInterface() { - return deploymentInfo.getMdbInterface(); + return getDeploymentInfo().getMdbInterface(); } public Class getServiceEndpointInterface() { - return deploymentInfo.getServiceEndpointInterface(); + return getDeploymentInfo().getServiceEndpointInterface(); } public BeanType getComponentType() { - return deploymentInfo.getComponentType(); + return getDeploymentInfo().getComponentType(); } public Container getContainer() { - return deploymentInfo.getContainer(); + return getDeploymentInfo().getContainer(); } public boolean isBeanManagedTransaction() { - return deploymentInfo.isBeanManagedTransaction(); + return getDeploymentInfo().isBeanManagedTransaction(); } public TransactionType getTransactionType(Method method) { - return deploymentInfo.getTransactionType(method); + return getDeploymentInfo().getTransactionType(method); } public String getObjectName() { @@ -270,27 +272,27 @@ return true; } - protected void start() throws Exception { - deploymentInfo = (CoreDeploymentInfo) openEjbSystem.getDeploymentInfo(deploymentId); - if (deploymentInfo == null) { - throw new IllegalStateException("Ejb does not exist " + deploymentId); - } + EjbDeployment initialize(CoreDeploymentInfo deploymentInfo) { + try { + javaCompSubContext = (Context) deploymentInfo.getJndiEnc().lookup("java:comp"); + if (componentContext != null) { + javaCompSubContext.bind("geronimo", componentContext); + } - javaCompSubContext = (Context) deploymentInfo.getJndiEnc().lookup("java:comp"); - if (componentContext != null) { - javaCompSubContext.bind("geronimo", componentContext); - } - synchronized(deploymentInfo){ deploymentInfo.set(EjbDeployment.class, this); - deploymentInfo.notifyAll(); + + this.deploymentInfo.set(deploymentInfo); + + return this; + } catch (NamingException e) { + throw new IllegalStateException("Unable to complete EjbDeployment initialization", e); } } - protected void stop() { - if (deploymentInfo != null) { - deploymentInfo.setDestroyed(true); - deploymentInfo.set(EjbDeployment.class, null); - deploymentInfo = null; - } + void destroy() { + CoreDeploymentInfo info = deploymentInfo.getAndSet(null); + if (info != null) { + info.set(EjbDeployment.class, null); + } } } Modified: geronimo/server/branches/2.2/plugins/openejb/geronimo-openejb/src/main/java/org/apache/geronimo/openejb/EjbDeploymentGBean.java URL: http://svn.apache.org/viewvc/geronimo/server/branches/2.2/plugins/openejb/geronimo-openejb/src/main/java/org/apache/geronimo/openejb/EjbDeploymentGBean.java?rev=830343&r1=830342&r2=830343&view=diff ============================================================================== --- geronimo/server/branches/2.2/plugins/openejb/geronimo-openejb/src/main/java/org/apache/geronimo/openejb/EjbDeploymentGBean.java (original) +++ geronimo/server/branches/2.2/plugins/openejb/geronimo-openejb/src/main/java/org/apache/geronimo/openejb/EjbDeploymentGBean.java Tue Oct 27 21:17:18 2009 @@ -79,11 +79,11 @@ } public void doStop() throws Exception { - stop(); + destroy(); } public void doFail() { - stop(); + destroy(); } // do not use this gbean info, instead use StatelessDeploymentGBean, StatefulDeploymentGBean, EntityDeploymentGBean, or MessageDrivenDeploymentGBean Modified: geronimo/server/branches/2.2/plugins/openejb/geronimo-openejb/src/main/java/org/apache/geronimo/openejb/EjbModuleImpl.java URL: http://svn.apache.org/viewvc/geronimo/server/branches/2.2/plugins/openejb/geronimo-openejb/src/main/java/org/apache/geronimo/openejb/EjbModuleImpl.java?rev=830343&r1=830342&r2=830343&view=diff ============================================================================== --- geronimo/server/branches/2.2/plugins/openejb/geronimo-openejb/src/main/java/org/apache/geronimo/openejb/EjbModuleImpl.java (original) +++ geronimo/server/branches/2.2/plugins/openejb/geronimo-openejb/src/main/java/org/apache/geronimo/openejb/EjbModuleImpl.java Tue Oct 27 21:17:18 2009 @@ -16,40 +16,61 @@ */ package org.apache.geronimo.openejb; -import java.util.ArrayList; -import java.util.Collection; -import java.util.Hashtable; -import java.util.List; -import javax.management.ObjectName; - +import org.apache.geronimo.gbean.ReferenceCollection; +import org.apache.geronimo.gbean.ReferenceCollectionEvent; +import org.apache.geronimo.gbean.ReferenceCollectionListener; +import org.apache.geronimo.gbean.GBeanLifecycle; +import org.apache.geronimo.gbean.annotation.ParamAttribute; +import org.apache.geronimo.gbean.annotation.ParamReference; +import org.apache.geronimo.gbean.annotation.SpecialAttributeType; +import org.apache.geronimo.gbean.annotation.ParamSpecial; +import org.apache.geronimo.gbean.annotation.GBean; import org.apache.geronimo.j2ee.management.impl.InvalidObjectNameException; +import org.apache.geronimo.j2ee.j2eeobjectnames.NameFactory; import org.apache.geronimo.kernel.ObjectNameUtil; import org.apache.geronimo.management.EJB; import org.apache.geronimo.management.EJBModule; import org.apache.geronimo.management.J2EEApplication; import org.apache.geronimo.management.J2EEServer; -import org.apache.openejb.assembler.classic.EjbJarInfo; -import org.apache.openejb.UndeployException; import org.apache.openejb.NoSuchApplicationException; -import org.slf4j.LoggerFactory; +import org.apache.openejb.UndeployException; +import org.apache.openejb.assembler.classic.EjbJarInfo; import org.slf4j.Logger; +import org.slf4j.LoggerFactory; + +import javax.management.ObjectName; +import java.util.ArrayList; +import java.util.Collection; +import java.util.Hashtable; +import java.util.List; +import java.util.HashMap; +import java.util.Map; /** * @version $Revision$ $Date$ */ -public class EjbModuleImpl implements EJBModule { + +@GBean(j2eeType = NameFactory.EJB_MODULE) +public class EjbModuleImpl implements EJBModule, GBeanLifecycle { private static final Logger log = LoggerFactory.getLogger(EjbModuleImpl.class); private final J2EEServer server; private final J2EEApplication application; private final String deploymentDescriptor; private final String objectName; - private final Collection ejbs; + private final Map ejbs = new HashMap(); private final ClassLoader classLoader; private final OpenEjbSystem openEjbSystem; private final EjbJarInfo ejbJarInfo; - public EjbModuleImpl(String objectName, J2EEServer server, J2EEApplication application, String deploymentDescriptor, Collection ejbs, ClassLoader classLoader, OpenEjbSystem openEjbSystem, EjbJarInfo ejbJarInfo) { + public EjbModuleImpl(@ParamSpecial(type = SpecialAttributeType.objectName) String objectName, + @ParamReference(name = "J2EEServer") J2EEServer server, + @ParamReference(name = "J2EEApplication") J2EEApplication application, + @ParamAttribute(name = "deploymentDescriptor") String deploymentDescriptor, + @ParamReference(name = "EJBCollection") Collection ejbs, + @ParamSpecial(type = SpecialAttributeType.classLoader) ClassLoader classLoader, + @ParamReference(name = "OpenEjbSystem") OpenEjbSystem openEjbSystem, + @ParamAttribute(name = "ejbJarInfo") EjbJarInfo ejbJarInfo) { this.objectName = objectName; ObjectName myObjectName = ObjectNameUtil.getObjectName(objectName); verifyObjectName(myObjectName); @@ -57,7 +78,21 @@ this.server = server; this.application = application; this.deploymentDescriptor = deploymentDescriptor; - this.ejbs = ejbs; + ((ReferenceCollection) ejbs).addReferenceCollectionListener(new ReferenceCollectionListener() { + + public void memberAdded(ReferenceCollectionEvent event) { + EjbDeployment ejb = (EjbDeployment) event.getMember(); + addEjb(ejb); + } + + public void memberRemoved(ReferenceCollectionEvent event) { + EjbDeployment ejb = (EjbDeployment) event.getMember(); + removeEjb(ejb); + } + }); + for (EjbDeployment ejb : ejbs) { + addEjb(ejb); + } this.classLoader = classLoader; @@ -65,6 +100,16 @@ this.ejbJarInfo = ejbJarInfo; } + private void removeEjb(EjbDeployment ejb) { + GeronimoThreadContextListener.get().removeEjb(ejb.getDeploymentId()); + ejbs.remove(ejb.getDeploymentId()); + } + + private void addEjb(EjbDeployment ejb) { + ejbs.put(ejb.getDeploymentId(), ejb); + GeronimoThreadContextListener.get().addEjb(ejb); + } + public String getObjectName() { return objectName; } @@ -107,7 +152,7 @@ ArrayList copy; synchronized (ejbs) { - copy = new ArrayList(ejbs); + copy = new ArrayList(ejbs.values()); } String[] result = new String[copy.size()]; @@ -118,24 +163,28 @@ } - protected void start() throws Exception { + public void doStart() throws Exception { openEjbSystem.createEjbJar(ejbJarInfo, classLoader); } - protected void stop() { + public void doStop() { try { openEjbSystem.removeEjbJar(ejbJarInfo, classLoader); } catch (NoSuchApplicationException e) { log.error("Module does not exist.", e); } catch (UndeployException e) { List causes = e.getCauses(); - log.error(e.getMessage()+": Encountered "+causes.size()+" failures."); + log.error(e.getMessage() + ": Encountered " + causes.size() + " failures."); for (Throwable throwable : causes) { log.info(throwable.toString(), throwable); } } } + public void doFail() { + doStop(); + } + /** * ObjectName must match this pattern: *

Modified: geronimo/server/branches/2.2/plugins/openejb/geronimo-openejb/src/main/java/org/apache/geronimo/openejb/GeronimoThreadContextListener.java URL: http://svn.apache.org/viewvc/geronimo/server/branches/2.2/plugins/openejb/geronimo-openejb/src/main/java/org/apache/geronimo/openejb/GeronimoThreadContextListener.java?rev=830343&r1=830342&r2=830343&view=diff ============================================================================== --- geronimo/server/branches/2.2/plugins/openejb/geronimo-openejb/src/main/java/org/apache/geronimo/openejb/GeronimoThreadContextListener.java (original) +++ geronimo/server/branches/2.2/plugins/openejb/geronimo-openejb/src/main/java/org/apache/geronimo/openejb/GeronimoThreadContextListener.java Tue Oct 27 21:17:18 2009 @@ -34,6 +34,14 @@ import org.apache.openejb.core.ThreadContext; import org.apache.openejb.core.ThreadContextListener; +import java.util.Map; +import java.util.concurrent.ConcurrentHashMap; +import java.util.concurrent.Future; +import java.util.concurrent.FutureTask; +import java.util.concurrent.Callable; +import java.util.concurrent.ExecutionException; +import java.util.concurrent.atomic.AtomicReference; + /** * @version $Rev$ $Date$ */ @@ -51,26 +59,38 @@ // do nothing.. the goal here is to kick off the onetime init above } + private final Map ejbs = new ConcurrentHashMap(); + private GeronimoThreadContextListener() { } + public static GeronimoThreadContextListener get() { + return instance; + } + + public void addEjb(EjbDeployment ejbDeployment) { + this.ejbs.put(ejbDeployment.getDeploymentId(), new Deployment(ejbDeployment)); + } + + public void removeEjb(String id) { + this.ejbs.remove(id); + } + + private EjbDeployment getEjbDeployment(CoreDeploymentInfo deploymentInfo) { + Deployment deployment = ejbs.get(deploymentInfo.getDeploymentID()); + + if (deployment == null) return null; + + return deployment.get(deploymentInfo); + } + + public void contextEntered(ThreadContext oldContext, ThreadContext newContext) { CoreDeploymentInfo deploymentInfo = newContext.getDeploymentInfo(); if (deploymentInfo == null) return; - if (deploymentInfo.get(EjbDeployment.class) == null) { - synchronized (deploymentInfo) { - if (deploymentInfo.get(EjbDeployment.class) == null) { - if (!deploymentInfo.isDestroyed()) { - try { - deploymentInfo.wait(); - } catch (InterruptedException e) { - log.warn("Wait on deploymentInfo interrupted unexpectedly"); - } - } - } - } - } - EjbDeployment ejbDeployment = deploymentInfo.get(EjbDeployment.class); + + EjbDeployment ejbDeployment = getEjbDeployment(deploymentInfo); + if (ejbDeployment == null) return; // Geronimo call context is used to track old state that must be restored @@ -156,6 +176,59 @@ } } + private static final class Deployment { + private final EjbDeployment geronimoDeployment; + private final AtomicReference> initialized = new AtomicReference>(); + + private Deployment(EjbDeployment geronimoDeployment) { + this.geronimoDeployment = geronimoDeployment; + } + + public EjbDeployment get(final CoreDeploymentInfo openejbDeployment) { + try { + // Has the deployment been initialized yet? + + // If there is a Future object in the AtomicReference, then + // it's either been initialized or is being initialized now. + Future initializedRef = initialized.get(); + if (initializedRef != null) return initializedRef.get(); + + // The deployment has not been initialized nor is being initialized + + // We will construct this FutureTask and compete with the + // other threads for the right to initialize the deployment + FutureTask initializer = new FutureTask(new Callable() { + public EjbDeployment call() throws Exception { + return geronimoDeployment.initialize(openejbDeployment); + } + }); + + + do { + // If our FutureTask was the one to win the slot + // than we are the ones responsisble for initializing + // the deployment while the others wait. + if (initialized.compareAndSet(null, initializer)) { + initializer.run(); + } + + // If we didn't win the slot and no other FutureTask + // has been set by a different thread, than we need + // to try again. + } while ((initializedRef = initialized.get()) == null); + + + // At this point we can safely return the initialized deployment + return initializedRef.get(); + } catch (InterruptedException e) { + Thread.interrupted(); + throw new IllegalStateException("EjbDeployment.initialize() interrupted", e); + } catch (ExecutionException e) { + throw new IllegalStateException("EjbDeployment.initialize() failed", e.getCause()); + } + } + } + private static final class GeronimoCallContext { private Context oldJndiContext; private ConnectorInstanceContext oldConnectorContext; Modified: geronimo/server/branches/2.2/plugins/openejb/geronimo-openejb/src/test/java/org/apache/geronimo/openejb/GBeanTest.java URL: http://svn.apache.org/viewvc/geronimo/server/branches/2.2/plugins/openejb/geronimo-openejb/src/test/java/org/apache/geronimo/openejb/GBeanTest.java?rev=830343&r1=830342&r2=830343&view=diff ============================================================================== --- geronimo/server/branches/2.2/plugins/openejb/geronimo-openejb/src/test/java/org/apache/geronimo/openejb/GBeanTest.java (original) +++ geronimo/server/branches/2.2/plugins/openejb/geronimo-openejb/src/test/java/org/apache/geronimo/openejb/GBeanTest.java Tue Oct 27 21:17:18 2009 @@ -28,7 +28,7 @@ } public void testEjbModuleImplGBean() { - GBeanInfo.getGBeanInfo(EjbModuleImplGBean.class.getName(), getClass().getClassLoader()); + GBeanInfo.getGBeanInfo(EjbModuleImpl.class.getName(), getClass().getClassLoader()); } public void testEntityDeploymentGBean() {