]> source.dussan.org Git - archiva.git/commitdiff
multiple fixes
authorNicolas De Loof <nicolas@apache.org>
Mon, 25 Feb 2008 14:43:31 +0000 (14:43 +0000)
committerNicolas De Loof <nicolas@apache.org>
Mon, 25 Feb 2008 14:43:31 +0000 (14:43 +0000)
refactoring & code cleanup
throws exception when converted plexus descriptor doesn't specify field-name
"-Dplexus-spring.debug=true" option to dump converted XML (requires dom4j)

git-svn-id: https://svn.apache.org/repos/asf/maven/archiva/branches@630864 13f79535-47bb-0310-9956-ffa450edef68

springy/plexus-spring/pom.xml
springy/plexus-spring/src/main/java/org/codehaus/plexus/spring/PlexusBeanDefinitionDocumentReader.java
springy/plexus-spring/src/main/java/org/codehaus/plexus/spring/PlexusComponentFactoryBean.java
springy/plexus-spring/src/main/java/org/codehaus/plexus/spring/PlexusInSpringTestCase.java
springy/plexus-spring/src/main/java/org/codehaus/plexus/spring/PlexusNamespaceHandler.java
springy/plexus-spring/src/main/resources/plexus.xsd
springy/plexus-spring/src/test/java/org/codehaus/plexus/spring/FieldInjectionTest.java

index cc81db28686ff871dcc869768269726867869615..a5983c141ab9b81557625e9deb7139e37d91ab9e 100644 (file)
       <artifactId>plexus-component-api</artifactId>\r
       <version>1.0-alpha-33</version>\r
     </dependency>\r
+    <dependency>\r
+      <groupId>dom4j</groupId>\r
+      <artifactId>dom4j</artifactId>\r
+      <version>1.6.1</version>\r
+      <optional>true</optional>\r
+    </dependency>\r
     <dependency>\r
       <groupId>junit</groupId>\r
       <artifactId>junit</artifactId>\r
index d954a1c3a7fd5e2721bfc423aa74ac0f6b32563f..3866db78d950bb6d638691ee4e5e1872fd7be273 100644 (file)
@@ -1,6 +1,5 @@
 package org.codehaus.plexus.spring;\r
 \r
-\r
 /*\r
  * Licensed to the Apache Software Foundation (ASF) under one\r
  * or more contributor license agreements.  See the NOTICE file\r
@@ -29,6 +28,9 @@ import javax.xml.transform.dom.DOMResult;
 import javax.xml.transform.dom.DOMSource;\r
 import javax.xml.transform.stream.StreamSource;\r
 \r
+import org.dom4j.io.DOMReader;\r
+import org.dom4j.io.OutputFormat;\r
+import org.dom4j.io.XMLWriter;\r
 import org.springframework.beans.factory.BeanDefinitionStoreException;\r
 import org.springframework.beans.factory.xml.BeanDefinitionDocumentReader;\r
 import org.springframework.beans.factory.xml.DefaultBeanDefinitionDocumentReader;\r
@@ -47,12 +49,25 @@ public class PlexusBeanDefinitionDocumentReader
     public void registerBeanDefinitions( Document doc, XmlReaderContext readerContext )\r
     {\r
         doc = convertPlexusDescriptorToSpringBeans( doc );\r
+        if ( Boolean.getBoolean( "spring-plexus.debug" ) )\r
+        {\r
+            try\r
+            {\r
+                XMLWriter writer = new XMLWriter( System.out, OutputFormat.createPrettyPrint() );\r
+                writer.write( new DOMReader().read( doc ) );\r
+            }\r
+            catch ( Exception e )\r
+            {\r
+                // ignored\r
+            }\r
+        }\r
+\r
         super.registerBeanDefinitions( doc, readerContext );\r
     }\r
 \r
     protected Document convertPlexusDescriptorToSpringBeans( Document doc )\r
     {\r
-        if ( ! "component-set".equals( doc.getDocumentElement().getNodeName() ) )\r
+        if ( !"component-set".equals( doc.getDocumentElement().getNodeName() ) )\r
         {\r
             return doc;\r
         }\r
@@ -73,7 +88,8 @@ public class PlexusBeanDefinitionDocumentReader
         }\r
         catch ( Exception e )\r
         {\r
-            throw new BeanDefinitionStoreException( "Failed to translate plexus component descriptor to Spring XML context", e );\r
+            throw new BeanDefinitionStoreException(\r
+                "Failed to translate plexus component descriptor to Spring XML context", e );\r
         }\r
     }\r
 }\r
index 5dc9954f60e46c6acc68c5e8b8cc5b6629218fb1..735d5955f61861ed24e11c952320fcafc5a78db6 100644 (file)
@@ -20,6 +20,7 @@ package org.codehaus.plexus.spring;
  */\r
 \r
 import java.lang.reflect.Field;\r
