You are viewing a plain text version of this content. The canonical link for it is here.
Posted to dev@tapestry.apache.org by hl...@apache.org on 2011/02/11 12:57:33 UTC

svn commit: r1069763 - in /tapestry/tapestry5/trunk/tapestry-core/src: main/java/org/apache/tapestry5/internal/services/ main/java/org/apache/tapestry5/services/ test/java/org/apache/tapestry5/internal/services/ test/java/org/apache/tapestry5/internal/...

Author: hlship
Date: Fri Feb 11 11:57:32 2011
New Revision: 1069763

URL: http://svn.apache.org/viewvc?rev=1069763&view=rev
Log:
TAP5-1208: Shadow FieldConduit values to the adapted field when in development mode

Modified:
    tapestry/tapestry5/trunk/tapestry-core/src/main/java/org/apache/tapestry5/internal/services/ComponentClassTransformerImpl.java
    tapestry/tapestry5/trunk/tapestry-core/src/main/java/org/apache/tapestry5/internal/services/InternalClassTransformationImpl.java
    tapestry/tapestry5/trunk/tapestry-core/src/main/java/org/apache/tapestry5/services/TransformField.java
    tapestry/tapestry5/trunk/tapestry-core/src/test/java/org/apache/tapestry5/internal/services/InternalClassTransformationImplTest.java
    tapestry/tapestry5/trunk/tapestry-core/src/test/java/org/apache/tapestry5/internal/transform/ApplicationStateWorkerTest.java

Modified: tapestry/tapestry5/trunk/tapestry-core/src/main/java/org/apache/tapestry5/internal/services/ComponentClassTransformerImpl.java
URL: http://svn.apache.org/viewvc/tapestry/tapestry5/trunk/tapestry-core/src/main/java/org/apache/tapestry5/internal/services/ComponentClassTransformerImpl.java?rev=1069763&r1=1069762&r2=1069763&view=diff
==============================================================================
--- tapestry/tapestry5/trunk/tapestry-core/src/main/java/org/apache/tapestry5/internal/services/ComponentClassTransformerImpl.java (original)
+++ tapestry/tapestry5/trunk/tapestry-core/src/main/java/org/apache/tapestry5/internal/services/ComponentClassTransformerImpl.java Fri Feb 11 11:57:32 2011
@@ -1,4 +1,4 @@
-// Copyright 2006, 2007, 2008, 2010 The Apache Software Foundation
+// Copyright 2006, 2007, 2008, 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.
@@ -21,6 +21,7 @@ import javassist.CtClass;
 import javassist.CtConstructor;
 import javassist.NotFoundException;
 
+import org.apache.tapestry5.SymbolConstants;
 import org.apache.tapestry5.TapestryMarkers;
 import org.apache.tapestry5.internal.InternalConstants;
 import org.apache.tapestry5.internal.model.MutableComponentModelImpl;
@@ -28,6 +29,7 @@ import org.apache.tapestry5.ioc.LoggerSo
 import org.apache.tapestry5.ioc.OperationTracker;
 import org.apache.tapestry5.ioc.Resource;
 import org.apache.tapestry5.ioc.annotations.Primary;
+import org.apache.tapestry5.ioc.annotations.Symbol;
 import org.apache.tapestry5.ioc.internal.services.CtClassSource;
 import org.apache.tapestry5.ioc.internal.util.ClasspathResource;
 import org.apache.tapestry5.ioc.internal.util.CollectionFactory;
@@ -62,6 +64,8 @@ public class ComponentClassTransformerIm
 
     private final ComponentClassCache componentClassCache;
 
+    private final boolean developmentMode;
+
     private final OperationTracker tracker;
 
     private final String[] SUBPACKAGES =
@@ -87,6 +91,9 @@ public class ComponentClassTransformerIm
 
     ComponentClassCache componentClassCache,
 
+    @Symbol(SymbolConstants.PRODUCTION_MODE)
+    boolean productionMode,
+
     OperationTracker tracker)
     {
         this.workerChain = workerChain;
@@ -94,6 +101,7 @@ public class ComponentClassTransformerIm
         this.classFactory = classFactory;
         this.componentClassCache = componentClassCache;
         this.classSource = classSource;
+        this.developmentMode = !productionMode;
         this.tracker = tracker;
     }
 
@@ -184,7 +192,7 @@ public class ComponentClassTransformerIm
                         parentModel);
 
                 InternalClassTransformation transformation = parentTransformation == null ? new InternalClassTransformationImpl(
-                        classFactory, ctClass, componentClassCache, model, classSource)
+                        classFactory, ctClass, componentClassCache, model, classSource, developmentMode)
                         : parentTransformation.createChildTransformation(ctClass, model);
 
                 String transformerDescription = null;

