You are viewing a plain text version of this content. The canonical link for it is here.
Posted to dev@tapestry.apache.org by jk...@apache.org on 2006/05/10 17:20:02 UTC

svn commit: r405773 - in /tapestry/tapestry4/trunk: ./ framework/src/descriptor/META-INF/ framework/src/java/org/apache/tapestry/enhance/ framework/src/test/org/apache/tapestry/engine/ framework/src/test/org/apache/tapestry/enhance/ framework/src/test/...

Author: jkuhnert
Date: Wed May 10 08:19:53 2006
New Revision: 405773

URL: http://svn.apache.org/viewcvs?rev=405773&view=rev
Log:
Applied patches for #TAPESTRY-917, fixed broken unit tests

Added:
    tapestry/tapestry4/trunk/framework/src/java/org/apache/tapestry/enhance/AutowireWorker.java   (with props)
    tapestry/tapestry4/trunk/framework/src/java/org/apache/tapestry/enhance/AutowireWorkerFactory.java   (with props)
    tapestry/tapestry4/trunk/framework/src/test/org/apache/tapestry/enhance/HelloService.java   (with props)
    tapestry/tapestry4/trunk/framework/src/test/org/apache/tapestry/enhance/HelloServiceImpl.java   (with props)
    tapestry/tapestry4/trunk/framework/src/test/org/apache/tapestry/enhance/TestAutowireWorker.java   (with props)
    tapestry/tapestry4/trunk/framework/src/test/org/apache/tapestry/enhance/autowire-multiple.xml   (with props)
    tapestry/tapestry4/trunk/framework/src/test/org/apache/tapestry/enhance/autowire-single.xml   (with props)
Modified:
    tapestry/tapestry4/trunk/framework/src/descriptor/META-INF/tapestry.enhance.xml
    tapestry/tapestry4/trunk/framework/src/java/org/apache/tapestry/enhance/EnhanceMessages.java
    tapestry/tapestry4/trunk/framework/src/java/org/apache/tapestry/enhance/EnhanceStrings.properties
    tapestry/tapestry4/trunk/framework/src/java/org/apache/tapestry/enhance/EnhancementOperation.java
    tapestry/tapestry4/trunk/framework/src/java/org/apache/tapestry/enhance/EnhancementOperationImpl.java
    tapestry/tapestry4/trunk/framework/src/test/org/apache/tapestry/engine/EngineServiceLinkTest.java
    tapestry/tapestry4/trunk/framework/src/test/org/apache/tapestry/enhance/TestEnhancementOperation.java
    tapestry/tapestry4/trunk/framework/src/test/org/apache/tapestry/util/io/Basic.txt
    tapestry/tapestry4/trunk/framework/src/test/org/apache/tapestry/util/io/NoAscii.txt
    tapestry/tapestry4/trunk/framework/src/test/org/apache/tapestry/util/io/NoOffset.txt
    tapestry/tapestry4/trunk/framework/src/test/org/apache/tapestry/util/io/Options.txt
    tapestry/tapestry4/trunk/framework/src/test/org/apache/tapestry/util/io/TestBinaryDumpOutputStream.java
    tapestry/tapestry4/trunk/status.xml

Modified: tapestry/tapestry4/trunk/framework/src/descriptor/META-INF/tapestry.enhance.xml
URL: http://svn.apache.org/viewcvs/tapestry/tapestry4/trunk/framework/src/descriptor/META-INF/tapestry.enhance.xml?rev=405773&r1=405772&r2=405773&view=diff
==============================================================================
--- tapestry/tapestry4/trunk/framework/src/descriptor/META-INF/tapestry.enhance.xml (original)
+++ tapestry/tapestry4/trunk/framework/src/descriptor/META-INF/tapestry.enhance.xml Wed May 10 08:19:53 2006
@@ -62,6 +62,19 @@
        
   </configuration-point>
   
+  <service-point id="AutowireWorkerFactory" interface="org.apache.hivemind.ServiceImplementationFactory" parameters-occurs="none">
+    Constructs AutowireWorker.
+    <invoke-factory>
+      <construct class="org.apache.tapestry.enhance.AutowireWorkerFactory" />
+    </invoke-factory>
+  </service-point>
+
+  <service-point id="AutowireWorker" interface="org.apache.tapestry.enhance.EnhancementWorker">
+    Automatically injects HiveMind service objects into read-only properties if exactly
+    one HiveMind service point is compatible with the property type.
+    <invoke-factory service-id="AutowireWorkerFactory" />
+  </service-point>
+  
   <contribution configuration-id="EnhancementWorkers">
     
     <!-- These can actually run in any order, as long as abstract-property runs later. -->