+import java.util.ArrayList;\r
 import java.util.Collection;\r
 import java.util.HashMap;\r
 import java.util.Iterator;\r
@@ -28,8 +29,10 @@ import java.util.List;
 import java.util.Map;\r
 \r
 import org.codehaus.plexus.PlexusConstants;\r
+import org.codehaus.plexus.context.Context;\r
 import org.codehaus.plexus.logging.LogEnabled;\r
 import org.codehaus.plexus.logging.LoggerManager;\r
+import org.codehaus.plexus.personality.plexus.lifecycle.phase.Contextualizable;\r
 import org.codehaus.plexus.personality.plexus.lifecycle.phase.Disposable;\r
 import org.codehaus.plexus.personality.plexus.lifecycle.phase.Initializable;\r
 import org.springframework.beans.BeansException;\r
@@ -50,17 +53,17 @@ import org.springframework.util.ReflectionUtils;
  * <ul>\r
  * <li>Support for direct field injection or "requirements"</li>\r
  * <li>Support for LogEnabled, Initializable and Disposable plexus interfaces</li>\r
- * <li>Support for plexus.requirement to get a Map<role-hint, component> for a role\r
+ * <li>Support for plexus.requirement to get a Map<role-hint, component> for a\r
+ * role\r
  * </ul>\r
- * If not set, the beanFActory will auto-detect the loggerManager to use by searching for the adequate bean in the\r
- * spring context.\r
+ * If not set, the beanFActory will auto-detect the loggerManager to use by\r
+ * searching for the adequate bean in the spring context.\r
  *\r
  * @author <a href="mailto:nicolas@apache.org">Nicolas De Loof</a>\r
  */\r
 public class PlexusComponentFactoryBean\r
     implements FactoryBean, BeanFactoryAware, DisposableBean\r
 {\r
-\r
     private static final char HINT = '#';\r
 \r
     private Class role;\r
@@ -73,6 +76,8 @@ public class PlexusComponentFactoryBean
 \r
     private ListableBeanFactory beanFactory;\r
 \r
+    private Context contextWrapper;\r
+\r
     private LoggerManager loggerManager;\r
 \r
     private TypeConverter typeConverter = new SimpleTypeConverter();\r
@@ -104,6 +109,9 @@ public class PlexusComponentFactoryBean
             throw new BeanCreationException( "Plexus poolable instanciation-strategy is not supported" );\r
         }\r
 \r
