Fix issue Felix-846.
Despite the provided approach is not the cleanest (due to a maven issue), this patch allows setting iPOJO metadata in the pom file inside a CDATA block such as in:
	<plugin>
		<groupId>org.apache.felix</groupId>
		<artifactId>maven-ipojo-plugin</artifactId>
		<version>1.1.0-SNAPSHOT</version>
		<executions>
			<execution>
				<goals>
					<goal>ipojo-bundle</goal>
				</goals>
				<configuration>
					<ignoreAnnotations>true</ignoreAnnotations>
					<metadata>
   					<![CDATA[
   					<ipojo 
    					xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
						xsi:schemaLocation="org.apache.felix.ipojo http://felix.apache.org/ipojo/schemas/1.1.0-SNAPSHOT/core.xsd 
	 					org.apache.felix.ipojo.whiteboard http://felix.apache.org/ipojo/schemas/1.1.0-SNAPSHOT/whiteboard-pattern.xsd"
						xmlns="org.apache.felix.ipojo"
						xmlns:wbp="org.apache.felix.ipojo.whiteboard">
						<component classname="org.apache.felix.ipojo.test.FooProvider" name="fooprovider">
							<provides>
								<property field="foo" value="foo"/>
							</provides>
						</component>
	
						<component classname="org.apache.felix.ipojo.test.FooWhiteBoardPattern" name="under-providers">
								<wbp:wbp 
									filter="(objectclass=org.apache.felix.ipojo.test.FooService)" 
									onArrival="onArrival" onDeparture="onDeparture" onModification="onModification"
								/>
								<provides/>
						</component>
	
						<component classname="org.apache.felix.ipojo.test.FooWhiteBoardPattern" name="under-properties">
								<wbp:wbp filter="(foo=foo)" onArrival="onArrival" onDeparture="onDeparture" 
									onModification="onModification"
								/>
								<provides/>
						</component>
					</ipojo>
					]]>
					</metadata>
				</configuration>
			</execution>
		</executions>
	</plugin>
	
	
So, the metadata attribute can be either absent (only annotations), or can contain the name of the metadata file or can contain iPOJO metadata in a CDATA block.

git-svn-id: https://svn.apache.org/repos/asf/felix/trunk@728951 13f79535-47bb-0310-9956-ffa450edef68
diff --git a/ipojo/arch/pom.xml b/ipojo/arch/pom.xml
index 28baaa8..b92a089 100644
--- a/ipojo/arch/pom.xml
+++ b/ipojo/arch/pom.xml
@@ -70,21 +70,36 @@
 					</instructions>
 				</configuration>
 			</plugin>
-			<plugin>
-				<groupId>org.apache.felix</groupId>
-				<artifactId>maven-ipojo-plugin</artifactId>
-				<version>1.1.0-SNAPSHOT</version>
-				<executions>
-					<execution>
-						<goals>
-							<goal>ipojo-bundle</goal>
-						</goals>
-						<configuration>
-							<ignoreAnnotations>true</ignoreAnnotations>
-						</configuration>
-					</execution>
-				</executions>
-			</plugin>
+	<plugin>
+		<groupId>org.apache.felix</groupId>
+		<artifactId>maven-ipojo-plugin</artifactId>
+		<version>1.1.0-SNAPSHOT</version>
+		<executions>
+			<execution>
+				<goals>
+					<goal>ipojo-bundle</goal>
+				</goals>
+				<configuration>
+					<ignoreAnnotations>true</ignoreAnnotations>
+					<metadata>
+					<![CDATA[
+						<ipojo>
+							<component classname="org.apache.felix.ipojo.arch.ArchCommandImpl"
+								public="false">
+								<Provides />
+								<requires field="m_archs" optional="true" />
+								<requires field="m_factories" optional="true" />
+								<requires field="m_handlers" optional="true" />
+							</component>
+							<instance component="org.apache.felix.ipojo.arch.ArchCommandImpl"
+								name="ArchCommand" />
+						</ipojo>
+						]]>
+					</metadata>
+				</configuration>
+			</execution>
+		</executions>
+	</plugin>
 			<plugin>
 				<groupId>org.codehaus.mojo</groupId>
 				<artifactId>rat-maven-plugin</artifactId>
