You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@tapestry.apache.org by hl...@apache.org on 2011/09/24 06:51:55 UTC

svn commit: r1175103 - in /tapestry/tapestry5/trunk/tapestry-ioc/src: main/java/org/apache/tapestry5/ioc/internal/ main/java/org/apache/tapestry5/ioc/internal/util/ main/resources/org/apache/tapestry5/ioc/internal/ test/java/org/apache/tapestry5/ioc/ t...

Author: hlship
Date: Sat Sep 24 04:51:55 2011
New Revision: 1175103

URL: http://svn.apache.org/viewvc?rev=1175103&view=rev
Log:
TAP5-1665: Tapestry could create non-singleton services more efficiently

Added:
    tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/util/ConstructionPlan.java
    tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/util/ConstructorInvoker.java
    tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/util/InitializationPlan.java
    tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/util/LoggingInvokableWrapper.java
Modified:
    tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/AbstractReloadableObjectCreator.java
    tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/ConstructorServiceCreator.java
    tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/IOCMessages.java
    tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/RegistryImpl.java
    tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/util/InternalUtils.java
    tapestry/tapestry5/trunk/tapestry-ioc/src/main/resources/org/apache/tapestry5/ioc/internal/IOCStrings.properties
    tapestry/tapestry5/trunk/tapestry-ioc/src/test/java/org/apache/tapestry5/ioc/IntegrationTest.java
    tapestry/tapestry5/trunk/tapestry-ioc/src/test/java/org/apache/tapestry5/ioc/internal/DefaultModuleDefImplTest.java

Modified: tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/AbstractReloadableObjectCreator.java
URL: http://svn.apache.org/viewvc/tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/AbstractReloadableObjectCreator.java?rev=1175103&r1=1175102&r2=1175103&view=diff
==============================================================================
--- tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/AbstractReloadableObjectCreator.java (original)
+++ tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/AbstractReloadableObjectCreator.java Sat Sep 24 04:51:55 2011
@@ -1,4 +1,4 @@
-// Copyright 2010 The Apache Software Foundation
+// Copyright 2010, 2011 The Apache Software Foundation
 //
 // Licensed under the Apache License, Version 2.0 (the "License");
 // you may not use this file except in compliance with the License.
@@ -14,25 +14,9 @@
 
 package org.apache.tapestry5.ioc.internal;
 
-import java.io.File;
-import java.net.URL;
-import java.net.URLClassLoader;
-import java.util.Set;
-
-import javassist.CannotCompileException;
-import javassist.ClassPath;
-import javassist.ClassPool;
-import javassist.CtClass;
-import javassist.Loader;
-import javassist.LoaderClassPath;
-import javassist.NotFoundException;
-import javassist.Translator;
+import javassist.*;
 import javassist.expr.ConstructorCall;
 import javassist.expr.ExprEditor;
-import javassist.expr.FieldAccess;
-import javassist.expr.MethodCall;
-import javassist.expr.NewExpr;
-
 import org.apache.tapestry5.ioc.Invokable;
 import org.apache.tapestry5.ioc.ObjectCreator;
 import org.apache.tapestry5.ioc.OperationTracker;
@@ -45,6 +29,10 @@ import org.apache.tapestry5.ioc.services
 import org.apache.tapestry5.services.UpdateListener;
 import org.slf4j.Logger;
 
+import java.net.URL;
+import java.net.URLClassLoader;
+import java.util.Set;
+
 @SuppressWarnings("all")
 public abstract class AbstractReloadableObjectCreator implements ObjectCreator, UpdateListener, Translator
 {
@@ -69,8 +57,6 @@ public abstract class AbstractReloadable
 
     private final String implementationClassName;
 
-    private final String classFilePath;
-
     private final Logger logger;
 
     private final OperationTracker tracker;
@@ -88,14 +74,12 @@ public abstract class AbstractReloadable
     private boolean firstTime = true;
 
     protected AbstractReloadableObjectCreator(ClassLoader baseClassLoader, String implementationClassName,
-            Logger logger, OperationTracker tracker)
+                                              Logger logger, OperationTracker tracker)
     {
         this.baseClassLoader = baseClassLoader;
         this.implementationClassName = implementationClassName;
         this.logger = logger;
         this.tracker = tracker;
-
-        classFilePath = ClassFabUtils.getPathForClassNamed(implementationClassName);
     }
 
     public synchronized void checkForUpdates()
@@ -146,14 +130,16 @@ public abstract class AbstractReloadable
                 Class reloadedClass = reloadImplementationClass();
 
                 return createInstance(reloadedClass);
-            };
+            }
+
+            ;
         });
     }
 
     /**
      * Invoked when an instance of the class is needed. It is the responsibility of this method (as implemented in a
      * subclass) to instantiate the class and inject dependencies into the class.
-     * 
+     *
      * @see InternalUtils#findAutobuildConstructor(Class)
      */
     abstract protected Object createInstance(Class clazz);
@@ -185,8 +171,7 @@ public abstract class AbstractReloadable
             firstTime = false;
 
             return result;
-        }
-        catch (Throwable ex)
+        } catch (Throwable ex)
         {
             throw new RuntimeException(String.format("Unable to %s class %s: %s", firstTime ? "load" : "reload",
                     implementationClassName, InternalUtils.toMessage(ex)), ex);
@@ -273,7 +258,9 @@ public abstract class AbstractReloadable
         return className.indexOf('$') >= 0;
     }
 