+        // Spring MAY cache the object built by this factory if getSingleton()\r
+        // returns true,\r
+        // but can also requires us to ensure unicity.\r
         if ( "singleton".equals( instanciationStrategy ) && !instances.isEmpty() )\r
         {\r
             return instances.get( 0 );\r
@@ -121,57 +129,9 @@ public class PlexusComponentFactoryBean
                 public void doWith( Field field )\r
                     throws IllegalArgumentException, IllegalAccessException\r
                 {\r
-                    Object dependency = requirements.get( field.getName() );\r
-                    if ( dependency instanceof RuntimeBeanReference )\r
-                    {\r
-                        String beanName = ( (RuntimeBeanReference) dependency ).getBeanName();\r
-                        if ( Map.class.isAssignableFrom( field.getType() ) )\r
-                        {\r
-                            // component ask plexus for a Map of all available components for the role\r
-                            Map map = new HashMap();\r
-                            String mask = beanName + HINT;\r
-                            String[] beans = beanFactory.getBeanDefinitionNames();\r
-                            for ( int i = 0; i < beans.length; i++ )\r
-                            {\r
-                                String name = beans[i];\r
-                                if ( name.startsWith( mask ) )\r
-                                {\r
-                                    map.put( name.substring( mask.length() ), beanFactory.getBean( name ) );\r
-                                }\r
-                            }\r
-                            if ( beanFactory.containsBean( beanName ) )\r
-                            {\r
-                                map.put( PlexusConstants.PLEXUS_DEFAULT_HINT, beanFactory.getBean( beanName ) );\r
-                            }\r
-                            dependency = map;\r
-                        }\r
-                        else if ( Collection.class.isAssignableFrom( field.getType() ) )\r
-                        {\r
-                            List list = new LinkedList();\r
-                            String mask = beanName + HINT;\r
-                            String[] beans = beanFactory.getBeanDefinitionNames();\r
-                            for ( int i = 0; i < beans.length; i++ )\r
-                            {\r
-                                String name = beans[i];\r
-                                if ( name.startsWith( mask ) )\r
-                                {\r
-                                    list.add( beanFactory.getBean( name ) );\r
-                                }\r
-                            }\r
-                            if ( beanFactory.containsBean( beanName ) )\r
-                            {\r
-                                list.add( beanFactory.getBean( beanName ) );\r
-                            }\r
-                            dependency = list;\r
-                        }\r
-                        else\r
-                        {\r
-                             dependency = beanFactory.getBean( beanName );\r
-                        }\r
-                    }\r
+                    Object dependency = resolveRequirement( field );\r
                     if ( dependency != null )\r
                     {\r
-                        dependency = typeConverter.convertIfNecessary( dependency, field.getType() );\r
                         ReflectionUtils.makeAccessible( field );\r
                         ReflectionUtils.setField( field, component, dependency );\r
                     }\r
@@ -179,12 +139,16 @@ public class PlexusComponentFactoryBean
             }, ReflectionUtils.COPYABLE_FIELDS );\r
         }\r
 \r
-\r
         if ( component instanceof LogEnabled )\r
         {\r
             ( (LogEnabled) component ).enableLogging( getLoggerManager().getLoggerForComponent( role.getName() ) );\r
         }\r
 \r
+        if (component instanceof Contextualizable )\r
+        {\r
+            ((Contextualizable) component).contextualize( contextWrapper );\r
+        }\r
+\r
         if ( component instanceof Initializable )\r
         {\r
             ( (Initializable) component ).initialize();\r
@@ -205,7 +169,11 @@ public class PlexusComponentFactoryBean
         return "per-lookup".equals( instanciationStrategy );\r
     }\r
 \r
-    private LoggerManager getLoggerManager()\r
+    /**\r
+     * Retrieve the loggerManager instance to be used for LogEnabled components\r
+     * @return\r
+     */\r
+    protected LoggerManager getLoggerManager()\r
     {\r
         if ( loggerManager == null )\r
         {\r
@@ -221,7 +189,7 @@ public class PlexusComponentFactoryBean
             else\r
             {\r
                 throw new BeanInitializationException(\r
-                                                       "You must explicitly set a LoggerManager or define a unique one in bean context" );\r
+                    "You must explicitly set a LoggerManager or define a unique one in bean context" );\r
             }\r
         }\r
         return loggerManager;\r