Modified: tapestry/tapestry5/trunk/tapestry-core/src/main/java/org/apache/tapestry5/internal/services/InternalClassTransformationImpl.java
URL: http://svn.apache.org/viewvc/tapestry/tapestry5/trunk/tapestry-core/src/main/java/org/apache/tapestry5/internal/services/InternalClassTransformationImpl.java?rev=1069763&r1=1069762&r2=1069763&view=diff
==============================================================================
--- tapestry/tapestry5/trunk/tapestry-core/src/main/java/org/apache/tapestry5/internal/services/InternalClassTransformationImpl.java (original)
+++ tapestry/tapestry5/trunk/tapestry-core/src/main/java/org/apache/tapestry5/internal/services/InternalClassTransformationImpl.java Fri Feb 11 11:57:32 2011
@@ -1,4 +1,4 @@
-// Copyright 2006, 2007, 2008, 2009, 2010 The Apache Software Foundation
+// Copyright 2006, 2007, 2008, 2009, 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.
@@ -707,7 +707,22 @@ public final class InternalClassTransfor
             // this does nothing. but for primitive types, it will unwrap
             // the wrapper type back to a primitive.
 
-            addNewMethod(readSig, String.format("return ($r) ((%s) %s.get());", cast, conduitFieldName));
+            BodyBuilder builder = new BodyBuilder();
+
+            builder.begin();
+
+            builder.addln("%s result = ($r) ((%s) %s.get());", type, cast, conduitFieldName);
+
+            if (developmentMode)
+            {
+                builder.addln("%s = result;", name);
+            }
+
+            builder.addln("return result;");
+
+            builder.end();
+
+            addNewMethod(readSig, builder.toString());
 
             replaceReadAccess(readMethodName);
 
@@ -717,7 +732,18 @@ public final class InternalClassTransfor
                     new String[]
                     { type }, null);
 
-            addNewMethod(writeSig, String.format("%s.set(($w) $1);", conduitFieldName));
+            builder.clear().begin();
+
+            if (developmentMode)
+            {
+                builder.addln("%s = $1;", name);
+            }
+
+            builder.addln("%s.set(($w) $1);", conduitFieldName);
+
+            builder.end();
+
+            addNewMethod(writeSig, builder.toString());
 
             replaceWriteAccess(writeMethodName);
         }
@@ -782,6 +808,11 @@ public final class InternalClassTransfor
 
     private final CtClassSource classSource;
 
+    // In development mode, extra logic is inserted to "shadow" fields (that have been replaced with a FieldConduit).
+    // The "live" value is stored into the field any time it is read or updated, to assist with debugging.
+    // https://issues.apache.org/jira/browse/TAP5-1208
+    private final boolean developmentMode;
+
     // If true, then during finish, it is necessary to search for field replacements
     // (field reads or writes replaces with method calls).
     private boolean fieldAccessReplaced;
@@ -800,11 +831,13 @@ public final class InternalClassTransfor
      * This is a constructor for a base class.
      */
     public InternalClassTransformationImpl(ClassFactory classFactory, CtClass ctClass,
-            ComponentClassCache componentClassCache, MutableComponentModel componentModel, CtClassSource classSource)
+            ComponentClassCache componentClassCache, MutableComponentModel componentModel, CtClassSource classSource,
+            boolean developmentMode)
     {
         this.ctClass = ctClass;
         this.componentClassCache = componentClassCache;
         this.classSource = classSource;
+        this.developmentMode = developmentMode;
         classPool = this.ctClass.getClassPool();
         this.classFactory = classFactory;
         parentTransformation = null;
@@ -835,10 +868,13 @@ public final class InternalClassTransfor
 
     /**
      * Constructor for a component sub-class.
+     * 
+     * @param developmentMode
+     *            TODO
      */
     private InternalClassTransformationImpl(CtClass ctClass, InternalClassTransformation parentTransformation,
             ClassFactory classFactory, CtClassSource classSource, ComponentClassCache componentClassCache,
-            MutableComponentModel componentModel)
+            MutableComponentModel componentModel, boolean developmentMode)
     {
         this.ctClass = ctClass;
         this.componentClassCache = componentClassCache;
@@ -848,6 +884,7 @@ public final class InternalClassTransfor
         logger = componentModel.getLogger();
         this.parentTransformation = parentTransformation;
         this.componentModel = componentModel;
+        this.developmentMode = developmentMode;
 
         providerType = toCtClass(ComponentValueProvider.class);
 
@@ -869,7 +906,7 @@ public final class InternalClassTransfor
     public InternalClassTransformation createChildTransformation(CtClass childClass, MutableComponentModel childModel)
     {
         return new InternalClassTransformationImpl(childClass, this, classFactory, classSource, componentClassCache,
-                childModel);
+                childModel, developmentMode);
     }
 
     private void freeze()