-    /** Does nothing. */
+    /**
+     * Does nothing.
+     */
     public void start(ClassPool pool) throws NotFoundException, CannotCompileException
     {
 

Modified: tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/ConstructorServiceCreator.java
URL: http://svn.apache.org/viewvc/tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/ConstructorServiceCreator.java?rev=1175103&r1=1175102&r2=1175103&view=diff
==============================================================================
--- tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/ConstructorServiceCreator.java (original)
+++ tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/ConstructorServiceCreator.java Sat Sep 24 04:51:55 2011
@@ -14,13 +14,11 @@
 
 package org.apache.tapestry5.ioc.internal;
 
-import org.apache.tapestry5.ioc.Invokable;
+import org.apache.tapestry5.ioc.ObjectCreator;
 import org.apache.tapestry5.ioc.ServiceBuilderResources;
-import org.apache.tapestry5.ioc.internal.util.InjectionResources;
 import org.apache.tapestry5.ioc.internal.util.InternalUtils;
 
 import java.lang.reflect.Constructor;
-import java.lang.reflect.InvocationTargetException;
 
 /**
  * A service creator based on an implementation class' constructor, rather than a service builder method.
@@ -30,7 +28,7 @@ public class ConstructorServiceCreator e
     private final Constructor constructor;
 
     public ConstructorServiceCreator(ServiceBuilderResources resources, String creatorDescription,
-            Constructor constructor)
+                                     Constructor constructor)
     {
         super(resources, creatorDescription);
 
@@ -43,49 +41,23 @@ public class ConstructorServiceCreator e
         return creatorDescription;
     }
 
-    public Object createObject()
+    private ObjectCreator<?> plan;
+
+    private synchronized ObjectCreator<?> getPlan()
     {
-        return resources.getTracker().invoke("Invoking constructor " + creatorDescription, new Invokable<Object>()
+        if (plan == null)
         {
-            public Object invoke()
-            {
-                Throwable failure = null;
-                Object result = null;
-
-                InternalUtils.validateConstructorForAutobuild(constructor);
-
-                InjectionResources injectionResources = createInjectionResources();
-
-                try
-                {
-                    Object[] parameters = InternalUtils.calculateParametersForConstructor(constructor, resources,
-                            injectionResources, resources.getTracker());
-
-                    if (logger.isDebugEnabled())
-                        logger.debug(IOCMessages.invokingConstructor(creatorDescription));
-
-                    result = constructor.newInstance(parameters);
-
-                    InternalUtils.injectIntoFields(result, resources, injectionResources, resources.getTracker());
-                }
-                catch (InvocationTargetException ite)
-                {
-                    failure = ite.getTargetException();
-                }
-                catch (Exception ex)
-                {
-                    failure = ex;
-                }
-
-                if (failure != null)
-                    throw new RuntimeException(IOCMessages.constructorError(creatorDescription, serviceId, failure),
-                            failure);
-
-                InternalUtils.invokePostInjectionMethods(result, resources, injectionResources, resources.getTracker());
-
-                return result;
-            }
-        });
+            String description = String.format("Invoking constructor %s (for service '%s')", creatorDescription, resources.getServiceId());
 
+            plan = InternalUtils.createConstructorConstructionPlan(resources.getTracker(), resources, createInjectionResources(), logger,
+                    description, constructor);
+        }
+
+        return plan;
+    }
+
+    public Object createObject()
+    {
+        return getPlan().createObject();
     }
 }

Modified: tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/IOCMessages.java
URL: http://svn.apache.org/viewvc/tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/IOCMessages.java?rev=1175103&r1=1175102&r2=1175103&view=diff
==============================================================================
--- tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/IOCMessages.java (original)
+++ tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/IOCMessages.java Sat Sep 24 04:51:55 2011
@@ -21,10 +21,8 @@ import org.apache.tapestry5.ioc.def.Serv
 import org.apache.tapestry5.ioc.def.ServiceDef2;
 import org.apache.tapestry5.ioc.internal.util.CollectionFactory;
 import org.apache.tapestry5.ioc.internal.util.InternalUtils;
-import static org.apache.tapestry5.ioc.internal.util.InternalUtils.asString;
 import org.apache.tapestry5.ioc.internal.util.MessagesImpl;
 import org.apache.tapestry5.ioc.services.ClassFabUtils;
-import static org.apache.tapestry5.ioc.services.ClassFabUtils.toJavaClassName;
 
 import java.lang.reflect.Constructor;
 import java.lang.reflect.Method;
@@ -33,6 +31,9 @@ import java.util.Collection;
 import java.util.List;
 import java.util.Map;
 
+import static org.apache.tapestry5.ioc.internal.util.InternalUtils.asString;
+import static org.apache.tapestry5.ioc.services.ClassFabUtils.toJavaClassName;
+
 final class IOCMessages
 {
     private static final Messages MESSAGES = MessagesImpl.forClass(IOCMessages.class);
@@ -57,7 +58,7 @@ final class IOCMessages
     static String serviceWrongInterface(String serviceId, Class actualInterface, Class requestedInterface)
     {
         return MESSAGES.format("service-wrong-interface", serviceId, actualInterface.getName(),
-                               requestedInterface.getName());
+                requestedInterface.getName());
     }
 
     static String instantiateBuilderError(Class builderClass, Throwable cause)
@@ -70,11 +71,6 @@ final class IOCMessages
         return MESSAGES.format("builder-method-error", methodId, serviceId, cause);
     }
 
-    static String constructorError(String creatorDescription, String serviceId, Throwable cause)
-    {
-        return MESSAGES.format("constructor-error", creatorDescription, serviceId, cause);
-    }
-
     static String builderMethodReturnedNull(String methodId, String serviceId)
     {
         return MESSAGES.format("builder-method-returned-null", methodId, serviceId);
@@ -107,7 +103,7 @@ final class IOCMessages
     static String decoratorReturnedWrongType(Method method, String serviceId, Object returned, Class serviceInterface)
     {
         return MESSAGES.format("decorator-returned-wrong-type", asString(method), serviceId, returned,
-                               serviceInterface.getName());
+                serviceInterface.getName());
     }
 
     static String invokingMethod(String methodId)
@@ -134,7 +130,7 @@ final class IOCMessages
     static String contributionWrongReturnType(Method method)
     {
         return MESSAGES.format("contribution-wrong-return-type", asString(method),
-                               toJavaClassName(method.getReturnType()));
+                toJavaClassName(method.getReturnType()));
     }
 
     static String tooManyContributionParameters(Method method)
@@ -167,7 +163,7 @@ final class IOCMessages
                                            Class expectedClass)
     {
         return MESSAGES.format("contribution-wrong-key-type", serviceId, actualClass.getName(),
-                               expectedClass.getName());
+                expectedClass.getName());
     }
 
     static String tooManyConfigurationParameters(String methodId)
@@ -265,17 +261,17 @@ final class IOCMessages
     static String noServicesMatchMarker(Class objectType, List<Class> markers)
     {
         return MESSAGES.format("no-services-match-marker",
-                               ClassFabUtils.toJavaClassName(objectType),
-                               toJavaClassNames(markers));
+                ClassFabUtils.toJavaClassName(objectType),
+                toJavaClassNames(markers));
     }
 
     static String manyServicesMatchMarker(Class objectType, List<Class> markers,
                                           Collection<ServiceDef2> matchingServices)
     {
         return MESSAGES.format("many-services-match-marker",
-                               ClassFabUtils.toJavaClassName(objectType),
-                               toJavaClassNames(markers),
-                               InternalUtils.joinSorted(matchingServices));
+                ClassFabUtils.toJavaClassName(objectType),
+                toJavaClassNames(markers),
+                InternalUtils.joinSorted(matchingServices));
     }
 
     static String overlappingServiceProxyProviders()
@@ -297,12 +293,12 @@ final class IOCMessages
     {
         return MESSAGES.format("no-convention-service-implementation-found", clazz.getName(), clazz.getName());
     }
-    
+
     static String contributionForNonexistentService(ContributionDef cd)
     {
         return MESSAGES.format("contribution-for-nonexistent-service", cd, cd.getServiceId());
     }
-    
+
     static String contributionForUnqualifiedService(ContributionDef2 cd)
     {
         return MESSAGES.format("contribution-for-unqualified-service", cd, cd.getServiceInterface(), cd.getMarkers());

Modified: tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/RegistryImpl.java
URL: http://svn.apache.org/viewvc/tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/RegistryImpl.java?rev=1175103&r1=1175102&r2=1175103&view=diff
==============================================================================
--- tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/RegistryImpl.java (original)
+++ tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/RegistryImpl.java Sat Sep 24 04:51:55 2011
@@ -14,73 +14,25 @@
 
 package org.apache.tapestry5.ioc.internal;
 
-import java.lang.reflect.Constructor;
-import java.lang.reflect.InvocationTargetException;
-import java.util.Collection;
-import java.util.Collections;
-import java.util.HashSet;
-import java.util.List;
-import java.util.Map;
-import java.util.Set;
-
 import org.apache.tapestry5.func.F;
 import org.apache.tapestry5.func.Flow;
 import org.apache.tapestry5.func.Mapper;
 import org.apache.tapestry5.func.Predicate;
-import org.apache.tapestry5.ioc.AdvisorDef;
-import org.apache.tapestry5.ioc.AnnotationProvider;
-import org.apache.tapestry5.ioc.Configuration;
-import org.apache.tapestry5.ioc.IOCConstants;
-import org.apache.tapestry5.ioc.Invokable;
-import org.apache.tapestry5.ioc.LoggerSource;
-import org.apache.tapestry5.ioc.MappedConfiguration;
-import org.apache.tapestry5.ioc.ObjectCreator;
-import org.apache.tapestry5.ioc.ObjectLocator;
-import org.apache.tapestry5.ioc.ObjectProvider;
-import org.apache.tapestry5.ioc.OperationTracker;
-import org.apache.tapestry5.ioc.OrderedConfiguration;
-import org.apache.tapestry5.ioc.Registry;
-import org.apache.tapestry5.ioc.ScopeConstants;
-import org.apache.tapestry5.ioc.ServiceAdvisor;
-import org.apache.tapestry5.ioc.ServiceBuilderResources;
-import org.apache.tapestry5.ioc.ServiceDecorator;
-import org.apache.tapestry5.ioc.ServiceLifecycle;
-import org.apache.tapestry5.ioc.ServiceLifecycle2;
-import org.apache.tapestry5.ioc.ServiceResources;
+import org.apache.tapestry5.ioc.*;
 import org.apache.tapestry5.ioc.annotations.Local;
-import org.apache.tapestry5.ioc.def.ContributionDef;
-import org.apache.tapestry5.ioc.def.ContributionDef2;
-import org.apache.tapestry5.ioc.def.DecoratorDef;
-import org.apache.tapestry5.ioc.def.ModuleDef;
-import org.apache.tapestry5.ioc.def.ServiceDef;
-import org.apache.tapestry5.ioc.def.ServiceDef2;
-import org.apache.tapestry5.ioc.def.ServiceDef3;
+import org.apache.tapestry5.ioc.def.*;
 import org.apache.tapestry5.ioc.internal.services.PerthreadManagerImpl;
 import org.apache.tapestry5.ioc.internal.services.RegistryShutdownHubImpl;
-import org.apache.tapestry5.ioc.internal.util.CollectionFactory;
-import org.apache.tapestry5.ioc.internal.util.InjectionResources;
-import org.apache.tapestry5.ioc.internal.util.InternalUtils;
-import org.apache.tapestry5.ioc.internal.util.MapInjectionResources;
-import org.apache.tapestry5.ioc.internal.util.OneShotLock;
-import org.apache.tapestry5.ioc.internal.util.Orderer;
-import org.apache.tapestry5.ioc.services.Builtin;
-import org.apache.tapestry5.ioc.services.ClassFab;
-import org.apache.tapestry5.ioc.services.ClassFactory;
-import org.apache.tapestry5.ioc.services.MasterObjectProvider;
-import org.apache.tapestry5.ioc.services.PerthreadManager;
-import org.apache.tapestry5.ioc.services.PlasticProxyFactory;
-import org.apache.tapestry5.ioc.services.RegistryShutdownHub;
-import org.apache.tapestry5.ioc.services.RegistryShutdownListener;
-import org.apache.tapestry5.ioc.services.ServiceActivityScoreboard;
-import org.apache.tapestry5.ioc.services.ServiceLifecycleSource;
-import org.apache.tapestry5.ioc.services.Status;
-import org.apache.tapestry5.ioc.services.SymbolSource;
-import org.apache.tapestry5.ioc.services.TapestryIOCModule;
+import org.apache.tapestry5.ioc.internal.util.*;
+import org.apache.tapestry5.ioc.services.*;
 import org.apache.tapestry5.ioc.util.AvailableValues;
 import org.apache.tapestry5.ioc.util.UnknownValueException;
 import org.apache.tapestry5.services.UpdateListenerHub;
 import org.slf4j.Logger;
 
+import java.lang.reflect.Constructor;
+import java.util.*;
+
 @SuppressWarnings("all")
 public class RegistryImpl implements Registry, InternalRegistry, ServiceProxyProvider
 {
@@ -158,18 +110,14 @@ public class RegistryImpl implements Reg
 
     /**
      * Constructs the registry from a set of module definitions and other resources.
-     * 
-     * @param moduleDefs
-     *            defines the modules (and builders, decorators, etc., within)
-     * @param classFactory
-     *            TODO
-     * @param proxyFactory
-     *            TODO
-     * @param loggerSource
-     *            used to obtain Logger instances
+     *
+     * @param moduleDefs   defines the modules (and builders, decorators, etc., within)
+     * @param classFactory TODO
+     * @param proxyFactory TODO
+     * @param loggerSource used to obtain Logger instances
      */
     public RegistryImpl(Collection<ModuleDef> moduleDefs, ClassFactory classFactory, PlasticProxyFactory proxyFactory,
-            LoggerSource loggerSource)
+                        LoggerSource loggerSource)
     {
         assert moduleDefs != null;
         assert classFactory != null;
@@ -269,11 +217,16 @@ public class RegistryImpl implements Reg
 
                 if (cd2.getServiceId() != null)
                 {
-                    if (!serviceIdToModule.containsKey(serviceId)) { throw new IllegalArgumentException(
-                            IOCMessages.contributionForNonexistentService(cd)); }
+                    if (!serviceIdToModule.containsKey(serviceId))
+                    {
+                        throw new IllegalArgumentException(
+                                IOCMessages.contributionForNonexistentService(cd));
+                    }
+                } else if (!isContributionForExistentService(module, cd2))
+                {
+                    throw new IllegalArgumentException(
+                            IOCMessages.contributionForUnqualifiedService(cd2));
                 }
-                else if (!isContributionForExistentService(module, cd2)) { throw new IllegalArgumentException(
-                        IOCMessages.contributionForUnqualifiedService(cd2)); }
             }
         }
 