@@ -262,7 +230,7 @@ public class PlexusComponentFactoryBean
      */\r
     public void setInstanciationStrategy( String instanciationStrategy )\r
     {\r
-        if (instanciationStrategy.length() == 0)\r
+        if ( instanciationStrategy.length() == 0 )\r
         {\r
             instanciationStrategy = "singleton";\r
         }\r
@@ -282,4 +250,64 @@ public class PlexusComponentFactoryBean
         this.typeConverter = typeConverter;\r
     }\r
 \r
+    /**\r
+     * Create a Map of all available implementation of the expected role\r
+     * @param beanName\r
+     * @return Map<role-hint, component>\r
+     */\r
+    protected Map getRoleMap( String beanName )\r
+    {\r
+        Map map = new HashMap();\r
+        String mask = beanName + HINT;\r
+        String[] beans = beanFactory.getBeanDefinitionNames();\r
+        for ( int i = 0; i < beans.length; i++ )\r
+        {\r
+            String name = beans[i];\r
+            if ( name.startsWith( mask ) )\r
+            {\r
+                map.put( name.substring( mask.length() ), beanFactory.getBean( name ) );\r
+            }\r
+        }\r
+        if ( beanFactory.containsBean( beanName ) )\r
+        {\r
+            map.put( PlexusConstants.PLEXUS_DEFAULT_HINT, beanFactory.getBean( beanName ) );\r
+        }\r
+        return map;\r
+    }\r
+\r
+\r
+    /**\r
+     * Resolve the requirement that this field exposes in the component\r
+     * @param field\r
+     * @return\r
+     */\r
+    protected Object resolveRequirement( Field field )\r
+    {\r
+        Object dependency =  requirements.get( field.getName() );\r
+        if ( dependency instanceof RuntimeBeanReference )\r
+        {\r
+            String beanName = ( (RuntimeBeanReference) dependency ).getBeanName();\r
+            if ( Map.class.isAssignableFrom( field.getType() ) )\r
+            {\r
+                // component ask plexus for a Map of all available\r
+                // components for the role\r
+                dependency = getRoleMap( beanName );\r
+            }\r
+            else if ( Collection.class.isAssignableFrom( field.getType() ) )\r
+            {\r
+                dependency = new ArrayList( getRoleMap( beanName ).values() );\r
+            }\r
+            else\r
+            {\r
+                dependency = beanFactory.getBean( beanName );\r
+            }\r
+        }\r
+        if (dependency != null)\r
+        {\r
+            dependency = typeConverter.convertIfNecessary( dependency, field.getType() );\r
+        }\r
+        return dependency;\r
+\r
+    }\r
+\r
 }\r
index 079a567315cadf07b30de9fa58ef904f82135ba1..f2bd24113417f840aac8bde0ece5911d46ef4260 100644 (file)
@@ -47,7 +47,6 @@ public class PlexusInSpringTestCase
         applicationContext =
             new PlexusClassPathXmlApplicationContext( new String[] {
                 "classpath*:META-INF/plexus/components.xml",
-                "classpath*:META-INF/plexus/components-fragment.xml",
                 "classpath*:" + getPlexusConfigLocation(),
                 "classpath*:" + getSpringConfigLocation()} );
     }
index 03081a05f852b29b87ae9e716d605f8830fbe431..4fce66574fa6875f66ec4b220ef5dea0832e2b31 100644 (file)
@@ -32,6 +32,7 @@ import org.springframework.beans.factory.xml.AbstractBeanDefinitionParser;
 import org.springframework.beans.factory.xml.AbstractSingleBeanDefinitionParser;\r
 import org.springframework.beans.factory.xml.NamespaceHandlerSupport;\r
 import org.springframework.beans.factory.xml.ParserContext;\r
+import org.springframework.context.ApplicationContextException;\r
 import org.springframework.util.xml.DomUtils;\r
 import org.w3c.dom.Element;\r
 \r
