You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@felix.apache.org by cl...@apache.org on 2007/06/24 19:44:57 UTC

svn commit: r550265 [1/2] - in /felix/trunk: ./ ipojo/arch/ ipojo/arch/src/main/resources/ ipojo/core/ ipojo/core/src/main/java/org/apache/felix/ipojo/ ipojo/core/src/main/java/org/apache/felix/ipojo/composite/service/importer/ ipojo/core/src/main/java...

Author: clement
Date: Sun Jun 24 10:44:53 2007
New Revision: 550265

URL: http://svn.apache.org/viewvc?view=rev&rev=550265
Log:
Commit the new iPOJO Version (Felix-311)
Change the global pom file : the iPOJO profile is no more useful thanks to the new maven plugin. However, manipulator and metadata move inside the plugins profile (required to compile the new maven plugin)

Added:
    felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/composite/service/provides/POJOWriter.java
    felix/trunk/ipojo/plugin/src/main/java/org/apache/felix/ipojo/plugin/ManipulatorMojo.java
Removed:
    felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/composite/service/provides/manipulation/
    felix/trunk/ipojo/plugin/src/main/java/org/apache/felix/ipojo/manipulation/
    felix/trunk/ipojo/plugin/src/main/java/org/apache/felix/ipojo/parser/
    felix/trunk/ipojo/plugin/src/main/java/org/apache/felix/ipojo/plugin/Clazz.java
    felix/trunk/ipojo/plugin/src/main/java/org/apache/felix/ipojo/plugin/IPojoPluginConfiguration.java
    felix/trunk/ipojo/plugin/src/main/java/org/apache/felix/ipojo/plugin/Jar.java
    felix/trunk/ipojo/plugin/src/main/java/org/apache/felix/ipojo/plugin/OsgiJarMojo.java
    felix/trunk/ipojo/plugin/src/main/java/org/apache/felix/ipojo/plugin/OsgiManifest.java
    felix/trunk/ipojo/plugin/src/main/java/org/apache/felix/ipojo/plugin/QuotedTokenizer.java
    felix/trunk/ipojo/plugin/src/main/resources/META-INF/plexus/
Modified:
    felix/trunk/ipojo/arch/pom.xml
    felix/trunk/ipojo/arch/src/main/resources/metadata.xml
    felix/trunk/ipojo/core/pom.xml
    felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/Activator.java
    felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/ComponentFactory.java
    felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/Handler.java
    felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/InstanceCreator.java
    felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/InstanceManager.java
    felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/composite/service/importer/ImportExportDescription.java
    felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/composite/service/importer/ImportExportHandler.java
    felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/composite/service/provides/CompositionMetadata.java
    felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/composite/service/provides/ProvidedServiceHandler.java
    felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/handlers/configuration/ConfigurationHandler.java
    felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/handlers/dependency/DependencyHandler.java
    felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/handlers/dependency/DependencyHandlerDescription.java
    felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/handlers/lifecycle/callback/LifecycleCallback.java
    felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/handlers/lifecycle/callback/LifecycleCallbackHandler.java
    felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/handlers/providedservice/Property.java
    felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/handlers/providedservice/ProvidedService.java
    felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/handlers/providedservice/ProvidedServiceHandler.java
    felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/parser/MethodMetadata.java
    felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/util/Callback.java
    felix/trunk/ipojo/plugin/pom.xml
    felix/trunk/ipojo/plugin/src/main/resources/archetype-resources/pom.xml
    felix/trunk/ipojo/plugin/src/main/resources/archetype-resources/src/main/resources/metadata.xml
    felix/trunk/pom.xml

Modified: felix/trunk/ipojo/arch/pom.xml
URL: http://svn.apache.org/viewvc/felix/trunk/ipojo/arch/pom.xml?view=diff&rev=550265&r1=550264&r2=550265
==============================================================================
--- felix/trunk/ipojo/arch/pom.xml (original)
+++ felix/trunk/ipojo/arch/pom.xml Sun Jun 24 10:44:53 2007
@@ -5,46 +5,54 @@
     <version>0.9.0-incubator-SNAPSHOT</version>
   </parent>
   <modelVersion>4.0.0</modelVersion>
-  <packaging>ipojo-bundle</packaging>
+  <packaging>bundle</packaging>
   <name>Apache Felix iPOJO Arch Command</name>
-  <version>0.7.1-incubator-SNAPSHOT</version>
+  <version>0.7.3-incubator-SNAPSHOT</version>
   <artifactId>org.apache.felix.ipojo.arch</artifactId>
   <dependencies>
     <dependency>
       <groupId>${pom.groupId}</groupId>
       <artifactId>org.apache.felix.ipojo</artifactId>
       <version>${pom.version}</version>
-      <scope>provided</scope>
     </dependency>
     <dependency>
       <groupId>${pom.groupId}</groupId>
       <artifactId>org.apache.felix.ipojo.metadata</artifactId>
       <version>${pom.version}</version>
-      <scope>provided</scope>
     </dependency>
     <dependency>
       <groupId>${pom.groupId}</groupId>
       <artifactId>org.apache.felix.shell</artifactId>
       <version>0.9.0-incubator-SNAPSHOT</version>
-      <scope>provided</scope>
     </dependency>
   </dependencies>
   <build>
-    <plugins>
+  <plugins>
       <plugin>
-        <groupId>${pom.groupId}</groupId>
-        <artifactId>org.apache.felix.ipojo.plugin</artifactId>
+        <groupId>org.apache.felix</groupId>
+        <artifactId>maven-bundle-plugin</artifactId>
         <extensions>true</extensions>
         <configuration>
-          <osgiManifest>
-            <bundleName>iPOJO Arch Command</bundleName>
-            <bundleVersion>0.7.1.incubator-SNAPSHOT</bundleVersion>
-            <bundleSymbolicName>${pom.artifactId}</bundleSymbolicName>
-            <bundleDescription>Architecture Shell Command (arch)</bundleDescription>
-            <iPOJOMetadata>metadata.xml</iPOJOMetadata>
-          </osgiManifest>
+          <instructions>
+            <Bundle-SymbolicName>${pom.artifactId}</Bundle-SymbolicName>
+            <Private-Package>org.apache.felix.ipojo.arch</Private-Package>
+          </instructions>
         </configuration>
       </plugin>
+      <plugin>
+	      <groupId>org.apache.felix</groupId>
+	      <artifactId>org.apache.felix.ipojo.plugin</artifactId>
+		  <executions>
+          	<execution>
+            	<goals>
+	              <goal>ipojo-bundle</goal>
+               </goals>
+            <configuration>
+   				<metadata>metadata.xml</metadata>
+            </configuration>
+          </execution>
+        </executions>
+      </plugin>
     </plugins>
-  </build>
+   </build>
 </project>

Modified: felix/trunk/ipojo/arch/src/main/resources/metadata.xml
URL: http://svn.apache.org/viewvc/felix/trunk/ipojo/arch/src/main/resources/metadata.xml?view=diff&rev=550265&r1=550264&r2=550265
==============================================================================
--- felix/trunk/ipojo/arch/src/main/resources/metadata.xml (original)
+++ felix/trunk/ipojo/arch/src/main/resources/metadata.xml Sun Jun 24 10:44:53 2007
@@ -2,7 +2,7 @@
 <iPOJO>
 	<Component className="org.apache.felix.ipojo.arch.ArchCommandImpl">
 		  <Provides interface="org.ungoverned.osgi.service.shell.Command"/>
-		  <Dependency field="archiService" optional="true"/>
+		  <Requires field="archiService" optional="true"/>
 	</Component>
 	<instance component="org.apache.felix.ipojo.arch.ArchCommandImpl" name="ArchCommand"/>
 </iPOJO>

Modified: felix/trunk/ipojo/core/pom.xml
URL: http://svn.apache.org/viewvc/felix/trunk/ipojo/core/pom.xml?view=diff&rev=550265&r1=550264&r2=550265
==============================================================================
--- felix/trunk/ipojo/core/pom.xml (original)
+++ felix/trunk/ipojo/core/pom.xml Sun Jun 24 10:44:53 2007
@@ -8,19 +8,17 @@
   <packaging>bundle</packaging>
   <name>Apache Felix iPOJO</name>
   <artifactId>org.apache.felix.ipojo</artifactId>
-  <version>0.7.1-incubator-SNAPSHOT</version>
+  <version>0.7.3-incubator-SNAPSHOT</version>
   <dependencies>
     <dependency>
       <groupId>${pom.groupId}</groupId>
       <artifactId>org.osgi.core</artifactId>
       <version>0.9.0-incubator-SNAPSHOT</version>
-      <scope>provided</scope>
     </dependency>
     <dependency>
       <groupId>${pom.groupId}</groupId>
       <artifactId>org.osgi.compendium</artifactId>
       <version>0.9.0-incubator-SNAPSHOT</version>
-      <scope>provided</scope>
     </dependency>
     <dependency>
       <groupId>asm</groupId>
@@ -30,7 +28,12 @@
     <dependency>
       <groupId>${pom.groupId}</groupId>
       <artifactId>org.apache.felix.ipojo.metadata</artifactId>
-      <version>0.7.1-incubator-SNAPSHOT</version>
+      <version>0.7.3-incubator-SNAPSHOT</version>
+    </dependency>
+    <dependency>
+      <groupId>${pom.groupId}</groupId>
+      <artifactId>org.apache.felix.ipojo.manipulator</artifactId>
+      <version>0.7.3-incubator-SNAPSHOT</version>
     </dependency>
   </dependencies>
   <build>
@@ -50,6 +53,7 @@
               org.osgi.service.log
             </Import-Package>
             <Private-Package>
+            	org.apache.felix.ipojo.manipulation,
     			org.apache.felix.ipojo.composite.architecture,
     			org.apache.felix.ipojo.composite.service*,
     			org.apache.felix.ipojo.composite.instance,
@@ -57,17 +61,18 @@
     			org.apache.felix.ipojo.handlers.configuration,
     			org.apache.felix.ipojo.handlers.dependency.nullable,
               	org.apache.felix.ipojo.handlers.lifecycle.callback,