@@ -298,18 +251,19 @@ public class RegistryImpl implements Reg
         // Match services with the correct interface AND having as markers *all* the marker annotations
 
         Flow<ServiceDef2> filtered = serviceDefs.filter(F.and(new Predicate<ServiceDef2>()
-        {
-            public boolean accept(ServiceDef2 object)
-            {
-                return object.getServiceInterface().equals(cd.getServiceInterface());
-            }
-        }, new Predicate<ServiceDef2>()
+                {
+                    public boolean accept(ServiceDef2 object)
+                    {
+                        return object.getServiceInterface().equals(cd.getServiceInterface());
+                    }
+                }, new Predicate<ServiceDef2>()
         {
             public boolean accept(ServiceDef2 serviceDef)
             {
                 return serviceDef.getMarkers().containsAll(contributionMarkers);
             }
-        }));
+        }
+        ));
 
         // That's a lot of logic; the good news is it will short-circuit as soon as it finds a single match,
         // thanks to the laziness inside Flow.
@@ -458,8 +412,7 @@ public class RegistryImpl implements Reg
         try
         {
             return serviceInterface.cast(service);
-        }
-        catch (ClassCastException ex)
+        } catch (ClassCastException ex)
         {
             throw new RuntimeException(IOCMessages.serviceWrongInterface(serviceId, builtinTypes.get(serviceId),
                     serviceInterface));
@@ -567,8 +520,8 @@ public class RegistryImpl implements Reg
     }
 
     private <K, V> void addToMappedConfiguration(Map<K, V> map, Map<K, MappedConfigurationOverride<K, V>> overrides,
-            Map<K, ContributionDef> keyToContribution, Class<K> keyClass, Class<V> valueType, ServiceDef3 serviceDef,
-            final Module module)
+                                                 Map<K, ContributionDef> keyToContribution, Class<K> keyClass, Class<V> valueType, ServiceDef3 serviceDef,
+                                                 final Module module)
     {
         String serviceId = serviceDef.getServiceId();
         Set<ContributionDef2> contributions = module.getContributorDefsForService(serviceDef);
@@ -603,7 +556,7 @@ public class RegistryImpl implements Reg
     }
 
     private <T> void addToUnorderedConfiguration(Collection<T> collection, Class<T> valueType, ServiceDef3 serviceDef,
-            final Module module)
+                                                 final Module module)
     {
         String serviceId = serviceDef.getServiceId();
         Set<ContributionDef2> contributions = module.getContributorDefsForService(serviceDef);
@@ -638,8 +591,8 @@ public class RegistryImpl implements Reg
     }
 
     private <T> void addToOrderedConfiguration(Orderer<T> orderer,
-            Map<String, OrderedConfigurationOverride<T>> overrides, Class<T> valueType, ServiceDef3 serviceDef,
-            final Module module)
+                                               Map<String, OrderedConfigurationOverride<T>> overrides, Class<T> valueType, ServiceDef3 serviceDef,
+                                               final Module module)
     {
         String serviceId = serviceDef.getServiceId();
         Set<ContributionDef2> contributions = module.getContributorDefsForService(serviceDef);
@@ -807,7 +760,7 @@ public class RegistryImpl implements Reg
     }
 
     public <T> T getObject(Class<T> objectType, AnnotationProvider annotationProvider, ObjectLocator locator,
-            Module localModule)
+                           Module localModule)
     {
         lock.check();
 
@@ -908,11 +861,9 @@ public class RegistryImpl implements Reg
     /**
      * Filters the set into a new set, containing only elements shared between the set and the
      * filter collection.
-     * 
-     * @param set
-     *            to be filtered
-     * @param filter
-     *            values to keep from the set
+     *
+     * @param set    to be filtered
+     * @param filter values to keep from the set
      * @return a new set containing only the shared values
      */
     private static <T> Set<T> intersection(Set<T> set, Collection<T> filter)
@@ -983,32 +934,18 @@ public class RegistryImpl implements Reg
         final Constructor constructor = InternalUtils.findAutobuildConstructor(clazz);
 
         if (constructor == null)
+        {
             throw new RuntimeException(IOCMessages.noAutobuildConstructor(clazz));
+        }
 
         Map<Class, Object> resourcesMap = CollectionFactory.newMap();
         resourcesMap.put(OperationTracker.class, RegistryImpl.this);
 
-        final InjectionResources resources = new MapInjectionResources(resourcesMap);
-
-        final Invokable<T> operation = new Invokable<T>()
-        {
-            public T invoke()
-            {
-                InternalUtils.validateConstructorForAutobuild(constructor);
-
-                Object result = invokeConstructor(constructor, resources);
-
-                InternalUtils.injectIntoFields(result, RegistryImpl.this, resources, RegistryImpl.this);
+        InjectionResources resources = new MapInjectionResources(resourcesMap);
 
-                return clazz.cast(result);
-            }
-        };
+        ObjectCreator<T> plan = InternalUtils.createConstructorConstructionPlan(this, this, resources, null, "Invoking " + proxyFactory.getConstructorLocation(constructor).toString(), constructor);
 
-        T result = invoke("Autobuilding instance of class " + clazz.getName(), operation);
-
-        InternalUtils.invokePostInjectionMethods(result, this, resources, this);
-
-        return result;
+        return plan.createObject();
     }
 
     public <T> T proxy(Class<T> interfaceClass, Class<? extends T> implementationClass)