@@ -74,6 +87,11 @@
     <command id="inject-component" object="service:InjectComponentWorker" before="abstract-property"/>
     <command id="inject-bean" object="service:InjectBeanWorker" before="abstract-property"/>
     <command id="inject-asset" object="service:InjectAssetWorker" before="abstract-property"/>
+    <command 
+      id="inject-autowire" 
+      object="service:AutowireWorker" 
+      before="tapestry.enhance.abstract-property"
+      after="tapestry.enhance.inject-messages,tapestry.enhance.inject-specification,tapestry.enhance.specified-property,tapestry.enhance.parameter,tapestry.enhance.dispatch-inject,tapestry.enhance.inject-component,tapestry.enhance.inject-bean,tapestry.enhance.inject-asset"/>
     
     <!-- After all the previous workers have had their chance, we "fill in" any unclaimed properties
          as transient page properties. -->

Added: tapestry/tapestry4/trunk/framework/src/java/org/apache/tapestry/enhance/AutowireWorker.java
URL: http://svn.apache.org/viewcvs/tapestry/tapestry4/trunk/framework/src/java/org/apache/tapestry/enhance/AutowireWorker.java?rev=405773&view=auto
==============================================================================
--- tapestry/tapestry4/trunk/framework/src/java/org/apache/tapestry/enhance/AutowireWorker.java (added)
+++ tapestry/tapestry4/trunk/framework/src/java/org/apache/tapestry/enhance/AutowireWorker.java Wed May 10 08:19:53 2006
@@ -0,0 +1,67 @@
+// Copyright 2005 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.tapestry.enhance;
+
+import java.util.Iterator;
+import java.util.List;
+
+import org.apache.commons.logging.Log;
+import org.apache.hivemind.Location;
+import org.apache.hivemind.internal.Module;
+import org.apache.tapestry.spec.IComponentSpecification;
+
+/**
+ * An enhancement worker which automatically injects HiveMind services
+ * into pages/components if exactly one service point exists which is
+ * compatible with the read-only property's type.
+ * 
+ * @author James Carman
+ * @version 1.0
+ */
+public class AutowireWorker implements EnhancementWorker
+{
+    private final Log _log;
+    private final Module _module;
+
+    public AutowireWorker( Module module, Log log )
+    {
+        this._module = module;
+        this._log = log;
+    }
+
+    public void performEnhancement( EnhancementOperation op, IComponentSpecification spec )
+    {
+        final List propertyNames = op.findUnclaimedAbstractProperties();
+        for( Iterator i = propertyNames.iterator(); i.hasNext(); ) {
+            String propertyName = ( String ) i.next();
+            
+            Class propertyType = op.getPropertyType( propertyName );
+            if( propertyType == null )
+                propertyType = Object.class;
+            
+            if (!op.canClaimAsReadOnlyProperty(propertyName))
+                continue;
+            
+            if( _module.containsService( propertyType )) {
+                final Object serviceProxy = _module.getService( propertyType );
+                final Location location = spec.getLocation();
+                _log.debug( EnhanceMessages.autowiring( propertyName, spec, serviceProxy ) );
+                final String fieldName = op.addInjectedField( "_$" + propertyName, propertyType, serviceProxy );
+                EnhanceUtils.createSimpleAccessor( op, fieldName, propertyName, propertyType, location );
+                op.claimReadonlyProperty( propertyName );
+            }
+
+        }
+    }
+}

Propchange: tapestry/tapestry4/trunk/framework/src/java/org/apache/tapestry/enhance/AutowireWorker.java
------------------------------------------------------------------------------
    svn:executable = *

Added: tapestry/tapestry4/trunk/framework/src/java/org/apache/tapestry/enhance/AutowireWorkerFactory.java
URL: http://svn.apache.org/viewcvs/tapestry/tapestry4/trunk/framework/src/java/org/apache/tapestry/enhance/AutowireWorkerFactory.java?rev=405773&view=auto
==============================================================================
--- tapestry/tapestry4/trunk/framework/src/java/org/apache/tapestry/enhance/AutowireWorkerFactory.java (added)
+++ tapestry/tapestry4/trunk/framework/src/java/org/apache/tapestry/enhance/AutowireWorkerFactory.java Wed May 10 08:19:53 2006
@@ -0,0 +1,33 @@
+// Copyright 2005 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.tapestry.enhance;
+
+import org.apache.hivemind.ServiceImplementationFactory;
+import org.apache.hivemind.ServiceImplementationFactoryParameters;
+
+/**
+ * Constructs {@link AutowireWorker}s.  This is necessary because the
+ * {@link AutowireWorker} must have its HiveMind module injected into it.
+ * 
+ * @author James Carman
+ * @version 1.0
+ */
+public class AutowireWorkerFactory implements ServiceImplementationFactory
+{
+    public Object createCoreServiceImplementation(
+            ServiceImplementationFactoryParameters params )
+    {
+        return new AutowireWorker( params.getInvokingModule(), params.getLog() );
+    }
+}