@@ -48,10 +49,11 @@ public class PlexusNamespaceHandler
     public void init()\r
     {\r
         registerBeanDefinitionParser( "component", new PlexusComponentBeanDefinitionParser() );\r
-        registerBeanDefinitionParser( "requirement", new PlexusPropertyBeanDefinitionParser() );\r
+        registerBeanDefinitionParser( "requirement", new NopBeanDefinitionParser() );\r
+        registerBeanDefinitionParser( "configuration", new NopBeanDefinitionParser() );\r
     }\r
 \r
-    private class PlexusPropertyBeanDefinitionParser\r
+    private class NopBeanDefinitionParser\r
         extends AbstractBeanDefinitionParser\r
     {\r
         protected AbstractBeanDefinition parseInternal( Element element, ParserContext parserContext )\r
@@ -86,6 +88,10 @@ public class PlexusNamespaceHandler
             {\r
                 Element child = (Element) iterator.next();\r
                 String name = child.getAttribute( "name" );\r
+                if (name.length() == 0)\r
+                {\r
+                    throw new ApplicationContextException( "No field name for plexus requirement on " + implementation );\r
+                }\r
                 String role = child.getAttribute( "role" );\r
                 String roleHint = child.getAttribute( "role-hint" );\r
                 String ref = PlexusToSpringUtils.buildSpringId( role, roleHint );\r
index 6b5558bebf345ecfbf00e1a932dc6b188410d998..694228c0829f6ff1461c4620d19e6a3009178d26 100644 (file)
@@ -1,8 +1,8 @@
 <?xml version="1.0" encoding="UTF-8"?>\r
-<xsd:schema xmlns="http://plexus.codehaus.org/spring" xmlns:xsd="http://www.w3.org/2001/XMLSchema" \r
-targetNamespace="http://plexus.codehaus.org/spring" \r
+<xsd:schema xmlns="http://plexus.codehaus.org/spring" xmlns:xsd="http://www.w3.org/2001/XMLSchema"\r
+targetNamespace="http://plexus.codehaus.org/spring"\r
 elementFormDefault="qualified" attributeFormDefault="unqualified">\r
\r
+\r
   <xsd:element name="component">\r
         <xsd:complexType>\r
           <xsd:sequence>\r
index 16c016a5d57c9b1de9e0aedc38519fdde52266db..1f288bd4354ecd9a15b87860827fcf17b662dcfb 100644 (file)
@@ -29,19 +29,19 @@ public class FieldInjectionTest
     public void testFieldInjectionInSpringContext()\r
         throws Exception\r
     {\r
-        ConfigurableApplicationContext applicationContext = new PlexusClassPathXmlApplicationContext( new String[] { "components.xml", "applicationContext.xml" } );       \r
+        ConfigurableApplicationContext applicationContext = new PlexusClassPathXmlApplicationContext( new String[] { "components.xml", "applicationContext.xml" } );\r
         PlexusBean plexusBean = (PlexusBean) applicationContext.getBean( "plexusBean" );\r
         assertEquals( PlexusBean.INITIALIZED, plexusBean.getState() );\r
         assertEquals( "field injection failed", "expected SpringBean", plexusBean.toString() );\r
         applicationContext.close();\r
         assertEquals( PlexusBean.DISPOSED, plexusBean.getState() );\r
-        \r
+\r
     }\r
-    \r
-    public void testIbjectMapForRole()\r
+\r
+    public void testInjectMapForRole()\r
         throws Exception\r
     {\r
-        ConfigurableApplicationContext applicationContext = new PlexusClassPathXmlApplicationContext( new String[] { "components.xml", "applicationContext.xml" } );       \r
+        ConfigurableApplicationContext applicationContext = new PlexusClassPathXmlApplicationContext( new String[] { "components.xml", "applicationContext.xml" } );\r
         ComplexPlexusBean plexusBean = (ComplexPlexusBean) applicationContext.getBean( "complexPlexusBean" );\r
         assertEquals( "2 components for role org.codehaus.plexus.spring.PlexusBean", plexusBean.toString() );\r
     }\r