@@ -1028,7 +965,7 @@ public class RegistryImpl implements Reg
     }
 
     private <T> T createNonReloadingProxy(Class<T> interfaceClass, final Class<? extends T> implementationClass,
-            final ObjectLocator locator)
+                                          final ObjectLocator locator)
     {
         final ObjectCreator<T> autobuildCreator = new ObjectCreator<T>()
         {
@@ -1056,7 +993,7 @@ public class RegistryImpl implements Reg
     }
 
     private <T> T createReloadingProxy(Class<T> interfaceClass, final Class<? extends T> implementationClass,
-            ObjectLocator locator)
+                                       ObjectLocator locator)
     {
         ReloadableObjectCreator creator = new ReloadableObjectCreator(implementationClass.getClassLoader(),
                 implementationClass.getName(), loggerSource.getLogger(implementationClass), this, locator);
@@ -1082,37 +1019,6 @@ public class RegistryImpl implements Reg
         return operationTracker.invoke(description, operation);
     }
 
-    private Object invokeConstructor(final Constructor constructor, final InjectionResources resources)
-    {
-        final String description = proxyFactory.getConstructorLocation(constructor).toString();
-
-        return invoke("Invoking " + description, new Invokable<Object>()
-        {
-            public Object invoke()
-            {
-                Throwable failure;
-
-                try
-                {
-                    Object[] parameters = InternalUtils.calculateParametersForConstructor(constructor,
-                            RegistryImpl.this, resources, RegistryImpl.this);
-
-                    return constructor.newInstance(parameters);
-                }
-                catch (InvocationTargetException ite)
-                {
-                    failure = ite.getTargetException();
-                }
-                catch (Exception ex)
-                {
-                    failure = ex;
-                }
-
-                throw new RuntimeException(IOCMessages.autobuildConstructorError(description, failure), failure);
-            }
-        });
-    }
-
     public Set<Class> getMarkerAnnotations()
     {
         return markerToServiceDef.keySet();

Added: tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/util/ConstructionPlan.java
URL: http://svn.apache.org/viewvc/tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/util/ConstructionPlan.java?rev=1175103&view=auto
==============================================================================
--- tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/util/ConstructionPlan.java (added)
+++ tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/util/ConstructionPlan.java Sat Sep 24 04:51:55 2011
@@ -0,0 +1,83 @@
+// Copyright 2011 The Apache Software Foundation
+//
+// Licensed 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.tapestry5.ioc.internal.util;
+
+import org.apache.tapestry5.ioc.Invokable;
+import org.apache.tapestry5.ioc.ObjectCreator;
+import org.apache.tapestry5.ioc.OperationTracker;
+
+import java.util.List;
+
+/**
+ * Encapsulates the initial construction of an object instance, followed by a series
+ * {@link InitializationPlan}s to initialize fields and invoke other methods of the constructed object.
+ *
+ * @since 5.3
+ */
+public class ConstructionPlan<T> implements ObjectCreator<T>
+{
+    private final OperationTracker tracker;
+
+    private final String description;
+
+    private final Invokable<T> instanceConstructor;
+
+    private List<InitializationPlan> initializationPlans;
+
+    public ConstructionPlan(OperationTracker tracker, String description, Invokable<T> instanceConstructor)
+    {
+        this.tracker = tracker;
+        this.description = description;
+        this.instanceConstructor = instanceConstructor;
+    }
+
+    public ConstructionPlan add(InitializationPlan plan)
+    {
+        if (initializationPlans == null)
+        {
+            initializationPlans = CollectionFactory.newList();
+        }
+
+        initializationPlans.add(plan);
+
+        return this;
+    }
+
+    public T createObject()
+    {
+        T result = tracker.invoke(description, instanceConstructor);
+
+        if (initializationPlans != null)
+        {
+            executeInitializationPLans(result);
+        }
+
+        return result;
+    }
+
+    private void executeInitializationPLans(final T newInstance)
+    {
+        for (final InitializationPlan<T> plan : initializationPlans)
+        {
+            tracker.run(plan.getDescription(), new Runnable()
+            {
+                public void run()
+                {
+                    plan.initialize(newInstance);
+                }
+            });
+        }
+    }
+}

Added: tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/util/ConstructorInvoker.java
URL: http://svn.apache.org/viewvc/tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/util/ConstructorInvoker.java?rev=1175103&view=auto
==============================================================================
--- tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/util/ConstructorInvoker.java (added)
+++ tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/util/ConstructorInvoker.java Sat Sep 24 04:51:55 2011
@@ -0,0 +1,57 @@
+// Copyright 2011 The Apache Software Foundation
+//
+// Licensed 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.tapestry5.ioc.internal.util;
+
+import org.apache.tapestry5.ioc.Invokable;
+
+import java.lang.reflect.Constructor;
+import java.lang.reflect.InvocationTargetException;
+
+/**
+ * Wraps the invocation of a constructor (with exception reporting) as an {@link Invokable}.
+ *
+ * @since 5.3
+ */
+public class ConstructorInvoker<T> implements Invokable<T>
+{
+    private final Constructor<T> constructor;
+
+    private final Object[] constructorParameters;
+
+    public ConstructorInvoker(Constructor constructor, Object[] constructorParameters)
+    {
+        this.constructor = constructor;
+        this.constructorParameters = constructorParameters;
+    }
+
+    public T invoke()
+    {
+        Throwable fail;
+
+        try
+        {
+            return constructor.newInstance(constructorParameters);
+        } catch (InvocationTargetException ex)
+        {
+            fail = ex.getTargetException();
+        } catch (Exception ex)
+        {
+            fail = ex;
+        }
+
+        throw new RuntimeException(String.format("Error invoking constructor %s: %s",
+                constructor, InternalUtils.toMessage(fail)), fail);
+    }
+}

Added: tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/util/InitializationPlan.java
URL: http://svn.apache.org/viewvc/tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/util/InitializationPlan.java?rev=1175103&view=auto
==============================================================================
--- tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/util/InitializationPlan.java (added)
+++ tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/util/InitializationPlan.java Sat Sep 24 04:51:55 2011
@@ -0,0 +1,35 @@
+// Copyright 2011 The Apache Software Foundation
+//
+// Licensed 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.tapestry5.ioc.internal.util;
+
+/**
+ * Performs one initialization step on a newly created object.
+ *
+ * @since 5.3
+ */
+public interface InitializationPlan<T>
+{
+    /**
+     * The description of the operation, used with the {@link org.apache.tapestry5.ioc.OperationTracker}.
+     *
+     * @return
+     */
+    String getDescription();
+
+    /**
+     * Invoked by the {@link ConstructionPlan} inside a {@linkplain org.apache.tapestry5.ioc.OperationTracker#run(String, Runnable) operation tracker block}.
+     */
+    void initialize(T instance);
+}

Modified: tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/util/InternalUtils.java
URL: http://svn.apache.org/viewvc/tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/util/InternalUtils.java?rev=1175103&r1=1175102&r2=1175103&view=diff
==============================================================================
--- tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/util/InternalUtils.java (original)
+++ tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/util/InternalUtils.java Sat Sep 24 04:51:55 2011
@@ -26,6 +26,7 @@ import org.apache.tapestry5.ioc.services
 import org.apache.tapestry5.plastic.MethodAdvice;
 import org.apache.tapestry5.plastic.MethodInvocation;
 import org.apache.tapestry5.plastic.PlasticUtils;
+import org.slf4j.Logger;
 
 import javax.inject.Named;
 import java.io.Closeable;
@@ -1428,4 +1429,190 @@ public class InternalUtils
             }
         };
     }