Propchange: tapestry/tapestry4/trunk/framework/src/java/org/apache/tapestry/enhance/AutowireWorkerFactory.java
------------------------------------------------------------------------------
    svn:executable = *

Modified: tapestry/tapestry4/trunk/framework/src/java/org/apache/tapestry/enhance/EnhanceMessages.java
URL: http://svn.apache.org/viewcvs/tapestry/tapestry4/trunk/framework/src/java/org/apache/tapestry/enhance/EnhanceMessages.java?rev=405773&r1=405772&r2=405773&view=diff
==============================================================================
--- tapestry/tapestry4/trunk/framework/src/java/org/apache/tapestry/enhance/EnhanceMessages.java (original)
+++ tapestry/tapestry4/trunk/framework/src/java/org/apache/tapestry/enhance/EnhanceMessages.java Wed May 10 08:19:53 2006
@@ -22,6 +22,7 @@
 import org.apache.hivemind.service.ClassFabUtils;
 import org.apache.hivemind.service.MethodSignature;
 import org.apache.tapestry.Tapestry;
+import org.apache.tapestry.spec.IComponentSpecification;
 
 /**
  * Messages for this package.
@@ -157,5 +158,10 @@
     static String mustBeBoolean(String propertyName)
     {
         return _formatter.format("must-be-boolean", propertyName);
+    }
+    
+    static String autowiring( String propertyName, IComponentSpecification spec, Object proxy )
+    {
+        return _formatter.format( "autowiring", propertyName, spec.getDescription(), proxy );
     }
 }

Modified: tapestry/tapestry4/trunk/framework/src/java/org/apache/tapestry/enhance/EnhanceStrings.properties
URL: http://svn.apache.org/viewcvs/tapestry/tapestry4/trunk/framework/src/java/org/apache/tapestry/enhance/EnhanceStrings.properties?rev=405773&r1=405772&r2=405773&view=diff
==============================================================================
--- tapestry/tapestry4/trunk/framework/src/java/org/apache/tapestry/enhance/EnhanceStrings.properties (original)
+++ tapestry/tapestry4/trunk/framework/src/java/org/apache/tapestry/enhance/EnhanceStrings.properties Wed May 10 08:19:53 2006
@@ -31,3 +31,4 @@
 method-conflict=A new implementation of method ''{0}'' conflicts with an existing implementation (at {1}).
 readonly-property=Property {0} should be read-only; remove method {1}.
 must-be-boolean=Property {0} must be type boolean for this type of injection.
+autowiring=Autowiring property {0} for component {1} to {2}.

Modified: tapestry/tapestry4/trunk/framework/src/java/org/apache/tapestry/enhance/EnhancementOperation.java
URL: http://svn.apache.org/viewcvs/tapestry/tapestry4/trunk/framework/src/java/org/apache/tapestry/enhance/EnhancementOperation.java?rev=405773&r1=405772&r2=405773&view=diff
==============================================================================
--- tapestry/tapestry4/trunk/framework/src/java/org/apache/tapestry/enhance/EnhancementOperation.java (original)
+++ tapestry/tapestry4/trunk/framework/src/java/org/apache/tapestry/enhance/EnhancementOperation.java Wed May 10 08:19:53 2006
@@ -52,7 +52,17 @@
      */
 
     void claimReadonlyProperty(String propertyName);
-
+    
+    /**
+     * Checks to see if the specified property can be claimed as read only. 
+     * 
+     * @param propertyName
+     *          The property to check.
+     * @return True, if no setter method has been created for the specified property and
+     *          the property hasn't been claimed by someone else.
+     */
+    boolean canClaimAsReadOnlyProperty(String propertyName);
+    
     /**
      * Returns a list of the names of existing properties that are not claimed
      * and which have abstract accessor methods.

Modified: tapestry/tapestry4/trunk/framework/src/java/org/apache/tapestry/enhance/EnhancementOperationImpl.java
URL: http://svn.apache.org/viewcvs/tapestry/tapestry4/trunk/framework/src/java/org/apache/tapestry/enhance/EnhancementOperationImpl.java?rev=405773&r1=405772&r2=405773&view=diff
==============================================================================
--- tapestry/tapestry4/trunk/framework/src/java/org/apache/tapestry/enhance/EnhancementOperationImpl.java (original)
+++ tapestry/tapestry4/trunk/framework/src/java/org/apache/tapestry/enhance/EnhancementOperationImpl.java Wed May 10 08:19:53 2006
@@ -249,13 +249,28 @@
 
         _claimedProperties.add(propertyName);
     }
+    
+    /** 
+     * {@inheritDoc}
+     */
+    public boolean canClaimAsReadOnlyProperty(String propertyName)
+    {
+        if(_claimedProperties.contains(propertyName)) 
+            return false;
+        
+        PropertyDescriptor pd = getPropertyDescriptor(propertyName);
+        
+        if (pd == null) return false;
+        
+        return pd.getWriteMethod() == null ? true : false;
+    }
 
     public void claimReadonlyProperty(String propertyName)
     {
         claimProperty(propertyName);
-
+        
         PropertyDescriptor pd = getPropertyDescriptor(propertyName);
-
+        
         if (pd != null && pd.getWriteMethod() != null)
             throw new ApplicationRuntimeException(EnhanceMessages
                     .readonlyProperty(propertyName, pd.getWriteMethod()));
@@ -347,8 +362,8 @@
                 .propertyTypeMismatch(_baseClass, name, propertyType,
                         expectedType));
     }
