From 4d56b896198960695b7d9812c00142b2c9e31b5b Mon Sep 17 00:00:00 2001 From: Juergen Hoeller Date: Mon, 28 Jun 2010 19:47:13 +0000 Subject: [PATCH] transaction names based on method id from most specific method (target class instead of interface; SPR-7317) --- .../interceptor/TransactionAspectSupport.java | 25 ++++++++++++++++--- .../interceptor/TransactionInterceptor.java | 2 +- .../BeanFactoryTransactionTests.java | 15 +++++------ 3 files changed, 31 insertions(+), 11 deletions(-) diff --git a/org.springframework.transaction/src/main/java/org/springframework/transaction/interceptor/TransactionAspectSupport.java b/org.springframework.transaction/src/main/java/org/springframework/transaction/interceptor/TransactionAspectSupport.java index 2527d49be43..5890e5bf202 100644 --- a/org.springframework.transaction/src/main/java/org/springframework/transaction/interceptor/TransactionAspectSupport.java +++ b/org.springframework.transaction/src/main/java/org/springframework/transaction/interceptor/TransactionAspectSupport.java @@ -270,7 +270,25 @@ public abstract class TransactionAspectSupport implements BeanFactoryAware, Init // If the transaction attribute is null, the method is non-transactional. TransactionAttribute txAttr = getTransactionAttributeSource().getTransactionAttribute(method, targetClass); PlatformTransactionManager tm = determineTransactionManager(txAttr); - return createTransactionIfNecessary(tm, txAttr, methodIdentification(method)); + return createTransactionIfNecessary(tm, txAttr, methodIdentification(method, targetClass)); + } + + /** + * Convenience method to return a String representation of this Method + * for use in logging. Can be overridden in subclasses to provide a + * different identifier for the given method. + * @param method the method we're interested in + * @param targetClass class the method is on + * @return log message identifying this method + * @see org.springframework.util.ClassUtils#getQualifiedMethodName + */ + protected String methodIdentification(Method method, Class targetClass) { + String simpleMethodId = methodIdentification(method); + if (simpleMethodId != null) { + return simpleMethodId; + } + Method specificMethod = ClassUtils.getMostSpecificMethod(method, targetClass); + return ClassUtils.getQualifiedMethodName(specificMethod); } /** @@ -279,10 +297,11 @@ public abstract class TransactionAspectSupport implements BeanFactoryAware, Init * different identifier for the given method. * @param method the method we're interested in * @return log message identifying this method - * @see org.springframework.util.ClassUtils#getQualifiedMethodName + * @deprecated in favor of {@link #methodIdentification(Method, Class)} */ + @Deprecated protected String methodIdentification(Method method) { - return ClassUtils.getQualifiedMethodName(method); + return null; } /** diff --git a/org.springframework.transaction/src/main/java/org/springframework/transaction/interceptor/TransactionInterceptor.java b/org.springframework.transaction/src/main/java/org/springframework/transaction/interceptor/TransactionInterceptor.java index e7665f980d7..6db3ef8169a 100644 --- a/org.springframework.transaction/src/main/java/org/springframework/transaction/interceptor/TransactionInterceptor.java +++ b/org.springframework.transaction/src/main/java/org/springframework/transaction/interceptor/TransactionInterceptor.java @@ -98,7 +98,7 @@ public class TransactionInterceptor extends TransactionAspectSupport implements final TransactionAttribute txAttr = getTransactionAttributeSource().getTransactionAttribute(invocation.getMethod(), targetClass); final PlatformTransactionManager tm = determineTransactionManager(txAttr); - final String joinpointIdentification = methodIdentification(invocation.getMethod()); + final String joinpointIdentification = methodIdentification(invocation.getMethod(), targetClass); if (txAttr == null || !(tm instanceof CallbackPreferringPlatformTransactionManager)) { // Standard transaction demarcation with getTransaction and commit/rollback calls. diff --git a/org.springframework.transaction/src/test/java/org/springframework/transaction/interceptor/BeanFactoryTransactionTests.java b/org.springframework.transaction/src/test/java/org/springframework/transaction/interceptor/BeanFactoryTransactionTests.java index f83009c4668..fb789915293 100644 --- a/org.springframework.transaction/src/test/java/org/springframework/transaction/interceptor/BeanFactoryTransactionTests.java +++ b/org.springframework.transaction/src/test/java/org/springframework/transaction/interceptor/BeanFactoryTransactionTests.java @@ -1,5 +1,5 @@ /* - * Copyright 2002-2005 the original author or authors. + * Copyright 2002-2010 the original author or authors. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -57,20 +57,20 @@ public class BeanFactoryTransactionTests extends TestCase { public void testGetsAreNotTransactionalWithProxyFactory1() throws NoSuchMethodException { ITestBean testBean = (ITestBean) factory.getBean("proxyFactory1"); assertTrue("testBean is a dynamic proxy", Proxy.isProxyClass(testBean.getClass())); - doTestGetsAreNotTransactional(testBean, ITestBean.class); + doTestGetsAreNotTransactional(testBean); } public void testGetsAreNotTransactionalWithProxyFactory2DynamicProxy() throws NoSuchMethodException { this.factory.preInstantiateSingletons(); ITestBean testBean = (ITestBean) factory.getBean("proxyFactory2DynamicProxy"); assertTrue("testBean is a dynamic proxy", Proxy.isProxyClass(testBean.getClass())); - doTestGetsAreNotTransactional(testBean, ITestBean.class); + doTestGetsAreNotTransactional(testBean); } public void testGetsAreNotTransactionalWithProxyFactory2Cglib() throws NoSuchMethodException { ITestBean testBean = (ITestBean) factory.getBean("proxyFactory2Cglib"); assertTrue("testBean is CGLIB advised", AopUtils.isCglibProxy(testBean)); - doTestGetsAreNotTransactional(testBean, TestBean.class); + doTestGetsAreNotTransactional(testBean); } public void testProxyFactory2Lazy() throws NoSuchMethodException { @@ -103,14 +103,14 @@ public class BeanFactoryTransactionTests extends TestCase { txnCounter.counter = 0; preCounter.counter = 0; postCounter.counter = 0; - doTestGetsAreNotTransactional(testBean, TestBean.class); + doTestGetsAreNotTransactional(testBean); // Can't assert it's equal to 4 as the pointcut may be optimized and only invoked once assertTrue(0 < txnCounter.counter && txnCounter.counter <= 4); assertEquals(4, preCounter.counter); assertEquals(4, postCounter.counter); } - private void doTestGetsAreNotTransactional(final ITestBean testBean, final Class proxyClass) { + private void doTestGetsAreNotTransactional(final ITestBean testBean) { // Install facade MockControl ptmControl = MockControl.createControl(PlatformTransactionManager.class); PlatformTransactionManager ptm = (PlatformTransactionManager) ptmControl.getMock(); @@ -132,7 +132,8 @@ public class BeanFactoryTransactionTests extends TestCase { throw new IllegalStateException("getTransaction should not get invoked more than once"); } invoked = true; - if (!((definition.getName().indexOf(proxyClass.getName()) != -1) && + System.out.println(definition.getName()); + if (!((definition.getName().indexOf(TestBean.class.getName()) != -1) && (definition.getName().indexOf("setAge") != -1))) { throw new IllegalStateException( "transaction name should contain class and method name: " + definition.getName());