Modified: tapestry/tapestry5/trunk/tapestry-core/src/main/java/org/apache/tapestry5/services/TransformField.java
URL: http://svn.apache.org/viewvc/tapestry/tapestry5/trunk/tapestry-core/src/main/java/org/apache/tapestry5/services/TransformField.java?rev=1069763&r1=1069762&r2=1069763&view=diff
==============================================================================
--- tapestry/tapestry5/trunk/tapestry-core/src/main/java/org/apache/tapestry5/services/TransformField.java (original)
+++ tapestry/tapestry5/trunk/tapestry-core/src/main/java/org/apache/tapestry5/services/TransformField.java Fri Feb 11 11:57:32 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.
@@ -63,25 +63,24 @@ public interface TransformField extends 
     void claim(Object tag);
 
     /**
-     * Replaces read and write field access with a conduit. The field will be deleted.
-     *
+     * Replaces read and write field access with a conduit. 
+     * 
      * @param conduitProvider
      *            provides the actual conduit at class instantiation time
      */
     void replaceAccess(ComponentValueProvider<FieldValueConduit> conduitProvider);
 
     /**
-     * Replaces read and write field access with a conduit. The field itself will be deleted.
-     *
+     * Replaces read and write field access with a conduit. 
+     * 
      * @param conduitField
      *            identifies the field containing (via injection) an instance of {@link FieldValueConduit}
      */
     void replaceAccess(TransformField conduitField);
 
     /**
-     * Replaces read and write field access with a conduit. A new field is created for the conduit instance,
-     * and the original field is deleted.
-     *
+     * Replaces read and write field access with a conduit. A new field is created for the conduit instance.
+     * 
      * @param conduit
      *            used to replace read and write access to the field
      */

Modified: tapestry/tapestry5/trunk/tapestry-core/src/test/java/org/apache/tapestry5/internal/services/InternalClassTransformationImplTest.java
URL: http://svn.apache.org/viewvc/tapestry/tapestry5/trunk/tapestry-core/src/test/java/org/apache/tapestry5/internal/services/InternalClassTransformationImplTest.java?rev=1069763&r1=1069762&r2=1069763&view=diff
==============================================================================
--- tapestry/tapestry5/trunk/tapestry-core/src/test/java/org/apache/tapestry5/internal/services/InternalClassTransformationImplTest.java (original)
+++ tapestry/tapestry5/trunk/tapestry-core/src/test/java/org/apache/tapestry5/internal/services/InternalClassTransformationImplTest.java Fri Feb 11 11:57:32 2011
@@ -1,4 +1,4 @@
-// Copyright 2006, 2007, 2008, 2010 The Apache Software Foundation
+// Copyright 2006, 2007, 2008, 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.
@@ -41,7 +41,17 @@ import org.apache.tapestry5.internal.mod
 import org.apache.tapestry5.internal.test.InternalBaseTestCase;
 import org.apache.tapestry5.internal.transform.InheritedAnnotation;
 import org.apache.tapestry5.internal.transform.TestPackageAwareLoader;
-import org.apache.tapestry5.internal.transform.pages.*;
+import org.apache.tapestry5.internal.transform.pages.AbstractFoo;
+import org.apache.tapestry5.internal.transform.pages.BarImpl;
+import org.apache.tapestry5.internal.transform.pages.ChildClassInheritsAnnotation;
+import org.apache.tapestry5.internal.transform.pages.ClaimedFields;
+import org.apache.tapestry5.internal.transform.pages.EventHandlerTarget;
+import org.apache.tapestry5.internal.transform.pages.FieldAccessBean;
+import org.apache.tapestry5.internal.transform.pages.MethodAccessSubject;
+import org.apache.tapestry5.internal.transform.pages.MethodIdentifier;
+import org.apache.tapestry5.internal.transform.pages.ParentClass;
+import org.apache.tapestry5.internal.transform.pages.ReadOnlyBean;
+import org.apache.tapestry5.internal.transform.pages.TargetObject;
 import org.apache.tapestry5.ioc.internal.services.ClassFactoryClassPool;
 import org.apache.tapestry5.ioc.internal.services.ClassFactoryImpl;
 import org.apache.tapestry5.ioc.internal.services.CtClassSourceImpl;
