You are viewing a plain text version of this content. The canonical link for it is here.
Posted to dev@tapestry.apache.org by dr...@apache.org on 2010/10/21 17:46:22 UTC

svn commit: r1026032 - in /tapestry/tapestry5/trunk/tapestry-ioc/src: main/java/org/apache/tapestry5/ioc/ main/java/org/apache/tapestry5/ioc/annotations/ main/java/org/apache/tapestry5/ioc/def/ main/java/org/apache/tapestry5/ioc/internal/ main/java/org...

Author: drobiazko
Date: Thu Oct 21 15:46:21 2010
New Revision: 1026032

URL: http://svn.apache.org/viewvc?rev=1026032&view=rev
Log:
TAP5-1272: New annotations @Decorate and @Advise to identify methods that decorate or annotate services 

Added:
    tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/AdvisorDef2.java   (with props)
    tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/Markable.java   (with props)
    tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/annotations/Advise.java   (with props)
    tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/annotations/Decorate.java   (with props)
    tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/def/DecoratorDef2.java   (with props)
    tapestry/tapestry5/trunk/tapestry-ioc/src/test/java/org/apache/tapestry5/ioc/GreeterModule2.java   (with props)
    tapestry/tapestry5/trunk/tapestry-ioc/src/test/java/org/apache/tapestry5/ioc/internal/AdviseByMarkerModule.java   (with props)
    tapestry/tapestry5/trunk/tapestry-ioc/src/test/java/org/apache/tapestry5/ioc/internal/DecorateByMarkerModule.java   (with props)
Modified:
    tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/def/ContributionDef2.java
    tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/AbstractServiceInstrumenter.java
    tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/AdvisorDefImpl.java
    tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/DecoratorDefImpl.java
    tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/DefaultModuleDefImpl.java
    tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/ModuleImpl.java
    tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/util/InternalUtils.java
    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/ModuleImplTest.java

Added: tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/AdvisorDef2.java
URL: http://svn.apache.org/viewvc/tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/AdvisorDef2.java?rev=1026032&view=auto
==============================================================================
--- tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/AdvisorDef2.java (added)
+++ tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/AdvisorDef2.java Thu Oct 21 15:46:21 2010
@@ -0,0 +1,29 @@
+// Copyright 2010 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;
+
+/**
+ * Extended version of {@link org.apache.tapestry5.ioc.AdvisorDef} introduced to determine any
+ * module method annotated with {@link org.apache.tapestry5.ioc.annotations.Advise} as an advisor
+ * method. Before version 5.2 an advice is applied to any service whose id matched the pattern
+ * provided by {@link org.apache.tapestry5.ioc.annotations.Match} annotation. As of version 5.2 a
+ * service to advice may also be identified by a combination of
+ * {@link org.apache.tapestry5.ioc.annotations.Advise} annotation and a set of marker annotations.
+ *
+ * @since 5.2.2
+ */
+public interface AdvisorDef2 extends AdvisorDef, Markable
+{
+
+}

Propchange: tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/AdvisorDef2.java
------------------------------------------------------------------------------
    svn:mime-type = text/plain

Added: tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/Markable.java
URL: http://svn.apache.org/viewvc/tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/Markable.java?rev=1026032&view=auto
==============================================================================
--- tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/Markable.java (added)
+++ tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/Markable.java Thu Oct 21 15:46:21 2010
@@ -0,0 +1,44 @@
+// Copyright 2010 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;
+
+import java.util.Set;
+
+import org.apache.tapestry5.ioc.def.ServiceDef;
+
+
+/**
+ * Interface implemented by objects which need to disambiguate services with marker annotations.
+ *
+ * @since 5.2.2
+ */
+public interface Markable
+{
+    /**
+     * Returns an optional set of <em>marker annotation</em>. Marker annotations are used to disambiguate services; the
+     * combination of a marker annotation and a service type is expected to be unique. Note that it is not possible
+     * to identify which annotations are markers and which are not when this set is constructed, so it may include
+     * non-marker annotations.
+     *
+     * @see ServiceDef#getMarkers()
+     */
+    Set<Class> getMarkers();
+
+    /**
+     * Returns the service interface associated with the service.
+     *
+     * @see ServiceDef#getServiceInterface()
+     */
+    Class getServiceInterface();
+}

Propchange: tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/Markable.java
------------------------------------------------------------------------------
    svn:mime-type = text/plain

Added: tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/annotations/Advise.java
URL: http://svn.apache.org/viewvc/tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/annotations/Advise.java?rev=1026032&view=auto
==============================================================================
--- tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/annotations/Advise.java (added)
+++ tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/annotations/Advise.java Thu Oct 21 15:46:21 2010
@@ -0,0 +1,45 @@
+// Copyright 2010 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.annotations;
+
+import static java.lang.annotation.ElementType.METHOD;
+import static java.lang.annotation.RetentionPolicy.RUNTIME;
+
+import java.lang.annotation.Documented;
+import java.lang.annotation.Retention;
+import java.lang.annotation.Target;
+
+/**
+ * An annotation that may be placed on a advisor method of a module. The annotation may/should be used in combination with
+ * marker annotations to disambiguate the service to advise. This annotation was introduced as an alternative
+ * to the naming convention for advisor methods.
+ *
+ * @since 5.2.2
+ *
+ */
+@Target(METHOD)
+@Retention(RUNTIME)
+@Documented
+public @interface Advise
+{
+    /**
+     * Type of the service to advise.
+     */
+    Class serviceInterface();
+   
+    /**
+     * Id of the advisor.
+     */
+    String id() default "";
+}