diff --git a/ipojo/arch/src/main/resources/metadata.xml b/ipojo/arch/src/main/resources/metadata.xml
deleted file mode 100644
index 06e13ed..0000000
--- a/ipojo/arch/src/main/resources/metadata.xml
+++ /dev/null
@@ -1,30 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-	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.
--->
-<ipojo>
-	<component classname="org.apache.felix.ipojo.arch.ArchCommandImpl"
-		public="false">
-		<Provides />
-		<requires field="m_archs" optional="true" />
-		<requires field="m_factories" optional="true"/>
-		<requires field="m_handlers" optional="true"/>
-	</component>
-	<instance component="org.apache.felix.ipojo.arch.ArchCommandImpl"
-		name="ArchCommand" />
-</ipojo>
\ No newline at end of file
diff --git a/ipojo/manipulator/src/main/java/org/apache/felix/ipojo/manipulator/Pojoization.java b/ipojo/manipulator/src/main/java/org/apache/felix/ipojo/manipulator/Pojoization.java
index ef77a22..70650a1 100644
--- a/ipojo/manipulator/src/main/java/org/apache/felix/ipojo/manipulator/Pojoization.java
+++ b/ipojo/manipulator/src/main/java/org/apache/felix/ipojo/manipulator/Pojoization.java
@@ -135,6 +135,46 @@
     public void setUseLocalXSD() {
         m_ignoreLocalXSD = false;
     }
+    
+    /**
+     * Manipulates an input bundle.
+     * This method creates an iPOJO bundle based on the given metadata file.
+     * The original and final bundles must be different.
+     * @param in the original bundle.
+     * @param out the final bundle.
+     * @param metadata the iPOJO metadata input stream. 
+     */
+    public void pojoization(File in, File out, InputStream metadata) {
+        m_metadata = parseXMLMetadata(metadata);
+        if (m_metadata == null) { // An error occurs during the parsing.
+            return;
+        }
+        // m_metadata can be either an empty array or an Element
+        // array with component type description. It also can be null
+        // if no metadata file is given.
+        
+        JarFile inputJar;
+        try {
+            inputJar = new JarFile(in);
+        } catch (IOException e) {
+            error("The input file " + in.getAbsolutePath() + " is not a Jar file");
+            return;
+        }
+
+        // Get the list of declared component
+        m_components = getDeclaredComponents(m_metadata);
+
+        // Start the manipulation
+        manipulation(inputJar, out);
+
+        // Check that all declared components are manipulated
+        for (int i = 0; i < m_components.size(); i++) {
+            ComponentInfo ci = (ComponentInfo) m_components.get(i);
+            if (!ci.m_isManipulated) {
+                error("The component " + ci.m_classname + " is declared but not in the bundle");
+            }
+        }
+    }
 
     /**
      * Manipulates an input bundle.
@@ -147,14 +187,28 @@
     public void pojoization(File in, File out, File metadataFile) {
         // Get the metadata.xml location if not null
         if (metadataFile != null) {
-            String path = metadataFile.getAbsolutePath();
-            if (!path.startsWith("/")) {
-                path = "/" + path;
+            try {
+                InputStream stream = null;
+                URL url = metadataFile.toURL();
+                if (url == null) {
+                    warn("Cannot find the metadata file : " + metadataFile.getAbsolutePath());
+                    m_metadata = new Element[0];
+                } else {
+                    stream = url.openStream();
+                    m_metadata = parseXMLMetadata(stream);
+                }
+            } catch (MalformedURLException e) {
+                error("Cannot open the metadata input stream from " + metadataFile.getAbsolutePath() + ": " + e.getMessage());
+                m_metadata = null;
+            } catch (IOException e) {
+                error("Cannot open the metadata input stream: " + metadataFile.getAbsolutePath() + ": " + e.getMessage());
+                m_metadata = null;
             }
-            m_metadata = parseXMLMetadata(path);
+            
             if (m_metadata == null) { // An error occurs during the parsing.
                 return;
             }
+            
             // m_metadata can be either an empty array or an Element
             // array with component type description. It also can be null
             // if no metadata file is given.
@@ -663,21 +717,12 @@
 
     /**
      * Parse XML Metadata.
-     * @param path : path of the file to parse.
+     * @param stream metadata input stream.
      * @return the parsed element array.
      */