-              	org.objectweb.asm*
+              	org.objectweb.asm,
+              	org.objectweb.asm.commons
             </Private-Package>
             <Export-Package>
-              org.apache.felix.ipojo; version="0.7.1", 
-              org.apache.felix.ipojo.metadata; version="0.7.1", 
-              org.apache.felix.ipojo.architecture; version="0.7.1", 
-              org.apache.felix.ipojo.parser; version="0.7.1",
-              org.apache.felix.ipojo.util; version="0.7.1",
-              org.apache.felix.ipojo.handlers.dependency; version="0.7.1",
-              org.apache.felix.ipojo.handlers.providedservice; version="0.7.1", 
-              org.apache.felix.ipojo.composite; version="0.7.1",
+              org.apache.felix.ipojo; version="0.7.3", 
+              org.apache.felix.ipojo.metadata; version="0.7.3", 
+              org.apache.felix.ipojo.architecture; version="0.7.3", 
+              org.apache.felix.ipojo.parser; version="0.7.3",
+              org.apache.felix.ipojo.util; version="0.7.3",
+              org.apache.felix.ipojo.handlers.dependency; version="0.7.3",
+              org.apache.felix.ipojo.handlers.providedservice; version="0.7.3", 
+              org.apache.felix.ipojo.composite; version="0.7.3",
               org.osgi.service.cm,
               org.osgi.service.log
             </Export-Package>