Propchange: tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/annotations/Advise.java
------------------------------------------------------------------------------
    svn:mime-type = text/plain

Added: tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/annotations/Decorate.java
URL: http://svn.apache.org/viewvc/tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/annotations/Decorate.java?rev=1026032&view=auto
==============================================================================
--- tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/annotations/Decorate.java (added)
+++ tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/annotations/Decorate.java Thu Oct 21 15:46:21 2010
@@ -0,0 +1,45 @@
+// Copyright 2010 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.annotations;
+
+import static java.lang.annotation.ElementType.METHOD;
+import static java.lang.annotation.RetentionPolicy.RUNTIME;
+
+import java.lang.annotation.Documented;
+import java.lang.annotation.Retention;
+import java.lang.annotation.Target;
+
+/**
+ * An annotation that may be placed on a decorator method of a module. The annotation may/should be used in combination with
+ * marker annotations to disambiguate the service to advise. This annotation was introduced as an alternative
+ * to the naming convention for decorator methods.
+ *
+ * @since 5.2.2
+ *
+ */
+@Target(METHOD)
+@Retention(RUNTIME)
+@Documented
+public @interface Decorate
+{
+    /**
+     * Type of the service to decorate.
+     */
+    Class serviceInterface();
+   
+    /**
+     * Id of the decorator.
+     */
+    String id();
+}

Propchange: tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/annotations/Decorate.java
------------------------------------------------------------------------------
    svn:mime-type = text/plain

Modified: tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/def/ContributionDef2.java
URL: http://svn.apache.org/viewvc/tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/def/ContributionDef2.java?rev=1026032&r1=1026031&r2=1026032&view=diff
==============================================================================
--- tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/def/ContributionDef2.java (original)
+++ tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/def/ContributionDef2.java Thu Oct 21 15:46:21 2010
@@ -13,8 +13,7 @@
 // limitations under the License.
 package org.apache.tapestry5.ioc.def;
 
-import java.util.Set;
-
+import org.apache.tapestry5.ioc.Markable;
 import org.apache.tapestry5.ioc.annotations.Contribute;
 
 /**
@@ -26,22 +25,7 @@ import org.apache.tapestry5.ioc.annotati
  * 
  * @since 5.2.0
  */
-public interface ContributionDef2 extends ContributionDef
+public interface ContributionDef2 extends ContributionDef, Markable
 {
-    /**
-     * Returns an optional set of <em>marker annotation</em>. Marker annotations are used to disambiguate services; the
-     * combination of a marker annotation and a service type is expected to be unique. Note that it is not possible
-     * to identify which annotations are markers and which are not when this set is contructed, so it may include
-     * non-marker annotations.
-     * 
-     * @see ServiceDef#getMarkers()
-     */
-    Set<Class> getMarkers();
-
-    /**
-     * Returns the service interface associated with the service to contribute into.
-     * 
-     * @see ServiceDef#getServiceInterface()
-     */
-    Class getServiceInterface();
+	
 }

Added: tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/def/DecoratorDef2.java
URL: http://svn.apache.org/viewvc/tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/def/DecoratorDef2.java?rev=1026032&view=auto
==============================================================================
--- tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/def/DecoratorDef2.java (added)
+++ tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/def/DecoratorDef2.java Thu Oct 21 15:46:21 2010
@@ -0,0 +1,33 @@
+// Copyright 2010 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.def;
+
+import org.apache.tapestry5.ioc.Markable;
+
+/**
+ * Extended version of {@link org.apache.tapestry5.ioc.def.DecoratorDef} introduced to determine any
+ * module method annotated with {@link org.apache.tapestry5.ioc.annotations.Decorate} as a decorator
+ * method. Before version 5.2 a decorator was applied to any service whose id matched the pattern
+ * provided
+ * by {@link org.apache.tapestry5.ioc.annotations.Match} annotation. As of version 5.2 a service to
+ * decorate may also be identified by a
+ * combination of {@link org.apache.tapestry5.ioc.annotations.Advise} annotation and
+ * a set of marker annotations.
+ *
+ * @since 5.2.2
+ */
+public interface DecoratorDef2 extends DecoratorDef, Markable
+{
+
+}

Propchange: tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/def/DecoratorDef2.java
------------------------------------------------------------------------------
    svn:mime-type = text/plain

Modified: tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/AbstractServiceInstrumenter.java
URL: http://svn.apache.org/viewvc/tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/AbstractServiceInstrumenter.java?rev=1026032&r1=1026031&r2=1026032&view=diff
==============================================================================
--- tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/AbstractServiceInstrumenter.java (original)
+++ tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/AbstractServiceInstrumenter.java Thu Oct 21 15:46:21 2010
@@ -16,6 +16,7 @@ package org.apache.tapestry5.ioc.interna
 
 import java.lang.reflect.Method;
 import java.util.List;