-
-    private PropertyDescriptor getPropertyDescriptor(String name)
+    
+    PropertyDescriptor getPropertyDescriptor(String name)
     {
         return (PropertyDescriptor) _properties.get(name);
     }

Modified: tapestry/tapestry4/trunk/framework/src/test/org/apache/tapestry/engine/EngineServiceLinkTest.java
URL: http://svn.apache.org/viewcvs/tapestry/tapestry4/trunk/framework/src/test/org/apache/tapestry/engine/EngineServiceLinkTest.java?rev=405773&r1=405772&r2=405773&view=diff
==============================================================================
--- tapestry/tapestry4/trunk/framework/src/test/org/apache/tapestry/engine/EngineServiceLinkTest.java (original)
+++ tapestry/tapestry4/trunk/framework/src/test/org/apache/tapestry/engine/EngineServiceLinkTest.java Wed May 10 08:19:53 2006
@@ -155,18 +155,18 @@
         EngineServiceLink l = new EngineServiceLink(rc, "/ctx/app", ENCODING, _urlCodec, request,
                 buildParameters("myservice", null), false);
 
+        trainGetServerPort(request, 9187);
+        
         trainGetScheme(request, "HTTP");
-
+        
         trainGetServerName(request, "TESTSERVER.COM");
-
-        trainGetServerPort(request, 9187);
-
+        
         trainEncodeURL(rc, 
         		"HTTP://TESTSERVER.COM:9187/ctx/app?service=myservice", 
         		"HTTP://TESTSERVER.COM:9187/ctx/app?service=myservice");
         
         replayControls();
-
+        
         assertEquals("HTTP://TESTSERVER.COM:9187/ctx/app?service=myservice", l.getAbsoluteURL());
 
         verifyControls();

Added: tapestry/tapestry4/trunk/framework/src/test/org/apache/tapestry/enhance/HelloService.java
URL: http://svn.apache.org/viewcvs/tapestry/tapestry4/trunk/framework/src/test/org/apache/tapestry/enhance/HelloService.java?rev=405773&view=auto
==============================================================================
--- tapestry/tapestry4/trunk/framework/src/test/org/apache/tapestry/enhance/HelloService.java (added)
+++ tapestry/tapestry4/trunk/framework/src/test/org/apache/tapestry/enhance/HelloService.java Wed May 10 08:19:53 2006
@@ -0,0 +1,24 @@
+// Copyright 2006 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.tapestry.enhance;
+
+
+/**
+ * @author James Carman
+ *
+ */
+public interface HelloService
+{
+    public String sayHello( String name );
+}

Propchange: tapestry/tapestry4/trunk/framework/src/test/org/apache/tapestry/enhance/HelloService.java
------------------------------------------------------------------------------
    svn:executable = *

Added: tapestry/tapestry4/trunk/framework/src/test/org/apache/tapestry/enhance/HelloServiceImpl.java
URL: http://svn.apache.org/viewcvs/tapestry/tapestry4/trunk/framework/src/test/org/apache/tapestry/enhance/HelloServiceImpl.java?rev=405773&view=auto
==============================================================================
--- tapestry/tapestry4/trunk/framework/src/test/org/apache/tapestry/enhance/HelloServiceImpl.java (added)
+++ tapestry/tapestry4/trunk/framework/src/test/org/apache/tapestry/enhance/HelloServiceImpl.java Wed May 10 08:19:53 2006
@@ -0,0 +1,27 @@
+// Copyright 2006 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.tapestry.enhance;
+
+
+/**
+ * @author James Carman
+ *
+ */
+public class HelloServiceImpl implements HelloService
+{
+    public String sayHello( String name )
+    {
+        return "Hello, " + name + "!";
+    }
+}

Propchange: tapestry/tapestry4/trunk/framework/src/test/org/apache/tapestry/enhance/HelloServiceImpl.java
------------------------------------------------------------------------------
    svn:executable = *