+
+    public static <T> ObjectCreator<T> createConstructorConstructionPlan(final OperationTracker tracker, final ObjectLocator locator,
+                                                                         final InjectionResources resources,
+                                                                         final Logger logger,
+                                                                         final String description,
+                                                                         final Constructor<T> constructor)
+    {
+        return tracker.invoke(String.format("Creating plan to instantiate %s via %s",
+                constructor.getDeclaringClass().getName(),
+                constructor), new Invokable<ObjectCreator<T>>()
+        {
+            public ObjectCreator<T> invoke()
+            {
+                validateConstructorForAutobuild(constructor);
+
+                Object[] constructorParameters = calculateParameters(locator, resources, constructor.getParameterTypes(), constructor.getGenericParameterTypes(), constructor.getParameterAnnotations(), tracker);
+
+                Invokable<T> core = new ConstructorInvoker<T>(constructor, constructorParameters);
+
+                Invokable<T> wrapped = logger == null ? core : new LoggingInvokableWrapper<T>(logger, description, core);
+
+                ConstructionPlan<T> plan = new ConstructionPlan(tracker, description, wrapped);
+
+                extendPlanForInjectedFields(plan, tracker, locator, resources, constructor.getDeclaringClass());
+
+                extendPlanForPostInjectionMethods(plan, tracker, locator, resources, constructor.getDeclaringClass());
+
+                return plan;
+            }
+        });
+    }
+
+    private static <T> void extendPlanForInjectedFields(final ConstructionPlan<T> plan, OperationTracker tracker, final ObjectLocator locator, final InjectionResources resources, Class<T> instantiatedClass)
+    {
+        Class clazz = instantiatedClass;
+
+        while (clazz != Object.class)
+        {
+            Field[] fields = clazz.getDeclaredFields();
+
+            for (final Field f : fields)
+            {
+                // Ignore all static and final fields.
+
+                int fieldModifiers = f.getModifiers();
+
+                if (Modifier.isStatic(fieldModifiers) || Modifier.isFinal(fieldModifiers))
+                    continue;
+
+                final AnnotationProvider ap = new AnnotationProvider()
+                {
+                    public <T extends Annotation> T getAnnotation(Class<T> annotationClass)
+                    {
+                        return f.getAnnotation(annotationClass);
+                    }
+                };
+
+                String description = String.format("Calculating possible injection value for field %s.%s (%s)",
+                        clazz.getName(), f.getName(),
+                        PlasticUtils.toTypeName(f.getType()));
+
+                tracker.run(description, new Runnable()
+                {
+                    public void run()
+                    {
+                        final Class<?> fieldType = f.getType();
+
+                        InjectService is = ap.getAnnotation(InjectService.class);
+                        if (is != null)
+                        {
+                            addInjectPlan(plan, f, locator.getService(is.value(), fieldType));
+                            return;
+                        }
+
+                        if (ap.getAnnotation(Inject.class) != null || ap.getAnnotation(InjectResource.class) != null)
+                        {
+                            Object value = resources.findResource(fieldType, f.getGenericType());
+
+                            if (value != null)
+                            {
+                                addInjectPlan(plan, f, value);
+                                return;
+                            }
+
+                            addInjectPlan(plan, f, locator.getObject(fieldType, ap));
+                            return;
+                        }
+
+                        if (ap.getAnnotation(javax.inject.Inject.class) != null)
+                        {
+                            Named named = ap.getAnnotation(Named.class);
+
+                            if (named == null)
+                            {
+                                addInjectPlan(plan, f, locator.getObject(fieldType, ap));
+                            } else
+                            {
+                                addInjectPlan(plan, f, locator.getService(named.value(), fieldType));
+                            }
+
+                            return;
+                        }
+
+                        // Ignore fields that do not have the necessary annotation.
+
+                    }
+                });
+            }
+
+            clazz = clazz.getSuperclass();
+        }
+    }
+
+    private static <T> void addInjectPlan(ConstructionPlan<T> plan, final Field field, final Object injectedValue)
+    {
+        plan.add(new InitializationPlan<T>()
+        {
+            public String getDescription()
+            {
+                return String.format("Injecting %s into field %s of class %s.",
+                        injectedValue,
+                        field.getName(),
+                        field.getDeclaringClass().getName());
+            }
+
+            public void initialize(T instance)
+            {
+                inject(instance, field, injectedValue);
+            }
+        });
+    }
+
+    private static <T> void extendPlanForPostInjectionMethods(ConstructionPlan<T> plan, OperationTracker tracker, ObjectLocator locator, InjectionResources resources, Class<T> instantiatedClass)
+    {
+        for (Method m : instantiatedClass.getMethods())
+        {
+            if (m.getAnnotation(PostInjection.class) != null)
+            {
+                extendPlanForPostInjectionMethod(plan, tracker, locator, resources, m);
+            }
+        }
+    }
+
+    private static void extendPlanForPostInjectionMethod(final ConstructionPlan<?> plan, final OperationTracker tracker, final ObjectLocator locator, final InjectionResources resources, final Method method)
+    {
+        tracker.run("Computing parameters for post-injection method " + method,
+                new Runnable()
+                {
+                    public void run()
+                    {
+                        final Object[] parameters = InternalUtils.calculateParametersForMethod(method, locator,
+                                resources, tracker);
+
+                        plan.add(new InitializationPlan<Object>()
+                        {
+                            public String getDescription()
+                            {
+                                return "Invoking " + method;
+                            }
+
+                            public void initialize(Object instance)
+                            {
+                                Throwable fail = null;
+
+                                try
+                                {
+                                    method.invoke(instance, parameters);
+                                } catch (InvocationTargetException ex)
+                                {
+                                    fail = ex.getTargetException();
+                                } catch (Exception ex)
+                                {
+                                    fail = ex;
+                                }
+
+                                if (fail != null)
+                                {
+                                    throw new RuntimeException(String
+                                            .format("Exception invoking method %s: %s", method, toMessage(fail)), fail);
+                                }
+                            }
+                        });
+                    }
+                });
+    }
+
 }