+import java.util.Set;
 
 import org.apache.tapestry5.ioc.IdMatcher;
 import org.apache.tapestry5.ioc.def.ServiceDef;
@@ -39,10 +40,16 @@ public class AbstractServiceInstrumenter
     protected final String[] constraints;
 
     protected final ClassFactory classFactory;
+   
+    private final Set<Class> markers;
+   
+    private final Class serviceInterface;
 
-    public AbstractServiceInstrumenter(Method method, String[] patterns, String[] constraints, ClassFactory classFactory)
+    public AbstractServiceInstrumenter(Method method, String[] patterns, String[] constraints, Class serviceInterface, Set<Class> markers, ClassFactory classFactory)
     {
         this.method = method;
+        this.serviceInterface = serviceInterface;
+        this.markers = markers;
         this.classFactory = classFactory;
 
         assert patterns != null;
@@ -80,4 +87,14 @@ public class AbstractServiceInstrumenter
 
         return idMatcher.matches(serviceId);
     }
+
+    public Set<Class> getMarkers()
+    {
+        return markers;
+    }
+
+    public Class getServiceInterface()
+    {
+        return serviceInterface;
+    }
 }

Modified: tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/AdvisorDefImpl.java
URL: http://svn.apache.org/viewvc/tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/AdvisorDefImpl.java?rev=1026032&r1=1026031&r2=1026032&view=diff
==============================================================================
--- tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/AdvisorDefImpl.java (original)
+++ tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/AdvisorDefImpl.java Thu Oct 21 15:46:21 2010
@@ -15,22 +15,23 @@
 package org.apache.tapestry5.ioc.internal;
 
 import java.lang.reflect.Method;
+import java.util.Set;
 
-import org.apache.tapestry5.ioc.AdvisorDef;
+import org.apache.tapestry5.ioc.AdvisorDef2;
 import org.apache.tapestry5.ioc.ModuleBuilderSource;
 import org.apache.tapestry5.ioc.ServiceAdvisor;
 import org.apache.tapestry5.ioc.ServiceResources;
 import org.apache.tapestry5.ioc.internal.util.InternalUtils;
 import org.apache.tapestry5.ioc.services.ClassFactory;
 