Added: tapestry/tapestry4/trunk/framework/src/test/org/apache/tapestry/enhance/TestAutowireWorker.java
URL: http://svn.apache.org/viewcvs/tapestry/tapestry4/trunk/framework/src/test/org/apache/tapestry/enhance/TestAutowireWorker.java?rev=405773&view=auto
==============================================================================
--- tapestry/tapestry4/trunk/framework/src/test/org/apache/tapestry/enhance/TestAutowireWorker.java (added)
+++ tapestry/tapestry4/trunk/framework/src/test/org/apache/tapestry/enhance/TestAutowireWorker.java Wed May 10 08:19:53 2006
@@ -0,0 +1,116 @@
+// Copyright May 2, 2006 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.tapestry.enhance;
+
+import java.lang.reflect.Modifier;
+import java.util.Collections;
+
+import org.apache.hivemind.Location;
+import org.apache.hivemind.Registry;
+import org.apache.hivemind.impl.RegistryBuilder;
+import org.apache.hivemind.service.MethodSignature;
+import org.apache.tapestry.spec.IComponentSpecification;
+import org.easymock.MockControl;
+
+
+/**
+ * 
+ * @author James Carman
+ *
+ */
+public class TestAutowireWorker extends BaseEnhancementTestCase
+{
+
+    private static final String HELLO_SERVICE_PROPERTY = "helloService";
+
+    public void testWithNoService() throws Exception
+    {
+        assertNotAutowired( RegistryBuilder.constructDefaultRegistry() );
+    }
+    
+    public void testWithManyServices() throws Exception
+    {        
+        assertNotAutowired( buildFrameworkRegistry("autowire-multiple.xml" ) );   
+    }
+    
+    public void testWithOneService() throws Exception
+    {
+        final Registry registry = buildFrameworkRegistry("autowire-single.xml" );
+        Location l = newLocation();
+        MockControl opControl = newControl(EnhancementOperation.class);
+        EnhancementOperation op = (EnhancementOperation) opControl.getMock();
+        
+        op.findUnclaimedAbstractProperties();
+        opControl.setReturnValue( Collections.singletonList( HELLO_SERVICE_PROPERTY ) );
+        
+        op.getPropertyType( HELLO_SERVICE_PROPERTY );
+        opControl.setReturnValue( HelloService.class );
+        
+        op.canClaimAsReadOnlyProperty(HELLO_SERVICE_PROPERTY);
+        opControl.setReturnValue(true);
+        
+        MockControl specControl = newControl( IComponentSpecification.class );
+        IComponentSpecification spec = ( IComponentSpecification )specControl.getMock();
+        
+        spec.getLocation();
+        specControl.setReturnValue( l );
+        
+        spec.getDescription();
+        specControl.setReturnValue( "Component1" );
+        
+        final String fieldName = "_$" + HELLO_SERVICE_PROPERTY;
+        final HelloService proxy = ( HelloService )registry.getService( HelloService.class );
+        
+        op.addInjectedField( fieldName, HelloService.class, proxy );
+        opControl.setReturnValue( fieldName );
+        
+        op.getAccessorMethodName( HELLO_SERVICE_PROPERTY );
+        opControl.setReturnValue( "getHelloService" );
+        
+        op.addMethod(Modifier.PUBLIC, new MethodSignature(HelloService.class, "getHelloService", null,
+                null), "return " + fieldName + ";", l);
+        op.claimReadonlyProperty( HELLO_SERVICE_PROPERTY );
+        opControl.setVoidCallable();
+        
+        replayControls();
+        
+        final EnhancementWorker worker = ( EnhancementWorker )registry.getService( "tapestry.enhance.AutowireWorker", EnhancementWorker.class );
+        worker.performEnhancement( op, spec );
+        
+        verifyControls();
+    }
+    
+    private void assertNotAutowired( Registry registry )
+    {
+        MockControl opControl = newControl(EnhancementOperation.class);
+        EnhancementOperation op = (EnhancementOperation) opControl.getMock();
+        
+        op.findUnclaimedAbstractProperties();
+        opControl.setReturnValue( Collections.singletonList( HELLO_SERVICE_PROPERTY ) );
+        
+        op.getPropertyType( HELLO_SERVICE_PROPERTY );
+        opControl.setReturnValue( HelloService.class );
+        
+        op.canClaimAsReadOnlyProperty(HELLO_SERVICE_PROPERTY);
+        opControl.setReturnValue(true);
+        
+        replayControls();
+        
+        final EnhancementWorker worker = ( EnhancementWorker )registry.getService( "tapestry.enhance.AutowireWorker", EnhancementWorker.class );
+        worker.performEnhancement( op, null);
+        
+        verifyControls();
+    }
+    
+}

Propchange: tapestry/tapestry4/trunk/framework/src/test/org/apache/tapestry/enhance/TestAutowireWorker.java
------------------------------------------------------------------------------
    svn:executable = *