@@ -134,7 +144,7 @@ public class InternalClassTransformation
         replay();
 
         InternalClassTransformation ct = new InternalClassTransformationImpl(classFactory, targetObjectCtClass,
-                new ComponentClassCacheImpl(classFactory, null), model, classSource);
+                new ComponentClassCacheImpl(classFactory, null), model, classSource, false);
 
         worker.transform(ct, model);
 
@@ -223,7 +233,7 @@ public class InternalClassTransformation
 
         MutableComponentModel model = stubMutableComponentModel(logger);
 
-        return new InternalClassTransformationImpl(classFactory, ctClass, null, model, null);
+        return new InternalClassTransformationImpl(classFactory, ctClass, null, model, null, false);
     }
 
     private MutableComponentModel stubMutableComponentModel(Logger logger)
@@ -722,7 +732,7 @@ public class InternalClassTransformation
         replay();
 
         InternalClassTransformation ct = new InternalClassTransformationImpl(classFactory, targetObjectCtClass, null,
-                model, null);
+                model, null, false);
 
         // Default behavior is to add an injected field for the InternalComponentResources object,
         // so we'll just check that.
@@ -751,7 +761,7 @@ public class InternalClassTransformation
         CtClass targetObjectCtClass = findCtClass(ReadOnlyBean.class);
 
         InternalClassTransformation ct = new InternalClassTransformationImpl(classFactory, targetObjectCtClass, null,
-                model, null);
+                model, null, false);
 
         ct.makeReadOnly("_value");
 
@@ -788,7 +798,7 @@ public class InternalClassTransformation
         CtClass targetObjectCtClass = findCtClass(ReadOnlyBean.class);
 
         InternalClassTransformation ct = new InternalClassTransformationImpl(classFactory, targetObjectCtClass, null,
-                model, null);
+                model, null, false);
 
         ct.injectField("_value", "Tapestry");
 
@@ -831,7 +841,7 @@ public class InternalClassTransformation
         CtClass targetObjectCtClass = findCtClass(FieldAccessBean.class);
 
         InternalClassTransformation ct = new InternalClassTransformationImpl(classFactory, targetObjectCtClass, null,
-                model, null);
+                model, null, false);
 
         replaceAccessToField(ct, "foo");
         replaceAccessToField(ct, "bar");

Modified: tapestry/tapestry5/trunk/tapestry-core/src/test/java/org/apache/tapestry5/internal/transform/ApplicationStateWorkerTest.java
URL: http://svn.apache.org/viewvc/tapestry/tapestry5/trunk/tapestry-core/src/test/java/org/apache/tapestry5/internal/transform/ApplicationStateWorkerTest.java?rev=1069763&r1=1069762&r2=1069763&view=diff
==============================================================================
--- tapestry/tapestry5/trunk/tapestry-core/src/test/java/org/apache/tapestry5/internal/transform/ApplicationStateWorkerTest.java (original)
+++ tapestry/tapestry5/trunk/tapestry-core/src/test/java/org/apache/tapestry5/internal/transform/ApplicationStateWorkerTest.java Fri Feb 11 11:57:32 2011
@@ -1,10 +1,10 @@
-// Copyright 2007, 2008 The Apache Software Foundation
+// Copyright 2007, 2008, 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
+// 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,
@@ -61,7 +61,7 @@ public class ApplicationStateWorkerTest 
     @BeforeMethod
     public void setup_classpool()
     {
-        //  _classPool = new ClassPool();
+        // _classPool = new ClassPool();
 
         classFactoryClassPool = new ClassFactoryClassPool(contextClassLoader);
 
@@ -113,7 +113,7 @@ public class ApplicationStateWorkerTest 
         replay();
 
         InternalClassTransformation transformation = new InternalClassTransformationImpl(classFactory, ctClass, null,
-                                                                                         model, null);
+                model, null, false);
         new ApplicationStateWorker(manager, cache).transform(transformation, model);
 
         verify();
@@ -159,7 +159,6 @@ public class ApplicationStateWorkerTest 
         verify();
     }
 
-
     @Test
     public void read_field_with_create_disabled() throws Exception
     {
@@ -180,7 +179,7 @@ public class ApplicationStateWorkerTest 
         replay();
 
         InternalClassTransformation transformation = new InternalClassTransformationImpl(classFactory, ctClass, null,
-                                                                                         model, null);
+                model, null, false);
         new ApplicationStateWorker(manager, cache).transform(transformation, model);
 
         verify();
@@ -201,7 +200,6 @@ public class ApplicationStateWorkerTest 
 
         verify();
 
-
         Object aso = new SimpleASO();
 
         train_getIfExists(manager, asoClass, aso);