You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@hivemind.apache.org by jc...@apache.org on 2005/02/28 13:42:33 UTC

cvs commit: jakarta-hivemind/library/src/documentation/content/xdocs/hivemind-lib MethodInterceptorFactory.xml

jcarman     2005/02/28 04:42:33

  Modified:    .        .classpath
               src/documentation/content/xdocs site.xml links.ent
               library  build.xml
               library/src/descriptor/META-INF hivemodule.xml
  Added:       library/src/test/org/apache/hivemind/lib/impl
                        TestMethodInterceptorFactory.java
                        NonMethodInterceptor.xml
                        ServiceMethodInterceptor.xml FortuneCookie.java
                        InstanceMethodInterceptor.xml
                        SuffixMethodInterceptor.java FortuneCookieImpl.java
               library/src/java/org/apache/hivemind/lib/impl
                        MethodInterceptorFactory.java
               library/src/documentation/content/xdocs/hivemind-lib
                        MethodInterceptorFactory.xml
  Log:
  Create interceptor factory supporting aopalliance MethodInterceptors
  PR: HIVEMIND-45
  
  Revision  Changes    Path
  1.49      +1 -0      jakarta-hivemind/.classpath
  
  Index: .classpath
  ===================================================================
  RCS file: /home/cvs/jakarta-hivemind/.classpath,v
  retrieving revision 1.48
  retrieving revision 1.49
  diff -u -r1.48 -r1.49
  --- .classpath	11 Feb 2005 01:55:41 -0000	1.48
  +++ .classpath	28 Feb 2005 12:42:01 -0000	1.49
  @@ -27,5 +27,6 @@
   	<classpathentry kind="lib" path="ext-package/lib/groovy-all-1.0-beta-9.jar"/>
   	<classpathentry kind="lib" path="ext-package/lib/cglib-full-2.0.1.jar"/>
   	<classpathentry kind="lib" path="ext-package/lib/easymockclassextension-1.1.jar"/>
  +	<classpathentry kind="lib" path="ext-package/lib/aopalliance-1.0.jar"/>
   	<classpathentry kind="output" path="bin"/>
   </classpath>
  
  
  
  1.1                  jakarta-hivemind/library/src/test/org/apache/hivemind/lib/impl/TestMethodInterceptorFactory.java
  
  Index: TestMethodInterceptorFactory.java
  ===================================================================
  //Copyright 2004, 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.hivemind.lib.impl;
  
  import org.apache.hivemind.ApplicationRuntimeException;
  import org.apache.hivemind.Registry;
  import org.apache.hivemind.test.HiveMindTestCase;
  
  /**
   * Tests for {@link MethodInterceptorFactory}.
   * 
   * @author James Carman
   * @since 1.1
   */
  public class TestMethodInterceptorFactory extends HiveMindTestCase
  {
  
      public void testWithInstanceMethodInterceptor() throws Exception
      {
          Registry registry = buildFrameworkRegistry("InstanceMethodInterceptor.xml");
          final FortuneCookie cookie = (FortuneCookie) registry.getService(FortuneCookie.class);
          assertEquals( FortuneCookieImpl.FORTUNE + SuffixMethodInterceptor.SUFFIX, cookie.generateFortune());
      }
      
      public void testWithServiceMethodInterceptor() throws Exception
      {
          Registry registry = buildFrameworkRegistry("ServiceMethodInterceptor.xml");
          final FortuneCookie cookie = (FortuneCookie) registry.getService(FortuneCookie.class);
          assertEquals( FortuneCookieImpl.FORTUNE + SuffixMethodInterceptor.SUFFIX, cookie.generateFortune());
      }
      
      public void testWithNonMethodInterceptor() throws Exception
      {
          Registry registry = buildFrameworkRegistry("NonMethodInterceptor.xml");
          try
          {
              final FortuneCookie cookie = (FortuneCookie) registry.getService(FortuneCookie.class);
              cookie.generateFortune();
              fail( "Should not be able to construct service interceptor using non-MethodInterceptor instance." );
          }
          catch( ApplicationRuntimeException e )
          {
          }
          
      }
  }
  
  
  
  1.1                  jakarta-hivemind/library/src/test/org/apache/hivemind/lib/impl/NonMethodInterceptor.xml
  
  Index: NonMethodInterceptor.xml
  ===================================================================
  <?xml version="1.0"?>
  <!-- 
     Copyright 2004, 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.
  -->
  
  <module id="hivemind.lib.test" version="1.0.0">
    
    <service-point id="FortuneCookie" interface="org.apache.hivemind.lib.impl.FortuneCookie" >
      <create-instance class="org.apache.hivemind.lib.impl.FortuneCookieImpl" />
      <interceptor service-id="hivemind.lib.MethodInterceptorFactory">
        <impl object="instance:java.lang.String" />
      </interceptor>
    </service-point>
    
  </module>
  
  
  1.1                  jakarta-hivemind/library/src/test/org/apache/hivemind/lib/impl/ServiceMethodInterceptor.xml
  
  Index: ServiceMethodInterceptor.xml
  ===================================================================
  <?xml version="1.0"?>
  <!-- 
     Copyright 2004, 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.
  -->
  
  <module id="hivemind.lib.test" version="1.0.0">
    
    <service-point id="FortuneCookie" interface="org.apache.hivemind.lib.impl.FortuneCookie">
      <create-instance class="org.apache.hivemind.lib.impl.FortuneCookieImpl"/>
      <interceptor service-id="hivemind.lib.MethodInterceptorFactory">
        <impl object="service:SuffixMethodInterceptor" />
      </interceptor>
    </service-point>
    
    <service-point id="SuffixMethodInterceptor" interface="org.aopalliance.intercept.MethodInterceptor">
      <create-instance class="org.apache.hivemind.lib.impl.SuffixMethodInterceptor"/>
    </service-point>
    
  </module>
  
  
  1.1                  jakarta-hivemind/library/src/test/org/apache/hivemind/lib/impl/FortuneCookie.java
  
  Index: FortuneCookie.java
  ===================================================================
  //Copyright 2004, 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.hivemind.lib.impl;
  
  /**
   * @author James Carman
   * @since 1.1
   */
  public interface FortuneCookie
  {
      public String generateFortune();
  }
  
  
  
  1.1                  jakarta-hivemind/library/src/test/org/apache/hivemind/lib/impl/InstanceMethodInterceptor.xml
  
  Index: InstanceMethodInterceptor.xml
  ===================================================================
  <?xml version="1.0"?>
  <!-- 
     Copyright 2004, 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.
  -->
  
  <module id="hivemind.lib.test" version="1.0.0">
    
    <service-point id="FortuneCookie" interface="org.apache.hivemind.lib.impl.FortuneCookie">
      <create-instance class="org.apache.hivemind.lib.impl.FortuneCookieImpl"/>
      <interceptor service-id="hivemind.lib.MethodInterceptorFactory">
        <impl object="instance:org.apache.hivemind.lib.impl.SuffixMethodInterceptor" />
      </interceptor>
    </service-point>
    
  </module>
  
  
  1.1                  jakarta-hivemind/library/src/test/org/apache/hivemind/lib/impl/SuffixMethodInterceptor.java
  
  Index: SuffixMethodInterceptor.java
  ===================================================================
  //Copyright 2004, 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.hivemind.lib.impl;
  
  import org.aopalliance.intercept.MethodInterceptor;
  import org.aopalliance.intercept.MethodInvocation;
  
  /**
   * 
   * @author James Carman
   * @since 1.1
   */
  public class SuffixMethodInterceptor implements MethodInterceptor
  {
      public static final String SUFFIX = " in bed.";
      
      public Object invoke(MethodInvocation invocation) throws Throwable
      {
          return invocation.proceed() + SUFFIX;
      }
  }
  
  
  
  1.1                  jakarta-hivemind/library/src/test/org/apache/hivemind/lib/impl/FortuneCookieImpl.java
  
  Index: FortuneCookieImpl.java
  ===================================================================
  //Copyright 2004, 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.hivemind.lib.impl;
  
  /**
   * @author James Carman
   * @since 1.1
   */
  public class FortuneCookieImpl implements FortuneCookie
  {
      public static final String FORTUNE = "You will conquer obstacles to achieve success";
      
      public String generateFortune()
      {
          return FORTUNE;
      }
  
  }
  
  
  
  1.43      +1 -0      jakarta-hivemind/src/documentation/content/xdocs/site.xml
  
  Index: site.xml
  ===================================================================
  RCS file: /home/cvs/jakarta-hivemind/src/documentation/content/xdocs/site.xml,v
  retrieving revision 1.42
  retrieving revision 1.43
  diff -u -r1.42 -r1.43
  --- site.xml	19 Feb 2005 17:57:40 -0000	1.42
  +++ site.xml	28 Feb 2005 12:42:01 -0000	1.43
  @@ -123,6 +123,7 @@
         <hivemind.lib.ChainFactory label="ChainFactory" href="ChainFactory.html"/>
         <hivemind.lib.DefaultImplementationBuilder label="DefaultImplementationBuilder" href="DefaultImplementationBuilder.html"/>
   			<hivemind.lib.EJBProxyFactory label="EJBProxyFactory" href="EJBProxyFactory.html"/>
  +			<hivemind.lib.MethodInterceptorFactory label="MethodInterceptorFactory" href="MethodInterceptorFactory.html"/>
   			<hivemind.lib.NameLookup label="NameLookup" href="NameLookup.html"/>
         <hivemind.lib.PlaceholderFactory label="PlaceholderFactory" href="PlaceholderFactory.html"/> 
         <hivemind.lib.PipelineFactory label="PipelineFactory" href="PipelineFactory.html"/>     
  
  
  
  1.25      +2 -1      jakarta-hivemind/src/documentation/content/xdocs/links.ent
  
  Index: links.ent
  ===================================================================
  RCS file: /home/cvs/jakarta-hivemind/src/documentation/content/xdocs/links.ent,v
  retrieving revision 1.24
  retrieving revision 1.25
  diff -u -r1.24 -r1.25
  --- links.ent	19 Feb 2005 17:57:40 -0000	1.24
  +++ links.ent	28 Feb 2005 12:42:01 -0000	1.25
  @@ -159,4 +159,5 @@
   <!ENTITY hivemind.lib.NameLookup '<link href="site:hivemind.lib.NameLookup">hivemind.lib.NameLookup</link>'>
   <!ENTITY hivemind.lib.RemoteExceptionCoordinator '<link href="site:hivemind.lib.RemoteExceptionCoordinator">hivemind.lib.RemoteExceptionCoordinator</link>'>
   <!ENTITY hivemind.lib.ChainBuilder '<link href="site:hivemind.lib.ChainBuilder">hivemind.lib.ChainBuilder</link>'>
  -<!ENTITY hivemind.lib.ChainFactory '<link href="site:hivemind.lib.ChainFactory">hivemind.lib.ChainFactory</link>'>
  \ No newline at end of file
  +<!ENTITY hivemind.lib.ChainFactory '<link href="site:hivemind.lib.ChainFactory">hivemind.lib.ChainFactory</link>'>
  +<!ENTITY hivemind.lib.MethodInterceptorFactory '<link href="site:hivemind.lib.MethodInterceptorFactory">hivemind.lib.MethodInterceptorFactory</link>'>
  
  
  
  1.16      +1 -1      jakarta-hivemind/library/build.xml
  
  Index: build.xml
  ===================================================================
  RCS file: /home/cvs/jakarta-hivemind/library/build.xml,v
  retrieving revision 1.15
  retrieving revision 1.16
  diff -u -r1.15 -r1.16
  --- build.xml	1 Feb 2005 11:59:01 -0000	1.15
  +++ build.xml	28 Feb 2005 12:42:05 -0000	1.16
  @@ -46,7 +46,7 @@
   		<ibiblio-dependency artifact="servletapi" version="2.3" group="servletapi" use="test"/>				
   		<ibiblio-dependency artifact="oro" version="2.0.6" group="oro" use="test"/>			
   		<ibiblio-dependency artifact="easymock" version="1.1" group="easymock" use="test"/>
  -		
  +		<ibiblio-dependency artifact="aopalliance" version="1.0" group="aopalliance" />
   		<project-dependency artifact="hivemind"/>
   		
   		<default-compile/>
  
  
  
  1.1                  jakarta-hivemind/library/src/java/org/apache/hivemind/lib/impl/MethodInterceptorFactory.java
  
  Index: MethodInterceptorFactory.java
  ===================================================================
  //Copyright 2004, 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.hivemind.lib.impl;
  
  import java.lang.reflect.AccessibleObject;
  import java.lang.reflect.InvocationHandler;
  import java.lang.reflect.InvocationTargetException;
  import java.lang.reflect.Method;
  import java.lang.reflect.Proxy;
  import java.util.List;
  
  import org.aopalliance.intercept.MethodInterceptor;
  import org.aopalliance.intercept.MethodInvocation;
  import org.apache.hivemind.ApplicationRuntimeException;
  import org.apache.hivemind.InterceptorStack;
  import org.apache.hivemind.ServiceInterceptorFactory;
  import org.apache.hivemind.impl.BaseLocatable;
  import org.apache.hivemind.internal.Module;
  import org.apache.hivemind.util.Defense;
  
  /**
   * A service interceptor factory supporting the AOP Alliance MethodInterceptor interface.
   * <b>Note:</b>The current implementation uses JDK proxies as opposed to Javassist! 
   * @author James Carman
   * @since 1.1
   */
  public class MethodInterceptorFactory extends BaseLocatable implements ServiceInterceptorFactory
  {
  
      /**
       * 
       * @see org.apache.hivemind.ServiceInterceptorFactory#createInterceptor(org.apache.hivemind.InterceptorStack, org.apache.hivemind.internal.Module, java.util.List)
       */
      public void createInterceptor(InterceptorStack stack, Module invokingModule, List parameters)
      {
          final Class[] interfaces = new Class[]{stack.getServiceInterface()};
          final ClassLoader classLoader = invokingModule.getClassResolver().getClassLoader();
          final Object parameter = parameters.get( 0 );
          Defense.isAssignable( parameter, MethodInterceptor.class, "Implementation Object" );
          MethodInterceptor methodInterceptor = ( MethodInterceptor )parameter;
          final InvocationHandler invocationHandler = new MethodInterceptorInvocationHandler( methodInterceptor, stack );
          stack.push( Proxy.newProxyInstance( classLoader, interfaces, invocationHandler ) );
      }
      
      /**
       * A java proxy InvocationHandler implementation which allows a MethodInterceptor to intercept the method invocation.
       */
      private final class MethodInterceptorInvocationHandler implements InvocationHandler
      {
          private final MethodInterceptor methodInterceptor;
          private final InterceptorStack stack;
          private final Object target;
  
          /**
           * Constructs a MethodInterceptorInvocationHandler
           *
           * @param stack       the interceptor stack
           */
          public MethodInterceptorInvocationHandler( MethodInterceptor methodInterceptor, InterceptorStack stack )
          {
              this.stack = stack;
              this.target = stack.peek();
              this.methodInterceptor = methodInterceptor;
          }
  
          /**
           * Calls the MethodInterceptor's invoke method.
           * @param proxy  a reference to the proxy instance
           * @param method the method being invoked
           * @param args   the arguments to the method
           * @return the value returned by the MethodInterceptor
           * @throws Throwable
           */
          public Object invoke( Object proxy, Method method, Object[] args ) throws Throwable
          {
              return methodInterceptor.invoke( new MethodInvocationImpl( target, method, args, stack.peek() ) );
          }
      }
  
      /**
       * A java reflection-based implementation of a MethodInvocation
       */
      private final class MethodInvocationImpl implements MethodInvocation
      {
          private final Object next;
          private final Method method;
          private final Object[] arguments;
          private final Object proxy;
  
          /**
           * Constructs a MethodInvocationImpl object.
           *
           * @param next      the next object
           * @param method    the method
           * @param arguments the arguments
           * @param proxy     the outermost proxy object (allows calling another method instead).
           */
          public MethodInvocationImpl( Object next, Method method, Object[] arguments, Object proxy )
          {
              this.next = next;
              this.method = method;
              this.arguments = arguments;
              this.proxy = proxy;
          }
  
          /**
           * Invokes the method on the next object.
           *
           * @return value returned by invoking the method on the next object
           * @throws Throwable throwable thrown by invoking method on the next object
           */
          public final Object proceed() throws Throwable
          {
              try
              {
                  return method.invoke( next, arguments );
              }
              catch( InvocationTargetException e )
              {
                  throw e.getTargetException();
              }
          }
  
          public final Method getMethod()
          {
              return method;
          }
  
          public final AccessibleObject getStaticPart()
          {
              return method;
          }
  
          public final Object getThis()
          {
              return proxy;
          }
  
          public final Object[] getArguments()
          {
              return arguments;
          }
      }
  }
  
  
  
  1.23      +18 -1     jakarta-hivemind/library/src/descriptor/META-INF/hivemodule.xml
  
  Index: hivemodule.xml
  ===================================================================
  RCS file: /home/cvs/jakarta-hivemind/library/src/descriptor/META-INF/hivemodule.xml,v
  retrieving revision 1.22
  retrieving revision 1.23
  diff -u -r1.22 -r1.23
  --- hivemodule.xml	10 Feb 2005 01:04:34 -0000	1.22
  +++ hivemodule.xml	28 Feb 2005 12:42:33 -0000	1.23
  @@ -440,5 +440,22 @@
       </parameters-schema>
       
     </service-point>
  -  
  +  <service-point id="MethodInterceptorFactory" parameters-occurs="1" interface="org.apache.hivemind.ServiceInterceptorFactory">
  +    <invoke-factory>
  +      <construct class="org.apache.hivemind.lib.impl.MethodInterceptorFactory" />
  +    </invoke-factory>
  +    
  +    <parameters-schema>
  +      <element name="impl">
  +        <attribute name="object" required="true" translator="object">
  +          The implementation object which implements the MethodInterceptor interface.
  +        </attribute>
  +
  +		<rules>
  +		  <push-attribute attribute="object" />
  +		  <invoke-parent method="addElement" />
  +		</rules>
  +      </element>
  +    </parameters-schema>
  +  </service-point>
   </module>
  
  
  
  1.1                  jakarta-hivemind/library/src/documentation/content/xdocs/hivemind-lib/MethodInterceptorFactory.xml
  
  Index: MethodInterceptorFactory.xml
  ===================================================================
  <?xml version="1.0"?>
  <!-- 
     Copyright 2004, 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.
  -->
  
  <!DOCTYPE document PUBLIC "-//APACHE//DTD Documentation V1.3//EN"
  	"http://xml.apache.org/forrest/dtd/document-v13.dtd" [
  	<!ENTITY projectroot '../'>
  	<!ENTITY % common-links SYSTEM "../links.ent">
  	%common-links;
  	]>
  <document>
  	<header>
  		<title>hivemind.lib.MethodInterceptorFactory Service</title>
  	</header>
  	<body>
  		<p>The <link href="&hivedoc;/service/hivemind.lib.MethodInterceptorFactory.html">
  		    MethodInterceptorFactory</link> is a service interceptor factory supporting
  		    AOP Alliance MethodInterceptors as service interceptors.</p>
  		<p>The <code>impl</code> parameter identifies the <code>MethodInterceptor</code> to
  		use.  It can be any object implementing the <code>MethodInterceptor</code> interface.</p>
  		<source><![CDATA[
         <interceptor service-id="hivemind.lib.MethodInterceptorFactory">
           <impl object="service:SomeService" />
         </interceptor> 
      
         <interceptor service-id="hivemind.lib.MethodInterceptorFactory">
           <impl object="instance:com.myco.interceptor.SecurityInterceptor" />
         </interceptor>]]>
      </source>
  	
  	</body>
  </document>
  
  
  

---------------------------------------------------------------------
To unsubscribe, e-mail: hivemind-cvs-unsubscribe@jakarta.apache.org
For additional commands, e-mail: hivemind-cvs-help@jakarta.apache.org