Modified: felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/Activator.java
URL: http://svn.apache.org/viewvc/felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/Activator.java?view=diff&rev=550265&r1=550264&r2=550265
==============================================================================
--- felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/Activator.java (original)
+++ felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/Activator.java Sun Jun 24 10:44:53 2007
@@ -152,7 +152,8 @@
             for (int j = 0; j < m_factories.length; j++) {
                 String componentClass = m_factories[j].getComponentClassName();
                 String factoryName = m_factories[j].getName();
-                if (conf.get("component") != null && (conf.get("component").equals(componentClass) || conf.get("component").equals(factoryName))) {
+                String componentName = m_factories[j].getComponentTypeName();
+                if (conf.get("component") != null && (conf.get("component").equals(componentClass) || conf.get("component").equals(factoryName)) || conf.get("component").equals(componentName)) {
                     try {
                         m_factories[j].createComponentInstance(conf);
                         created = true;

Modified: felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/ComponentFactory.java
URL: http://svn.apache.org/viewvc/felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/ComponentFactory.java?view=diff&rev=550265&r1=550264&r2=550265
==============================================================================
--- felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/ComponentFactory.java (original)
+++ felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/ComponentFactory.java Sun Jun 24 10:44:53 2007
@@ -21,11 +21,13 @@
 import java.io.IOException;
 import java.net.URL;
 import java.security.ProtectionDomain;
+import java.util.ArrayList;
 import java.util.Collection;
 import java.util.Dictionary;
 import java.util.Enumeration;
 import java.util.HashMap;
 import java.util.Iterator;
+import java.util.List;
 import java.util.Properties;
 
 import org.apache.felix.ipojo.architecture.ComponentDescription;
@@ -52,6 +54,11 @@
      * name (i.e. pid) of the created instance
      */
     private HashMap m_componentInstances = new HashMap();
+    
+    /**
+     * List of the managed instance name. This list is shared by all factories.
+     */
+    private static List m_instancesName = new ArrayList();
 
     /**
      * Ture if the component is a composition.
@@ -76,7 +83,7 @@
     /**
      * Composition Name.
      */
-    private String m_compositeName = null;
+    private String m_typeName = null;
 
     /**
      * Classloader to delegate loading.
@@ -188,6 +195,10 @@
     protected BundleContext getBundleContext() {
         return m_context;
     }
+    
+    protected String getComponentTypeName() {
+        return m_typeName;
+    }
 
     /**
      * Get the implementation class of the component type.
@@ -221,17 +232,11 @@
             m_isComposite = true;
             // Get the name
             if (cm.containsAttribute("name")) {
-                m_compositeName = cm.getAttribute("name");
+                m_typeName = cm.getAttribute("name");
             } else {
                 System.err.println("A composite needs a name");
                 return;
             }
-            // Compute factory name
-            if (m_componentMetadata.containsAttribute("factory") && !m_componentMetadata.getAttribute("factory").equalsIgnoreCase("no")) {
-                m_factoryName = m_componentMetadata.getAttribute("factory");
-            } else {
-                m_factoryName = m_compositeName;
-            }
         } else {
             if (cm.containsAttribute("className")) {
                 m_componentClassName = cm.getAttribute("className");
@@ -239,20 +244,56 @@
                 System.err.println("A component needs a class name");
                 return;
             }
-            if (m_componentMetadata.containsAttribute("factory") && !m_componentMetadata.getAttribute("factory").equalsIgnoreCase("no")) {
-                m_factoryName = m_componentMetadata.getAttribute("factory");
-            } else {
-                m_factoryName = m_componentMetadata.getAttribute("className");
+            // Get the name
+            if (cm.containsAttribute("name")) {
+                m_typeName = cm.getAttribute("name");
             }
         }
-        if (m_factoryName != null) {
-            m_logger = new Logger(m_context, m_factoryName, Logger.WARNING);
+        
+        if (m_typeName != null) {
+            m_logger = new Logger(m_context, m_typeName, Logger.WARNING);
+        } else {
+            m_logger = new Logger(m_context, m_componentClassName, Logger.WARNING);
+        }
+        
+        computeFactoryName();
+        
+    }
+    
+    /**
+     * Compute the factory name.
+     */
+    private void computeFactoryName() {
+        if (m_componentMetadata.containsAttribute("factory")) {
+            // DEPRECATED BLOCK
+            if (m_componentMetadata.getAttribute("factory").equalsIgnoreCase("no")) {
+                m_logger.log(Logger.WARNING, "'factory=no' is deprecated, Please use 'factory=false' instead of 'factory='no'");
+                m_factoryName = null;
+                return;
+            }
+            // END OF DEPRECATED BLOCK
+            if (m_componentMetadata.getAttribute("factory").equalsIgnoreCase("false")) {
+                m_factoryName = null;
+                return;
+            }
+            if (m_componentMetadata.getAttribute("factory").equalsIgnoreCase("true")) {
+                if (m_typeName == null) { //m_typeName is necessary set for composite.
+                    m_factoryName = m_componentMetadata.getAttribute("className");
+                } else {
+                    m_factoryName = m_typeName;
+                }
+                return;
+            }
+            // factory is set with the factory name
+            m_factoryName = m_componentMetadata.getAttribute("factory");
+            return;
         } else {
-            if (m_isComposite) {
-                m_logger = new Logger(m_context, m_compositeName, Logger.WARNING);
+            if (m_typeName == null) { //m_typeName is necessary set for composite.
+                m_factoryName = m_componentMetadata.getAttribute("className");
             } else {
-                m_logger = new Logger(m_context, m_componentClassName, Logger.WARNING);
+                m_factoryName = m_typeName;
             }
+            return;
         }
     }
 
@@ -269,15 +310,16 @@
         m_clazz = clazz;
         m_componentClassName = cm.getAttribute("className");
         m_componentMetadata = cm;
-
-        // Get factory PID :
-        if (m_componentMetadata.containsAttribute("factory") && !m_componentMetadata.getAttribute("factory").equalsIgnoreCase("no")) {
-            m_factoryName = m_componentMetadata.getAttribute("factory");
+        
+        // Get the name
+        if (cm.containsAttribute("name")) {
+            m_typeName = cm.getAttribute("name");
+            m_logger = new Logger(m_context, m_typeName, Logger.WARNING);
         } else {
-            m_factoryName = m_componentMetadata.getAttribute("className");
+            m_logger = new Logger(m_context, m_componentClassName, Logger.WARNING);
         }
 
-        m_logger = new Logger(m_context, m_factoryName, Logger.WARNING);
+        computeFactoryName();
     }
 
     /**
@@ -295,6 +337,7 @@
                     ((InstanceManager) ci).kill(); 
                 } 
             }
+            m_instancesName.remove(ci.getInstanceName());
         }
 
         m_logger.stop();
@@ -332,7 +375,7 @@
         }
 
         // Check if the factory should be exposed
-        if (m_componentMetadata.containsAttribute("factory") && m_componentMetadata.getAttribute("factory").equalsIgnoreCase("no")) {
+        if (m_factoryName == null) {
             return;
         }
 
@@ -342,6 +385,9 @@
             props.put("component.class", "no implementation class");
         }
         props.put("factory.name", m_factoryName);
+        if (m_typeName != null) {
+            props.put("component.type", m_typeName);
+        }
         props.put("component.providedServiceSpecifications", m_componentDesc.getprovidedServiceSpecification());
         props.put("component.properties", m_componentDesc.getProperties());
         props.put("component.description", m_componentDesc);
@@ -360,6 +406,7 @@
      * @param ci : the destroyed instance
      */
     protected synchronized void disposed(ComponentInstance ci) {
+        m_instancesName.remove(ci.getInstanceName());
         m_componentInstances.remove(ci.getInstanceName());
     }
 
@@ -432,7 +479,7 @@
      * not consistent with the component type of this factory.
      * @see org.apache.felix.ipojo.Factory#createComponentInstance(java.util.Dictionary)
      */
-    public ComponentInstance createComponentInstance(Dictionary configuration) throws UnacceptableConfiguration {
+    public synchronized ComponentInstance createComponentInstance(Dictionary configuration) throws UnacceptableConfiguration {
         if (configuration == null) {
             configuration = new Properties();
         }
@@ -452,8 +499,10 @@
             configuration.put("name", pid);
         }
 
-        if (m_componentInstances.containsKey(pid)) {
+        if (m_instancesName.contains(pid)) {
             throw new UnacceptableConfiguration("Name already used : " + pid);
+        } else {
+            m_instancesName.add(pid);
         }
 
         IPojoContext context = new IPojoContext(m_context);
@@ -505,8 +554,10 @@
             configuration.put("name", pid);
         }
         
-        if (m_componentInstances.containsKey(pid)) {
+        if (m_instancesName.contains(pid)) {
             throw new UnacceptableConfiguration("Name already used : " + pid);
+        } else {
+            m_instancesName.add(pid);
         }
 
         IPojoContext context = new IPojoContext(m_context, serviceContext);
@@ -532,7 +583,8 @@
      * @param pid : name of the instance to delete
      * @see org.osgi.service.cm.ManagedServiceFactory#deleted(java.lang.String)
      */
-    public void deleted(String pid) {
+    public synchronized void deleted(String pid) {
+        m_instancesName.remove(pid);
         InstanceManager cm = (InstanceManager) m_componentInstances.remove(pid);
         if (cm == null) {
             return; // do nothing, the component does not exist !
@@ -548,7 +600,13 @@
      * @see org.apache.felix.ipojo.Factory#getName()
      */
     public String getName() {
-        return m_factoryName;
+        if (m_factoryName != null) {
+            return m_factoryName;
+        } else if (m_typeName != null) {
+            return m_typeName;
+        } else {
+            return m_componentClassName;
+        }
     }
 
     /**
@@ -561,7 +619,7 @@
      * @see org.osgi.service.cm.ManagedServiceFactory#updated(java.lang.String,
      * java.util.Dictionary)
      */
-    public void updated(String pid, Dictionary properties) throws ConfigurationException {
+    public synchronized void updated(String pid, Dictionary properties) throws ConfigurationException {
         InstanceManager cm = (InstanceManager) m_componentInstances.get(pid);
         if (cm == null) {
             try {
@@ -574,8 +632,7 @@
         } else {
             try {
                 properties.put("name", pid); // Add the name in the configuration
-                checkAcceptability(properties); // Test if the configuration is
-                // acceptable
+                checkAcceptability(properties); // Test if the configuration is acceptable
             } catch (UnacceptableConfiguration e) {
                 m_logger.log(Logger.ERROR, "The configuration is not acceptable : " + e.getMessage());
                 throw new ConfigurationException(properties.toString(), e.getMessage());
@@ -656,7 +713,7 @@
      */
     private synchronized String generateName() {
         String name = getName() + "-" + m_index;
-        while (m_componentInstances.containsKey(name)) {
+        while (m_instancesName.contains(name)) {
             m_index = m_index + 1;
             name = getName() + "-" + m_index;
         }

Modified: felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/Handler.java
URL: http://svn.apache.org/viewvc/felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/Handler.java?view=diff&rev=550265&r1=550264&r2=550265
==============================================================================
--- felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/Handler.java (original)
+++ felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/Handler.java Sun Jun 24 10:44:53 2007
@@ -69,6 +69,25 @@
     public Object getterCallback(String fieldName, Object value) {
         return value;
     }
+    
+    /**
+     * This method is called when the execution enter in a method.
+     * 
+     * @param methodId : the method identifier
+     */
+    public void entryCallback(String methodId) {
+    }
+
+    /**
+     * This method is called when the execution exit a method (before a return or a throw).
+     * If the given returned object is an instance of Exception, this means that the method throwed this exception.
+     * If the given returned object is null, either the method is void, either it returns null.
+     * You must not modified the returned object.
+     * @param methodId : the method identifier
+     * @param returnedObj : the returned object (boxed for primitive type)
+     */
+    public void exitCallback(String methodId, Object returnedObj) {
+    }
 
     /**
      * Is the actual state valid for this handler ?

Modified: felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/InstanceCreator.java
URL: http://svn.apache.org/viewvc/felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/InstanceCreator.java?view=diff&rev=550265&r1=550264&r2=550265
==============================================================================
--- felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/InstanceCreator.java (original)
+++ felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/InstanceCreator.java Sun Jun 24 10:44:53 2007
@@ -140,7 +140,7 @@
             Factory fact = null;
 
             try {
-                String fil = "(|(" + org.osgi.framework.Constants.SERVICE_PID + "=" + componentType + ")(component.class=" + componentType + "))";
+                String fil = "(|(" + org.osgi.framework.Constants.SERVICE_PID + "=" + componentType + ")(component.class=" + componentType + ")(component.type=" + componentType + ")";
                 ServiceReference[] refs = context.getServiceReferences(org.apache.felix.ipojo.Factory.class.getName(), fil);
                 if (refs != null) {
                     fact = (Factory) m_context.getService(refs[0]);

Modified: felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/InstanceManager.java
URL: http://svn.apache.org/viewvc/felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/InstanceManager.java?view=diff&rev=550265&r1=550264&r2=550265
==============================================================================
--- felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/InstanceManager.java (original)
+++ felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/InstanceManager.java Sun Jun 24 10:44:53 2007
@@ -22,10 +22,13 @@
 import java.lang.reflect.InvocationTargetException;
 import java.util.Dictionary;
 import java.util.HashMap;
+import java.util.Set;
 
 import org.apache.felix.ipojo.architecture.ComponentDescription;
 import org.apache.felix.ipojo.architecture.InstanceDescription;
 import org.apache.felix.ipojo.metadata.Element;
+import org.apache.felix.ipojo.parser.FieldMetadata;
+import org.apache.felix.ipojo.parser.MethodMetadata;
 import org.apache.felix.ipojo.util.Logger;
 import org.osgi.framework.BundleContext;
 
@@ -66,6 +69,11 @@
      * Map [field, handler list] storing handlers interested by the field.
      */
     private HashMap m_fieldRegistration = new HashMap();
+    
+    /**
+     * Map [method identifier, handler list] storing handlers interested by the method.
+     */
+    private HashMap m_methodRegistration = new HashMap();
 
     /**
      * Component state (STOPPED at the beginning).
@@ -91,6 +99,7 @@
      * Component type information.
      */
     private ComponentDescription m_componentDesc;
+    
 
     // Constructor
     /**
@@ -624,15 +633,16 @@
      * given in the list.
      * 
      * @param h : the handler to register
-     * @param fields : the fields list
+     * @param fields : the field metadata list
+     * @param methods : the method metadata list
      */
-    public void register(Handler h, String[] fields) {
+    public void register(Handler h, FieldMetadata[] fields, MethodMetadata[] methods) {
         register(h);
-        for (int i = 0; i < fields.length; i++) {
-            if (m_fieldRegistration.get(fields[i]) == null) {
-                m_fieldRegistration.put(fields[i], new Handler[] { h });
+        for (int i = 0; fields != null && i < fields.length; i++) {
+            if (m_fieldRegistration.get(fields[i].getFieldName()) == null) {
+                m_fieldRegistration.put(fields[i].getFieldName(), new Handler[] { h });
             } else {
-                Handler[] list = (Handler[]) m_fieldRegistration.get(fields[i]);
+                Handler[] list = (Handler[]) m_fieldRegistration.get(fields[i].getFieldName());
                 for (int j = 0; j < list.length; j++) {
                     if (list[j] == h) {
                         return;
@@ -641,24 +651,42 @@
                 Handler[] newList = new Handler[list.length + 1];
                 System.arraycopy(list, 0, newList, 0, list.length);
                 newList[list.length] = h;
-                m_fieldRegistration.put(fields[i], newList);
+                m_fieldRegistration.put(fields[i].getFieldName(), newList);
             }
         }
+        for (int i = 0; methods != null && i < methods.length; i++) {
+            if (m_methodRegistration.get(methods[i].getMethodIdentifier()) == null) {
+                m_methodRegistration.put(methods[i].getMethodIdentifier(), new Handler[] { h });
+            } else {
+                Handler[] list = (Handler[]) m_methodRegistration.get(methods[i].getMethodIdentifier());
+                for (int j = 0; j < list.length; j++) {
+                    if (list[j] == h) {
+                        return;
+                    }
+                }
+                Handler[] newList = new Handler[list.length + 1];
+                System.arraycopy(list, 0, newList, 0, list.length);
+                newList[list.length] = h;
+                m_methodRegistration.put(methods[i].getMethodIdentifier(), newList);
+            }
+        }
+        
     }
 
     /**
      * Unregister an handler for the field list. The handler will not be
-     * notified of field access but is allways register on the instance manager.
+     * notified of field access but is always register on the instance manager.
      * 
      * @param h : the handler to unregister.
-     * @param fields : the fields list
+     * @param fields : the field metadata list
+     * @param methods : the method metadata list
      */
-    public void unregister(Handler h, String[] fields) {
+    public void unregister(Handler h, FieldMetadata[] fields, MethodMetadata[] methods) {
         for (int i = 0; i < fields.length; i++) {
-            if (m_fieldRegistration.get(fields[i]) == null) {
+            if (m_fieldRegistration.get(fields[i].getFieldName()) == null) {
                 break;
             } else {
-                Handler[] list = (Handler[]) m_fieldRegistration.get(fields[i]);
+                Handler[] list = (Handler[]) m_fieldRegistration.get(fields[i].getFieldName());
                 int idx = -1;
                 for (int j = 0; j < list.length; j++) {
                     if (list[j] == h) {
@@ -678,7 +706,35 @@
                         }
                         list = newList;
                     }
-                    m_fieldRegistration.put(fields[i], list);
+                    m_fieldRegistration.put(fields[i].getFieldName(), list);
+                }
+            }
+        }
+        for (int i = 0; i < methods.length; i++) {
+            if (m_methodRegistration.get(methods[i].getMethodIdentifier()) == null) {
+                break;
+            } else {
+                Handler[] list = (Handler[]) m_methodRegistration.get(methods[i].getMethodIdentifier());
+                int idx = -1;
+                for (int j = 0; j < list.length; j++) {
+                    if (list[j] == h) {
+                        idx = j;
+                        break;
+                    }
+                }
+
+                if (idx >= 0) {
+                    if ((list.length - 1) == 0) {
+                        list = new Handler[0];
+                    } else {
+                        Handler[] newList = new Handler[list.length - 1];
+                        System.arraycopy(list, 0, newList, 0, idx);
+                        if (idx < newList.length) {
+                            System.arraycopy(list, idx + 1, newList, idx, newList.length - idx);
+                        }
+                        list = newList;
+                    }
+                    m_methodRegistration.put(methods[i].getMethodIdentifier(), list);
                 }
             }
         }
@@ -711,6 +767,14 @@
             }
         }
     }
+    
+    public Set getRegistredFields() {
+        return m_fieldRegistration.keySet();
+    }
+    
+    public Set getRegistredMethods() {
+        return m_methodRegistration.keySet();
+    }
 
     /**
      * This method is called by the manipulated class each time that a GETFIELD
@@ -738,6 +802,31 @@
             return result;
         } else {
             return initialValue;
+        }
+    }
+    
+    /**
+     * Dispatch entry method event on registred handler.
+     * @param methodId : method id
+     */
+    public void entryCallback(String methodId) {
+        Handler[] list = (Handler[]) m_methodRegistration.get(methodId);
+        for (int i = 0; list != null && i < list.length; i++) {
+            list[i].entryCallback(methodId);
+        }
+    }
+
+    /**
+     * Dispatch exit method event on registred handler.
+     * The given returned object is an instance of Exception if the method has throwed an exception.
+     * If the given object is null, either the method returns void, either the method has returned null.
+     * @param methodId : method id
+     * @param e : returned object.
+     */
+    public void exitCallback(String methodId, Object e) {
+        Handler[] list = (Handler[]) m_methodRegistration.get(methodId);
+        for (int i = 0; list != null && i < list.length; i++) {
+            list[i].exitCallback(methodId, e);
         }
     }
 

Modified: felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/composite/service/importer/ImportExportDescription.java
URL: http://svn.apache.org/viewvc/felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/composite/service/importer/ImportExportDescription.java?view=diff&rev=550265&r1=550264&r2=550265
==============================================================================
--- felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/composite/service/importer/ImportExportDescription.java (original)
+++ felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/composite/service/importer/ImportExportDescription.java Sun Jun 24 10:44:53 2007
@@ -63,7 +63,7 @@
         Element handler = super.getHandlerInfo();
         for (int i = 0; i < m_imports.size(); i++) {
             ServiceImporter imp = (ServiceImporter) m_imports.get(i);
-            Element impo = new Element("Import", "");
+            Element impo = new Element("Requires", "");
             impo.addAttribute(new Attribute("Specification", imp.getSpecification()));
             if (imp.getFilter() != null) { impo.addAttribute(new Attribute("Filter", imp.getFilter())); }
             if (imp.isSatisfied()) {

Modified: felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/composite/service/importer/ImportExportHandler.java
URL: http://svn.apache.org/viewvc/felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/composite/service/importer/ImportExportHandler.java?view=diff&rev=550265&r1=550264&r2=550265
==============================================================================
--- felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/composite/service/importer/ImportExportHandler.java (original)
+++ felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/composite/service/importer/ImportExportHandler.java Sun Jun 24 10:44:53 2007
@@ -82,7 +82,17 @@
         m_context = im.getContext();
         m_scope = m_manager.getServiceContext();
 
-        Element[] imp = metadata.getElements("import");
+        Element[] imp = metadata.getElements("requires");
+
+        //DEPRECATED BLOCK:
+        if (imp.length == 0) {
+            imp = metadata.getElements("import");
+            if (imp.length != 0) {
+                im.getFactory().getLogger().log(Logger.WARNING, "Import is deprecated, please use 'requires' instead of 'import'");
+            }
+        }
+        // END OF DEPRECATED BLOCK
+        
         Element[] exp = metadata.getElements("export");
 
         for (int i = 0; i < imp.length; i++) {

Modified: felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/composite/service/provides/CompositionMetadata.java
URL: http://svn.apache.org/viewvc/felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/composite/service/provides/CompositionMetadata.java?view=diff&rev=550265&r1=550264&r2=550265
==============================================================================
--- felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/composite/service/provides/CompositionMetadata.java (original)
+++ felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/composite/service/provides/CompositionMetadata.java Sun Jun 24 10:44:53 2007
@@ -28,8 +28,7 @@
 import java.util.Set;
 
 import org.apache.felix.ipojo.Factory;
-import org.apache.felix.ipojo.composite.service.provides.manipulation.Manipulator;
-import org.apache.felix.ipojo.composite.service.provides.manipulation.POJOWriter;
+import org.apache.felix.ipojo.manipulation.Manipulator;
 import org.apache.felix.ipojo.metadata.Attribute;
 import org.apache.felix.ipojo.metadata.Element;
 import org.apache.felix.ipojo.util.Logger;
@@ -58,16 +57,11 @@
      * Bundle Context.
      */
     private BundleContext m_context;
-
-    /**
-     * Manipulated field of the build Pojo. 
-     */
-    private HashMap m_manipulatedFields = new HashMap();
-
+    
     /**
-     * Manipulated interface of the build Pojo.
+     * Manipulation Metadata.
      */
-    private String[] m_manipulatedInterfaces = new String[0];
+    private Element m_manipulationMetadata;
 
     /**
      * Reference on the handler.
@@ -243,9 +237,8 @@
         byte[] pojo = POJOWriter.dump(url, m_specification.getName(), m_name, getFieldList(), getMethodList());
         Manipulator m = new Manipulator();
         try {
-            byte[] ff = m.process(pojo);
-            m_manipulatedFields = m.getFields();
-            m_manipulatedInterfaces = m.getInterfaces();
+            byte[] ff = m.manipulate(pojo);
+            m_manipulationMetadata = m.getManipulationMetadata();
             return ff;
         } catch (IOException e) {
             e.printStackTrace();
@@ -261,7 +254,7 @@
     protected Element buildMetadata(String in) {
         Element elem = new Element("component", "");
         Attribute className = new Attribute("className", m_name);
-        Attribute factory = new Attribute("factory", "no");
+        Attribute factory = new Attribute("factory", "false");
         elem.addAttribute(className);
         elem.addAttribute(factory);
 
@@ -275,7 +268,7 @@
         for (int i = 0; i < fields.size(); i++) {
             FieldMetadata field = (FieldMetadata) fields.get(i);
             if (field.isUseful() && field.getSpecification().isInterface()) {
-                Element dep = new Element("Dependency", "");
+                Element dep = new Element("requires", "");
                 dep.addAttribute(new Attribute("field", field.getName()));
                 if (field.getSpecification().isOptional()) {
                     dep.addAttribute(new Attribute("optional", "true"));
@@ -299,28 +292,7 @@
         }
 
         // Insert information to metadata
-        Element manip = new Element("Manipulation", "");
-        for (int j = 0; j < m_manipulatedInterfaces.length; j++) {
-            // Create an interface element for each implemented interface
-            Element itf = new Element("Interface", "");
-            Attribute att = new Attribute("name", m_manipulatedInterfaces[j]);
-            itf.addAttribute(att);
-            manip.addElement(itf);
-        }
-
-        Iterator it = m_manipulatedFields.keySet().iterator();
-        while (it.hasNext()) {
-            Element field = new Element("Field", "");
-            String name = (String) it.next();
-            String type = (String) m_manipulatedFields.get(name);
-            Attribute attName = new Attribute("name", name);
-            Attribute attType = new Attribute("type", type);
-            field.addAttribute(attName);
-            field.addAttribute(attType);
-            manip.addElement(field);
-        }
-
-        elem.addElement(manip);
+        elem.addElement(m_manipulationMetadata);
 
         return elem;
     }

Added: felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/composite/service/provides/POJOWriter.java
URL: http://svn.apache.org/viewvc/felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/composite/service/provides/POJOWriter.java?view=auto&rev=550265
==============================================================================
--- felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/composite/service/provides/POJOWriter.java (added)
+++ felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/composite/service/provides/POJOWriter.java Sun Jun 24 10:44:53 2007
@@ -0,0 +1,406 @@
+/* 
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you 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.felix.ipojo.composite.service.provides;
+
+import java.io.IOException;
+import java.io.InputStream;
+import java.net.URL;
+import java.util.List;
+
+import org.apache.felix.ipojo.handlers.dependency.nullable.MethodSignature;
+import org.apache.felix.ipojo.handlers.dependency.nullable.MethodSignatureVisitor;
+import org.objectweb.asm.ClassReader;
+import org.objectweb.asm.ClassWriter;
+import org.objectweb.asm.Label;
+import org.objectweb.asm.MethodVisitor;
+import org.objectweb.asm.Opcodes;
+import org.objectweb.asm.Type;
+
+/**
+ * Create the proxy class.
+ * 
+ * @author <a href="mailto:dev@felix.apache.org">Felix Project Team</a>
+ */
+public class POJOWriter implements Opcodes {
+
+    /**
+     * Create a class.
+     * @param cw : class writer
+     * @param className : class name
+     * @param spec : implemented specification
+     */
+    private static void createClass(ClassWriter cw, String className, String spec) {
+        // Create the class
+        cw.visit(V1_2, ACC_PUBLIC + ACC_SUPER, className, null, "java/lang/Object", new String[] { spec.replace('.', '/') });
+    }
+
+    /**
+     * Inject field in the current class.
+     * @param cw : class writer.
+     * @param fields : list of field to inject.
+     */
+    private static void injectFields(ClassWriter cw, List fields) {
+        // Inject fields
+        for (int i = 0; i < fields.size(); i++) {
+            FieldMetadata field = (FieldMetadata) fields.get(i);
+            if (field.isUseful()) {
+                SpecificationMetadata spec = field.getSpecification();
+                String fieldName = field.getName();
+                String desc = "";
+                if (field.isAggregate()) {
+                    desc = "[L" + spec.getName().replace('.', '/') + ";";
+                } else {
+                    desc = "L" + spec.getName().replace('.', '/') + ";";
+                }
+
+                cw.visitField(Opcodes.ACC_PRIVATE, fieldName, desc, null, null);
+            }
+        }
+    }
+
+    /**
+     * Return the proxy classname for the contract contractname by delegating on available service.
+     * @param url URL of the needed contract
+     * @param contractName : The interface to implement
+     * @param className : The class name to create
+     * @param fields : the list of fields on which delegate
+     * @param methods : the list of method on which delegate
+     * @return byte[] : the build class
+     */
+    public static byte[] dump(URL url, String contractName, String className, List fields, List methods) {
+
+        ClassReader cr = null;
+        InputStream is = null;
+        byte[] b = null;
+        try {
+            is = url.openStream();
+            cr = new ClassReader(is);
+            MethodSignatureVisitor msv = new MethodSignatureVisitor();
+            cr.accept(msv, ClassReader.SKIP_FRAMES);
+            is.close();
+
+            MethodSignature[] methodsSign = msv.getMethods();
+
+            ClassWriter cw = new ClassWriter(ClassWriter.COMPUTE_MAXS);
+
+            // Create the class
+            className = className.replace('.', '/');
+            createClass(cw, className, contractName);
+
+            // Inject fields inside the POJO
+            injectFields(cw, fields);
+
+            // Inject a constructor <INIT>()V
+            MethodVisitor cst = cw.visitMethod(ACC_PUBLIC, "<init>", "()V", null, null);
+            cst.visitVarInsn(ALOAD, 0);
+            cst.visitMethodInsn(INVOKESPECIAL, "java/lang/Object", "<init>", "()V");
+            cst.visitInsn(RETURN);
+            cst.visitMaxs(0, 0);
+            cst.visitEnd();
+
+            for (int i = 0; i < methodsSign.length; ++i) {
+                MethodSignature method = methodsSign[i];
+
+                // Get the field for this method
+                // 1) find the MethodMetadata
+                FieldMetadata delegator = null; // field to delegate
+                MethodMetadata methodDelegator = null; // field to delegate
+                for (int j = 0; j < methods.size(); j++) {
+                    MethodMetadata methodMeta = (MethodMetadata) methods.get(j);
+                    if (methodMeta.equals(method)) {
+                        delegator = methodMeta.getDelegation();
+                        methodDelegator = methodMeta;
+                    }
+                }
+
+                generateOneMethod(cw, className, methodDelegator, method, delegator);
+
+            }
+
+            // End process
+            cw.visitEnd();
+            b = cw.toByteArray();
+
+        } catch (IOException e) {
+            e.printStackTrace();
+        }
+
+        // Write the class :
+//        try {
+//            FileOutputStream fos = new FileOutputStream(
+//                    "F:\\dev\\workspaces\\iPOJO_dev\\Test_Manipulator\\manipulated\\org\\apache\\felix\\ipojo\\test\\scenarios\\component\\"
+//                            + className.replace('/', '.') + ".class");
+//
+//            fos.write(b);
+//
+//            fos.close();
+//        } catch (Exception e) {
+//            System.err.println("Exception : " + e.getMessage());
+//        }
+
+        return b;
+    }
+
+    /**
+     * Generate on method.
+     * @param cw : class writer
+     * @param className : the current class name
+     * @param method : the method to generate
+     * @param sign : method signature to generate
+     * @param delegator : the field on which delegate
+     */
+    private static void generateOneMethod(ClassWriter cw, String className, MethodMetadata method, MethodSignature sign, FieldMetadata delegator) {
+        String desc = sign.getDesc();
+        String name = sign.getName();
+        String signa = sign.getSignature();
+        String[] exc = sign.getException();
+
+        MethodVisitor mv = cw.visitMethod(ACC_PUBLIC, name, desc, signa, exc);
+
+        if (delegator.isOptional()) {
+            if (!delegator.isAggregate()) {
+                generateOptionalCase(mv, delegator, className);
+            }
+            if (delegator.isAggregate() /*&& method.getPolicy() == MethodMetadata.ONE_POLICY*/) {
+                generateOptionalAggregateCase(mv, delegator, className);
+            }
+        }
+
+        if (!delegator.isAggregate()) {
+            mv.visitVarInsn(ALOAD, 0);
+            mv.visitFieldInsn(GETFIELD, className, delegator.getName(), "L" + delegator.getSpecification().getName().replace('.', '/') + ";");
+
+            // Loads args
+            Type[] args = Type.getArgumentTypes(desc);
+            for (int i = 0; i < args.length; i++) {
+                writeLoad(args[i], i + 1, mv);
+            }
+
+            // Invoke
+            if (delegator.getSpecification().isInterface()) {
+                mv.visitMethodInsn(INVOKEINTERFACE, delegator.getSpecification().getName().replace('.', '/'), name, desc);
+            } else {
+                mv.visitMethodInsn(INVOKEVIRTUAL, delegator.getSpecification().getName().replace('.', '/'), name, desc);
+            }
+
+            // Return
+            writeReturn(Type.getReturnType(desc), mv);
+        } else {
+            if (method.getPolicy() == MethodMetadata.ONE_POLICY) {
+                // Aggregate and One Policy
+                mv.visitVarInsn(ALOAD, 0);
+                mv.visitFieldInsn(GETFIELD, className, delegator.getName(), "[L" + delegator.getSpecification().getName().replace('.', '/') + ";");
+                mv.visitInsn(ICONST_0); // Take the first one
+                mv.visitInsn(AALOAD);
+
+                // Loads args
+                Type[] args = Type.getArgumentTypes(desc);
+                for (int i = 0; i < args.length; i++) {
+                    writeLoad(args[i], i + 1, mv);
+                }
+
+                // Invoke
+                mv.visitMethodInsn(INVOKEINTERFACE, delegator.getSpecification().getName().replace('.', '/'), name, desc);
+
+                // Return
+                writeReturn(Type.getReturnType(desc), mv);
+            } else { // All policy
+                if (Type.getReturnType(desc).getSort() != Type.VOID) {
+                    System.err.println("All policy cannot be used on method which does not return void");
+                }
+
+                Type[] args = Type.getArgumentTypes(desc);
+                int index = args.length + 1;
+
+                // Init
+                mv.visitInsn(ICONST_0);
+                mv.visitVarInsn(ISTORE, index);
+                Label l1b = new Label();
+                mv.visitLabel(l1b);
+                Label l2b = new Label();
+                mv.visitJumpInsn(GOTO, l2b);
+
+                // Loop
+                Label l3b = new Label();
+                mv.visitLabel(l3b);
+                mv.visitVarInsn(ALOAD, 0);
+                mv.visitFieldInsn(GETFIELD, className, delegator.getName(), "[L" + delegator.getSpecification().getName().replace('.', '/') + ";");
+                mv.visitVarInsn(ILOAD, index);
+                mv.visitInsn(AALOAD);
+
+                // Loads args
+                for (int i = 0; i < args.length; i++) {
+                    writeLoad(args[i], i + 1, mv);
+                }
+
+                mv.visitMethodInsn(INVOKEINTERFACE, delegator.getSpecification().getName().replace('.', '/'), name, desc);
+
+                Label l4b = new Label();
+                mv.visitLabel(l4b);
+                mv.visitIincInsn(index, 1); // i++;
+
+                // Condition
+                mv.visitLabel(l2b);
+                mv.visitVarInsn(ILOAD, index);
+                mv.visitVarInsn(ALOAD, 0);
+                mv.visitFieldInsn(GETFIELD, className, delegator.getName(), "[L" + delegator.getSpecification().getName().replace('.', '/') + ";");
+                mv.visitInsn(ARRAYLENGTH);
+                mv.visitJumpInsn(IF_ICMPLT, l3b);
+
+                Label l5b = new Label();
+                mv.visitLabel(l5b);
+                mv.visitInsn(RETURN);
+            }
+        }
+
+        mv.visitMaxs(0, 0);
+        mv.visitEnd();
+    }
+
+    /**
+     * Generate Optional Case for aggregate field.
+     * @param mv : method visitor
+     * @param delegator : Field on which delegate
+     * @param className : current class name
+     */
+    private static void generateOptionalAggregateCase(MethodVisitor mv, FieldMetadata delegator, String className) {
+        mv.visitVarInsn(ALOAD, 0);
+        mv.visitFieldInsn(GETFIELD, className, delegator.getName(), "[L" + delegator.getSpecification().getName().replace('.', '/') + ";");
+        mv.visitInsn(ARRAYLENGTH);
+        Label l1a = new Label();
+        mv.visitJumpInsn(IFNE, l1a);
+        Label l2a = new Label();
+        mv.visitLabel(l2a);
+        mv.visitTypeInsn(NEW, "java/lang/UnsupportedOperationException");
+        mv.visitInsn(DUP);
+        mv.visitLdcInsn("Operation not supported");
+        mv.visitMethodInsn(INVOKESPECIAL, "java/lang/UnsupportedOperationException", "<init>", "(Ljava/lang/String;)V");
+        mv.visitInsn(ATHROW);
+        mv.visitLabel(l1a);
+    }
+
+    /**
+     * Generate Optional case for non aggregate fields.
+     * 
+     * @param mv : the method visitor
+     * @param delegator : the field on which delegate.
+     * @param className : the name of the current class.
+     */
+    private static void generateOptionalCase(MethodVisitor mv, FieldMetadata delegator, String className) {
+        mv.visitVarInsn(ALOAD, 0);
+        mv.visitFieldInsn(GETFIELD, className, delegator.getName(), "L" + delegator.getSpecification().getName().replace('.', '/') + ";");
+        mv.visitTypeInsn(INSTANCEOF, "org/apache/felix/ipojo/Nullable");
+        Label end = new Label();
+        mv.visitJumpInsn(IFEQ, end);
+        Label begin = new Label();
+        mv.visitLabel(begin);
+        mv.visitTypeInsn(NEW, "java/lang/UnsupportedOperationException");
+        mv.visitInsn(DUP);
+        mv.visitLdcInsn("Operation not supported");
+        mv.visitMethodInsn(INVOKESPECIAL, "java/lang/UnsupportedOperationException", "<init>", "(Ljava/lang/String;)V");
+        mv.visitInsn(ATHROW);
+        mv.visitLabel(end);
+    }
+
+    /**
+     * Write a return instruction according to the given type.
+     * @param t : the type
+     * @param mv : the method visitor
+     */
+    private static void writeReturn(Type t, MethodVisitor mv) {
+        switch (t.getSort()) {
+            case Type.BOOLEAN:
+            case Type.INT:
+            case Type.BYTE:
+            case Type.CHAR:
+            case Type.SHORT:
+                // Integer or Boolean : return 0 ( false)
+                mv.visitInsn(IRETURN);
+                break;
+            case Type.LONG:
+                // mv.visitInsn(LCONST_0);
+                mv.visitInsn(LRETURN);
+                break;
+            case Type.DOUBLE:
+                // Double : return 0.0
+                // mv.visitInsn(DCONST_0);
+                mv.visitInsn(DRETURN);
+                break;
+            case Type.FLOAT:
+                // Double : return 0.0
+                // mv.visitInsn(DCONST_0);
+                mv.visitInsn(FRETURN);
+                break;
+            case Type.ARRAY:
+            case Type.OBJECT:
+                // Return always null for array and object
+                // mv.visitInsn(ACONST_NULL);
+                mv.visitInsn(ARETURN);
+                break;
+            case Type.VOID:
+                mv.visitInsn(RETURN);
+                break;
+            default:
+                System.err.println("Type not yet managed : " + t);
+                break;
+        }
+    }
+
+    /**
+     * Write a load instruction according to the given type.
+     * @param t : the type
+     * @param mv : the method visitor
+     * @param index : variable name (index)
+     */
+    private static void writeLoad(Type t, int index, MethodVisitor mv) {
+        switch (t.getSort()) {
+            case Type.BOOLEAN:
+            case Type.INT:
+            case Type.BYTE:
+            case Type.CHAR:
+            case Type.SHORT:
+                // Integer or Boolean : return 0 ( false)
+                mv.visitVarInsn(ILOAD, index);
+                break;
+            case Type.LONG:
+                // mv.visitInsn(LCONST_0);
+                mv.visitVarInsn(LLOAD, index);
+                break;
+            case Type.FLOAT:
+                // mv.visitInsn(LCONST_0);
+                mv.visitVarInsn(FLOAD, index);
+                break;
+            case Type.DOUBLE:
+                // Double : return 0.0
+                // mv.visitInsn(DCONST_0);
+                mv.visitVarInsn(DLOAD, index);
+                break;
+            case Type.ARRAY:
+            case Type.OBJECT:
+                // Return always null for array and object
+                // mv.visitInsn(ACONST_NULL);
+                mv.visitVarInsn(ALOAD, index);
+                break;
+            default:
+                System.err.println("Type not yet managed : " + t);
+                break;
+        }
+    }
+
+}

Modified: felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/composite/service/provides/ProvidedServiceHandler.java
URL: http://svn.apache.org/viewvc/felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/composite/service/provides/ProvidedServiceHandler.java?view=diff&rev=550265&r1=550264&r2=550265
==============================================================================
--- felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/composite/service/provides/ProvidedServiceHandler.java (original)
+++ felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/composite/service/provides/ProvidedServiceHandler.java Sun Jun 24 10:44:53 2007
@@ -196,7 +196,17 @@
             m_services.add(sm);
         }
 
-        Element[] imports = metadata.getElements("import", "");
+        Element[] imports = metadata.getElements("requires", "");
+        
+        // DEPRECATED BLOCK:
+        if (imports.length == 0) {
+            imports = metadata.getElements("import");
+            if (imports.length != 0) {
+                m_manager.getFactory().getLogger().log(Logger.WARNING, "Import is deprecated, please use 'requires' instead of 'import'");
+            }
+        }
+        // END OF DEPRECATED BLOCK
+        
         for (int i = 0; i < imports.length; i++) {
             String itf = imports[i].getAttribute("specification");
             boolean agg = false;

Modified: felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/handlers/configuration/ConfigurationHandler.java
URL: http://svn.apache.org/viewvc/felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/handlers/configuration/ConfigurationHandler.java?view=diff&rev=550265&r1=550264&r2=550265
==============================================================================
--- felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/handlers/configuration/ConfigurationHandler.java (original)
+++ felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/handlers/configuration/ConfigurationHandler.java Sun Jun 24 10:44:53 2007
@@ -29,7 +29,9 @@
 import org.apache.felix.ipojo.architecture.PropertyDescription;
 import org.apache.felix.ipojo.handlers.providedservice.ProvidedServiceHandler;
 import org.apache.felix.ipojo.metadata.Element;
-import org.apache.felix.ipojo.parser.ParseUtils;
+import org.apache.felix.ipojo.parser.FieldMetadata;
+import org.apache.felix.ipojo.parser.ManipulationMetadata;
+import org.apache.felix.ipojo.parser.MethodMetadata;
 import org.apache.felix.ipojo.util.Logger;
 import org.osgi.framework.ServiceRegistration;
 
@@ -107,13 +109,22 @@
 
         // Check if the component is dynamically configurable
         m_isConfigurable = false;
+        // DEPRECATED BLOCK
         if (confs[0].containsAttribute("configurable") && confs[0].getAttribute("configurable").equalsIgnoreCase("true")) {
+            m_manager.getFactory().getLogger().log(Logger.WARNING, "The configurable attribute is deprecated, please use the propagation attribute");
+            m_isConfigurable = true;
+            m_toPropagate = configuration;
+        }
+        // END
+        if (confs[0].containsAttribute("propagation") && confs[0].getAttribute("propagation").equalsIgnoreCase("true")) {
             m_isConfigurable = true;
             m_toPropagate = configuration;
         }
 
         Element[] configurables = confs[0].getElements("Property");
 
+        ArrayList ff = new ArrayList();
+        
         for (int i = 0; i < configurables.length; i++) {
             String fieldName = null;
             String methodName = null;
@@ -150,36 +161,35 @@
             }
 
             // Detect the type of the property
-            Element manipulation = metadata.getElements("Manipulation")[0];
+            ManipulationMetadata manipulation = new ManipulationMetadata(metadata);
             String type = null;
             if (fieldName != null) {
-                for (int kk = 0; kk < manipulation.getElements("Field").length; kk++) {
-                    if (fieldName.equals(manipulation.getElements("Field")[kk].getAttribute("name"))) {
-                        type = manipulation.getElements("Field")[kk].getAttribute("type");
-                    }
-                }
-                if (type == null) {
+                FieldMetadata fm = manipulation.getField(fieldName);
+                if (fm == null) {
                     m_manager.getFactory().getLogger().log(Logger.ERROR,
                             "[" + m_manager.getClassName() + "] The field " + fieldName + " does not exist in the implementation");
                     return;
                 }
+                type = fm.getFieldType();
+                ff.add(fm);
             } else {
-                for (int kk = 0; kk < manipulation.getElements("Method").length; kk++) {
-                    if (methodName.equals(manipulation.getElements("Method")[kk].getAttribute("name"))) {
-                        if (manipulation.getElements("Method")[kk].containsAttribute("arguments")) {
-                            String[] arg = ParseUtils.parseArrays(manipulation.getElements("Method")[kk].getAttribute("arguments"));
-                            if (arg.length != 1) {
-                                m_manager.getFactory().getLogger().log(Logger.ERROR, "A configurable property need to have a method with only one argument");
-                                return;
-                            }
-                            type = arg[0];
-                        }
-                    }
-                }
-                if (type == null) {
+                MethodMetadata[] mm = manipulation.getMethods(methodName);
+                if (mm.length == 0) {
                     m_manager.getFactory().getLogger().log(Logger.ERROR,
-                            "The method " + methodName + " does not exist in the implementation, or does not have one argument");
+                            "[" + m_manager.getClassName() + "] The method " + methodName + " does not exist in the implementation");
                     return;
+                } else {
+                    if (mm[0].getMethodArguments().length != 1) {
+                        m_manager.getFactory().getLogger().log(Logger.ERROR,
+                                "[" + m_manager.getClassName() + "] The method " + methodName + " does not have one argument");
+                        return;
+                    }
+                    if (type != null && !type.equals(mm[0].getMethodArguments()[0])) {
+                        m_manager.getFactory().getLogger().log(Logger.ERROR,
+                                "[" + m_manager.getClassName() + "] The field type (" + type + ") and the method type (" + mm[0].getMethodArguments()[0] + ") are not the same.");
+                        return;
+                    }
+                    type = mm[0].getMethodArguments()[0];
                 }
             }
 
@@ -195,12 +205,7 @@
         }
 
         if (configurables.length > 0) {
-            ArrayList ff = new ArrayList();
             for (int k = 0; k < m_configurableProperties.length; k++) {
-                if (m_configurableProperties[k].getField() != null) {
-                    ff.add(m_configurableProperties[k].getField());
-                }                
-
                 // Check if the instance configuration contains value for the
                 // current property :
                 String name = m_configurableProperties[k].getName();
@@ -213,7 +218,7 @@
                     }
                 }
             }
-            m_manager.register(this, (String[]) ff.toArray(new String[0]));
+            m_manager.register(this, (FieldMetadata[]) ff.toArray(new FieldMetadata[0]), null);
         }
     }
 

Modified: felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/handlers/dependency/DependencyHandler.java
URL: http://svn.apache.org/viewvc/felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/handlers/dependency/DependencyHandler.java?view=diff&rev=550265&r1=550264&r2=550265
==============================================================================
--- felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/handlers/dependency/DependencyHandler.java (original)
+++ felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/handlers/dependency/DependencyHandler.java Sun Jun 24 10:44:53 2007
@@ -19,14 +19,18 @@
 package org.apache.felix.ipojo.handlers.dependency;
 
 import java.net.URL;
+import java.util.ArrayList;
 import java.util.Dictionary;
+import java.util.List;
 
 import org.apache.felix.ipojo.Handler;
 import org.apache.felix.ipojo.InstanceManager;
 import org.apache.felix.ipojo.architecture.HandlerDescription;
 import org.apache.felix.ipojo.handlers.dependency.nullable.NullableObjectWriter;
 import org.apache.felix.ipojo.metadata.Element;
-import org.apache.felix.ipojo.parser.ParseUtils;
+import org.apache.felix.ipojo.parser.FieldMetadata;
+import org.apache.felix.ipojo.parser.ManipulationMetadata;
+import org.apache.felix.ipojo.parser.MethodMetadata;
 import org.apache.felix.ipojo.util.Logger;
 import org.osgi.framework.ServiceReference;
 
@@ -157,72 +161,57 @@
      * @param manipulation : the component-type manipulation metadata
      * @return true if the dependency is valid
      */
-    private boolean checkDependency(Dependency dep, Element manipulation) {
+    private boolean checkDependency(Dependency dep, ManipulationMetadata manipulation) {
         // Check the internal type of dependency
         String field = dep.getField();
         DependencyCallback[] callbacks = dep.getCallbacks();
         
         for (int i = 0; i < callbacks.length; i++) {
-            for (int j = 0; j < manipulation.getElements("Method").length; j++) {
-                if (manipulation.getElements("Method")[j].getAttribute("name").equals(callbacks[i].getMethodName())) {
-                    if (manipulation.getElements("Method")[j].containsAttribute("Arguments")) {
-                        String[] args = ParseUtils.parseArrays(manipulation.getElements("Method")[j].getAttribute("Arguments"));
-                        if (args.length != 1) {
-                            getInstanceManager().getFactory().getLogger().log(Logger.ERROR, "A dependency callback " + callbacks[i].getMethodName() + " must have 0 or 1 argument");
-                            return false;
-                        } else {
-                            callbacks[i].setArgument(args[0]);
-                            if (!args[0].equals(ServiceReference.class.getName())) {
-                                if (dep.getSpecification() == null) {
-                                    dep.setSpecification(args[0]);
-                                }
-                                if (!dep.getSpecification().equals(args[0])) {
-                                    m_manager.getFactory().getLogger().log(Logger.WARNING, "[DependencyHandler on " + m_manager.getClassName() + "] The field type [" + args[0] + "] and the needed service interface ["
-                                                + dep.getSpecification() + "] are not the same");
-                                    dep.setSpecification(args[0]);
-                                }
-                            }
-                        }
-                    } else {
-                        callbacks[i].setArgument("EMPTY");
+            MethodMetadata[] mets = manipulation.getMethods(callbacks[i].getMethodName());
+            if (mets.length == 0) {
+                getInstanceManager().getFactory().getLogger().log(Logger.ERROR, "A dependency callback " + callbacks[i].getMethodName() + " does not exist in the implementation");
+                return false;
+            }
+            if (mets[0].getMethodArguments().length > 1) {
+                getInstanceManager().getFactory().getLogger().log(Logger.ERROR, "A dependency callback " + callbacks[i].getMethodName() + " must have 0 or 1 argument");
+                return false;
+            }
+            if (mets[0].getMethodArguments().length == 0) {
+                callbacks[i].setArgument("EMPTY");
+            } else {
+                callbacks[i].setArgument(mets[0].getMethodArguments()[0]);
+                if (!mets[0].getMethodArguments()[0].equals(ServiceReference.class.getName())) {
+                    if (dep.getSpecification() == null) {
+                        dep.setSpecification(mets[0].getMethodArguments()[0]);
+                    }
+                    if (!dep.getSpecification().equals(mets[0].getMethodArguments()[0])) {
+                        m_manager.getFactory().getLogger().log(Logger.WARNING, "[DependencyHandler on " + m_manager.getClassName() + "] The field type [" + mets[0].getMethodArguments()[0] + "] and the needed service interface ["
+                                    + dep.getSpecification() + "] are not the same");
+                        dep.setSpecification(mets[0].getMethodArguments()[0]);
                     }
                 }
-            }
+            }   
         }
         
         if (field != null) {
-            String type = null;
-            for (int i = 0; i < manipulation.getElements("Field").length; i++) {
-                if (field.equals(manipulation.getElements("Field")[i].getAttribute("name"))) {
-                    type = manipulation.getElements("Field")[i].getAttribute("type");
-                    break;
-                }
-            }
-
-            if (type == null) {
-                m_manager.getFactory().getLogger().log(Logger.ERROR,
-                        "[DependencyHandler on " + m_manager.getClassName() + "] A declared dependency was not found in the class : " + dep.getField());
+            FieldMetadata fm = manipulation.getField(field);
+            if (field == null) {
+                getInstanceManager().getFactory().getLogger().log(Logger.ERROR, "A dependency field " + field + " does not exist in the implementation class");
                 return false;
             }
+            String type = fm.getFieldType(); 
+            if (type.endsWith("[]")) {
+                // Set the dependency to multiple
+                dep.setAggregate();
+                type = type.substring(0, type.length() - 2);
+            }
 
-            if (type != null) {
-                if (type.endsWith("[]")) {
-                    // Set the dependency to multiple
-                    dep.setAggregate();
-                    type = type.substring(0, type.length() - 2);
-                }
-
-                if (dep.getSpecification() == null) {
-                    dep.setSpecification(type);
-                }
+            if (dep.getSpecification() == null) { dep.setSpecification(type); }
 
-                if (!dep.getSpecification().equals(type)) {
-                    m_manager.getFactory().getLogger().log(Logger.WARNING, "[DependencyHandler on " + m_manager.getClassName() + "] The field type [" + type + "] and the needed service interface ["
+            if (!dep.getSpecification().equals(type)) {
+                m_manager.getFactory().getLogger().log(Logger.WARNING, "[DependencyHandler on " + m_manager.getClassName() + "] The field type [" + type + "] and the needed service interface ["
                                 + dep.getSpecification() + "] are not the same");
-                    dep.setSpecification(type);
-                }
-            } else {
-                m_manager.getFactory().getLogger().log(Logger.WARNING, "[DependencyHandler on " + m_manager.getClassName() + "] The declared dependency " + dep.getField() + "  does not exist in the code");
+                dep.setSpecification(type);
             }
         }
         
@@ -241,9 +230,23 @@
         m_manager = im;
         m_dependencies = new Dependency[0];
         m_nullableClasses = new Class[0];
+        
+        ManipulationMetadata manipulation = new ManipulationMetadata(componentMetadata);
+        List fl = new ArrayList();
 
         // Create the dependency according to the component metadata
-        Element[] deps = componentMetadata.getElements("Dependency");
+        Element[] deps = componentMetadata.getElements("Requires"); 
+        
+        // DEPRECATED BLOCK :
+        if (deps.length == 0) {
+            deps = componentMetadata.getElements("Dependency");
+            if (deps.length != 0) {
+                im.getFactory().getLogger().log(Logger.WARNING, "Dependency is deprecated, please use 'requires' instead of 'dependency'");
+            }
+        }
+        // END OF DEPRECATED BLOCK
+
+         
         for (int i = 0; i < deps.length; i++) {
             // Create the dependency metadata
             String field = null;
@@ -285,9 +288,11 @@
             }
             
             // Check the dependency :
-            Element manipulation = componentMetadata.getElements("Manipulation")[0];
             if (checkDependency(dep, manipulation)) {
                 addDependency(dep);
+                if (dep.getField() != null) {
+                    fl.add(manipulation.getField(dep.getField()));
+                }
             } else {
                 m_manager.getFactory().getLogger().log(Logger.ERROR,
                         "[DependencyHandler on " + m_manager.getClassName() + "] The dependency on " + dep.getField() + " is not valid");
@@ -296,11 +301,7 @@
         }
 
         if (deps.length > 0) {
-            String[] fields = new String[m_dependencies.length];
-            for (int k = 0; k < m_dependencies.length; k++) {
-                fields[k] = m_dependencies[k].getField();
-            }
-            m_manager.register(this, fields);
+            m_manager.register(this, (FieldMetadata[]) fl.toArray(new FieldMetadata[0]), null);
         }
     }
 

Modified: felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/handlers/dependency/DependencyHandlerDescription.java
URL: http://svn.apache.org/viewvc/felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/handlers/dependency/DependencyHandlerDescription.java?view=diff&rev=550265&r1=550264&r2=550265
==============================================================================
--- felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/handlers/dependency/DependencyHandlerDescription.java (original)
+++ felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/handlers/dependency/DependencyHandlerDescription.java Sun Jun 24 10:44:53 2007
@@ -85,7 +85,7 @@
             if (m_dependencies[i].getState() == 2) {
                 state = "unresolved";
             }
-            Element dep = new Element("Dependency", "");
+            Element dep = new Element("Requires", "");
             dep.addAttribute(new Attribute("Specification", m_dependencies[i].getInterface()));
             dep.addAttribute(new Attribute("Filter", m_dependencies[i].getFilter()));
             dep.addAttribute(new Attribute("State", state));

Modified: felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/handlers/lifecycle/callback/LifecycleCallback.java
URL: http://svn.apache.org/viewvc/felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/handlers/lifecycle/callback/LifecycleCallback.java?view=diff&rev=550265&r1=550264&r2=550265
==============================================================================
--- felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/handlers/lifecycle/callback/LifecycleCallback.java (original)
+++ felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/handlers/lifecycle/callback/LifecycleCallback.java Sun Jun 24 10:44:53 2007
@@ -20,7 +20,7 @@
 
 import java.lang.reflect.InvocationTargetException;
 
-import org.apache.felix.ipojo.InstanceManager;
+import org.apache.felix.ipojo.parser.MethodMetadata;
 import org.apache.felix.ipojo.util.Callback;
 
 /**
@@ -29,52 +29,37 @@
  * @author <a href="mailto:dev@felix.apache.org">Felix Project Team</a>
  */
 public class LifecycleCallback {
-
+    
     /**
-     * Initial state of the transition.
+     * Invalid to Valid transition.
      */
-    private int m_initialState;
-
+    protected static final int VALIDATE = 1;
+    
     /**
-     * Final state of the transition.
+     * Valid to Invalid transition.
      */
-    private int m_finalState;
-
+    protected static final int INVALIDATE = 0;
+    
     /**
-     * Callback object.
+     * Transition on hwich calling the callback.
      */
-    private Callback m_callback;
+    private int m_transition;
 
     /**
-     * Method called by the callback.
+     * Callback object.
      */
-    private String m_method;
+    private Callback m_callback;
 
     /**
      * LifecycleCallback constructor.
      * 
      * @param hh : the callback handler calling the callback
-     * @param initialState : initial state of the callback
-     * @param finalState : finali state of the callback
-     * @param method : method to invoke
-     * @param isStatic : is the method static ?
-     */
-    public LifecycleCallback(LifecycleCallbackHandler hh, String initialState, String finalState, String method, boolean isStatic) {
-        if (initialState.equals("VALID")) {
-            m_initialState = InstanceManager.VALID;
-        }
-        if (initialState.equals("INVALID")) {
-            m_initialState = InstanceManager.INVALID;
-        }
-        if (finalState.equals("VALID")) {
-            m_finalState = InstanceManager.VALID;
-        }
-        if (finalState.equals("INVALID")) {
-            m_finalState = InstanceManager.INVALID;
-        }
-
-        m_method = method;
-        m_callback = new Callback(method, new String[0], isStatic, hh.getInstanceManager());
+     * @param transition : transition on which calling the callback
+     * @param mm : method metadata to invoke
+     */
+    public LifecycleCallback(LifecycleCallbackHandler hh, int transition, MethodMetadata mm) {
+        m_transition = transition;
+        m_callback = new Callback(mm, hh.getInstanceManager());
     }
 
     /**
@@ -88,17 +73,17 @@
     protected void call() throws NoSuchMethodException, IllegalAccessException, InvocationTargetException {
         m_callback.call();
     }
-
-    public int getFinalState() {
-        return m_finalState;
-    }
-
-    public int getInitialState() {
-        return m_initialState;
+    
+    protected int getTransition() {
+        return m_transition;
     }
-
-    public String getMethod() {
-        return m_method;
+    
+    /**
+     * Get the method name of the callback.
+     * @return the method name
+     */
+    protected String getMethod() {
+        return m_callback.getMethod();
     }
 
 }

Modified: felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/handlers/lifecycle/callback/LifecycleCallbackHandler.java
URL: http://svn.apache.org/viewvc/felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/handlers/lifecycle/callback/LifecycleCallbackHandler.java?view=diff&rev=550265&r1=550264&r2=550265
==============================================================================
--- felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/handlers/lifecycle/callback/LifecycleCallbackHandler.java (original)
+++ felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/handlers/lifecycle/callback/LifecycleCallbackHandler.java Sun Jun 24 10:44:53 2007
@@ -25,6 +25,8 @@
 import org.apache.felix.ipojo.Handler;
 import org.apache.felix.ipojo.InstanceManager;
 import org.apache.felix.ipojo.metadata.Element;
+import org.apache.felix.ipojo.parser.ManipulationMetadata;
+import org.apache.felix.ipojo.parser.MethodMetadata;
 import org.apache.felix.ipojo.util.Logger;
 
 /**
@@ -91,19 +93,48 @@
         if (metadata.containsAttribute("immediate") && metadata.getAttribute("immediate").equalsIgnoreCase("true")) {
             m_immediate = true;
         }
+        
+        ManipulationMetadata mm = new ManipulationMetadata(metadata);
 
         Element[] hooksMetadata = metadata.getElements("callback");
         for (int i = 0; i < hooksMetadata.length; i++) {
-            // Create an HookMetadata object
-            String initialState = hooksMetadata[i].getAttribute("initial");
-            String finalState = hooksMetadata[i].getAttribute("final");
-            String method = hooksMetadata[i].getAttribute("method");
-            boolean isStatic = false;
-            if (hooksMetadata[i].containsAttribute("isStatic") && hooksMetadata[i].getAttribute("isStatic").equals("true")) {
-                isStatic = true;
+            String methodName = hooksMetadata[i].getAttribute("method");
+            
+            MethodMetadata met = mm.getMethod(methodName, new String[0]);
+            if (met == null) {
+                cm.getFactory().getLogger().log(Logger.ERROR, "The method " + methodName + " is not implemented in the " + cm.getInstanceName());
+                return;
             }
-
-            LifecycleCallback hk = new LifecycleCallback(this, initialState, finalState, method, isStatic);
+            
+            int transition = -1;
+            if (hooksMetadata[i].containsAttribute("transition")) {
+                if (hooksMetadata[i].getAttribute("transition").equalsIgnoreCase("validate")) {
+                    transition = LifecycleCallback.VALIDATE;
+                }
+                if (hooksMetadata[i].getAttribute("transition").equalsIgnoreCase("invalidate")) {
+                    transition = LifecycleCallback.INVALIDATE; 
+                }
+            }
+            
+            //DEPRECATED BLOCK
+            if (hooksMetadata[i].containsAttribute("initial")) {
+                cm.getFactory().getLogger().log(Logger.WARNING, "initial & final are deprecated, please use 'transition=validate|invalidate' instead.");
+                if (hooksMetadata[i].containsAttribute("final")) {
+                    if (hooksMetadata[i].getAttribute("initial").equalsIgnoreCase("valid") && hooksMetadata[i].getAttribute("final").equalsIgnoreCase("invalid")) {
+                        transition = LifecycleCallback.INVALIDATE;
+                    } else {
+                        transition = LifecycleCallback.VALIDATE;
+                    }
+                } 
+            }
+            //END OF DEPRECATED BLOCK
+            
+            if (transition == -1) {
+                cm.getFactory().getLogger().log(Logger.ERROR, "Unknown or malformed transition");
+                return;
+            }
+            
+            LifecycleCallback hk = new LifecycleCallback(this, transition, met);
             addCallback(hk);
         }
         if (m_callbacks.length > 0 || m_immediate) {
@@ -137,17 +168,25 @@
     /**
      * When the state change call the associated callback.
      * 
-     * @param state : the new isntance state.
+     * @param state : the new instance state.
      * @see org.apache.felix.ipojo.Handler#stateChanged(int)
      */
     public void stateChanged(int state) {
+        int transition = -1;
+        if (m_state == ComponentInstance.INVALID && state == ComponentInstance.VALID) {
+            transition = LifecycleCallback.VALIDATE;
+        }
+        if (m_state == ComponentInstance.VALID && state == ComponentInstance.INVALID) {
+            transition = LifecycleCallback.INVALIDATE;
+        }
+        
         // Manage immediate component
-        if (m_state == ComponentInstance.INVALID && state == ComponentInstance.VALID && m_manager.getPojoObjects().length == 0) {
+        if (m_immediate && transition == LifecycleCallback.VALIDATE && m_manager.getPojoObjects().length == 0) {
             m_manager.createPojoObject();
         }
 
         for (int i = 0; i < m_callbacks.length; i++) {
-            if (m_callbacks[i].getInitialState() == m_state && m_callbacks[i].getFinalState() == state) {
+            if (m_callbacks[i].getTransition() == transition) {
                 try {
                     m_callbacks[i].call();
                 } catch (NoSuchMethodException e) {

Modified: felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/handlers/providedservice/Property.java
URL: http://svn.apache.org/viewvc/felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/handlers/providedservice/Property.java?view=diff&rev=550265&r1=550264&r2=550265
==============================================================================
--- felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/handlers/providedservice/Property.java (original)
+++ felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/handlers/providedservice/Property.java Sun Jun 24 10:44:53 2007
@@ -22,7 +22,8 @@
 import java.lang.reflect.Constructor;
 import java.lang.reflect.InvocationTargetException;
 
-import org.apache.felix.ipojo.metadata.Element;
+import org.apache.felix.ipojo.parser.FieldMetadata;
+import org.apache.felix.ipojo.parser.ManipulationMetadata;
 import org.apache.felix.ipojo.parser.ParseUtils;
 import org.apache.felix.ipojo.util.Logger;
 
@@ -76,7 +77,7 @@
      * @param value : initial value of the property
      * @param manipulation : manipulation metadata
      */
-    public Property(ProvidedService ps, String name, String field, String type, String value, Element manipulation) {
+    public Property(ProvidedService ps, String name, String field, String type, String value, ManipulationMetadata manipulation) {
         m_providedService = ps;
         m_name = name;
         m_field = field;
@@ -96,16 +97,13 @@
                 ps.getInstanceManager().getFactory().getLogger().log(Logger.ERROR, "The property " + m_name + " has neither type neither field.");
                 return;
             }
-            for (int j = 0; j < manipulation.getElements("Field").length; j++) {
-                if (field.equals(manipulation.getElements("Field")[j].getAttribute("name"))) {
-                    m_type = manipulation.getElements("Field")[j].getAttribute("type");
-                    break;
-                }
-            }
-            if (m_type == null) {
+            FieldMetadata fm = manipulation.getField(field);
+            if (fm == null) {
                 m_providedService.getInstanceManager().getFactory().getLogger().log(Logger.ERROR,
                         "[" + ps.getInstanceManager().getClassName() + "] A declared property was not found in the class : " + m_field);
+                return;
             }
+            m_type = fm.getFieldType();
         }
 
         if (m_initialValue != null) {

Modified: felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/handlers/providedservice/ProvidedService.java
URL: http://svn.apache.org/viewvc/felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/handlers/providedservice/ProvidedService.java?view=diff&rev=550265&r1=550264&r2=550265
==============================================================================
--- felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/handlers/providedservice/ProvidedService.java (original)
+++ felix/trunk/ipojo/core/src/main/java/org/apache/felix/ipojo/handlers/providedservice/ProvidedService.java Sun Jun 24 10:44:53 2007
@@ -96,7 +96,7 @@
         m_factoryPolicy = factoryPolicy;
 
         // Add service pid and factory pid
-        addProperty(new Property(this, org.osgi.framework.Constants.SERVICE_PID, handler.getInstanceManager().getInstanceName()));
+        addProperty(new Property(this, org.osgi.framework.Constants.SERVICE_PID, handler.getInstanceManager().getInstanceName()));       
         addProperty(new Property(this, "factory.pid", handler.getInstanceManager().getFactory().getName()));
     }