-public class AdvisorDefImpl extends AbstractServiceInstrumenter implements AdvisorDef
+public class AdvisorDefImpl extends AbstractServiceInstrumenter implements AdvisorDef2
 {
     private final String advisorId;
 
     public AdvisorDefImpl(Method method, String[] patterns, String[] constraints, ClassFactory classFactory,
-                          String advisorId)
+                          String advisorId, Class serviceInterface, Set<Class> markers)
     {
-        super(method, patterns, constraints, classFactory);
+        super(method, patterns, constraints, serviceInterface, markers, classFactory);
         assert InternalUtils.isNonBlank(advisorId);
 
         this.advisorId = advisorId;

Modified: tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/DecoratorDefImpl.java
URL: http://svn.apache.org/viewvc/tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/DecoratorDefImpl.java?rev=1026032&r1=1026031&r2=1026032&view=diff
==============================================================================
--- tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/DecoratorDefImpl.java (original)
+++ tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/DecoratorDefImpl.java Thu Oct 21 15:46:21 2010
@@ -15,23 +15,24 @@
 package org.apache.tapestry5.ioc.internal;
 
 import java.lang.reflect.Method;
+import java.util.Set;
 
 import org.apache.tapestry5.ioc.ModuleBuilderSource;
 import org.apache.tapestry5.ioc.ServiceDecorator;
 import org.apache.tapestry5.ioc.ServiceResources;
-import org.apache.tapestry5.ioc.def.DecoratorDef;
+import org.apache.tapestry5.ioc.def.DecoratorDef2;
 import org.apache.tapestry5.ioc.internal.util.InternalUtils;
 import org.apache.tapestry5.ioc.services.ClassFactory;
 
-public class DecoratorDefImpl extends AbstractServiceInstrumenter implements DecoratorDef
+public class DecoratorDefImpl extends AbstractServiceInstrumenter implements DecoratorDef2
 {
     private final String decoratorId;
 
     public DecoratorDefImpl(Method decoratorMethod, String[] patterns, String[] constraints, ClassFactory classFactory,
-                            String decoratorId
+                            String decoratorId, Class serviceInterface, Set<Class> markers
     )
     {
-        super(decoratorMethod, patterns, constraints, classFactory);
+        super(decoratorMethod, patterns, constraints, serviceInterface, markers, classFactory);
         assert InternalUtils.isNonBlank(decoratorId);
 
         this.decoratorId = decoratorId;

Modified: tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/DefaultModuleDefImpl.java
URL: http://svn.apache.org/viewvc/tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/DefaultModuleDefImpl.java?rev=1026032&r1=1026031&r2=1026032&view=diff
==============================================================================
--- tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/DefaultModuleDefImpl.java (original)
+++ tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/DefaultModuleDefImpl.java Thu Oct 21 15:46:21 2010
@@ -38,7 +38,9 @@ import org.apache.tapestry5.ioc.OrderedC
 import org.apache.tapestry5.ioc.ScopeConstants;
 import org.apache.tapestry5.ioc.ServiceBinder;
 import org.apache.tapestry5.ioc.ServiceBuilderResources;
+import org.apache.tapestry5.ioc.annotations.Advise;
 import org.apache.tapestry5.ioc.annotations.Contribute;
+import org.apache.tapestry5.ioc.annotations.Decorate;
 import org.apache.tapestry5.ioc.annotations.EagerLoad;
 import org.apache.tapestry5.ioc.annotations.Marker;
 import org.apache.tapestry5.ioc.annotations.Match;
@@ -231,7 +233,7 @@ public class DefaultModuleDefImpl implem
                 continue;
             }
 
-            if (name.startsWith(DECORATE_METHOD_NAME_PREFIX))
+            if (name.startsWith(DECORATE_METHOD_NAME_PREFIX) || m.isAnnotationPresent(Decorate.class))
             {
                 addDecoratorDef(m);
                 remainingMethods.remove(m);
@@ -245,7 +247,7 @@ public class DefaultModuleDefImpl implem
                 continue;
             }
 
-            if (name.startsWith(ADVISE_METHOD_NAME_PREFIX))
+            if (name.startsWith(ADVISE_METHOD_NAME_PREFIX) || m.isAnnotationPresent(Advise.class))
             {
                 addAdvisorDef(m);
                 remainingMethods.remove(m);
@@ -300,7 +302,7 @@ public class DefaultModuleDefImpl implem
         if (type == null)
             throw new RuntimeException(IOCMessages.noContributionParameter(method));
 
-        Set<Class> markers = extractContributionMarkers(method);
+        Set<Class> markers = extractMarkers(method, Contribute.class);
 
         ContributionDef2 def = new ContributionDefImpl(serviceId, method, classFactory, serviceInterface, markers);
 
@@ -309,9 +311,13 @@ public class DefaultModuleDefImpl implem
 
     private void addDecoratorDef(Method method)
     {
+        Decorate annotation = method.getAnnotation(Decorate.class);
+       
+        Class serviceInterface = annotation == null ? null : annotation.serviceInterface();
+       
         // TODO: methods just named "decorate"
 
-        String decoratorId = stripMethodPrefix(method, DECORATE_METHOD_NAME_PREFIX);
+        String decoratorId = annotation == null? stripMethodPrefix(method, DECORATE_METHOD_NAME_PREFIX) : extractId(serviceInterface, annotation.id());
 
         // TODO: Check for duplicates
 
@@ -319,15 +325,20 @@ public class DefaultModuleDefImpl implem
 
         if (returnType.isPrimitive() || returnType.isArray())
             throw new RuntimeException(IOCMessages.decoratorMethodWrongReturnType(method));
+       
+        Set<Class> markers = extractMarkers(method, Decorate.class);
 
-        DecoratorDef def = new DecoratorDefImpl(method, extractPatterns(decoratorId, method),
-                extractConstraints(method), classFactory, decoratorId);
+        DecoratorDef def = new DecoratorDefImpl(method, extractPatterns(annotation, decoratorId, method),
+                extractConstraints(method), classFactory, decoratorId, serviceInterface, markers);
 
         decoratorDefs.put(decoratorId, def);
     }
 
-    private String[] extractPatterns(String id, Method method)
+    private <T extends Annotation> String[] extractPatterns(T annotation, String id, Method method)
     {
+        if(annotation != null)
+            return new String[]{};
+       
         Match match = method.getAnnotation(Match.class);
 
         if (match == null)
@@ -349,9 +360,13 @@ public class DefaultModuleDefImpl implem
 
     private void addAdvisorDef(Method method)
     {
+        Advise annotation = method.getAnnotation(Advise.class);
+       
+        Class serviceInterface = annotation == null ? null : annotation.serviceInterface();
+       
         // TODO: methods just named "decorate"
 
-        String advisorId = stripMethodPrefix(method, ADVISE_METHOD_NAME_PREFIX);
+        String advisorId = annotation == null ? stripMethodPrefix(method, ADVISE_METHOD_NAME_PREFIX) : extractId(serviceInterface, annotation.id());
 
         // TODO: Check for duplicates
 
@@ -375,31 +390,24 @@ public class DefaultModuleDefImpl implem
         if (!found)
             throw new RuntimeException(String.format("Advise method %s must take a parameter of type %s.",
                     toString(method), MethodAdviceReceiver.class.getName()));
-
-        AdvisorDef def = new AdvisorDefImpl(method, extractPatterns(advisorId, method), extractConstraints(method),
-                classFactory, advisorId);
+       
+        Set<Class> markers = extractMarkers(method, Advise.class);
+       
+        AdvisorDef def = new AdvisorDefImpl(method, extractPatterns(annotation, advisorId, method), extractConstraints(method),
+                classFactory, advisorId, serviceInterface, markers);
 
         advisorDefs.put(advisorId, def);
 
     }
-
-    private String toString(Method method)
+    
+    private String extractId(Class serviceInterface, String id)
     {
-        return InternalUtils.asString(method, classFactory);
+    	return InternalUtils.isBlank(id) ? serviceInterface.getSimpleName() : id;
     }
 
-    private boolean methodContainsObjectParameter(Method method)
+    private String toString(Method method)
     {
-        for (Class parameterType : method.getParameterTypes())
-        {
-            // TODO: But what if the type Object parameter has an injection?
-            // We should skip it and look for a different parameter.
-
-            if (parameterType.equals(Object.class))
-                return true;
-        }
-
-        return false;
+        return InternalUtils.asString(method, classFactory);
     }
 
     private String stripMethodPrefix(Method method, String prefix)
@@ -479,7 +487,7 @@ public class DefaultModuleDefImpl implem
     }
 
     @SuppressWarnings("rawtypes")
-    private Set<Class> extractContributionMarkers(Method method)
+    private Set<Class> extractMarkers(Method method, final Class annotationClassToSkip)
     {
         return F.flow(method.getAnnotations()).map(new Mapper<Annotation, Class>()
         {
@@ -491,7 +499,7 @@ public class DefaultModuleDefImpl implem
         {
             public boolean accept(Class object)
             {
-                return !object.equals(Contribute.class);
+                return !object.equals(annotationClassToSkip);
 
             }
         }).toSet();

Modified: tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/ModuleImpl.java
URL: http://svn.apache.org/viewvc/tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/ModuleImpl.java?rev=1026032&r1=1026031&r2=1026032&view=diff
==============================================================================
--- tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/ModuleImpl.java (original)
+++ tapestry/tapestry5/trunk/tapestry-ioc/src/main/java/org/apache/tapestry5/ioc/internal/ModuleImpl.java Thu Oct 21 15:46:21 2010
@@ -29,6 +29,7 @@ import java.util.Set;
 
 import org.apache.tapestry5.ioc.AdvisorDef;
 import org.apache.tapestry5.ioc.Invokable;
+import org.apache.tapestry5.ioc.Markable;
 import org.apache.tapestry5.ioc.ObjectCreator;
 import org.apache.tapestry5.ioc.ObjectLocator;
 import org.apache.tapestry5.ioc.OperationTracker;
@@ -143,7 +144,7 @@ public class ModuleImpl implements Modul
 
         for (DecoratorDef def : moduleDef.getDecoratorDefs())
         {
-            if (def.matches(serviceDef))
+            if (def.matches(serviceDef) || markerMatched(serviceDef, InternalUtils.toDecoratorDef2(def)))
                 result.add(def);
         }
 
@@ -156,7 +157,7 @@ public class ModuleImpl implements Modul
 
         for (AdvisorDef def : moduleDef.getAdvisorDefs())
         {
-            if (def.matches(serviceDef))
+            if (def.matches(serviceDef) || markerMatched(serviceDef, InternalUtils.toAdvisorDef2(def)))
                 result.add(def);
         }
 
@@ -544,34 +545,41 @@ public class ModuleImpl implements Modul
             }
             else
             {
-                if (!serviceDef.getServiceInterface().equals(def.getServiceInterface()))
-                    continue;
-
-                Set<Class> contributionMarkers = CollectionFactory.newSet(def.getMarkers());
-
-                if (contributionMarkers.contains(Local.class))
+                if(markerMatched(serviceDef, def))
                 {
-                    // If @Local is present, filter out services that aren't in the same module.
-                    // Don't consider @Local to be a marker annotation
-                    // for the later match, however.
+                    result.add(def);
+                }
+            }
+        }
 
-                    if (!isLocalServiceDef(serviceDef))
-                        continue;
+        return result;
+    }
+   
+    private boolean markerMatched(ServiceDef serviceDef, Markable markable)
+    {
+        if (!serviceDef.getServiceInterface().equals(markable.getServiceInterface()))
+            return false;;
 
-                    contributionMarkers.remove(Local.class);
-                }
+        Set<Class> contributionMarkers = CollectionFactory.newSet(markable.getMarkers());
 
-                // Filter out any stray annotations that aren't used by some
-                // service, in any module, as a marker annotation.
+        if (contributionMarkers.contains(Local.class))
+        {
+            // If @Local is present, filter out services that aren't in the same module.
+            // Don't consider @Local to be a marker annotation
+            // for the later match, however.
 
-                contributionMarkers.retainAll(registry.getMarkerAnnotations());
+            if (!isLocalServiceDef(serviceDef))
+                return false;
 
-                if (serviceDef.getMarkers().containsAll(contributionMarkers))
-                    result.add(def);
-            }
+            contributionMarkers.remove(Local.class);
         }
 
-        return result;
+        // Filter out any stray annotations that aren't used by some
+        // service, in any module, as a marker annotation.
+
+        contributionMarkers.retainAll(registry.getMarkerAnnotations());
+
+        return serviceDef.getMarkers().containsAll(contributionMarkers);
     }
 
     private boolean isLocalServiceDef(ServiceDef serviceDef)

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=1026032&r1=1026031&r2=1026032&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 Thu Oct 21 15:46:21 2010
@@ -43,6 +43,7 @@ import java.util.regex.Pattern;
 import org.apache.tapestry5.func.Mapper;
 import org.apache.tapestry5.func.Predicate;
 import org.apache.tapestry5.ioc.AdvisorDef;