Added: tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/util/LoggingInvokableWrapper.java
URL: http://svn.apache.org/viewvc/tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/util/LoggingInvokableWrapper.java?rev=1175103&view=auto
==============================================================================
--- tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/util/LoggingInvokableWrapper.java (added)
+++ tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/util/LoggingInvokableWrapper.java Sat Sep 24 04:51:55 2011
@@ -0,0 +1,44 @@
+// Copyright 2011 The Apache Software Foundation
+//
+// Licensed 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.tapestry5.ioc.internal.util;
+
+import org.apache.tapestry5.ioc.Invokable;
+import org.slf4j.Logger;
+
+/**
+ * @since 5.3
+ */
+public class LoggingInvokableWrapper<T> implements Invokable<T>
+{
+    private final Logger logger;
+
+    private final String message;
+
+    private final Invokable<T> delegate;
+
+    public LoggingInvokableWrapper(Logger logger, String message, Invokable<T> delegate)
+    {
+        this.logger = logger;
+        this.message = message;
+        this.delegate = delegate;
+    }
+
+    public T invoke()
+    {
+        logger.debug(message);
+
+        return delegate.invoke();
+    }
+}

Modified: tapestry/tapestry5/trunk/tapestry-ioc/src/main/resources/org/apache/tapestry5/ioc/internal/IOCStrings.properties
URL: http://svn.apache.org/viewvc/tapestry/tapestry5/trunk/tapestry-ioc/src/main/resources/org/apache/tapestry5/ioc/internal/IOCStrings.properties?rev=1175103&r1=1175102&r2=1175103&view=diff
==============================================================================
--- tapestry/tapestry5/trunk/tapestry-ioc/src/main/resources/org/apache/tapestry5/ioc/internal/IOCStrings.properties (original)
+++ tapestry/tapestry5/trunk/tapestry-ioc/src/main/resources/org/apache/tapestry5/ioc/internal/IOCStrings.properties Sat Sep 24 04:51:55 2011
@@ -20,7 +20,6 @@ decorator-method-wrong-return-type=Metho
 service-wrong-interface=Service '%s' implements interface %s, which is not compatible with the requested type %s.
 instantiate-builder-error=Unable to instantiate class %s as a module: %s
 builder-method-error=Error invoking service builder method %s (for service '%s'): %s