-    private Element[] parseXMLMetadata(String path) {
-        File metadata = new File(path);
-        URL url;
+    private Element[] parseXMLMetadata(InputStream stream) {
         Element[] meta = null;
         try {
-            url = metadata.toURL();
-            if (url == null) {
-                warn("Cannot find the metadata file : " + path);
-                return new Element[0];
-            }
-
-            InputStream stream = url.openStream();            
             XMLReader parser = (XMLReader) Class.forName("org.apache.xerces.parsers.SAXParser").newInstance();
             XMLMetadataParser handler = new XMLMetadataParser();
             parser.setContentHandler(handler);
@@ -685,18 +730,7 @@
                     true); 
             parser.setFeature("http://apache.org/xml/features/validation/schema", 
                     true);
-            
-            
-           
-            
-//            parser
-//                    .setProperty(
-//                            "http://apache.org/xml/properties/schema/external-noNamespaceSchemaLocation",
-//                            xsd.toString());
-//
-//            
-            
-            
+   
             parser.setErrorHandler(handler);
             
             if (! m_ignoreLocalXSD) {
@@ -708,26 +742,23 @@
             meta = handler.getMetadata();
             stream.close();
 
-        } catch (MalformedURLException e) {
-            error("Malformed metadata URL for " + path);
-            return null;
         } catch (IOException e) {
-            error("Cannot open the file : " + path);
+            error("Cannot open the metadata input stream: " + e.getMessage());
             return null;
         } catch (ParseException e) {
-            error("Parsing error when parsing the XML file " + path + " : " + e.getMessage());
+            error("Parsing error when parsing the XML file: " + e.getMessage());
             return null;
         } catch (SAXParseException e) {
             error("Error during metadata parsing at line " + e.getLineNumber() + " : " + e.getMessage());
             return null;
         } catch (SAXException e) {
-            error("Parsing error when parsing (Sax Error) the XML file " + path + " : " + e.getMessage());
+            error("Parsing error when parsing (Sax Error) the XML file: " + e.getMessage());
             return null;
         } catch (InstantiationException e) {
-            error("Cannot instantiate the SAX parser for the XML file " + path + " : " + e.getMessage());
+            error("Cannot instantiate the SAX parser for the XML file: " + e.getMessage());
             return null;
         } catch (IllegalAccessException e) {
-            error("Cannot instantiate  the SAX parser (IllegalAccess) for the XML file " + path + " : " + e.getMessage());
+            error("Cannot instantiate  the SAX parser (IllegalAccess) to the XML file: " + e.getMessage());
             return null;
         } catch (ClassNotFoundException e) {
             error("Cannot load the SAX Parser : " + e.getMessage());
@@ -735,7 +766,7 @@
         }
 
         if (meta == null || meta.length == 0) {
-            warn("Neither component types, nor instances in " + path);
+            warn("Neither component types, nor instances in the metadata");
         }
 
         return meta;
diff --git a/ipojo/plugin/src/main/java/org/apache/felix/ipojo/plugin/ManipulatorMojo.java b/ipojo/plugin/src/main/java/org/apache/felix/ipojo/plugin/ManipulatorMojo.java
index 9c36a61..a6fb400 100644
--- a/ipojo/plugin/src/main/java/org/apache/felix/ipojo/plugin/ManipulatorMojo.java
+++ b/ipojo/plugin/src/main/java/org/apache/felix/ipojo/plugin/ManipulatorMojo.java
@@ -18,7 +18,11 @@
  */
 package org.apache.felix.ipojo.plugin;
 
+import java.io.ByteArrayInputStream;
 import java.io.File;
+import java.io.FileInputStream;
+import java.io.FileNotFoundException;
+import java.io.InputStream;
 import java.util.Arrays;
 import java.util.List;
 
@@ -66,7 +70,7 @@
     private String m_jarName;
 
     /**
-     * Location of the metadata file.
+     * Location of the metadata file or iPOJO metadata configuration.
      * @parameter alias="metadata" default-value="metadata.xml"
      */
     private String m_metadata;
@@ -111,10 +115,14 @@
      * @parameter alias="IgnoreEmbeddedSchemas" default-value="false"
      */
     private boolean m_ignoreEmbeddedXSD;
-
+    
     protected MavenProject getProject() {
         return this.m_project;
     }
+    
+    private boolean isXML() {
+        return m_metadata != null && m_metadata.contains("<");
+    }
 
     /**
      * Execute method : this method launches the pojoization.
@@ -127,27 +135,46 @@
             this.getLog().debug("Ignoring project " + this.getProject().getArtifact() + " : type " + this.getProject().getArtifact().getType() + " is not supported by iPOJO plugin, supported types are " + this.m_supportedProjectTypes);
             return;
         }
+        
 
         getLog().info("Start bundle manipulation");
-        // Get metadata file
+
+        // Get metadata
+        // Check if metadata are contained in the configuration
+        InputStream is = null;
         
-        // Look for the metadata file in the output directory
-        File meta = new File(m_outputDirectory + File.separator + m_metadata);
+        if (isXML()) {
+            is = new ByteArrayInputStream(m_metadata.getBytes()); 
+        } else {
+            if (m_metadata == null) {
+                // Try with metadata.xml
+                m_metadata = "metadata.xml";
+            }
+            // Look for the metadata file in the output directory
+            File meta = new File(m_outputDirectory + File.separator + m_metadata);
+            // If not found look inside the pom directory 
+            if (! meta.exists()) {
+                meta = new File(m_project.getBasedir() + File.separator + m_metadata);
+            }
         
-        // If not found look inside the pom directory
-        if (! meta.exists()) {
-            meta = new File(m_project.getBasedir() + File.separator + m_metadata);
-        }
-        
-        getLog().info("Metadata file : " + meta.getAbsolutePath());
-        if (!meta.exists()) {
-            // Verify if annotations are ignored
-            if (m_ignoreAnnotations) {
-                getLog().info("No metadata file found - ignoring annotations");
-                return;
-            } else {
-                getLog().info("No metadata file found - trying to use only annotations");
-                meta = null;
+            getLog().info("Metadata file : " + meta.getAbsolutePath());
+            if (!meta.exists()) {
+                // Verify if annotations are ignored
+                if (m_ignoreAnnotations) {
+                    getLog().info("No metadata file found - ignoring annotations");
+                    return;
+                } else {
+                    getLog().info("No metadata file found - trying to use only annotations");
+                    meta = null;
+                }
+            }
+            
+            if (meta != null) {
+                try {
+                    is = new FileInputStream(meta);
+                } catch (FileNotFoundException e) {
+                    throw new MojoExecutionException("the specified metadata file does not exist: " + e.getMessage());
+                }
             }
         }
 
@@ -163,7 +190,14 @@
         Pojoization pojo = new Pojoization();
         if (!m_ignoreAnnotations) { pojo.setAnnotationProcessing(); }
         if (!m_ignoreEmbeddedXSD) { pojo.setUseLocalXSD(); }
-        pojo.pojoization(in, out, meta);
+        
+        // Executes the pojoization.
+        if (is == null) {
+            pojo.pojoization(in, out, (File) null); // Only annotations
+        } else  {
+            pojo.pojoization(in, out, is);
+        }
+        
         for (int i = 0; i < pojo.getWarnings().size(); i++) {
             getLog().warn((String) pojo.getWarnings().get(i));
         }
diff --git a/ipojo/tests/core/lifecycle-controller/pom.xml b/ipojo/tests/core/lifecycle-controller/pom.xml
index 547b259..261edd5 100644
--- a/ipojo/tests/core/lifecycle-controller/pom.xml
+++ b/ipojo/tests/core/lifecycle-controller/pom.xml
@@ -85,6 +85,34 @@
 						</goals>

 						<configuration>

 							<ignoreAnnotations>true</ignoreAnnotations>

+							<metadata>

+							    <![CDATA[

+								<ipojo

+   									 xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"

+    								 xsi:schemaLocation="org.apache.felix.ipojo http://felix.apache.org/ipojo/schemas/1.1.0-SNAPSHOT/core.xsd"

+    								 xmlns="org.apache.felix.ipojo">

+									 <component

+										classname="org.apache.felix.ipojo.test.scenarios.component.LifecycleControllerTest"

+										name="LFC-Test">

+										<provides />

+										<controller field="m_state" />

+										<properties>

+											<property name="conf" field="m_conf" method="setConf" />

+										</properties>

+									 </component>

+

+								     <component

+										classname="org.apache.felix.ipojo.test.scenarios.component.LifecycleControllerTest"

+										name="LFC-Test-Immediate" immediate="true" architecture="true">

+										<provides />

+										<controller field="m_state" />

+										<properties>

+											<property name="conf" field="m_conf" method="setConf" />

+										</properties>

+									 </component>

+								 </ipojo>

+								 ]]>

+							</metadata>

 						</configuration>

 					</execution>

 				</executions>

diff --git a/ipojo/tests/core/lifecycle-controller/src/main/resources/metadata.xml b/ipojo/tests/core/lifecycle-controller/src/main/resources/metadata.xml
deleted file mode 100644
index 91d881c..0000000
--- a/ipojo/tests/core/lifecycle-controller/src/main/resources/metadata.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<ipojo

-    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"

-    xsi:schemaLocation="org.apache.felix.ipojo http://felix.apache.org/ipojo/schemas/1.1.0-SNAPSHOT/core.xsd"

-    xmlns="org.apache.felix.ipojo">

-	<component

-		classname="org.apache.felix.ipojo.test.scenarios.component.LifecycleControllerTest"

-		name="LFC-Test">

-		<provides />

-		<controller field="m_state" />

-		<properties>

-			<property name="conf" field="m_conf" method="setConf" />

-		</properties>

-	</component>

-

-	<component

-		classname="org.apache.felix.ipojo.test.scenarios.component.LifecycleControllerTest"

-		name="LFC-Test-Immediate" immediate="true" architecture="true">

-		<provides />

-		<controller field="m_state" />

-		<properties>

-			<property name="conf" field="m_conf" method="setConf" />

-		</properties>

-	</component>

-</ipojo>

diff --git a/ipojo/tests/handler/whiteboard/pom.xml b/ipojo/tests/handler/whiteboard/pom.xml
index f366305..423f42c 100644
--- a/ipojo/tests/handler/whiteboard/pom.xml
+++ b/ipojo/tests/handler/whiteboard/pom.xml
@@ -41,21 +41,52 @@
           </instructions>

         </configuration>

       </plugin>

-      <plugin>

-	      <groupId>org.apache.felix</groupId>

-	      <artifactId>maven-ipojo-plugin</artifactId>

-	      <version>1.1.0-SNAPSHOT</version>

-		  <executions>

-          	<execution>

-            	<goals>

-	              <goal>ipojo-bundle</goal>

-               </goals>

-                <configuration>

-   					<ignoreAnnotations>true</ignoreAnnotations>

-            	</configuration>

-          </execution>

-        </executions>

-      </plugin>

+	<plugin>

+		<groupId>org.apache.felix</groupId>

+		<artifactId>maven-ipojo-plugin</artifactId>

+		<version>1.1.0-SNAPSHOT</version>

+		<executions>

+			<execution>

+				<goals>

+					<goal>ipojo-bundle</goal>

+				</goals>

+				<configuration>

+					<ignoreAnnotations>true</ignoreAnnotations>

+					<metadata>

+   					<![CDATA[

+   					<ipojo 

+    					xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"

+						xsi:schemaLocation="org.apache.felix.ipojo http://felix.apache.org/ipojo/schemas/1.1.0-SNAPSHOT/core.xsd 

+	 					org.apache.felix.ipojo.whiteboard http://felix.apache.org/ipojo/schemas/1.1.0-SNAPSHOT/whiteboard-pattern.xsd"

+						xmlns="org.apache.felix.ipojo"

+						xmlns:wbp="org.apache.felix.ipojo.whiteboard">

+						<component classname="org.apache.felix.ipojo.test.FooProvider" name="fooprovider">

+							<provides>

+								<property field="foo" value="foo"/>

+							</provides>

+						</component>

+	

+						<component classname="org.apache.felix.ipojo.test.FooWhiteBoardPattern" name="under-providers">

+								<wbp:wbp 

+									filter="(objectclass=org.apache.felix.ipojo.test.FooService)" 

+									onArrival="onArrival" onDeparture="onDeparture" onModification="onModification"

+								/>

+								<provides/>

+						</component>

+	

+						<component classname="org.apache.felix.ipojo.test.FooWhiteBoardPattern" name="under-properties">

+								<wbp:wbp filter="(foo=foo)" onArrival="onArrival" onDeparture="onDeparture" 

+									onModification="onModification"

+								/>

+								<provides/>

+						</component>

+					</ipojo>

+					]]>

+					</metadata>

+				</configuration>

+			</execution>

+		</executions>

+	</plugin>

     </plugins>

   </build>

 </project>

diff --git a/ipojo/tests/handler/whiteboard/src/main/resources/metadata.xml b/ipojo/tests/handler/whiteboard/src/main/resources/metadata.xml
deleted file mode 100644
index eb08399..0000000
--- a/ipojo/tests/handler/whiteboard/src/main/resources/metadata.xml
+++ /dev/null
@@ -1,22 +0,0 @@
-<ipojo 

-    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"

-	xsi:schemaLocation="org.apache.felix.ipojo http://felix.apache.org/ipojo/schemas/1.1.0-SNAPSHOT/core.xsd 

-	    org.apache.felix.ipojo.whiteboard http://felix.apache.org/ipojo/schemas/1.1.0-SNAPSHOT/whiteboard-pattern.xsd"

-	xmlns="org.apache.felix.ipojo"

-	xmlns:wbp="org.apache.felix.ipojo.whiteboard">

-	<component classname="org.apache.felix.ipojo.test.FooProvider" name="fooprovider">

-		<provides>

-			<property field="foo" value="foo"/>

-		</provides>

-	</component>

-	

-	<component classname="org.apache.felix.ipojo.test.FooWhiteBoardPattern" name="under-providers">

-		<wbp:wbp filter="(objectclass=org.apache.felix.ipojo.test.FooService)" onArrival="onArrival" onDeparture="onDeparture" onModification="onModification"/>

-		<provides/>

-	</component>

-	

-	<component classname="org.apache.felix.ipojo.test.FooWhiteBoardPattern" name="under-properties">

-		<wbp:wbp filter="(foo=foo)" onArrival="onArrival" onDeparture="onDeparture" onModification="onModification"/>

-		<provides/>

-	</component>

-</ipojo>