+import org.apache.tapestry5.ioc.AdvisorDef2;
 import org.apache.tapestry5.ioc.AnnotationProvider;
 import org.apache.tapestry5.ioc.Configuration;
 import org.apache.tapestry5.ioc.IOCConstants;
@@ -55,7 +56,9 @@ import org.apache.tapestry5.ioc.ObjectCr
 import org.apache.tapestry5.ioc.ObjectLocator;
 import org.apache.tapestry5.ioc.OperationTracker;
 import org.apache.tapestry5.ioc.OrderedConfiguration;
+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;
@@ -66,6 +69,7 @@ import org.apache.tapestry5.ioc.annotati
 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.DecoratorDef2;
 import org.apache.tapestry5.ioc.def.ModuleDef;
 import org.apache.tapestry5.ioc.def.ModuleDef2;
 import org.apache.tapestry5.ioc.def.ServiceDef;
@@ -1052,6 +1056,94 @@ public class InternalUtils
 
         };
     }
+   
+    /**
+     * @since 5.2.2
+     */
+    public static AdvisorDef2 toAdvisorDef2(final AdvisorDef advisor)
+    {
+        if (advisor instanceof AdvisorDef2)
+            return (AdvisorDef2) advisor;
+       
+        return new AdvisorDef2()
+        {
+
+            public ServiceAdvisor createAdvisor(ModuleBuilderSource moduleSource, ServiceResources resources)
+            {
+                return advisor.createAdvisor(moduleSource, resources);
+            }
+
+            public String getAdvisorId()
+            {
+                return advisor.getAdvisorId();
+            }
+
+            public String[] getConstraints()
+            {
+                return advisor.getConstraints();
+            }
+
+            public boolean matches(ServiceDef serviceDef)
+            {
+                return advisor.matches(serviceDef);
+            }
+
+            public Set<Class> getMarkers()
+            {
+                return Collections.emptySet();
+            }
+
+            public Class getServiceInterface()
+            {
+                return null;
+            }
+           
+        };
+    }
+   
+    /**
+     * @since 5.2.2
+     */
+    public static DecoratorDef2 toDecoratorDef2(final DecoratorDef decorator)
+    {
+        if (decorator instanceof DecoratorDef2)
+            return (DecoratorDef2) decorator;
+       
+        return new DecoratorDef2()
+        {
+
+            public ServiceDecorator createDecorator(ModuleBuilderSource moduleSource, ServiceResources resources)
+            {
+                return decorator.createDecorator(moduleSource, resources);
+            }
+
+            public String[] getConstraints()
+            {
+                return decorator.getConstraints();
+            }
+
+            public String getDecoratorId()
+            {
+                return decorator.getDecoratorId();
+            }
+
+            public boolean matches(ServiceDef serviceDef)
+            {
+                return decorator.matches(serviceDef);
+            }
+
+            public Set<Class> getMarkers()
+            {
+                return Collections.emptySet();
+            }
+
+            public Class getServiceInterface()
+            {
+                return null;
+            }
+           
+        };
+    }
 
     /**
      * Determines if the indicated class is stored as a locally accessible file

Added: tapestry/tapestry5/trunk/tapestry-ioc/src/test/java/org/apache/tapestry5/ioc/GreeterModule2.java
URL: http://svn.apache.org/viewvc/tapestry/tapestry5/trunk/tapestry-ioc/src/test/java/org/apache/tapestry5/ioc/GreeterModule2.java?rev=1026032&view=auto
==============================================================================
--- tapestry/tapestry5/trunk/tapestry-ioc/src/test/java/org/apache/tapestry5/ioc/GreeterModule2.java (added)
+++ tapestry/tapestry5/trunk/tapestry-ioc/src/test/java/org/apache/tapestry5/ioc/GreeterModule2.java Thu Oct 21 15:46:21 2010
@@ -0,0 +1,43 @@
+// Copyright 2010 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;
+
+import org.apache.tapestry5.ioc.annotations.Marker;
+
+public class GreeterModule2
+{
+    @Marker(GreenMarker.class)
+    public Greeter buildGreenGreeter()
+    {
+        return new Greeter()
+        {
+            public String getGreeting()
+            {
+                return "Green";
+            }
+        };
+    }
+   
+    @Marker(BlueMarker.class)
+    public Greeter buildBlueGreeter()
+    {
+        return new Greeter()
+        {
+            public String getGreeting()
+            {
+                return "Blue";
+            }
+        };
+    }
+}

Propchange: tapestry/tapestry5/trunk/tapestry-ioc/src/test/java/org/apache/tapestry5/ioc/GreeterModule2.java
------------------------------------------------------------------------------
    svn:mime-type = text/plain

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=1026032&r1=1026031&r2=1026032&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 Thu Oct 21 15:46:21 2010
@@ -25,8 +25,10 @@ import java.util.HashMap;
 import java.util.List;
 import java.util.Map;
 
+import org.apache.tapestry5.ioc.internal.AdviseByMarkerModule;
 import org.apache.tapestry5.ioc.internal.AlphabetModule;
 import org.apache.tapestry5.ioc.internal.AlphabetModule2;
+import org.apache.tapestry5.ioc.internal.DecorateByMarkerModule;
 import org.apache.tapestry5.ioc.internal.ExceptionInConstructorModule;
 import org.apache.tapestry5.ioc.internal.ExtraPublicConstructorsModule;
 import org.apache.tapestry5.ioc.internal.IOCInternalTestCase;
@@ -1515,6 +1517,58 @@ public class IntegrationTest extends IOC
 
         r.shutdown();
     }
+   
+    @Test
+    public void advise_by_annotation()
+    {
+        Registry r = buildRegistry(GreeterModule2.class, AdviseByMarkerModule.class);
+
+        Greeter green = r.getService("GreenGreeter", Greeter.class);
+
+        assertEquals(green.getGreeting(), "gamma[beta[alpha[Green]]]");
+
+        r.shutdown();
+
+    }
+   
+    @Test
+    public void advise_by_locale_annotation()
+    {
+        Registry r = buildRegistry(GreeterModule2.class, AdviseByMarkerModule.class);
+       
+        Greeter red = r.getService("RedGreeter", Greeter.class);
+
+        assertEquals(red.getGreeting(), "delta[Red]");
+
+        r.shutdown();
+
+    }
+   
+    @Test
+    public void decorate_by_annotation()
+    {
+        Registry r = buildRegistry(GreeterModule2.class, DecorateByMarkerModule.class);
+
+        Greeter green = r.getService("GreenGreeter", Greeter.class);
+
+        assertEquals(green.getGreeting(), "Decorated by foo[Decorated by baz[Decorated by bar[Green]]]");
+
+        r.shutdown();
+
+    }
+   
+    @Test
+    public void decorate_by_locale_annotation()
+    {
+        Registry r = buildRegistry(GreeterModule2.class, DecorateByMarkerModule.class);
+       
+        Greeter red = r.getService("RedGreeter", Greeter.class);
+
+        assertEquals(red.getGreeting(), "Decorated by barney[Red]");
+
+        r.shutdown();
+
+    }
 
     @Test
     public void startup_inside_module()

Added: tapestry/tapestry5/trunk/tapestry-ioc/src/test/java/org/apache/tapestry5/ioc/internal/AdviseByMarkerModule.java
URL: http://svn.apache.org/viewvc/tapestry/tapestry5/trunk/tapestry-ioc/src/test/java/org/apache/tapestry5/ioc/internal/AdviseByMarkerModule.java?rev=1026032&view=auto
==============================================================================
--- tapestry/tapestry5/trunk/tapestry-ioc/src/test/java/org/apache/tapestry5/ioc/internal/AdviseByMarkerModule.java (added)
+++ tapestry/tapestry5/trunk/tapestry-ioc/src/test/java/org/apache/tapestry5/ioc/internal/AdviseByMarkerModule.java Thu Oct 21 15:46:21 2010
@@ -0,0 +1,90 @@
+// Copyright 2010 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;
+
+import org.apache.tapestry5.ioc.GreenMarker;
+import org.apache.tapestry5.ioc.Greeter;
+import org.apache.tapestry5.ioc.Invocation;
+import org.apache.tapestry5.ioc.MethodAdvice;
+import org.apache.tapestry5.ioc.MethodAdviceReceiver;
+import org.apache.tapestry5.ioc.RedMarker;
+import org.apache.tapestry5.ioc.annotations.Advise;
+import org.apache.tapestry5.ioc.annotations.Local;
+import org.apache.tapestry5.ioc.annotations.Marker;
+import org.apache.tapestry5.ioc.annotations.Order;
+
+
+public class AdviseByMarkerModule
+{
+   
+    @Advise(serviceInterface=Greeter.class, id="foo")
+    @GreenMarker
+    @Order("before:Greeter")
+    public static void doAdviseOneMoreTime(MethodAdviceReceiver receiver)
+    {
+        doAdvise(receiver, "gamma");
+    }
+   
+    @Advise(serviceInterface=Greeter.class, id="bar")
+    @GreenMarker
+    @Order({"after:foo", "before:Greeter"})
+    public static void doAdviseAgain(MethodAdviceReceiver receiver)
+    {
+        doAdvise(receiver, "beta");
+    }
+    
+    @Advise(serviceInterface=Greeter.class)
+    @GreenMarker
+    public static void doAdvise(MethodAdviceReceiver receiver)
+    {
+        doAdvise(receiver, "alpha");
+    }
+    
+    private static void doAdvise(MethodAdviceReceiver receiver, final String id)
+    {
+        receiver.adviseAllMethods(new MethodAdvice()
+        {
+           
+            public void advise(Invocation invocation)
+            {
+                invocation.proceed();
+               
+                Object result = invocation.getResult();
+               
+                invocation.overrideResult(String.format("%s[%s]", id, result));
+               
+            }
+        });
+    }
+   
+    @Advise(serviceInterface=Greeter.class, id="barney")
+    @Local
+    public static void localAdvise(MethodAdviceReceiver receiver)
+    {
+        doAdvise(receiver, "delta");
+    }
+   
+    @Marker(RedMarker.class)
+    public Greeter buildRedGreeter()
+    {
+        return new Greeter()
+        {
+            public String getGreeting()
+            {
+                return "Red";
+            }
+        };
+    }
+
+}

Propchange: tapestry/tapestry5/trunk/tapestry-ioc/src/test/java/org/apache/tapestry5/ioc/internal/AdviseByMarkerModule.java
------------------------------------------------------------------------------
    svn:mime-type = text/plain

Added: tapestry/tapestry5/trunk/tapestry-ioc/src/test/java/org/apache/tapestry5/ioc/internal/DecorateByMarkerModule.java
URL: http://svn.apache.org/viewvc/tapestry/tapestry5/trunk/tapestry-ioc/src/test/java/org/apache/tapestry5/ioc/internal/DecorateByMarkerModule.java?rev=1026032&view=auto
==============================================================================
--- tapestry/tapestry5/trunk/tapestry-ioc/src/test/java/org/apache/tapestry5/ioc/internal/DecorateByMarkerModule.java (added)
+++ tapestry/tapestry5/trunk/tapestry-ioc/src/test/java/org/apache/tapestry5/ioc/internal/DecorateByMarkerModule.java Thu Oct 21 15:46:21 2010
@@ -0,0 +1,99 @@
+// Copyright 2010 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;
+
+import org.apache.tapestry5.ioc.GreenMarker;
+import org.apache.tapestry5.ioc.Greeter;
+import org.apache.tapestry5.ioc.Invocation;
+import org.apache.tapestry5.ioc.MethodAdvice;
+import org.apache.tapestry5.ioc.RedMarker;
+import org.apache.tapestry5.ioc.ServiceResources;
+import org.apache.tapestry5.ioc.annotations.Decorate;
+import org.apache.tapestry5.ioc.annotations.Local;
+import org.apache.tapestry5.ioc.annotations.Marker;
+import org.apache.tapestry5.ioc.annotations.Order;
+import org.apache.tapestry5.ioc.services.AspectDecorator;
+import org.apache.tapestry5.ioc.services.AspectInterceptorBuilder;
+
+
+public class DecorateByMarkerModule
+{
+   
+    @Decorate(serviceInterface=Greeter.class, id="foo")
+    @GreenMarker
+    public static <T> T greeter(ServiceResources resources, T delegate, AspectDecorator aspectDecorator)
+    {
+        return doDecorate("foo", resources, delegate, aspectDecorator);
+    }
+   
+    @Decorate(serviceInterface=Greeter.class, id="bar")
+    @GreenMarker
+    @Order("after:foo")
+    public static <T> T greeter2(ServiceResources resources, T delegate, AspectDecorator aspectDecorator)
+    {
+        return doDecorate("bar", resources, delegate, aspectDecorator);
+    }
+   
+    @Decorate(serviceInterface=Greeter.class, id="baz")
+    @GreenMarker
+    @Order({"after:foo", "before:bar"})
+    public static <T> T greeter3(ServiceResources resources, T delegate, AspectDecorator aspectDecorator)
+    {
+        return doDecorate("baz", resources, delegate, aspectDecorator);
+    }
+   
+    @Decorate(serviceInterface=Greeter.class, id="barney")
+    @Local
+    public static <T> T localAdvise(ServiceResources resources, T delegate, AspectDecorator aspectDecorator)
+    {
+        return doDecorate("barney", resources, delegate, aspectDecorator);
+    }
+   
+    private static <T> T doDecorate(final String decoratorId, ServiceResources resources, T delegate, AspectDecorator aspectDecorator)
+    {
+        Class<T> serviceInterface = resources.getServiceInterface();
+       
+        AspectInterceptorBuilder<T> builder = aspectDecorator.createBuilder(serviceInterface, delegate, String.format(
+                "<Interceptor for %s(%s)>", resources.getServiceId(), serviceInterface.getName()));
+
+        builder.adviseAllMethods(new MethodAdvice()
+        {
+           
+            public void advise(Invocation invocation)
+            {
+                invocation.proceed();
+               
+                Object result = invocation.getResult();
+               
+                invocation.overrideResult(String.format("Decorated by %s[%s]", decoratorId, result));
+               
+            }
+        });
+
+        return builder.build();
+    }
+   
+    @Marker(RedMarker.class)
+    public Greeter buildRedGreeter()
+    {
+        return new Greeter()
+        {
+            public String getGreeting()
+            {
+                return "Red";
+            }
+        };
+    }
+
+}

Propchange: tapestry/tapestry5/trunk/tapestry-ioc/src/test/java/org/apache/tapestry5/ioc/internal/DecorateByMarkerModule.java
------------------------------------------------------------------------------
    svn:mime-type = text/plain

Modified: tapestry/tapestry5/trunk/tapestry-ioc/src/test/java/org/apache/tapestry5/ioc/internal/ModuleImplTest.java
URL: http://svn.apache.org/viewvc/tapestry/tapestry5/trunk/tapestry-ioc/src/test/java/org/apache/tapestry5/ioc/internal/ModuleImplTest.java?rev=1026032&r1=1026031&r2=1026032&view=diff
==============================================================================
--- tapestry/tapestry5/trunk/tapestry-ioc/src/test/java/org/apache/tapestry5/ioc/internal/ModuleImplTest.java (original)
+++ tapestry/tapestry5/trunk/tapestry-ioc/src/test/java/org/apache/tapestry5/ioc/internal/ModuleImplTest.java Thu Oct 21 15:46:21 2010
@@ -77,6 +77,7 @@ public class ModuleImplTest extends IOCI
         expect(rawDefs.iterator()).andReturn(Arrays.asList(def1, def2).iterator());
 
         train_matches(def1, serviceDef, false);
+        expect(serviceDef.getServiceInterface()).andReturn(Runnable.class);
         train_matches(def2, serviceDef, true);
 
         replay();