Modified: tapestry/tapestry4/trunk/framework/src/test/org/apache/tapestry/enhance/TestEnhancementOperation.java
URL: http://svn.apache.org/viewcvs/tapestry/tapestry4/trunk/framework/src/test/org/apache/tapestry/enhance/TestEnhancementOperation.java?rev=405773&r1=405772&r2=405773&view=diff
==============================================================================
--- tapestry/tapestry4/trunk/framework/src/test/org/apache/tapestry/enhance/TestEnhancementOperation.java (original)
+++ tapestry/tapestry4/trunk/framework/src/test/org/apache/tapestry/enhance/TestEnhancementOperation.java Wed May 10 08:19:53 2006
@@ -127,11 +127,15 @@
 
         replayControls();
 
-        EnhancementOperation eo = new EnhancementOperationImpl(new DefaultClassResolver(), spec,
+        EnhancementOperationImpl eo = new EnhancementOperationImpl(new DefaultClassResolver(), spec,
                 BaseComponent.class, cf, null);
-
+        
+        assertFalse(eo.canClaimAsReadOnlyProperty("foo"));
+        
         eo.claimReadonlyProperty("foo");
-
+        
+        assertFalse(eo.canClaimAsReadOnlyProperty("foo"));
+        
         verifyControls();
     }
 

Added: tapestry/tapestry4/trunk/framework/src/test/org/apache/tapestry/enhance/autowire-multiple.xml
URL: http://svn.apache.org/viewcvs/tapestry/tapestry4/trunk/framework/src/test/org/apache/tapestry/enhance/autowire-multiple.xml?rev=405773&view=auto
==============================================================================
--- tapestry/tapestry4/trunk/framework/src/test/org/apache/tapestry/enhance/autowire-multiple.xml (added)
+++ tapestry/tapestry4/trunk/framework/src/test/org/apache/tapestry/enhance/autowire-multiple.xml Wed May 10 08:19:53 2006
@@ -0,0 +1,31 @@
+<?xml version="1.0"?>
+<!-- 
+   Copyright 2006 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.
+-->
+
+<module id="autowire.multiple" version="1.0.0">
+  <service-point id="Hello1" interface="org.apache.tapestry.enhance.HelloService">
+    <invoke-factory>
+      <construct class="org.apache.tapestry.enhance.HelloServiceImpl" />
+    </invoke-factory>
+  </service-point>
+
+  <service-point id="Hello2" interface="org.apache.tapestry.enhance.HelloService">
+    <invoke-factory>
+      <construct class="org.apache.tapestry.enhance.HelloServiceImpl" />
+    </invoke-factory>
+  </service-point>
+
+</module>
\ No newline at end of file

Propchange: tapestry/tapestry4/trunk/framework/src/test/org/apache/tapestry/enhance/autowire-multiple.xml
------------------------------------------------------------------------------
    svn:executable = *

Added: tapestry/tapestry4/trunk/framework/src/test/org/apache/tapestry/enhance/autowire-single.xml
URL: http://svn.apache.org/viewcvs/tapestry/tapestry4/trunk/framework/src/test/org/apache/tapestry/enhance/autowire-single.xml?rev=405773&view=auto
==============================================================================
--- tapestry/tapestry4/trunk/framework/src/test/org/apache/tapestry/enhance/autowire-single.xml (added)
+++ tapestry/tapestry4/trunk/framework/src/test/org/apache/tapestry/enhance/autowire-single.xml Wed May 10 08:19:53 2006
@@ -0,0 +1,25 @@
+<?xml version="1.0"?>
+<!-- 
+   Copyright 2006 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.
+-->
+
+<module id="autowire.single" version="1.0.0">
+  <service-point id="Hello" interface="org.apache.tapestry.enhance.HelloService">
+    <invoke-factory>
+      <construct class="org.apache.tapestry.enhance.HelloServiceImpl" />
+    </invoke-factory>
+  </service-point>
+
+</module>
\ No newline at end of file

Propchange: tapestry/tapestry4/trunk/framework/src/test/org/apache/tapestry/enhance/autowire-single.xml
------------------------------------------------------------------------------
    svn:executable = *