-constructor-error=Error invoking constructor %s (for service '%s'): %s
 builder-method-returned-null=Builder method %s (for service '%s') returned null.
 no-service-matches-type=No service implements the interface %s.
 many-service-matches=Service interface %s is matched by %d services: %s.  \

Modified: tapestry/tapestry5/trunk/tapestry-ioc/src/test/java/org/apache/tapestry5/ioc/IntegrationTest.java
URL: http://svn.apache.org/viewvc/tapestry/tapestry5/trunk/tapestry-ioc/src/test/java/org/apache/tapestry5/ioc/IntegrationTest.java?rev=1175103&r1=1175102&r2=1175103&view=diff
==============================================================================
--- tapestry/tapestry5/trunk/tapestry-ioc/src/test/java/org/apache/tapestry5/ioc/IntegrationTest.java (original)
+++ tapestry/tapestry5/trunk/tapestry-ioc/src/test/java/org/apache/tapestry5/ioc/IntegrationTest.java Sat Sep 24 04:51:55 2011
@@ -405,7 +405,7 @@ public class IntegrationTest extends IOC
         } catch (RuntimeException ex)
         {
             assertMessageContains(ex, "Error invoking constructor", "ExceptionInConstructorServiceImpl()",
-                    "for service 'Pingable'", "Yes, we have no tomatoes.");
+                    "Yes, we have no tomatoes.");
         }
 
         r.shutdown();
