You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@tomee.apache.org by db...@apache.org on 2007/08/02 08:21:52 UTC
svn commit: r562026 - in /openejb/trunk/openejb3/container/openejb-core/src:
main/java/org/apache/openejb/assembler/classic/
main/java/org/apache/openejb/config/ main/java/org/apache/openejb/core/ivm/
test/java/org/apache/openejb/assembler/classic/
Author: dblevins
Date: Wed Aug 1 23:21:51 2007
New Revision: 562026
URL: http://svn.apache.org/viewvc?view=rev&rev=562026
Log:
Fix for OPENEJB-623: Apply container-transaction delcarations in proper order
Added:
openejb/trunk/openejb3/container/openejb-core/src/main/java/org/apache/openejb/assembler/classic/MethodTransactionBuilder.java
openejb/trunk/openejb3/container/openejb-core/src/test/java/org/apache/openejb/assembler/classic/MethodTransactionInfoComparatorTest.java
Modified:
openejb/trunk/openejb3/container/openejb-core/src/main/java/org/apache/openejb/assembler/classic/Assembler.java
openejb/trunk/openejb3/container/openejb-core/src/main/java/org/apache/openejb/assembler/classic/AssemblerTool.java
openejb/trunk/openejb3/container/openejb-core/src/main/java/org/apache/openejb/config/ConfigurationFactory.java
openejb/trunk/openejb3/container/openejb-core/src/main/java/org/apache/openejb/core/ivm/BaseEjbProxyHandler.java
Modified: openejb/trunk/openejb3/container/openejb-core/src/main/java/org/apache/openejb/assembler/classic/Assembler.java
URL: http://svn.apache.org/viewvc/openejb/trunk/openejb3/container/openejb-core/src/main/java/org/apache/openejb/assembler/classic/Assembler.java?view=diff&rev=562026&r1=562025&r2=562026
==============================================================================
--- openejb/trunk/openejb3/container/openejb-core/src/main/java/org/apache/openejb/assembler/classic/Assembler.java (original)
+++ openejb/trunk/openejb3/container/openejb-core/src/main/java/org/apache/openejb/assembler/classic/Assembler.java Wed Aug 1 23:21:51 2007
@@ -407,10 +407,10 @@
jaccPermissionsBuilder.install(policyContext);
}
+ MethodTransactionBuilder methodTransactionBuilder = new MethodTransactionBuilder();
+ methodTransactionBuilder.build(deployments, ejbJar.methodTransactions);
- // process transaction attributes
for (DeploymentInfo deploymentInfo : deployments.values()) {
- applyTransactionAttributes((CoreDeploymentInfo) deploymentInfo, ejbJar.methodTransactions);
containerSystem.addDeployment(deploymentInfo);
}
Modified: openejb/trunk/openejb3/container/openejb-core/src/main/java/org/apache/openejb/assembler/classic/AssemblerTool.java
URL: http://svn.apache.org/viewvc/openejb/trunk/openejb3/container/openejb-core/src/main/java/org/apache/openejb/assembler/classic/AssemblerTool.java?view=diff&rev=562026&r1=562025&r2=562026
==============================================================================
--- openejb/trunk/openejb3/container/openejb-core/src/main/java/org/apache/openejb/assembler/classic/AssemblerTool.java (original)
+++ openejb/trunk/openejb3/container/openejb-core/src/main/java/org/apache/openejb/assembler/classic/AssemblerTool.java Wed Aug 1 23:21:51 2007
@@ -52,78 +52,6 @@
System.setProperty("noBanner", "true");
}
- public static void applyTransactionAttributes(CoreDeploymentInfo deploymentInfo, List<MethodTransactionInfo> mtis) throws OpenEJBException {
- /*TODO: Add better exception handling. This method doesn't throws any exceptions!!
- there is a lot of complex code here, I'm sure something could go wrong the user
- might want to know about.
- */
- for (MethodTransactionInfo transInfo : mtis) {
- for (MethodInfo methodInfo : transInfo.methods) {
-
- if (methodInfo.ejbDeploymentId == null || methodInfo.ejbDeploymentId.equals(deploymentInfo.getDeploymentID())) {
- if (!deploymentInfo.isBeanManagedTransaction()) {
-
- List<Method> methods = new ArrayList<Method>();
-
- if (methodInfo.methodIntf == null) {
- resolveMethods(methods, deploymentInfo.getBeanClass(), methodInfo);
- if (deploymentInfo.getRemoteInterface() != null) {
- resolveMethods(methods, deploymentInfo.getRemoteInterface(), methodInfo);
- }
- if (deploymentInfo.getHomeInterface() != null) {
- resolveMethods(methods, deploymentInfo.getHomeInterface(), methodInfo);
- }
- if (deploymentInfo.getLocalInterface() != null) {
- resolveMethods(methods, deploymentInfo.getLocalInterface(), methodInfo);
- }
- if (deploymentInfo.getLocalHomeInterface() != null) {
- resolveMethods(methods, deploymentInfo.getLocalHomeInterface(), methodInfo);
- }
- if(deploymentInfo.getMdbInterface() != null) {
- resolveMethods(methods, deploymentInfo.getMdbInterface(), methodInfo);
- }
- if(deploymentInfo.getServiceEndpointInterface() != null) {
- resolveMethods(methods, deploymentInfo.getServiceEndpointInterface(), methodInfo);
- }
- for (Class intf : deploymentInfo.getBusinessRemoteInterfaces()) {
- resolveMethods(methods, intf, methodInfo);
- }
- for (Class intf : deploymentInfo.getBusinessLocalInterfaces()) {
- resolveMethods(methods, intf, methodInfo);
- }
- } else if (methodInfo.methodIntf.equals("Home")) {
- resolveMethods(methods, deploymentInfo.getHomeInterface(), methodInfo);
- } else if (methodInfo.methodIntf.equals("Remote")) {
- resolveMethods(methods, deploymentInfo.getRemoteInterface(), methodInfo);
- for (Class intf : deploymentInfo.getBusinessRemoteInterfaces()) {
- resolveMethods(methods, intf, methodInfo);
- }
- } else if (methodInfo.methodIntf.equals("LocalHome")) {
- resolveMethods(methods, deploymentInfo.getLocalHomeInterface(), methodInfo);
- } else if (methodInfo.methodIntf.equals("Local")) {
- resolveMethods(methods, deploymentInfo.getLocalInterface(), methodInfo);
- for (Class intf : deploymentInfo.getBusinessRemoteInterfaces()) {
- resolveMethods(methods, intf, methodInfo);
- }
- } else if (methodInfo.methodIntf.equals("ServiceEndpoint")) {
- resolveMethods(methods, deploymentInfo.getServiceEndpointInterface(), methodInfo);
- }
-
- for (Method method : methods) {
- if ((method.getDeclaringClass() == javax.ejb.EJBObject.class ||
- method.getDeclaringClass() == javax.ejb.EJBHome.class) &&
- !method.getName().equals("remove")) {
- continue;
- }
- deploymentInfo.setMethodTransactionAttribute(method, transInfo.transAttribute);
- }
- }
- }
- }
- }
-
- }
-
protected static void resolveMethods(List<Method> methods, Class intrface, MethodInfo mi)
throws SecurityException {
/*TODO: Add better exception handling. There is a lot of complex code here, I'm sure something could go wrong the user
Added: openejb/trunk/openejb3/container/openejb-core/src/main/java/org/apache/openejb/assembler/classic/MethodTransactionBuilder.java
URL: http://svn.apache.org/viewvc/openejb/trunk/openejb3/container/openejb-core/src/main/java/org/apache/openejb/assembler/classic/MethodTransactionBuilder.java?view=auto&rev=562026
==============================================================================
--- openejb/trunk/openejb3/container/openejb-core/src/main/java/org/apache/openejb/assembler/classic/MethodTransactionBuilder.java (added)
+++ openejb/trunk/openejb3/container/openejb-core/src/main/java/org/apache/openejb/assembler/classic/MethodTransactionBuilder.java Wed Aug 1 23:21:51 2007
@@ -0,0 +1,166 @@
+/**
+ * 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.openejb.assembler.classic;
+
+import org.apache.openejb.core.CoreDeploymentInfo;
+import org.apache.openejb.OpenEJBException;
+import org.apache.openejb.DeploymentInfo;
+
+import java.util.Comparator;
+import java.util.List;
+import java.util.ArrayList;
+import java.util.Collections;
+import java.util.HashMap;
+import java.lang.reflect.Method;
+
+/**
+ * @version $Rev$ $Date$
+ */
+public class MethodTransactionBuilder {
+
+ public void build(HashMap<String, DeploymentInfo> deployments, List<MethodTransactionInfo> methodTransactions) throws OpenEJBException {
+ for (DeploymentInfo deploymentInfo : deployments.values()) {
+ applyTransactionAttributes((CoreDeploymentInfo) deploymentInfo, methodTransactions);
+ }
+ }
+
+ public static void applyTransactionAttributes(CoreDeploymentInfo deploymentInfo, List<MethodTransactionInfo> mtis) throws OpenEJBException {
+ /*TODO: Add better exception handling. This method doesn't throws any exceptions!!
+ there is a lot of complex code here, I'm sure something could go wrong the user
+ might want to know about.
+ */
+
+ mtis = normalize(mtis);
+
+ for (MethodTransactionInfo transInfo : mtis) {
+ for (MethodInfo methodInfo : transInfo.methods) {
+
+ if (methodInfo.ejbDeploymentId == null || methodInfo.ejbDeploymentId.equals(deploymentInfo.getDeploymentID())) {
+ if (!deploymentInfo.isBeanManagedTransaction()) {
+
+ List<Method> methods = new ArrayList<Method>();
+
+ if (methodInfo.methodIntf == null) {
+ AssemblerTool.resolveMethods(methods, deploymentInfo.getBeanClass(), methodInfo);
+ if (deploymentInfo.getRemoteInterface() != null) {
+ AssemblerTool.resolveMethods(methods, deploymentInfo.getRemoteInterface(), methodInfo);
+ }
+ if (deploymentInfo.getHomeInterface() != null) {
+ AssemblerTool.resolveMethods(methods, deploymentInfo.getHomeInterface(), methodInfo);
+ }
+ if (deploymentInfo.getLocalInterface() != null) {
+ AssemblerTool.resolveMethods(methods, deploymentInfo.getLocalInterface(), methodInfo);
+ }
+ if (deploymentInfo.getLocalHomeInterface() != null) {
+ AssemblerTool.resolveMethods(methods, deploymentInfo.getLocalHomeInterface(), methodInfo);
+ }
+ if(deploymentInfo.getMdbInterface() != null) {
+ AssemblerTool.resolveMethods(methods, deploymentInfo.getMdbInterface(), methodInfo);
+ }
+ if(deploymentInfo.getServiceEndpointInterface() != null) {
+ AssemblerTool.resolveMethods(methods, deploymentInfo.getServiceEndpointInterface(), methodInfo);
+ }
+ for (Class intf : deploymentInfo.getBusinessRemoteInterfaces()) {
+ AssemblerTool.resolveMethods(methods, intf, methodInfo);
+ }
+ for (Class intf : deploymentInfo.getBusinessLocalInterfaces()) {
+ AssemblerTool.resolveMethods(methods, intf, methodInfo);
+ }
+ } else if (methodInfo.methodIntf.equals("Home")) {
+ AssemblerTool.resolveMethods(methods, deploymentInfo.getHomeInterface(), methodInfo);
+ } else if (methodInfo.methodIntf.equals("Remote")) {
+ AssemblerTool.resolveMethods(methods, deploymentInfo.getRemoteInterface(), methodInfo);
+ for (Class intf : deploymentInfo.getBusinessRemoteInterfaces()) {
+ AssemblerTool.resolveMethods(methods, intf, methodInfo);
+ }
+ } else if (methodInfo.methodIntf.equals("LocalHome")) {
+ AssemblerTool.resolveMethods(methods, deploymentInfo.getLocalHomeInterface(), methodInfo);
+ } else if (methodInfo.methodIntf.equals("Local")) {
+ AssemblerTool.resolveMethods(methods, deploymentInfo.getLocalInterface(), methodInfo);
+ for (Class intf : deploymentInfo.getBusinessRemoteInterfaces()) {
+ AssemblerTool.resolveMethods(methods, intf, methodInfo);
+ }
+ } else if (methodInfo.methodIntf.equals("ServiceEndpoint")) {
+ AssemblerTool.resolveMethods(methods, deploymentInfo.getServiceEndpointInterface(), methodInfo);
+ }
+
+ for (Method method : methods) {
+ if ((method.getDeclaringClass() == javax.ejb.EJBObject.class ||
+ method.getDeclaringClass() == javax.ejb.EJBHome.class) &&
+ !method.getName().equals("remove")) {
+ continue;
+ }
+ deploymentInfo.setMethodTransactionAttribute(method, transInfo.transAttribute);
+ }
+ }
+ }
+ }
+ }
+
+ }
+
+ public static enum Level {
+ PACKAGE, CLASS, OVERLOADED_METHOD, EXACT_METHOD
+ }
+
+ /**
+ * This method splits the MethodTransactionInfo objects so that there is
+ * exactly one MethodInfo per MethodTransactionInfo. A single MethodTransactionInfo
+ * with three MethodInfos would be expanded into three MethodTransactionInfo with
+ * one MethodInfo each.
+ *
+ * The MethodTransactionInfo list is then sorted from least to most specific.
+ *
+ * @param infos
+ * @return a normalized list of new MethodTransactionInfo objects
+ */
+ public static List<MethodTransactionInfo> normalize(List<MethodTransactionInfo> infos){
+ List<MethodTransactionInfo> normalized = new ArrayList<MethodTransactionInfo>();
+ for (MethodTransactionInfo oldInfo : infos) {
+ for (MethodInfo methodInfo : oldInfo.methods) {
+ MethodTransactionInfo newInfo = new MethodTransactionInfo();
+ newInfo.description = oldInfo.description;
+ newInfo.methods.add(methodInfo);
+ newInfo.transAttribute = oldInfo.transAttribute;
+
+ normalized.add(newInfo);
+ }
+ }
+
+ Collections.sort(normalized, new MethodTransactionComparator());
+
+ return normalized;
+ }
+
+ public static class MethodTransactionComparator implements Comparator<MethodTransactionInfo> {
+ public int compare(MethodTransactionInfo a, MethodTransactionInfo b) {
+ Level levelA = level(a);
+ Level levelB = level(b);
+
+ return levelA.ordinal() - levelB.ordinal();
+ }
+ }
+
+ private static Level level(MethodTransactionInfo info) {
+ MethodInfo methodInfo = info.methods.get(0);
+ if (methodInfo.ejbName.equals("*")) return Level.PACKAGE;
+ if (methodInfo.methodName == null || methodInfo.methodName.equals("*")) return Level.CLASS;
+ if (methodInfo.methodParams == null) return Level.OVERLOADED_METHOD;
+ return Level.EXACT_METHOD;
+ }
+
+}
Modified: openejb/trunk/openejb3/container/openejb-core/src/main/java/org/apache/openejb/config/ConfigurationFactory.java
URL: http://svn.apache.org/viewvc/openejb/trunk/openejb3/container/openejb-core/src/main/java/org/apache/openejb/config/ConfigurationFactory.java?view=diff&rev=562026&r1=562025&r2=562026
==============================================================================
--- openejb/trunk/openejb3/container/openejb-core/src/main/java/org/apache/openejb/config/ConfigurationFactory.java (original)
+++ openejb/trunk/openejb3/container/openejb-core/src/main/java/org/apache/openejb/config/ConfigurationFactory.java Wed Aug 1 23:21:51 2007
@@ -128,7 +128,7 @@
if (debuggableVmHackery.equalsIgnoreCase("true")){
chain.add(new DebuggableVmHackery());
}
-
+
chain.add(new CmpJpaConversion());
chain.add(new OpenEjb2Conversion());
chain.add(new SunConversion());
Modified: openejb/trunk/openejb3/container/openejb-core/src/main/java/org/apache/openejb/core/ivm/BaseEjbProxyHandler.java
URL: http://svn.apache.org/viewvc/openejb/trunk/openejb3/container/openejb-core/src/main/java/org/apache/openejb/core/ivm/BaseEjbProxyHandler.java?view=diff&rev=562026&r1=562025&r2=562026
==============================================================================
--- openejb/trunk/openejb3/container/openejb-core/src/main/java/org/apache/openejb/core/ivm/BaseEjbProxyHandler.java (original)
+++ openejb/trunk/openejb3/container/openejb-core/src/main/java/org/apache/openejb/core/ivm/BaseEjbProxyHandler.java Wed Aug 1 23:21:51 2007
@@ -90,10 +90,10 @@
*/
protected boolean doIntraVmCopy;
protected boolean doCrossClassLoaderCopy;
- protected final InterfaceType interfaceType;
- private final WeakReference<List<Class>> interfaces;
private static final boolean REMOTE_COPY_ENABLED = parseRemoteCopySetting();
- private final WeakReference<Class> mainInterface;
+ protected final InterfaceType interfaceType;
+ private transient WeakReference<List<Class>> interfaces;
+ private transient WeakReference<Class> mainInterface;
public BaseEjbProxyHandler(DeploymentInfo deploymentInfo, Object pk, InterfaceType interfaceType, List<Class> interfaces) {
this.container = (RpcContainer) deploymentInfo.getContainer();
@@ -176,19 +176,6 @@
return value == null || !value.equalsIgnoreCase("FALSE");
}
- private void readObject(java.io.ObjectInputStream in) throws java.io.IOException, ClassNotFoundException, NoSuchMethodException {
-
- in.defaultReadObject();
-
- ContainerSystem containerSystem = SystemInstance.get().getComponent(ContainerSystem.class);
- setDeploymentInfo((CoreDeploymentInfo) containerSystem.getDeploymentInfo(deploymentID));
- container = (RpcContainer) getDeploymentInfo().getContainer();
-
- if (IntraVmCopyMonitor.isCrossClassLoaderOperation()) {
- doCrossClassLoaderCopy = true;
- }
- }
-
protected void checkAuthorization(Method method) throws org.apache.openejb.OpenEJBException {
}
@@ -561,6 +548,29 @@
deploymentInfo.set(ProxyRegistry.class, proxyRegistry);
}
return proxyRegistry.liveHandleRegistry;
+ }
+
+ private void writeObject(java.io.ObjectOutputStream out) throws IOException {
+ out.defaultWriteObject();
+
+ out.writeObject(interfaces.get());
+ out.writeObject(mainInterface.get());
+ }
+
+ private void readObject(java.io.ObjectInputStream in) throws java.io.IOException, ClassNotFoundException {
+
+ in.defaultReadObject();
+
+ ContainerSystem containerSystem = SystemInstance.get().getComponent(ContainerSystem.class);
+ setDeploymentInfo((CoreDeploymentInfo) containerSystem.getDeploymentInfo(deploymentID));
+ container = (RpcContainer) getDeploymentInfo().getContainer();
+
+ if (IntraVmCopyMonitor.isCrossClassLoaderOperation()) {
+ doCrossClassLoaderCopy = true;
+ }
+
+ interfaces = new WeakReference<List<Class>>((List<Class>) in.readObject());
+ mainInterface = new WeakReference<Class>((Class) in.readObject());
}
}
Added: openejb/trunk/openejb3/container/openejb-core/src/test/java/org/apache/openejb/assembler/classic/MethodTransactionInfoComparatorTest.java
URL: http://svn.apache.org/viewvc/openejb/trunk/openejb3/container/openejb-core/src/test/java/org/apache/openejb/assembler/classic/MethodTransactionInfoComparatorTest.java?view=auto&rev=562026
==============================================================================
--- openejb/trunk/openejb3/container/openejb-core/src/test/java/org/apache/openejb/assembler/classic/MethodTransactionInfoComparatorTest.java (added)
+++ openejb/trunk/openejb3/container/openejb-core/src/test/java/org/apache/openejb/assembler/classic/MethodTransactionInfoComparatorTest.java Wed Aug 1 23:21:51 2007
@@ -0,0 +1,85 @@
+/**
+ * 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.openejb.assembler.classic;
+
+import junit.framework.TestCase;
+
+import java.util.ArrayList;
+import java.util.Collections;
+import java.util.List;
+
+/**
+ * @version $Rev$ $Date$
+ */
+public class MethodTransactionInfoComparatorTest extends TestCase {
+
+ public void testOrdering() throws Exception {
+
+ ArrayList<MethodTransactionInfo> expected = new ArrayList<MethodTransactionInfo>();
+
+ MethodTransactionInfo info = null;
+ MethodInfo method = null;
+
+ // Package Interceptors (aka Default Interceptors) ///////////////
+ info = add(expected, new MethodTransactionInfo());
+ info.transAttribute = "Required";
+ method = new MethodInfo();
+ method.ejbName = "*";
+ info.methods.add(method);
+
+ // Class Interceptors ////////////////////////////////////////////
+ info = add(expected, new MethodTransactionInfo());
+ info.transAttribute = "Required";
+ method = new MethodInfo();
+ method.ejbName = "*";
+ info.methods.add(method);
+
+ // Method Interceptors (no params) ///////////////////////////////
+ info = add(expected, new MethodTransactionInfo());
+ info.transAttribute = "Required";
+ method = new MethodInfo();
+ method.ejbName = "PingEJB";
+ method.methodName = "ping";
+ info.methods.add(method);
+
+ // Method Interceptors (params) ///////////////////////////////
+ info = add(expected, new MethodTransactionInfo());
+ info.transAttribute = "Required";
+ method = new MethodInfo();
+ method.ejbName = "PingEJB";
+ method.methodName = "ping";
+ method.methodParams = new ArrayList<String>();
+ method.methodParams.add("java.lang.String");
+ info.methods.add(method);
+
+ ArrayList<MethodTransactionInfo> actual = new ArrayList<MethodTransactionInfo>(expected);
+ Collections.shuffle(actual);
+ Collections.sort(actual, new MethodTransactionBuilder.MethodTransactionComparator());
+
+ for (int i = 0; i < actual.size(); i++) {
+ MethodTransactionInfo a = actual.get(i);
+ MethodTransactionInfo e = expected.get(i);
+ assertSame(e, a);
+ }
+ }
+
+
+ private MethodTransactionInfo add(List list, MethodTransactionInfo bindingInfo) {
+ list.add(bindingInfo);
+ return bindingInfo;
+ }
+}