Modified: tapestry/tapestry4/trunk/framework/src/test/org/apache/tapestry/util/io/Basic.txt
URL: http://svn.apache.org/viewcvs/tapestry/tapestry4/trunk/framework/src/test/org/apache/tapestry/util/io/Basic.txt?rev=405773&r1=405772&r2=405773&view=diff
==============================================================================
--- tapestry/tapestry4/trunk/framework/src/test/org/apache/tapestry/util/io/Basic.txt (original)
+++ tapestry/tapestry4/trunk/framework/src/test/org/apache/tapestry/util/io/Basic.txt Wed May 10 08:19:53 2006
@@ -1,8 +1,6 @@
-0000: aced0005 73720011 6a617661 2e757469  |....sr..java.uti|
-0010: 6c2e4861 73684d61 700507da c1c31660  |l.HashMap......`|
-0020: d1030002 46000a6c 6f616446 6163746f  |....F..loadFacto|
-0030: 72490009 74687265 73686f6c 6478703f  |rI..thresholdxp?|
-0040: 40000000 00000c77 08000000 10000000  |@......w........|
-0050: 0274000b 67616262 61206761 62626174  |.t..gabba gabbat|
-0060: 000d7765 20616363 65707420 796f7574  |..we accept yout|
-0070: 0005616c 70686174 00046265 746178    |..alphat..betax |
+0000: aced0005 73720013 6a617661 2e757469  |....sr..java.uti|
+0010: 6c2e4172 7261794c 69737478 81d21d99  |l.ArrayListx....|
+0020: c7619d03 00014900 0473697a 65787000  |.a....I..sizexp.|
+0030: 00000377 04000000 0a740005 616c7068  |...w.....t..alph|
+0040: 61740004 62657461 74000b67 61626261  |at..betat..gabba|
+0050: 20676162 626178                      | gabbax         |

Modified: tapestry/tapestry4/trunk/framework/src/test/org/apache/tapestry/util/io/NoAscii.txt
URL: http://svn.apache.org/viewcvs/tapestry/tapestry4/trunk/framework/src/test/org/apache/tapestry/util/io/NoAscii.txt?rev=405773&r1=405772&r2=405773&view=diff
==============================================================================
--- tapestry/tapestry4/trunk/framework/src/test/org/apache/tapestry/util/io/NoAscii.txt (original)
+++ tapestry/tapestry4/trunk/framework/src/test/org/apache/tapestry/util/io/NoAscii.txt Wed May 10 08:19:53 2006
@@ -1,8 +1,6 @@
-0000: aced0005 73720011 6a617661 2e757469
-0010: 6c2e4861 73684d61 700507da c1c31660
-0020: d1030002 46000a6c 6f616446 6163746f
-0030: 72490009 74687265 73686f6c 6478703f
-0040: 40000000 00000c77 08000000 10000000
-0050: 0274000b 67616262 61206761 62626174
-0060: 000d7765 20616363 65707420 796f7574
-0070: 0005616c 70686174 00046265 746178  
+0000: aced0005 73720013 6a617661 2e757469
+0010: 6c2e4172 7261794c 69737478 81d21d99
+0020: c7619d03 00014900 0473697a 65787000
+0030: 00000377 04000000 0a740005 616c7068
+0040: 61740004 62657461 74000b67 61626261
+0050: 20676162 626178                    

Modified: tapestry/tapestry4/trunk/framework/src/test/org/apache/tapestry/util/io/NoOffset.txt
URL: http://svn.apache.org/viewcvs/tapestry/tapestry4/trunk/framework/src/test/org/apache/tapestry/util/io/NoOffset.txt?rev=405773&r1=405772&r2=405773&view=diff
==============================================================================
--- tapestry/tapestry4/trunk/framework/src/test/org/apache/tapestry/util/io/NoOffset.txt (original)
+++ tapestry/tapestry4/trunk/framework/src/test/org/apache/tapestry/util/io/NoOffset.txt Wed May 10 08:19:53 2006
@@ -1,8 +1,6 @@
-aced0005 73720011 6a617661 2e757469  |....sr..java.uti|
-6c2e4861 73684d61 700507da c1c31660  |l.HashMap......`|
-d1030002 46000a6c 6f616446 6163746f  |....F..loadFacto|
-72490009 74687265 73686f6c 6478703f  |rI..thresholdxp?|
-40000000 00000c77 08000000 10000000  |@......w........|
-0274000b 67616262 61206761 62626174  |.t..gabba gabbat|
-000d7765 20616363 65707420 796f7574  |..we accept yout|
-0005616c 70686174 00046265 746178    |..alphat..betax |
+aced0005 73720013 6a617661 2e757469  |....sr..java.uti|
+6c2e4172 7261794c 69737478 81d21d99  |l.ArrayListx....|
+c7619d03 00014900 0473697a 65787000  |.a....I..sizexp.|
+00000377 04000000 0a740005 616c7068  |...w.....t..alph|
+61740004 62657461 74000b67 61626261  |at..betat..gabba|
+20676162 626178                      | gabbax         |