@@ -583,12 +583,9 @@ public class IntegrationTest extends IOC
         } catch (RuntimeException ex)
         {
             assertMessageContains(ex,
-                    "Error invoking constructor org.apache.tapestry5.ioc.FailInConstructorRunnable()",
+                    "Error invoking constructor",
+                    "org.apache.tapestry5.ioc.FailInConstructorRunnable()",
                     "Failure in Runnable constructor.");
-
-            // Like to check that the message includes the source location
-
-            assertTrue(ex.getMessage().matches(".*\\(at FailInConstructorRunnable.java:\\d+\\).*"));
         }
 
         r.shutdown();

Modified: tapestry/tapestry5/trunk/tapestry-ioc/src/test/java/org/apache/tapestry5/ioc/internal/DefaultModuleDefImplTest.java
URL: http://svn.apache.org/viewvc/tapestry/tapestry5/trunk/tapestry-ioc/src/test/java/org/apache/tapestry5/ioc/internal/DefaultModuleDefImplTest.java?rev=1175103&r1=1175102&r2=1175103&view=diff
==============================================================================
--- tapestry/tapestry5/trunk/tapestry-ioc/src/test/java/org/apache/tapestry5/ioc/internal/DefaultModuleDefImplTest.java (original)
+++ tapestry/tapestry5/trunk/tapestry-ioc/src/test/java/org/apache/tapestry5/ioc/internal/DefaultModuleDefImplTest.java Sat Sep 24 04:51:55 2011
@@ -29,7 +29,6 @@ import org.apache.tapestry5.ioc.services
 import org.apache.tapestry5.ioc.services.MethodSignature;
 import org.apache.tapestry5.ioc.services.PlasticProxyFactory;
 import org.apache.tapestry5.ioc.test.IOCTestCase;
-import static org.easymock.EasyMock.contains;
 import org.slf4j.Logger;
 import org.testng.annotations.AfterClass;
 import org.testng.annotations.BeforeClass;
@@ -40,6 +39,8 @@ import java.lang.reflect.Modifier;
 import java.util.List;
 import java.util.Set;
 
+import static org.easymock.EasyMock.contains;
+
 public class DefaultModuleDefImplTest extends IOCTestCase
 {
     private ClassFactory classFactory;
@@ -225,8 +226,7 @@ public class DefaultModuleDefImplTest ex
             new DefaultModuleDefImpl(ServiceIdConflictMethodModule.class, logger, proxyFactory);
 
             unreachable();
-        }
-        catch (RuntimeException ex)
+        } catch (RuntimeException ex)
         {
             assertMessageContains(
                     ex,
@@ -250,8 +250,7 @@ public class DefaultModuleDefImplTest ex
         {
             new DefaultModuleDefImpl(VoidBuilderMethodModule.class, logger, null);
             unreachable();
-        }
-        catch (RuntimeException ex)
+        } catch (RuntimeException ex)
         {
             assertEquals(ex.getMessage(), IOCMessages.buildMethodWrongReturnType(m));
         }
@@ -272,8 +271,7 @@ public class DefaultModuleDefImplTest ex
         {
             new DefaultModuleDefImpl(BuilderMethodModule.class, logger, null);
             unreachable();
-        }
-        catch (RuntimeException ex)
+        } catch (RuntimeException ex)
         {
             assertEquals(ex.getMessage(), IOCMessages.buildMethodWrongReturnType(m));
         }
@@ -299,8 +297,7 @@ public class DefaultModuleDefImplTest ex
         {
             new DefaultModuleDefImpl(moduleClass, logger, null);
             unreachable();
-        }
-        catch (RuntimeException ex)
+        } catch (RuntimeException ex)
         {
             assertEquals(ex.getMessage(), IOCMessages.decoratorMethodWrongReturnType(m));
         }
@@ -379,8 +376,7 @@ public class DefaultModuleDefImplTest ex
         {
             new DefaultModuleDefImpl(moduleClass, logger, null);
             unreachable();
-        }
-        catch (RuntimeException ex)
+        } catch (RuntimeException ex)
         {
             assertEquals(
                     ex.getMessage(),
@@ -404,8 +400,7 @@ public class DefaultModuleDefImplTest ex
         {
             new DefaultModuleDefImpl(moduleClass, logger, null);
             unreachable();
-        }
-        catch (RuntimeException ex)
+        } catch (RuntimeException ex)
         {
             assertEquals(
                     ex.getMessage(),
@@ -464,8 +459,7 @@ public class DefaultModuleDefImplTest ex
         {
             new DefaultModuleDefImpl(UninstantiableAutobuildServiceModule.class, logger, null);
             unreachable();
-        }
-        catch (RuntimeException ex)
+        } catch (RuntimeException ex)
         {
             assertMessageContains(
                     ex,
@@ -486,8 +480,7 @@ public class DefaultModuleDefImplTest ex
         {
             new DefaultModuleDefImpl(NonStaticBindMethodModule.class, logger, proxyFactory);
             unreachable();
-        }
-        catch (RuntimeException ex)
+        } catch (RuntimeException ex)
         {
             assertMessageContains(ex,
                     "Method org.apache.tapestry5.ioc.internal.NonStaticBindMethodModule.bind(ServiceBinder)",
@@ -505,11 +498,9 @@ public class DefaultModuleDefImplTest ex
 
         train_getTracker(resources, tracker);
 
-        train_isDebugEnabled(logger, true);
-
         // The point is, we're choosing the constructor with the largest number of parameters.
 
-        logger.debug(contains("Invoking constructor org.apache.tapestry5.ioc.internal.MultipleConstructorsAutobuildService(StringHolder)"));
+        logger.debug(contains("org.apache.tapestry5.ioc.internal.MultipleConstructorsAutobuildService(StringHolder)"));
 
         train_getServiceId(resources, "StringHolder");
         train_getLogger(resources, logger);
@@ -545,8 +536,7 @@ public class DefaultModuleDefImplTest ex
         {
             new DefaultModuleDefImpl(ExceptionInBindMethod.class, logger, proxyFactory);
             unreachable();
-        }
-        catch (RuntimeException ex)
+        } catch (RuntimeException ex)
         {
             assertTrue(ex.getMessage().matches(
                     "Error invoking service binder method org.apache.tapestry5.ioc.internal.ExceptionInBindMethod.bind\\(ServiceBinder\\) "