Modified: tapestry/tapestry4/trunk/framework/src/test/org/apache/tapestry/util/io/Options.txt
URL: http://svn.apache.org/viewcvs/tapestry/tapestry4/trunk/framework/src/test/org/apache/tapestry/util/io/Options.txt?rev=405773&r1=405772&r2=405773&view=diff
==============================================================================
--- tapestry/tapestry4/trunk/framework/src/test/org/apache/tapestry/util/io/Options.txt (original)
+++ tapestry/tapestry4/trunk/framework/src/test/org/apache/tapestry/util/io/Options.txt Wed May 10 08:19:53 2006
@@ -1,3 +1,2 @@
-0000 = aced000573720011 6a6176612e757469 6c2e486173684d61 700507dac1c31660 d103000246000a6c 6f6164466163746f { ????sr??java.util.HashMap??????`????F??loadFacto }
-0030 = 7249000974687265 73686f6c6478703f 4000000000000c77 0800000010000000 0274000b67616262 6120676162626174 { rI??thresholdxp?@??????w?????????t??gabba gabbat }
-0060 = 000d776520616363 65707420796f7574 0005616c70686174 00046265746178                                     { ??we accept yout??alphat??betax                  }
+0000 = aced000573720013 6a6176612e757469 6c2e41727261794c 6973747881d21d99 c7619d0300014900 0473697a65787000 { ????sr??java.util.ArrayListx?????a????I??sizexp? }
+0030 = 0000037704000000 0a740005616c7068 6174000462657461 74000b6761626261 20676162626178                    { ???w?????t??alphat??betat??gabba gabbax          }

Modified: tapestry/tapestry4/trunk/framework/src/test/org/apache/tapestry/util/io/TestBinaryDumpOutputStream.java
URL: http://svn.apache.org/viewcvs/tapestry/tapestry4/trunk/framework/src/test/org/apache/tapestry/util/io/TestBinaryDumpOutputStream.java?rev=405773&r1=405772&r2=405773&view=diff
==============================================================================
--- tapestry/tapestry4/trunk/framework/src/test/org/apache/tapestry/util/io/TestBinaryDumpOutputStream.java (original)
+++ tapestry/tapestry4/trunk/framework/src/test/org/apache/tapestry/util/io/TestBinaryDumpOutputStream.java Wed May 10 08:19:53 2006
@@ -22,8 +22,8 @@
 import java.io.LineNumberReader;
 import java.io.ObjectOutputStream;
 import java.io.Reader;
-import java.util.HashMap;
-import java.util.Map;
+import java.util.ArrayList;
+import java.util.List;
 
 import junit.framework.TestCase;
 
@@ -43,7 +43,7 @@
     private String contentsOf(String path) throws Exception
     {
         String sep = System.getProperty("line.separator");
-
+        
         InputStream is = getClass().getResourceAsStream(path);
 
         is = new BufferedInputStream(is);
@@ -77,13 +77,12 @@
         CharArrayWriter writer = new CharArrayWriter();
 
         BinaryDumpOutputStream bdos = new BinaryDumpOutputStream(writer);
-
+        
         ObjectOutputStream oos = new ObjectOutputStream(bdos);
-
         oos.writeObject(createOutputObject());
-
+        
         oos.close();
-
+        
         assertEquals(contentsOf("Basic.txt"), writer.toString());
     }
 
@@ -91,13 +90,17 @@
      * Creates and returns the object to be written out to the stream. The tests are dependenent on
      * the serialization of HashMap and String not changing between JDKs. If such a change does
      * occur, we'll need to devise an Externalizable object to write to the stream.
+     * 
+     * I've changed this to use a List instead, as ordering of a list shouldn't change while
+     * ordering of a hashmap isn't guaranteed at all.
      */
-    private Map createOutputObject()
+    private List createOutputObject()
     {
-        Map map = new HashMap();
-        map.put("alpha", "beta");
-        map.put("gabba gabba", "we accept you");
-        return map;
+        List list = new ArrayList();
+        list.add("alpha");
+        list.add("beta");
+        list.add("gabba gabba");
+        return list;
     }
 
     public void testOptions() throws Exception

Modified: tapestry/tapestry4/trunk/status.xml
URL: http://svn.apache.org/viewcvs/tapestry/tapestry4/trunk/status.xml?rev=405773&r1=405772&r2=405773&view=diff
==============================================================================
--- tapestry/tapestry4/trunk/status.xml (original)
+++ tapestry/tapestry4/trunk/status.xml Wed May 10 08:19:53 2006
@@ -78,6 +78,13 @@
         Added a new utility implementation of IPropertySelectionModel that uses commons-beanutils to
         select values from a standard POJO object.
       </action>
+      <action type="add" dev="JK" due-to="James Carman" fixes-bug="TAPESTRY-917">
+        Applied patch that adds enhanced hivemind autowiring of services to components/pages.
+      </action>
+      <action type="update" dev="JK" fixes-bug="TAPESTRY-917" >
+        Added isReadOnly method to EnhancementOperation interface to support discovering properties
+        without having to throw exceptions.
+      </action>
     </release>
     <release version="4.0.1" date="unreleased" >
       <action type="fix" dev="JK" fixes-bug="TAPESTRY-863" due-to="unknown contributor">