You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@felix.apache.org by mc...@apache.org on 2008/12/03 13:03:13 UTC

svn commit: r722850 [2/3] - /felix/trunk/bundleplugin/src/main/java/org/osgi/impl/bundle/obr/resource/

Modified: felix/trunk/bundleplugin/src/main/java/org/osgi/impl/bundle/obr/resource/ManifestEntry.java
URL: http://svn.apache.org/viewvc/felix/trunk/bundleplugin/src/main/java/org/osgi/impl/bundle/obr/resource/ManifestEntry.java?rev=722850&r1=722849&r2=722850&view=diff
==============================================================================
--- felix/trunk/bundleplugin/src/main/java/org/osgi/impl/bundle/obr/resource/ManifestEntry.java (original)
+++ felix/trunk/bundleplugin/src/main/java/org/osgi/impl/bundle/obr/resource/ManifestEntry.java Wed Dec  3 04:03:12 2008
@@ -1,111 +1,125 @@
-/*
- * $Id: ManifestEntry.java 44 2007-07-13 20:49:41Z hargrave@us.ibm.com $
- * 
- * Copyright (c) OSGi Alliance (2002, 2006, 2007). All Rights Reserved.
- * 
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- *      http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package org.osgi.impl.bundle.obr.resource;
-
-import java.util.*;
-
-
-public class ManifestEntry implements Comparable {
-	String		name;
-	VersionRange	version;
-	Map			attributes;
-	public Map	directives;
-	public Set	uses;
-
-	public ManifestEntry(String name) {
-		this.name = name;
-	}
-
-	public ManifestEntry(String name, VersionRange version) {
-		this.name = name;
-		this.version = version;
-	}
-
-	public String toString() {
-		if (version == null)
-			return name;
-		return name + " ;version=" + version;
-	}
-
-	public String getName() {
-		return name;
-	}
-
-	public VersionRange getVersion() {
-		if (version != null)
-			return version;
-		return new VersionRange("0");
-	}
-
-	/*
-	 * (non-Javadoc)
-	 * 
-	 * @see java.lang.Comparable#compareTo(java.lang.Object)
-	 */
-	public int compareTo(Object o) {
-		ManifestEntry p = (ManifestEntry) o;
-		return name.compareTo(p.name);
-	}
-
-	/**
-	 * @return
-	 */
-	public Object getPath() {
-		return getName().replace('.', '/');
-	}
-
-	public Map getDirectives() {
-		return directives;
-	}
-
-	public Map getAttributes() {
-		return attributes;
-	}
-
-	/**
-	 * @param parameter
-	 */
-	public void addParameter(Parameter parameter) {
-		switch (parameter.type) {
-			case Parameter.ATTRIBUTE :
-				if (attributes == null)
-					attributes = new HashMap();
-				attributes.put(parameter.key, parameter.value);
-				if (parameter.key.equalsIgnoreCase("version")
-						|| parameter.key
-								.equalsIgnoreCase("specification-version"))
-					this.version = new VersionRange(parameter.value);
-				break;
-
-			case Parameter.DIRECTIVE :
-				if (directives == null)
-					directives = new HashMap();
-				directives.put(parameter.key, parameter.value);
-				break;
-		}
-	}
-
-	public ManifestEntry getAlias(String key) {
-		ManifestEntry me = new ManifestEntry(key);
-		me.attributes = attributes;
-		me.directives = directives;
-		me.version = version;
-		return me;
-	}
-
-}
+/*
+ * $Id: ManifestEntry.java 92 2008-11-06 07:46:37Z peter.kriens@aqute.biz $
+ * 
+ * Copyright (c) OSGi Alliance (2002, 2006, 2007). All Rights Reserved.
+ * 
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.osgi.impl.bundle.obr.resource;
+
+import java.util.*;
+
+
+public class ManifestEntry implements Comparable {
+	String		name;
+	VersionRange	version;
+	Map			attributes;
+	public Map	directives;
+	public Set	uses;
+
+	public ManifestEntry(String name) {
+		this.name = name;
+	}
+
+	public ManifestEntry(String name, VersionRange version) {
+		this.name = name;
+		this.version = version;
+	}
+
+	public String toString() {
+		if (version == null)
+			return name;
+		return name + " ;version=" + version;
+	}
+
+	public String getName() {
+		return name;
+	}
+
+	public VersionRange getVersion() {
+		if (version != null)
+			return version;
+		return new VersionRange("0");
+	}
+
+	/*
+	 * (non-Javadoc)
+	 * 
+	 * @see java.lang.Comparable#compareTo(java.lang.Object)
+	 */
+	public int compareTo(Object o) {
+		ManifestEntry p = (ManifestEntry) o;
+		return name.compareTo(p.name);
+	}
+
+	/**
+	 * @return
+	 */
+	public Object getPath() {
+		return getName().replace('.', '/');
+	}
+
+	public Map getDirectives() {
+		return directives;
+	}
+
+	public Map getAttributes() {
+		return attributes;
+	}
+
+	/**
+	 * @param parameter
+	 */
+	public void addParameter(Parameter parameter) {
+		switch (parameter.type) {
+			case Parameter.ATTRIBUTE :
+				if (attributes == null)
+					attributes = new HashMap();
+				attributes.put(parameter.key, parameter.value);
+				if (parameter.key.equalsIgnoreCase("version")
+						|| parameter.key
+								.equalsIgnoreCase("specification-version"))
+					this.version = new VersionRange(parameter.value);
+				break;
+
+			case Parameter.DIRECTIVE :
+				if (directives == null)
+					directives = new HashMap();
+				directives.put(parameter.key, parameter.value);
+				break;
+		}
+	}
+
+	public ManifestEntry getAlias(String key) {
+		ManifestEntry me = new ManifestEntry(key);
+		me.attributes = attributes;
+		me.directives = directives;
+		me.version = version;
+		return me;
+	}
+
+	public String getDirective(String directive) {
+		if ( directives == null )
+			return null;
+		
+		return (String) directives.get(directive);
+	}
+
+	public String getAttribute(String attribute) {
+		if ( attributes == null )
+			return null;
+		
+		return (String) attributes.get(attribute);
+	}
+
+}

Modified: felix/trunk/bundleplugin/src/main/java/org/osgi/impl/bundle/obr/resource/Parameter.java
URL: http://svn.apache.org/viewvc/felix/trunk/bundleplugin/src/main/java/org/osgi/impl/bundle/obr/resource/Parameter.java?rev=722850&r1=722849&r2=722850&view=diff
==============================================================================
--- felix/trunk/bundleplugin/src/main/java/org/osgi/impl/bundle/obr/resource/Parameter.java (original)
+++ felix/trunk/bundleplugin/src/main/java/org/osgi/impl/bundle/obr/resource/Parameter.java Wed Dec  3 04:03:12 2008
@@ -1,49 +1,49 @@
-/*
- * $Id: Parameter.java 44 2007-07-13 20:49:41Z hargrave@us.ibm.com $
- * 
- * Copyright (c) OSGi Alliance (2002, 2006, 2007). All Rights Reserved.
- * 
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- *      http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package org.osgi.impl.bundle.obr.resource;
-
-class Parameter {
-	final static int	ATTRIBUTE	= 1;
-	final static int	DIRECTIVE	= 2;
-	final static int	SINGLE		= 0;
-
-	int					type;
-	String				key;
-	String				value;
-
-	public String toString() {
-		StringBuffer sb = new StringBuffer();
-		sb.append(key);
-		switch (type) {
-			case ATTRIBUTE :
-				sb.append("=");
-				break;
-			case DIRECTIVE :
-				sb.append(":=");
-				break;
-			case SINGLE :
-				return sb.toString();
-		}
-		sb.append(value);
-		return sb.toString();
-	}
-
-	boolean is(String s, int type) {
-		return this.type == type && key.equalsIgnoreCase(s);
-	}
-}
+/*
+ * $Id: Parameter.java 44 2007-07-13 20:49:41Z hargrave@us.ibm.com $
+ * 
+ * Copyright (c) OSGi Alliance (2002, 2006, 2007). All Rights Reserved.
+ * 
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.osgi.impl.bundle.obr.resource;
+
+class Parameter {
+	final static int	ATTRIBUTE	= 1;
+	final static int	DIRECTIVE	= 2;
+	final static int	SINGLE		= 0;
+
+	int					type;
+	String				key;
+	String				value;
+
+	public String toString() {
+		StringBuffer sb = new StringBuffer();
+		sb.append(key);
+		switch (type) {
+			case ATTRIBUTE :
+				sb.append("=");
+				break;
+			case DIRECTIVE :
+				sb.append(":=");
+				break;
+			case SINGLE :
+				return sb.toString();
+		}
+		sb.append(value);
+		return sb.toString();
+	}
+
+	boolean is(String s, int type) {
+		return this.type == type && key.equalsIgnoreCase(s);
+	}
+}

Modified: felix/trunk/bundleplugin/src/main/java/org/osgi/impl/bundle/obr/resource/RepositoryImpl.java
URL: http://svn.apache.org/viewvc/felix/trunk/bundleplugin/src/main/java/org/osgi/impl/bundle/obr/resource/RepositoryImpl.java?rev=722850&r1=722849&r2=722850&view=diff
==============================================================================
--- felix/trunk/bundleplugin/src/main/java/org/osgi/impl/bundle/obr/resource/RepositoryImpl.java (original)
+++ felix/trunk/bundleplugin/src/main/java/org/osgi/impl/bundle/obr/resource/RepositoryImpl.java Wed Dec  3 04:03:12 2008
@@ -1,375 +1,375 @@
-/*
- * $Id: RepositoryImpl.java 44 2007-07-13 20:49:41Z hargrave@us.ibm.com $
- * 
- * Copyright (c) OSGi Alliance (2002, 2006, 2007). All Rights Reserved.
- * 
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- *      http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package org.osgi.impl.bundle.obr.resource;
-
-import java.io.*;
-import java.net.*;
-import java.util.*;
-import java.util.zip.*;
-
-import org.kxml2.io.KXmlParser;
-import org.osgi.service.obr.*;
-import org.xmlpull.v1.*;
-
-/**
- * Implements the basic repository. A repository holds a set of resources.
- * 
- * 
- * @version $Revision: 44 $
- */
-public class RepositoryImpl implements Repository {
-	transient Set			resources		= new HashSet();
-	URL						url;
-	String					date;
-	Set						visited			= new HashSet();
-	final static Resource[]	EMPTY_RESOURCE	= new Resource[0];
-	String					name			= "Untitled";
-	long					lastModified;
-	Exception				exception;
-	int						ranking=0;
-
-	/**
-	 * Each repository is identified by a single URL.
-	 * 
-	 * A repository can hold referrals to other repositories. These referred
-	 * repositories are included at the point of referall.
-	 * 
-	 * @param url
-	 */
-	public RepositoryImpl(URL url) {
-		this.url = url;
-	}
-
-	/**
-	 * Refresh the repository from the URL.
-	 * 
-	 * @throws Exception
-	 */
-	public boolean refresh() {
-		exception = null;
-		try {
-			resources.clear();
-			parseDocument(url);
-			visited = null;
-			return true;
-		}
-		catch (Exception e) {
-			e.printStackTrace();
-			exception = e;
-		}
-		return false;
-	}
-
-	/**
-	 * Parse the repository.
-	 * 
-	 * @param parser
-	 * @throws Exception
-	 */
-	private void parseRepository(XmlPullParser parser) throws Exception {
-		try {
-			parser.require(XmlPullParser.START_DOCUMENT, null, null);
-			parser.nextTag();
-			if (parser.getName().equals("bundles"))
-				parseOscar(parser);
-			else {
-				parser.require(XmlPullParser.START_TAG, null, "repository");
-				date = parser.getAttributeValue(null, "lastmodified");
-				name = parser.getAttributeValue(null, "name");
-				if (name == null)
-					name = "Untitled";
-
-				while (parser.nextTag() == XmlPullParser.START_TAG) {
-					if (parser.getName().equals("resource")) {
-						ResourceImpl resource = new ResourceImpl(this, parser);
-						resources.add(resource);
-					}
-					else if (parser.getName().equals("referral"))
-						referral(parser);
-					else
-						throw new IllegalArgumentException(
-								"Invalid tag in repository: " + url + " "
-										+ parser.getName());
-				}
-				parser.require(XmlPullParser.END_TAG, null, "repository");
-			}
-		}
-		catch (XmlPullParserException e) {
-			e.printStackTrace();
-			throw new IllegalArgumentException("XML unregognized around: "
-					+ e.getLineNumber() + " " + e.getMessage());
-		}
-	}
-
-	/**
-	 * Parse an old style OBR repository.
-	 * 
-	 * <dtd-version>1.0</dtd-version> <repository> <name>Oscar Bundle
-	 * Repository</name> <url>http://oscar-osgi.sourceforge.net/</url>
-	 * <date>Fri May 07 16:45:07 CEST 2004</date> <extern-repositories> <!--
-	 * Stefano Lenzi (kismet@interfree.it) -->
-	 * <url>http://domoware.isti.cnr.it/osgi-obr/niche-osgi-obr.xml</url>
-	 * <!--Manuel Palencia (santillan@dit.upm.es) --> <!--
-	 * <url>http://jmood.forge.os4os.org/repository.xml</url> --> <!-- Enrique
-	 * Rodriguez (erodriguez@apache.org) -->
-	 * <url>http://update.cainenable.org/repository.xml</url>
-	 * </extern-repositories> </repository> <bundle> <bundle-name>Bundle
-	 * Repository</bundle-name> <bundle-description> A bundle repository
-	 * service for Oscar. </bundle-description> <bundle-updatelocation>
-	 * http://oscar-osgi.sf.net/repo/bundlerepository/bundlerepository.jar
-	 * </bundle-updatelocation> <bundle-sourceurl>
-	 * http://oscar-osgi.sf.net/repo/bundlerepository/bundlerepository-src.jar
-	 * </bundle-sourceurl> <bundle-version>1.1.3</bundle-version>
-	 * <bundle-docurl> http://oscar-osgi.sf.net/repo/bundlerepository/
-	 * </bundle-docurl> <bundle-category>General</bundle-category>
-	 * <import-package package="org.osgi.framework"/> <export-package
-	 * package="org.ungoverned.osgi.service.bundlerepository"
-	 * specification-version="1.1.0"/> </bundle> *
-	 */
-	private void parseOscar(XmlPullParser parser) throws Exception {
-		parser.require(XmlPullParser.START_TAG, null, "bundles");
-		while (true) {
-			int event = parser.next();
-
-			// Error ..
-			if (event == XmlPullParser.TEXT)
-				event = parser.next();
-
-			if (event != XmlPullParser.START_TAG)
-				break;
-
-			ResourceImpl resource = new ResourceImpl(this);
-
-			if (parser.getName().equals("bundle")) {
-				while (parser.nextTag() == XmlPullParser.START_TAG) {
-					String key = parser.getName();
-					if (key.equals("import-package")) {
-						RequirementImpl requirement = new RequirementImpl(
-								"package");
-						
-						requirement.setOptional(false);
-						requirement.setMultiple(false);
-						
-						String p = parser.getAttributeValue(null, "package");
-						StringBuffer sb = new StringBuffer();
-						sb.append("(&(package=");
-						sb.append(p);
-						sb.append(")");
-						String version = parser.getAttributeValue(null,
-								"specification-version");
-						VersionRange v = new VersionRange("0");
-						if (version != null) {
-							sb.append("(version=");
-							sb.append(v= new VersionRange(version));
-							sb.append(")");
-						}
-						sb.append(")");
-						requirement.setFilter(sb.toString());
-						requirement.setComment("Import-Package: " + p + ";" + v );
-						resource.addRequirement(requirement);
-						
-						parser.nextTag();
-					}
-					else if (key.equals("export-package")) {
-						CapabilityImpl capability = new CapabilityImpl(
-								"package");
-						capability.addProperty("package", parser
-								.getAttributeValue(null, "package"));
-						String version = parser.getAttributeValue(null,
-								"specification-version");
-						if (version != null) {
-							capability.addProperty("version", new VersionRange(
-									version));
-						}
-						resource.addCapability(capability);
-						parser.nextTag();
-					}
-					else {
-						String value = parser.nextText().trim();
-						if (key.equals("bundle-sourceurl"))
-							resource.setSource(new URL(value));
-						else if (key.equals("bundle-docurl"))
-							resource.setDocumentation(new URL(value));
-						else if (key.equals("bundle-updatelocation"))
-							resource.setURL(new URL(value));
-						else if (key.equals("bundle-description"))
-							resource.setDescription(value);
-						else if (key.equals("bundle-category"))
-							resource.addCategory(value);
-						else if (key.equals("bundle-name")) {
-							resource.setName(value);
-							resource.setPresentationName(value);
-						}
-						else if (key.equals("bundle-version"))
-							resource.setVersion(new VersionRange(value));
-						else {
-							resource.put(key, value);
-						}
-					}
-				}
-				resources.add(resource);
-				parser.require(XmlPullParser.END_TAG, null, "bundle");
-			}
-			else if (parser.getName().equals("repository")) {
-				parser.require(XmlPullParser.START_TAG, null, "repository");
-				while (parser.nextTag() == XmlPullParser.START_TAG) {
-					String tag = parser.getName();
-					if (tag.equals("name")) {
-						String name = parser.nextText();
-						if (this.name == null)
-							this.name = name.trim();
-					}
-					else if (tag.equals("url"))
-						parser.nextText().trim();
-					else if (tag.equals("date"))
-						parser.nextText().trim();
-					else if (tag.equals("extern-repositories")) {
-						parser.require(XmlPullParser.START_TAG, null,
-								"extern-repositories");
-						while (parser.nextTag() == XmlPullParser.START_TAG) {
-							if (parser.getName().equals("url"))
-								parseDocument(new URL(parser.nextText().trim()));
-							else
-								throw new IllegalArgumentException(
-										"Invalid tag in repository while parsing extern repositories: "
-												+ url + " " + parser.getName());
-						}
-						parser.require(XmlPullParser.END_TAG, null,
-								"extern-repositories");
-					}
-					else
-						throw new IllegalArgumentException(
-								"Invalid tag in repository: " + url + " "
-										+ parser.getName());
-				}
-				parser.require(XmlPullParser.END_TAG, null, "repository");
-			}
-			else if (parser.getName().equals("dtd-version")) {
-				parser.nextText();
-			}
-			else
-				throw new IllegalArgumentException(
-						"Invalid tag in repository: " + url + " "
-								+ parser.getName());
-		}
-		parser.require(XmlPullParser.END_TAG, null, "bundles");
-	}
-
-	/**
-	 * We have a referral to another repository. Just create another parser and
-	 * read it inline.
-	 * 
-	 * @param parser
-	 */
-	void referral(XmlPullParser parser) {
-		// TODO handle depth!
-		try {
-			parser.require(XmlPullParser.START_TAG, null, "referral");
-			// String depth = parser.getAttributeValue(null, "depth");
-			String path = parser.getAttributeValue(null, "url");
-			URL url = new URL(this.url, path);
-			parseDocument(url);
-			parser.next();
-			parser.require(XmlPullParser.END_TAG, null, "referral");
-		}
-		catch (Exception e) {
-			e.printStackTrace();
-		}
-	}
-
-	/**
-	 * Parse a repository document.
-	 * 
-	 * @param url
-	 * @throws IOException
-	 * @throws XmlPullParserException
-	 * @throws Exception
-	 */
-	void parseDocument(URL url) throws IOException, XmlPullParserException,
-			Exception {
-		if (!visited.contains(url)) {
-			visited.add(url);
-			try {
-				System.out.println("Visiting: " + url);
-				InputStream in = null;
-				
-				if ( url.getPath().endsWith(".zip")) {
-					ZipInputStream zin = new ZipInputStream( url.openStream() );
-					ZipEntry entry = zin.getNextEntry();
-					while ( entry != null ) {
-						if ( entry.getName().equals("repository.xml")) {
-							in = zin;
-							break;
-						}
-						entry = zin.getNextEntry();
-					}
-				} else {
-					in = url.openStream();
-				}
-				Reader reader = new InputStreamReader(in);
-				XmlPullParser parser = new KXmlParser();
-				parser.setInput(reader);
-				parseRepository(parser);
-			} catch( MalformedURLException e ) {
-				System.out.println("Cannot create connection to url");
-			}
-		}
-	}
-
-	public URL getURL() {
-		return url;
-	}
-
-	/**
-	 * @return
-	 */
-	public Collection getResourceList() {
-		return resources;
-	}
-
-	public Resource[] getResources() {
-		return (Resource[]) getResourceList().toArray(EMPTY_RESOURCE);
-	}
-
-	public String getName() {
-		return name;
-	}
-
-	public Resource getResource(String id) {
-		for (Iterator i = getResourceList().iterator(); i.hasNext();) {
-			ResourceImpl resource = (ResourceImpl) i.next();
-			if (resource.getId().equals(id))
-				return resource;
-		}
-		return null;
-	}
-
-	public long getLastModified() {
-		return lastModified;
-	}
-
-	public int getRanking() {
-		return ranking;
-	}
-
-	public void setRanking(int ranking) {
-		this.ranking = ranking;
-	}
-
-}
+/*
+ * $Id: RepositoryImpl.java 44 2007-07-13 20:49:41Z hargrave@us.ibm.com $
+ * 
+ * Copyright (c) OSGi Alliance (2002, 2006, 2007). All Rights Reserved.
+ * 
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.osgi.impl.bundle.obr.resource;
+
+import java.io.*;
+import java.net.*;
+import java.util.*;
+import java.util.zip.*;
+
+import org.kxml2.io.KXmlParser;
+import org.osgi.service.obr.*;
+import org.xmlpull.v1.*;
+
+/**
+ * Implements the basic repository. A repository holds a set of resources.
+ * 
+ * 
+ * @version $Revision: 44 $
+ */
+public class RepositoryImpl implements Repository {
+	transient Set			resources		= new HashSet();
+	URL						url;
+	String					date;
+	Set						visited			= new HashSet();
+	final static Resource[]	EMPTY_RESOURCE	= new Resource[0];
+	String					name			= "Untitled";
+	long					lastModified;
+	Exception				exception;
+	int						ranking=0;
+
+	/**
+	 * Each repository is identified by a single URL.
+	 * 
+	 * A repository can hold referrals to other repositories. These referred
+	 * repositories are included at the point of referall.
+	 * 
+	 * @param url
+	 */
+	public RepositoryImpl(URL url) {
+		this.url = url;
+	}
+
+	/**
+	 * Refresh the repository from the URL.
+	 * 
+	 * @throws Exception
+	 */
+	public boolean refresh() {
+		exception = null;
+		try {
+			resources.clear();
+			parseDocument(url);
+			visited = null;
+			return true;
+		}
+		catch (Exception e) {
+			e.printStackTrace();
+			exception = e;
+		}
+		return false;
+	}
+
+	/**
+	 * Parse the repository.
+	 * 
+	 * @param parser
+	 * @throws Exception
+	 */
+	private void parseRepository(XmlPullParser parser) throws Exception {
+		try {
+			parser.require(XmlPullParser.START_DOCUMENT, null, null);
+			parser.nextTag();
+			if (parser.getName().equals("bundles"))
+				parseOscar(parser);
+			else {
+				parser.require(XmlPullParser.START_TAG, null, "repository");
+				date = parser.getAttributeValue(null, "lastmodified");
+				name = parser.getAttributeValue(null, "name");
+				if (name == null)
+					name = "Untitled";
+
+				while (parser.nextTag() == XmlPullParser.START_TAG) {
+					if (parser.getName().equals("resource")) {
+						ResourceImpl resource = new ResourceImpl(this, parser);
+						resources.add(resource);
+					}
+					else if (parser.getName().equals("referral"))
+						referral(parser);
+					else
+						throw new IllegalArgumentException(
+								"Invalid tag in repository: " + url + " "
+										+ parser.getName());
+				}
+				parser.require(XmlPullParser.END_TAG, null, "repository");
+			}
+		}
+		catch (XmlPullParserException e) {
+			e.printStackTrace();
+			throw new IllegalArgumentException("XML unregognized around: "
+					+ e.getLineNumber() + " " + e.getMessage());
+		}
+	}
+
+	/**
+	 * Parse an old style OBR repository.
+	 * 
+	 * <dtd-version>1.0</dtd-version> <repository> <name>Oscar Bundle
+	 * Repository</name> <url>http://oscar-osgi.sourceforge.net/</url>
+	 * <date>Fri May 07 16:45:07 CEST 2004</date> <extern-repositories> <!--
+	 * Stefano Lenzi (kismet@interfree.it) -->
+	 * <url>http://domoware.isti.cnr.it/osgi-obr/niche-osgi-obr.xml</url>
+	 * <!--Manuel Palencia (santillan@dit.upm.es) --> <!--
+	 * <url>http://jmood.forge.os4os.org/repository.xml</url> --> <!-- Enrique
+	 * Rodriguez (erodriguez@apache.org) -->
+	 * <url>http://update.cainenable.org/repository.xml</url>
+	 * </extern-repositories> </repository> <bundle> <bundle-name>Bundle
+	 * Repository</bundle-name> <bundle-description> A bundle repository
+	 * service for Oscar. </bundle-description> <bundle-updatelocation>
+	 * http://oscar-osgi.sf.net/repo/bundlerepository/bundlerepository.jar
+	 * </bundle-updatelocation> <bundle-sourceurl>
+	 * http://oscar-osgi.sf.net/repo/bundlerepository/bundlerepository-src.jar
+	 * </bundle-sourceurl> <bundle-version>1.1.3</bundle-version>
+	 * <bundle-docurl> http://oscar-osgi.sf.net/repo/bundlerepository/
+	 * </bundle-docurl> <bundle-category>General</bundle-category>
+	 * <import-package package="org.osgi.framework"/> <export-package
+	 * package="org.ungoverned.osgi.service.bundlerepository"
+	 * specification-version="1.1.0"/> </bundle> *
+	 */
+	private void parseOscar(XmlPullParser parser) throws Exception {
+		parser.require(XmlPullParser.START_TAG, null, "bundles");
+		while (true) {
+			int event = parser.next();
+
+			// Error ..
+			if (event == XmlPullParser.TEXT)
+				event = parser.next();
+
+			if (event != XmlPullParser.START_TAG)
+				break;
+
+			ResourceImpl resource = new ResourceImpl(this);
+
+			if (parser.getName().equals("bundle")) {
+				while (parser.nextTag() == XmlPullParser.START_TAG) {
+					String key = parser.getName();
+					if (key.equals("import-package")) {
+						RequirementImpl requirement = new RequirementImpl(
+								"package");
+						
+						requirement.setOptional(false);
+						requirement.setMultiple(false);
+						
+						String p = parser.getAttributeValue(null, "package");
+						StringBuffer sb = new StringBuffer();
+						sb.append("(&(package=");
+						sb.append(p);
+						sb.append(")");
+						String version = parser.getAttributeValue(null,
+								"specification-version");
+						VersionRange v = new VersionRange("0");
+						if (version != null) {
+							sb.append("(version=");
+							sb.append(v= new VersionRange(version));
+							sb.append(")");
+						}
+						sb.append(")");
+						requirement.setFilter(sb.toString());
+						requirement.setComment("Import-Package: " + p + ";" + v );
+						resource.addRequirement(requirement);
+						
+						parser.nextTag();
+					}
+					else if (key.equals("export-package")) {
+						CapabilityImpl capability = new CapabilityImpl(
+								"package");
+						capability.addProperty("package", parser
+								.getAttributeValue(null, "package"));
+						String version = parser.getAttributeValue(null,
+								"specification-version");
+						if (version != null) {
+							capability.addProperty("version", new VersionRange(
+									version));
+						}
+						resource.addCapability(capability);
+						parser.nextTag();
+					}
+					else {
+						String value = parser.nextText().trim();
+						if (key.equals("bundle-sourceurl"))
+							resource.setSource(new URL(value));
+						else if (key.equals("bundle-docurl"))
+							resource.setDocumentation(new URL(value));
+						else if (key.equals("bundle-updatelocation"))
+							resource.setURL(new URL(value));
+						else if (key.equals("bundle-description"))
+							resource.setDescription(value);
+						else if (key.equals("bundle-category"))
+							resource.addCategory(value);
+						else if (key.equals("bundle-name")) {
+							resource.setName(value);
+							resource.setPresentationName(value);
+						}
+						else if (key.equals("bundle-version"))
+							resource.setVersion(new VersionRange(value));
+						else {
+							resource.put(key, value);
+						}
+					}
+				}
+				resources.add(resource);
+				parser.require(XmlPullParser.END_TAG, null, "bundle");
+			}
+			else if (parser.getName().equals("repository")) {
+				parser.require(XmlPullParser.START_TAG, null, "repository");
+				while (parser.nextTag() == XmlPullParser.START_TAG) {
+					String tag = parser.getName();
+					if (tag.equals("name")) {
+						String name = parser.nextText();
+						if (this.name == null)
+							this.name = name.trim();
+					}
+					else if (tag.equals("url"))
+						parser.nextText().trim();
+					else if (tag.equals("date"))
+						parser.nextText().trim();
+					else if (tag.equals("extern-repositories")) {
+						parser.require(XmlPullParser.START_TAG, null,
+								"extern-repositories");
+						while (parser.nextTag() == XmlPullParser.START_TAG) {
+							if (parser.getName().equals("url"))
+								parseDocument(new URL(parser.nextText().trim()));
+							else
+								throw new IllegalArgumentException(
+										"Invalid tag in repository while parsing extern repositories: "
+												+ url + " " + parser.getName());
+						}
+						parser.require(XmlPullParser.END_TAG, null,
+								"extern-repositories");
+					}
+					else
+						throw new IllegalArgumentException(
+								"Invalid tag in repository: " + url + " "
+										+ parser.getName());
+				}
+				parser.require(XmlPullParser.END_TAG, null, "repository");
+			}
+			else if (parser.getName().equals("dtd-version")) {
+				parser.nextText();
+			}
+			else
+				throw new IllegalArgumentException(
+						"Invalid tag in repository: " + url + " "
+								+ parser.getName());
+		}
+		parser.require(XmlPullParser.END_TAG, null, "bundles");
+	}
+
+	/**
+	 * We have a referral to another repository. Just create another parser and
+	 * read it inline.
+	 * 
+	 * @param parser
+	 */
+	void referral(XmlPullParser parser) {
+		// TODO handle depth!
+		try {
+			parser.require(XmlPullParser.START_TAG, null, "referral");
+			// String depth = parser.getAttributeValue(null, "depth");
+			String path = parser.getAttributeValue(null, "url");
+			URL url = new URL(this.url, path);
+			parseDocument(url);
+			parser.next();
+			parser.require(XmlPullParser.END_TAG, null, "referral");
+		}
+		catch (Exception e) {
+			e.printStackTrace();
+		}
+	}
+
+	/**
+	 * Parse a repository document.
+	 * 
+	 * @param url
+	 * @throws IOException
+	 * @throws XmlPullParserException
+	 * @throws Exception
+	 */
+	void parseDocument(URL url) throws IOException, XmlPullParserException,
+			Exception {
+		if (!visited.contains(url)) {
+			visited.add(url);
+			try {
+				System.out.println("Visiting: " + url);
+				InputStream in = null;
+				
+				if ( url.getPath().endsWith(".zip")) {
+					ZipInputStream zin = new ZipInputStream( url.openStream() );
+					ZipEntry entry = zin.getNextEntry();
+					while ( entry != null ) {
+						if ( entry.getName().equals("repository.xml")) {
+							in = zin;
+							break;
+						}
+						entry = zin.getNextEntry();
+					}
+				} else {
+					in = url.openStream();
+				}
+				Reader reader = new InputStreamReader(in);
+				XmlPullParser parser = new KXmlParser();
+				parser.setInput(reader);
+				parseRepository(parser);
+			} catch( MalformedURLException e ) {
+				System.out.println("Cannot create connection to url");
+			}
+		}
+	}
+
+	public URL getURL() {
+		return url;
+	}
+
+	/**
+	 * @return
+	 */
+	public Collection getResourceList() {
+		return resources;
+	}
+
+	public Resource[] getResources() {
+		return (Resource[]) getResourceList().toArray(EMPTY_RESOURCE);
+	}
+
+	public String getName() {
+		return name;
+	}
+
+	public Resource getResource(String id) {
+		for (Iterator i = getResourceList().iterator(); i.hasNext();) {
+			ResourceImpl resource = (ResourceImpl) i.next();
+			if (resource.getId().equals(id))
+				return resource;
+		}
+		return null;
+	}
+
+	public long getLastModified() {
+		return lastModified;
+	}
+
+	public int getRanking() {
+		return ranking;
+	}
+
+	public void setRanking(int ranking) {
+		this.ranking = ranking;
+	}
+
+}

Modified: felix/trunk/bundleplugin/src/main/java/org/osgi/impl/bundle/obr/resource/RequirementImpl.java
URL: http://svn.apache.org/viewvc/felix/trunk/bundleplugin/src/main/java/org/osgi/impl/bundle/obr/resource/RequirementImpl.java?rev=722850&r1=722849&r2=722850&view=diff
==============================================================================
--- felix/trunk/bundleplugin/src/main/java/org/osgi/impl/bundle/obr/resource/RequirementImpl.java (original)
+++ felix/trunk/bundleplugin/src/main/java/org/osgi/impl/bundle/obr/resource/RequirementImpl.java Wed Dec  3 04:03:12 2008
@@ -1,177 +1,177 @@
-/*
- * $Id: RequirementImpl.java 44 2007-07-13 20:49:41Z hargrave@us.ibm.com $
- * 
- * Copyright (c) OSGi Alliance (2002, 2006, 2007). All Rights Reserved.
- * 
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- *      http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package org.osgi.impl.bundle.obr.resource;
-
-import org.osgi.service.obr.*;
-import org.xmlpull.v1.XmlPullParser;
-
-
-
-/**
- * Implements the Requirement interface.
- * 
- * 
- * @version $Revision: 44 $
- */
-public class RequirementImpl implements Requirement {
-	int		id;
-	String	name;
-	String	filter="()";
-	FilterImpl	_filter;
-	String	comment;
-	boolean optional;
-	boolean multiple;
-	boolean extend;
-	
-	/**
-	 * Create a requirement with the given name.
-	 * 
-	 * @param name
-	 */
-	public RequirementImpl(String name) {
-		this.name = name;
-	}
-
-
-	/**
-	 * Parse the requirement from the pull parser.
-	 * 
-	 * @param parser
-	 * @throws Exception
-	 */
-	public RequirementImpl(XmlPullParser parser) throws Exception {
-		parser.require(XmlPullParser.START_TAG, null, null );
-		name = parser.getAttributeValue(null, "name");
-		filter = parser.getAttributeValue(null, "filter");
-		
-		String opt = parser.getAttributeValue(null,"optional");
-		String mul = parser.getAttributeValue(null,"multiple");
-		String ext = parser.getAttributeValue(null,"extend");
-		optional = "true".equalsIgnoreCase(opt);
-		multiple = "true".equalsIgnoreCase(mul);
-		extend = "true".equalsIgnoreCase(ext);
-		
-		
-		StringBuffer sb = new StringBuffer();
-		while ( parser.next() == XmlPullParser.TEXT ) {
-			sb.append( parser.getText() );
-		}
-		if ( sb.length() > 0 )
-			setComment(sb.toString().trim());
-			
-		parser.require(XmlPullParser.END_TAG, null, null );
-	}
-
-	public void setFilter(String filter) {
-		this.filter = filter;
-		_filter= null;
-	}
-
-	public String getFilter() {
-		return filter;
-	}
-
-	public Tag toXML(String name) {
-		Tag tag = toXML(this);
-		tag.rename(name);
-		return tag;
-	}
-
-
-	public String getName() {
-		return name;
-	}
-
-	public boolean isSatisfied(Capability capability) {
-		if (_filter == null)
-			_filter = new FilterImpl(filter);
-
-		boolean result = _filter.match(capability.getProperties());
-		return result;
-	}
-
-	public String toString() {
-		return name + " " + filter;
-	}
-
-
-	public String getComment() {
-		return comment;
-	}
-
-
-	public void setComment(String comment) {
-		this.comment=comment;
-	}
-
-
-	public static Tag toXML(Requirement requirement) {
-		Tag req = new Tag("require");
-		req.addAttribute("name", requirement.getName());
-		req.addAttribute("filter", requirement.getFilter());
-		
-		req.addAttribute("optional", requirement.isOptional()+"");
-		req.addAttribute("multiple", requirement.isMultiple()+"");
-		req.addAttribute("extend", requirement.isExtend()+"");
-		
-		if ( requirement.getComment() != null )
-			req.addContent(requirement.getComment());
-		
-		return req;
-	}
-
-
-	public boolean isMultiple() {
-		return multiple;
-	}
-
-
-	public boolean isOptional() {
-		return optional;
-	}
-
-
-	public void setOptional(boolean b) {
-		optional = b;
-	}
-
-	public void setMultiple(boolean b) {
-		multiple = b;
-	}
-
-
-	public boolean equals(Object o) {
-		if ( ! (o instanceof Requirement) )
-			return false;
-		
-		Requirement r2 = (Requirement)o;
-		return filter.equals(r2.getFilter()) && name.equals(r2.getName()); 
-	}
-	
-	public int hashCode() {
-		return filter.hashCode() ^ name.hashCode();
-	}
-	
-	public boolean isExtend() {
-		return extend;
-	}
-	
-	public void setExtend(boolean extend) {
-		this.extend = extend;
-	}
-}
+/*
+ * $Id: RequirementImpl.java 44 2007-07-13 20:49:41Z hargrave@us.ibm.com $
+ * 
+ * Copyright (c) OSGi Alliance (2002, 2006, 2007). All Rights Reserved.
+ * 
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.osgi.impl.bundle.obr.resource;
+
+import org.osgi.service.obr.*;
+import org.xmlpull.v1.XmlPullParser;
+
+
+
+/**
+ * Implements the Requirement interface.
+ * 
+ * 
+ * @version $Revision: 44 $
+ */
+public class RequirementImpl implements Requirement {
+	int		id;
+	String	name;
+	String	filter="()";
+	FilterImpl	_filter;
+	String	comment;
+	boolean optional;
+	boolean multiple;
+	boolean extend;
+	
+	/**
+	 * Create a requirement with the given name.
+	 * 
+	 * @param name
+	 */
+	public RequirementImpl(String name) {
+		this.name = name;
+	}
+
+
+	/**
+	 * Parse the requirement from the pull parser.
+	 * 
+	 * @param parser
+	 * @throws Exception
+	 */
+	public RequirementImpl(XmlPullParser parser) throws Exception {
+		parser.require(XmlPullParser.START_TAG, null, null );
+		name = parser.getAttributeValue(null, "name");
+		filter = parser.getAttributeValue(null, "filter");
+		
+		String opt = parser.getAttributeValue(null,"optional");
+		String mul = parser.getAttributeValue(null,"multiple");
+		String ext = parser.getAttributeValue(null,"extend");
+		optional = "true".equalsIgnoreCase(opt);
+		multiple = "true".equalsIgnoreCase(mul);
+		extend = "true".equalsIgnoreCase(ext);
+		
+		
+		StringBuffer sb = new StringBuffer();
+		while ( parser.next() == XmlPullParser.TEXT ) {
+			sb.append( parser.getText() );
+		}
+		if ( sb.length() > 0 )
+			setComment(sb.toString().trim());
+			
+		parser.require(XmlPullParser.END_TAG, null, null );
+	}
+
+	public void setFilter(String filter) {
+		this.filter = filter;
+		_filter= null;
+	}
+
+	public String getFilter() {
+		return filter;
+	}
+
+	public Tag toXML(String name) {
+		Tag tag = toXML(this);
+		tag.rename(name);
+		return tag;
+	}
+
+
+	public String getName() {
+		return name;
+	}
+
+	public boolean isSatisfied(Capability capability) {
+		if (_filter == null)
+			_filter = new FilterImpl(filter);
+
+		boolean result = _filter.match(capability.getProperties());
+		return result;
+	}
+
+	public String toString() {
+		return name + " " + filter;
+	}
+
+
+	public String getComment() {
+		return comment;
+	}
+
+
+	public void setComment(String comment) {
+		this.comment=comment;
+	}
+
+
+	public static Tag toXML(Requirement requirement) {
+		Tag req = new Tag("require");
+		req.addAttribute("name", requirement.getName());
+		req.addAttribute("filter", requirement.getFilter());
+		
+		req.addAttribute("optional", requirement.isOptional()+"");
+		req.addAttribute("multiple", requirement.isMultiple()+"");
+		req.addAttribute("extend", requirement.isExtend()+"");
+		
+		if ( requirement.getComment() != null )
+			req.addContent(requirement.getComment());
+		
+		return req;
+	}
+
+
+	public boolean isMultiple() {
+		return multiple;
+	}
+
+
+	public boolean isOptional() {
+		return optional;
+	}
+
+
+	public void setOptional(boolean b) {
+		optional = b;
+	}
+
+	public void setMultiple(boolean b) {
+		multiple = b;
+	}
+
+
+	public boolean equals(Object o) {
+		if ( ! (o instanceof Requirement) )
+			return false;
+		
+		Requirement r2 = (Requirement)o;
+		return filter.equals(r2.getFilter()) && name.equals(r2.getName()); 
+	}
+	
+	public int hashCode() {
+		return filter.hashCode() ^ name.hashCode();
+	}
+	
+	public boolean isExtend() {
+		return extend;
+	}
+	
+	public void setExtend(boolean extend) {
+		this.extend = extend;
+	}
+}

Modified: felix/trunk/bundleplugin/src/main/java/org/osgi/impl/bundle/obr/resource/ResourceImpl.java
URL: http://svn.apache.org/viewvc/felix/trunk/bundleplugin/src/main/java/org/osgi/impl/bundle/obr/resource/ResourceImpl.java?rev=722850&r1=722849&r2=722850&view=diff
==============================================================================
--- felix/trunk/bundleplugin/src/main/java/org/osgi/impl/bundle/obr/resource/ResourceImpl.java (original)
+++ felix/trunk/bundleplugin/src/main/java/org/osgi/impl/bundle/obr/resource/ResourceImpl.java Wed Dec  3 04:03:12 2008
@@ -1,369 +1,369 @@
-/*
- * $Id: ResourceImpl.java 44 2007-07-13 20:49:41Z hargrave@us.ibm.com $
- * 
- * Copyright (c) OSGi Alliance (2002, 2006, 2007). All Rights Reserved.
- * 
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- *      http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package org.osgi.impl.bundle.obr.resource;
-
-import java.io.File;
-import java.net.URL;
-import java.util.*;
-
-import org.osgi.framework.Version;
-import org.osgi.service.obr.*;
-import org.xmlpull.v1.XmlPullParser;
-
-public class ResourceImpl implements Resource {
-	List			capabilities	= new ArrayList();
-	List			requirements	= new ArrayList();
-	URL				url;
-	String			symbolicName;
-	VersionRange		version;
-	List			categories		= new ArrayList();
-	long			size			= -1;
-	String			id;
-	static int		ID				= 1;
-	Map				map				= new HashMap();
-	RepositoryImpl	repository;
-	String			presentationName;
-	File			file;
-
-
-	public ResourceImpl(RepositoryImpl repository, String name,
-			VersionRange version) {
-		this.version = version;
-		if ( version == null)
-			this.version = new VersionRange("0");
-		this.symbolicName = name;
-		this.repository = repository;
-	}
-
-	public ResourceImpl(RepositoryImpl repository, XmlPullParser parser)
-			throws Exception {
-		this.repository = repository;
-		parser.require(XmlPullParser.START_TAG, null, "resource");
-		symbolicName = parser.getAttributeValue(null, "symbolicname");
-		if (symbolicName == null)
-			System.err.println("Hey, no symb name! "
-					+ parser.getAttributeValue(null, "uri"));
-
-		map.put(SYMBOLIC_NAME, symbolicName);
-		presentationName = parser.getAttributeValue(null, PRESENTATION_NAME);
-		if (presentationName != null)
-			map.put(PRESENTATION_NAME, presentationName);
-		String v = parser.getAttributeValue(null, "version");
-		if (v == null)
-			setVersion(new VersionRange("0"));
-		else
-			setVersion(new VersionRange(v));
-
-		setURL(toURL(parser.getAttributeValue(null, "uri")));
-
-		while (parser.nextTag() == XmlPullParser.START_TAG) {
-			if (parser.getName().equals("category")) {
-				categories.add(parser.getAttributeValue(null, "id").trim());
-			}
-			else if (parser.getName().equals("require"))
-				addRequirement(new RequirementImpl(parser));
-			else if (parser.getName().equals("capability"))
-				addCapability(new CapabilityImpl(parser));
-			else {
-				String text = parser.nextText();
-				if (text != null)
-					map.put(parser.getName(), text.trim());
-			}
-			parser.next();
-		}
-		parser.require(XmlPullParser.END_TAG, null, "resource");
-	}
-
-	public ResourceImpl(RepositoryImpl impl) {
-		this.repository = impl;
-	}
-
-	private URL toURL(String attributeValue) throws Exception {
-		if (attributeValue == null)
-			return null;
-
-		return new URL(repository.getURL(), attributeValue);
-	}
-
-	public void addCategory(String category) {
-		categories.add(category);
-	}
-
-	public void addCapability(CapabilityImpl capability) {
-		if (capability != null)
-			capabilities.add(capability);
-	}
-
-	public void addRequirement(RequirementImpl requirement) {
-		if (requirement != null)
-			requirements.add(requirement);
-	}
-
-	public void setLicense(URL license) {
-		if (license != null)
-			map.put(LICENSE_URL, license);
-	}
-
-	public String getDescription() {
-		return (String) map.get(DESCRIPTION);
-	}
-
-	public void setDescription(String description) {
-		if (description != null)
-			map.put(DESCRIPTION, description);
-	}
-
-	public Capability[] getCapabilities() {
-		return (Capability[]) capabilities.toArray(new Capability[capabilities
-				.size()]);
-	}
-
-	public URL getLicense() {
-		return (URL) map.get(LICENSE_URL);
-	}
-
-	public String getSymbolicName() {
-		return symbolicName;
-	}
-
-	public Requirement[] getRequirements() {
-		return (Requirement[]) requirements
-				.toArray(new Requirement[requirements.size()]);
-	}
-
-	public Tag toXML() {
-		return toXML(this );
-	}
-
-	public static Tag toXML(Resource resource) {
-		return toXML(resource,true);
-	}
-
-	public static Tag toXML(Resource resource, boolean relative ) {
-		Tag meta = new Tag("resource");
-		URL url = resource.getURL();
-		String urlString = url.toExternalForm();
-		
-		if ( relative )
-			urlString = makeRelative(resource.getRepository().getURL(), url);
-		
-		meta.addAttribute("uri", urlString );
-		meta.addAttribute(SYMBOLIC_NAME, resource.getSymbolicName());
-		if (resource.getPresentationName() != null)
-			meta
-					.addAttribute(PRESENTATION_NAME, resource
-							.getPresentationName());
-		meta.addAttribute(VERSION, resource.getVersion().toString());
-		meta.addAttribute("id", resource.getId());
-		Map map = new TreeMap(resource.getProperties());
-		for (int i = 0; i < Resource.KEYS.length; i++) {
-			String key = KEYS[i];
-			if (!(key.equals(URL) || key.equals(SYMBOLIC_NAME) || key
-					.equals(VERSION) || key.equals(PRESENTATION_NAME))) {
-				Object value = map.get(KEYS[i]);
-				if (value != null) {
-					if (value instanceof URL)
-						value = makeRelative(resource.getRepository().getURL(),(URL) value);
-					meta.addContent(new Tag(key, value.toString()));
-				}
-			}
-		}
-
-		String[] categories = resource.getCategories();
-		for (int i = 0; i < categories.length; i++) {
-			String category = categories[i];
-			meta.addContent(new Tag("category", new String[] {"id",
-					category.toLowerCase()}));
-		}
-
-		Capability[] capabilities = resource.getCapabilities();
-		for (int i = 0; i < capabilities.length; i++) {
-			meta.addContent(CapabilityImpl.toXML(capabilities[i]));
-		}
-
-		Requirement[] requirements = resource.getRequirements();
-		for (int i = 0; i < requirements.length; i++) {
-			meta.addContent(RequirementImpl.toXML(requirements[i]));
-		}
-		return meta;
-	}
-
-	public URL getURL() {
-		return url;
-	}
-
-	static String makeRelative(URL repository, URL url) {
-		try {
-			if (repository != null) {
-				String a = url.toExternalForm();
-				String b = repository.toExternalForm();
-				int index = b.lastIndexOf('/');
-				if ( index > 0 )
-					b = b.substring(0,index+1);
-				if (a.startsWith(b))
-					return a.substring(b.length());
-			}
-		}
-		catch (Exception e) {
-			// Ignore
-		}
-		return url.toExternalForm();
-	}
-
-	public void setURL(URL url) {
-		this.url = url;
-		if (url != null)
-			map.put(URL, url);
-	}
-
-	public String getCopyright() {
-		return (String) map.get(COPYRIGHT);
-	}
-
-	public Version getVersion() {
-		if (version == null)
-			version = new VersionRange("0");
-		return version.low;
-	}
-
-	void setVersion(VersionRange version) {
-		if (version == null)
-			this.version = new VersionRange("0");
-		else
-			this.version = version;
-	}
-
-	public void setCopyright(String copyright) {
-		if (copyright != null)
-			map.put(COPYRIGHT, copyright);
-	}
-
-	public URL getDocumentation() {
-		return (URL) map.get(DOCUMENTATION_URL);
-	}
-
-	public void setDocumentation(URL documentation) {
-		if (documentation != null)
-			map.put(DOCUMENTATION_URL, documentation);
-	}
-
-	public URL getSource() {
-		return (URL) map.get(SOURCE_URL);
-	}
-
-	public void setSource(URL source) {
-		if (source != null)
-			map.put(SOURCE_URL, source);
-	}
-
-	public boolean satisfies(RequirementImpl requirement) {
-		for (Iterator i = capabilities.iterator(); i.hasNext();) {
-			CapabilityImpl capability = (CapabilityImpl) i.next();
-			if (requirement.isSatisfied(capability))
-				return true;
-		}
-		return false;
-	}
-
-	public String toString() {
-		return symbolicName + "-" + version;
-	}
-
-	public long getSize() {
-		return size;
-	}
-
-	public void setSize(long size) {
-		this.size = size;
-		map.put(SIZE, new Long(size));
-	}
-
-	public Collection getRequirementList() {
-		return requirements;
-	}
-
-	public Collection getCapabilityList() {
-		return capabilities;
-	}
-
-	public int hashCode() {
-		return symbolicName.hashCode() ^ version.hashCode();
-	}
-
-	public boolean equals(Object o) {
-		try {
-			ResourceImpl other = (ResourceImpl) o;
-			return symbolicName.equals(other.symbolicName)
-					&& version.equals(other.version);
-		}
-		catch (ClassCastException e) {
-			return false;
-		}
-	}
-
-	public String[] getCategories() {
-		return (String[]) categories.toArray(new String[categories.size()]);
-	}
-
-	public Map getProperties() {
-		return Collections.unmodifiableMap(map);
-	}
-
-	public synchronized String getId() {
-		if ( id == null )
-			id = symbolicName + "/" + version;
-		return id;
-	}
-
-	public Repository getRepository() {
-		return repository;
-	}
-
-	void setName(String value) {
-		this.symbolicName = value;
-	}
-
-	void put(String name, Object value) {
-		map.put(name, value);
-	}
-
-	public void setPresentationName(String name) {
-		presentationName = name;
-		if (name != null)
-			map.put(PRESENTATION_NAME, name);
-	}
-
-	public String getPresentationName() {
-		return presentationName;
-	}
-
-	public void setFile(File zipFile) {
-		file = zipFile;
-	}
-
-	public Set getExtendList() {
-		Set set = new HashSet();
-		for (Iterator i = requirements.iterator(); i.hasNext();) {
-			RequirementImpl	impl = (RequirementImpl) i.next();
-			if ( impl.isExtend())
-				set.add(impl);
-		}
-		return set;
-	}
-
-}
+/*
+ * $Id: ResourceImpl.java 44 2007-07-13 20:49:41Z hargrave@us.ibm.com $
+ * 
+ * Copyright (c) OSGi Alliance (2002, 2006, 2007). All Rights Reserved.
+ * 
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.osgi.impl.bundle.obr.resource;
+
+import java.io.File;
+import java.net.URL;
+import java.util.*;
+
+import org.osgi.framework.Version;
+import org.osgi.service.obr.*;
+import org.xmlpull.v1.XmlPullParser;
+
+public class ResourceImpl implements Resource {
+	List			capabilities	= new ArrayList();
+	List			requirements	= new ArrayList();
+	URL				url;
+	String			symbolicName;
+	VersionRange		version;
+	List			categories		= new ArrayList();
+	long			size			= -1;
+	String			id;
+	static int		ID				= 1;
+	Map				map				= new HashMap();
+	RepositoryImpl	repository;
+	String			presentationName;
+	File			file;
+
+
+	public ResourceImpl(RepositoryImpl repository, String name,
+			VersionRange version) {
+		this.version = version;
+		if ( version == null)
+			this.version = new VersionRange("0");
+		this.symbolicName = name;
+		this.repository = repository;
+	}
+
+	public ResourceImpl(RepositoryImpl repository, XmlPullParser parser)
+			throws Exception {
+		this.repository = repository;
+		parser.require(XmlPullParser.START_TAG, null, "resource");
+		symbolicName = parser.getAttributeValue(null, "symbolicname");
+		if (symbolicName == null)
+			System.err.println("Hey, no symb name! "
+					+ parser.getAttributeValue(null, "uri"));
+
+		map.put(SYMBOLIC_NAME, symbolicName);
+		presentationName = parser.getAttributeValue(null, PRESENTATION_NAME);
+		if (presentationName != null)
+			map.put(PRESENTATION_NAME, presentationName);
+		String v = parser.getAttributeValue(null, "version");
+		if (v == null)
+			setVersion(new VersionRange("0"));
+		else
+			setVersion(new VersionRange(v));
+
+		setURL(toURL(parser.getAttributeValue(null, "uri")));
+
+		while (parser.nextTag() == XmlPullParser.START_TAG) {
+			if (parser.getName().equals("category")) {
+				categories.add(parser.getAttributeValue(null, "id").trim());
+			}
+			else if (parser.getName().equals("require"))
+				addRequirement(new RequirementImpl(parser));
+			else if (parser.getName().equals("capability"))
+				addCapability(new CapabilityImpl(parser));
+			else {
+				String text = parser.nextText();
+				if (text != null)
+					map.put(parser.getName(), text.trim());
+			}
+			parser.next();
+		}
+		parser.require(XmlPullParser.END_TAG, null, "resource");
+	}
+
+	public ResourceImpl(RepositoryImpl impl) {
+		this.repository = impl;
+	}
+
+	private URL toURL(String attributeValue) throws Exception {
+		if (attributeValue == null)
+			return null;
+
+		return new URL(repository.getURL(), attributeValue);
+	}
+
+	public void addCategory(String category) {
+		categories.add(category);
+	}
+
+	public void addCapability(CapabilityImpl capability) {
+		if (capability != null)
+			capabilities.add(capability);
+	}
+
+	public void addRequirement(RequirementImpl requirement) {
+		if (requirement != null)
+			requirements.add(requirement);
+	}
+
+	public void setLicense(URL license) {
+		if (license != null)
+			map.put(LICENSE_URL, license);
+	}
+
+	public String getDescription() {
+		return (String) map.get(DESCRIPTION);
+	}
+
+	public void setDescription(String description) {
+		if (description != null)
+			map.put(DESCRIPTION, description);
+	}
+
+	public Capability[] getCapabilities() {
+		return (Capability[]) capabilities.toArray(new Capability[capabilities
+				.size()]);
+	}
+
+	public URL getLicense() {
+		return (URL) map.get(LICENSE_URL);
+	}
+
+	public String getSymbolicName() {
+		return symbolicName;
+	}
+
+	public Requirement[] getRequirements() {
+		return (Requirement[]) requirements
+				.toArray(new Requirement[requirements.size()]);
+	}
+
+	public Tag toXML() {
+		return toXML(this );
+	}
+
+	public static Tag toXML(Resource resource) {
+		return toXML(resource,true);
+	}
+
+	public static Tag toXML(Resource resource, boolean relative ) {
+		Tag meta = new Tag("resource");
+		URL url = resource.getURL();
+		String urlString = url.toExternalForm();
+		
+		if ( relative )
+			urlString = makeRelative(resource.getRepository().getURL(), url);
+		
+		meta.addAttribute("uri", urlString );
+		meta.addAttribute(SYMBOLIC_NAME, resource.getSymbolicName());
+		if (resource.getPresentationName() != null)
+			meta
+					.addAttribute(PRESENTATION_NAME, resource
+							.getPresentationName());
+		meta.addAttribute(VERSION, resource.getVersion().toString());
+		meta.addAttribute("id", resource.getId());
+		Map map = new TreeMap(resource.getProperties());
+		for (int i = 0; i < Resource.KEYS.length; i++) {
+			String key = KEYS[i];
+			if (!(key.equals(URL) || key.equals(SYMBOLIC_NAME) || key
+					.equals(VERSION) || key.equals(PRESENTATION_NAME))) {
+				Object value = map.get(KEYS[i]);
+				if (value != null) {
+					if (value instanceof URL)
+						value = makeRelative(resource.getRepository().getURL(),(URL) value);
+					meta.addContent(new Tag(key, value.toString()));
+				}
+			}
+		}
+
+		String[] categories = resource.getCategories();
+		for (int i = 0; i < categories.length; i++) {
+			String category = categories[i];
+			meta.addContent(new Tag("category", new String[] {"id",
+					category.toLowerCase()}));
+		}
+
+		Capability[] capabilities = resource.getCapabilities();
+		for (int i = 0; i < capabilities.length; i++) {
+			meta.addContent(CapabilityImpl.toXML(capabilities[i]));
+		}
+
+		Requirement[] requirements = resource.getRequirements();
+		for (int i = 0; i < requirements.length; i++) {
+			meta.addContent(RequirementImpl.toXML(requirements[i]));
+		}
+		return meta;
+	}
+
+	public URL getURL() {
+		return url;
+	}
+
+	static String makeRelative(URL repository, URL url) {
+		try {
+			if (repository != null) {
+				String a = url.toExternalForm();
+				String b = repository.toExternalForm();
+				int index = b.lastIndexOf('/');
+				if ( index > 0 )
+					b = b.substring(0,index+1);
+				if (a.startsWith(b))
+					return a.substring(b.length());
+			}
+		}
+		catch (Exception e) {
+			// Ignore
+		}
+		return url.toExternalForm();
+	}
+
+	public void setURL(URL url) {
+		this.url = url;
+		if (url != null)
+			map.put(URL, url);
+	}
+
+	public String getCopyright() {
+		return (String) map.get(COPYRIGHT);
+	}
+
+	public Version getVersion() {
+		if (version == null)
+			version = new VersionRange("0");
+		return version.low;
+	}
+
+	void setVersion(VersionRange version) {
+		if (version == null)
+			this.version = new VersionRange("0");
+		else
+			this.version = version;
+	}
+
+	public void setCopyright(String copyright) {
+		if (copyright != null)
+			map.put(COPYRIGHT, copyright);
+	}
+
+	public URL getDocumentation() {
+		return (URL) map.get(DOCUMENTATION_URL);
+	}
+
+	public void setDocumentation(URL documentation) {
+		if (documentation != null)
+			map.put(DOCUMENTATION_URL, documentation);
+	}
+
+	public URL getSource() {
+		return (URL) map.get(SOURCE_URL);
+	}
+
+	public void setSource(URL source) {
+		if (source != null)
+			map.put(SOURCE_URL, source);
+	}
+
+	public boolean satisfies(RequirementImpl requirement) {
+		for (Iterator i = capabilities.iterator(); i.hasNext();) {
+			CapabilityImpl capability = (CapabilityImpl) i.next();
+			if (requirement.isSatisfied(capability))
+				return true;
+		}
+		return false;
+	}
+
+	public String toString() {
+		return symbolicName + "-" + version;
+	}
+
+	public long getSize() {
+		return size;
+	}
+
+	public void setSize(long size) {
+		this.size = size;
+		map.put(SIZE, new Long(size));
+	}
+
+	public Collection getRequirementList() {
+		return requirements;
+	}
+
+	public Collection getCapabilityList() {
+		return capabilities;
+	}
+
+	public int hashCode() {
+		return symbolicName.hashCode() ^ version.hashCode();
+	}
+
+	public boolean equals(Object o) {
+		try {
+			ResourceImpl other = (ResourceImpl) o;
+			return symbolicName.equals(other.symbolicName)
+					&& version.equals(other.version);
+		}
+		catch (ClassCastException e) {
+			return false;
+		}
+	}
+
+	public String[] getCategories() {
+		return (String[]) categories.toArray(new String[categories.size()]);
+	}
+
+	public Map getProperties() {
+		return Collections.unmodifiableMap(map);
+	}
+
+	public synchronized String getId() {
+		if ( id == null )
+			id = symbolicName + "/" + version;
+		return id;
+	}
+
+	public Repository getRepository() {
+		return repository;
+	}
+
+	void setName(String value) {
+		this.symbolicName = value;
+	}
+
+	void put(String name, Object value) {
+		map.put(name, value);
+	}
+
+	public void setPresentationName(String name) {
+		presentationName = name;
+		if (name != null)
+			map.put(PRESENTATION_NAME, name);
+	}
+
+	public String getPresentationName() {
+		return presentationName;
+	}
+
+	public void setFile(File zipFile) {
+		file = zipFile;
+	}
+
+	public Set getExtendList() {
+		Set set = new HashSet();
+		for (Iterator i = requirements.iterator(); i.hasNext();) {
+			RequirementImpl	impl = (RequirementImpl) i.next();
+			if ( impl.isExtend())
+				set.add(impl);
+		}
+		return set;
+	}
+
+}

Modified: felix/trunk/bundleplugin/src/main/java/org/osgi/impl/bundle/obr/resource/StringSet.java
URL: http://svn.apache.org/viewvc/felix/trunk/bundleplugin/src/main/java/org/osgi/impl/bundle/obr/resource/StringSet.java?rev=722850&r1=722849&r2=722850&view=diff
==============================================================================
--- felix/trunk/bundleplugin/src/main/java/org/osgi/impl/bundle/obr/resource/StringSet.java (original)
+++ felix/trunk/bundleplugin/src/main/java/org/osgi/impl/bundle/obr/resource/StringSet.java Wed Dec  3 04:03:12 2008
@@ -1,32 +1,32 @@
-/*
- * $Id: StringSet.java 44 2007-07-13 20:49:41Z hargrave@us.ibm.com $
- * 
- * Copyright (c) OSGi Alliance (2002, 2006, 2007). All Rights Reserved.
- * 
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- *      http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-
-package org.osgi.impl.bundle.obr.resource;
-
-import java.util.*;
-
-public class StringSet extends HashSet {
-	static final long	serialVersionUID	= 1L;
-
-	public StringSet(String set) {
-		StringTokenizer st = new StringTokenizer(set, ",");
-		while (st.hasMoreTokens())
-			add(st.nextToken().trim());
-	}
-}
+/*
+ * $Id: StringSet.java 44 2007-07-13 20:49:41Z hargrave@us.ibm.com $
+ * 
+ * Copyright (c) OSGi Alliance (2002, 2006, 2007). All Rights Reserved.
+ * 
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+
+package org.osgi.impl.bundle.obr.resource;
+
+import java.util.*;
+
+public class StringSet extends HashSet {
+	static final long	serialVersionUID	= 1L;
+
+	public StringSet(String set) {
+		StringTokenizer st = new StringTokenizer(set, ",");
+		while (st.hasMoreTokens())
+			add(st.nextToken().trim());
+	}
+}

Modified: felix/trunk/bundleplugin/src/main/java/org/osgi/impl/bundle/obr/resource/Tag.java
URL: http://svn.apache.org/viewvc/felix/trunk/bundleplugin/src/main/java/org/osgi/impl/bundle/obr/resource/Tag.java?rev=722850&r1=722849&r2=722850&view=diff
==============================================================================
--- felix/trunk/bundleplugin/src/main/java/org/osgi/impl/bundle/obr/resource/Tag.java (original)
+++ felix/trunk/bundleplugin/src/main/java/org/osgi/impl/bundle/obr/resource/Tag.java Wed Dec  3 04:03:12 2008
@@ -1,488 +1,488 @@
-/*
- * $Id: Tag.java 44 2007-07-13 20:49:41Z hargrave@us.ibm.com $
- * 
- * Copyright (c) OSGi Alliance (2002, 2006, 2007). All Rights Reserved.
- * 
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- *      http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package org.osgi.impl.bundle.obr.resource;
-
-import java.io.*;
-import java.text.SimpleDateFormat;
-import java.util.*;
-
-/**
- * The Tag class represents a minimal XML tree. It consist of a named element
- * with a hashtable of named attributes. Methods are provided to walk the tree
- * and get its constituents. The content of a Tag is a list that contains String
- * objects or other Tag objects.
- */
-public class Tag {
-	Tag						parent;
-	String					name;
-	Map						attributes	= new TreeMap();
-	Vector					content		= new Vector();
-
-	static SimpleDateFormat	format		= new SimpleDateFormat(
-												"yyyyMMddhhmmss.SSS");
-
-	/**
-	 * Construct a new Tag with a name.
-	 */
-	public Tag(String name) {
-		this.name = name;
-	}
-
-	/**
-	 * Construct a new Tag with a name.
-	 */
-	public Tag(String name, Map attributes) {
-		this.name = name;
-		this.attributes = attributes;
-	}
-
-	/**
-	 * Construct a new Tag with a name and a set of attributes. The attributes
-	 * are given as ( name, value ) ...
-	 */
-	public Tag(String name, String[] attributes) {
-		this.name = name;
-		for (int i = 0; i < attributes.length; i += 2)
-			addAttribute(attributes[i], attributes[i + 1]);
-	}
-
-	/**
-	 * Construct a new Tag with a single string as content.
-	 */
-	public Tag(String name, String content) {
-		this.name = name;
-		addContent(content);
-	}
-
-	/**
-	 * Add a new attribute.
-	 */
-	public void addAttribute(String key, String value) {
-		attributes.put(key, value);
-	}
-
-	/**
-	 * Add a new attribute.
-	 */
-	public void addAttribute(String key, Object value) {
-		if (value == null)
-			return;
-		attributes.put(key, value.toString());
-	}
-
-	/**
-	 * Add a new attribute.
-	 */
-	public void addAttribute(String key, int value) {
-		attributes.put(key, Integer.toString(value));
-	}
-
-	/**
-	 * Add a new date attribute. The date is formatted as the SimpleDateFormat
-	 * describes at the top of this class.
-	 */
-	public void addAttribute(String key, Date value) {
-		attributes.put(key, format.format(value));
-	}
-
-	/**
-	 * Add a new content string.
-	 */
-	public void addContent(String string) {
-		content.addElement(string);
-	}
-
-	/**
-	 * Add a new content tag.
-	 */
-	public void addContent(Tag tag) {
-		content.addElement(tag);
-		tag.parent = this;
-	}
-
-	/**
-	 * Return the name of the tag.
-	 */
-	public String getName() {
-		return name;
-	}
-
-	/**
-	 * Return the attribute value.
-	 */
-	public String getAttribute(String key) {
-		return (String) attributes.get(key);
-	}
-
-	/**
-	 * Return the attribute value or a default if not defined.
-	 */
-	public String getAttribute(String key, String deflt) {
-		String answer = getAttribute(key);
-		return answer == null ? deflt : answer;
-	}
-
-	/**
-	 * Answer the attributes as a Dictionary object.
-	 */
-	public Map getAttributes() {
-		return attributes;
-	}
-
-	/**
-	 * Return the contents.
-	 */
-	public Vector getContents() {
-		return content;
-	}
-
-	/**
-	 * Return a string representation of this Tag and all its children
-	 * recursively.
-	 */
-	public String toString() {
-		StringWriter sw = new StringWriter();
-		print(0, new PrintWriter(sw));
-		return sw.toString();
-	}
-
-	/**
-	 * Return only the tags of the first level of descendants that match the
-	 * name.
-	 */
-	public Vector getContents(String tag) {
-		Vector out = new Vector();
-		for (Enumeration e = content.elements(); e.hasMoreElements();) {
-			Object o = e.nextElement();
-			if (o instanceof Tag && ((Tag) o).getName().equals(tag))
-				out.addElement(o);
-		}
-		return out;
-	}
-
-	/**
-	 * Return the whole contents as a String (no tag info and attributes).
-	 */
-	public String getContentsAsString() {
-		StringBuffer sb = new StringBuffer();
-		getContentsAsString(sb);
-		return sb.toString();
-	}
-
-	/**
-	 * convenient method to get the contents in a StringBuffer.
-	 */
-	public void getContentsAsString(StringBuffer sb) {
-		for (Enumeration e = content.elements(); e.hasMoreElements();) {
-			Object o = e.nextElement();
-			if (o instanceof Tag)
-				((Tag) o).getContentsAsString(sb);
-			else
-				sb.append(o.toString());
-		}
-	}
-
-	/**
-	 * Print the tag formatted to a PrintWriter.
-	 */
-	public void print(int indent, PrintWriter pw) {
-		pw.print("\n");
-		spaces(pw, indent);
-		pw.print('<');
-		pw.print(name);
-
-		for (Iterator e = attributes.keySet().iterator(); e.hasNext();) {
-			String key = (String) e.next();
-			String value = escape((String) attributes.get(key));
-			pw.print(' ');
-			pw.print(key);
-			pw.print("=");
-			String quote = "'";
-			if (value.indexOf(quote) >= 0)
-				quote = "\"";
-			pw.print(quote);
-			pw.print(value);
-			pw.print(quote);
-		}
-
-		if (content.size() == 0)
-			pw.print('/');
-		else {
-			pw.print('>');
-			for (Enumeration e = content.elements(); e.hasMoreElements();) {
-				Object content = e.nextElement();
-				if (content instanceof String) {
-					formatted(pw, indent + 2, 60, escape((String) content));
-				}
-				else if (content instanceof Tag) {
-					Tag tag = (Tag) content;
-					tag.print(indent + 2, pw);
-				}
-			}
-			pw.print("\n");
-			spaces(pw, indent);
-			pw.print("</");
-			pw.print(name);
-		}
-		pw.print('>');
-	}
-
-	/**
-	 * Convenience method to print a string nicely and does character conversion
-	 * to entities.
-	 */
-	void formatted(PrintWriter pw, int left, int width, String s) {
-		int pos = width + 1;
-		s = s.trim();
-
-		for (int i = 0; i < s.length(); i++) {
-			char c = s.charAt(i);
-			if (i == 0 || (Character.isWhitespace(c) && pos > width - 3)) {
-				pw.print("\n");
-				spaces(pw, left);
-				pos = 0;
-			}
-			switch (c) {
-				case '<' :
-					pw.print("&lt;");
-					pos += 4;
-					break;
-				case '>' :
-					pw.print("&gt;");
-					pos += 4;
-					break;
-				case '&' :
-					pw.print("&amp;");
-					pos += 5;
-					break;
-				default :
-					pw.print(c);
-					pos++;
-					break;
-			}
-
-		}
-	}
-
-	/**
-	 * Escape a string, do entity conversion.
-	 */
-	String escape(String s) {
-		if  ( s == null )
-			return "?null?";
-		
-		StringBuffer sb = new StringBuffer();
-		for (int i = 0; i < s.length(); i++) {
-			char c = s.charAt(i);
-			switch (c) {
-				case '<' :
-					sb.append("&lt;");
-					break;
-				case '>' :
-					sb.append("&gt;");
-					break;
-				case '&' :
-					sb.append("&amp;");
-					break;
-				default :
-					sb.append(c);
-					break;
-			}
-		}
-		return sb.toString();
-	}
-
-	/**
-	 * Make spaces.
-	 */
-	void spaces(PrintWriter pw, int n) {
-		while (n-- > 0)
-			pw.print(' ');
-	}
-
-	/**
-	 * root/preferences/native/os
-	 */
-	public Tag[] select(String path) {
-		return select(path, (Tag) null);
-	}
-
-	public Tag[] select(String path, Tag mapping) {
-		Vector v = new Vector();
-		select(path, v, mapping);
-		Tag[] result = new Tag[v.size()];
-		v.copyInto(result);
-		return result;
-	}
-
-	void select(String path, Vector results, Tag mapping) {
-		if (path.startsWith("//")) {
-			int i = path.indexOf('/', 2);
-			String name = path.substring(2, i < 0 ? path.length() : i);
-
-			for (Enumeration e = content.elements(); e.hasMoreElements();) {
-				Object o = e.nextElement();
-				if (o instanceof Tag) {
-					Tag child = (Tag) o;
-					if (match(name, child, mapping))
-						results.add(child);
-					child.select(path, results, mapping);
-				}
-
-			}
-			return;
-		}
-
-		if (path.length() == 0) {
-			results.addElement(this);
-			return;
-		}
-
-		int i = path.indexOf("/");
-		String elementName = path;
-		String remainder = "";
-		if (i > 0) {
-			elementName = path.substring(0, i);
-			remainder = path.substring(i + 1);
-		}
-
-		for (Enumeration e = content.elements(); e.hasMoreElements();) {
-			Object o = e.nextElement();
-			if (o instanceof Tag) {
-				Tag child = (Tag) o;
-				if (child.getName().equals(elementName)
-						|| elementName.equals("*"))
-					child.select(remainder, results, mapping);
-			}
-		}
-	}
-
-	public boolean match(String search, Tag child, Tag mapping) {
-		String target = child.getName();
-		String sn = null;
-		String tn = null;
-
-		if (search.equals("*"))
-			return true;
-
-		int s = search.indexOf(':');
-		if (s > 0) {
-			sn = search.substring(0, s);
-			search = search.substring(s + 1);
-		}
-		int t = target.indexOf(':');
-		if (t > 0) {
-			tn = target.substring(0, t);
-			target = target.substring(t + 1);
-		}
-
-		if (!search.equals(target)) // different tag names
-			return false;
-
-		if (mapping == null) {
-			return tn == sn || (sn != null && sn.equals(tn));
-		}
-		else {
-			String suri = sn == null ? mapping.getAttribute("xmlns") : mapping
-					.getAttribute("xmlns:" + sn);
-			String turi = tn == null ? child.findRecursiveAttribute("xmlns")
-					: child.findRecursiveAttribute("xmlns:" + tn);
-			return turi == suri
-					|| (turi != null && suri != null && turi.equals(suri));
-		}
-	}
-
-	public String getString(String path) {
-		String attribute = null;
-		int index = path.indexOf("@");
-		if (index >= 0) {
-			// attribute
-			attribute = path.substring(index + 1);
-
-			if (index > 0) {
-				// prefix path
-				path = path.substring(index - 1); // skip -1
-			}
-			else
-				path = "";
-		}
-		Tag tags[] = select(path);
-		StringBuffer sb = new StringBuffer();
-		for (int i = 0; i < tags.length; i++) {
-			if (attribute == null)
-				tags[i].getContentsAsString(sb);
-			else
-				sb.append(tags[i].getAttribute(attribute));
-		}
-		return sb.toString();
-	}
-
-	public String getStringContent() {
-		StringBuffer sb = new StringBuffer();
-		for (Enumeration e = content.elements(); e.hasMoreElements();) {
-			Object c = e.nextElement();
-			if (!(c instanceof Tag))
-				sb.append(c);
-		}
-		return sb.toString();
-	}
-
-	public String getNameSpace() {
-		return getNameSpace(name);
-	}
-
-	public String getNameSpace(String name) {
-		int index = name.indexOf(':');
-		if (index > 0) {
-			String ns = name.substring(0, index);
-			return findRecursiveAttribute("xmlns:" + ns);
-		}
-		else
-			return findRecursiveAttribute("xmlns");
-	}
-
-	public String findRecursiveAttribute(String name) {
-		String value = getAttribute(name);
-		if (value != null)
-			return value;
-		if (parent != null)
-			return parent.findRecursiveAttribute(name);
-		return null;
-	}
-
-	public String getLocalName() {
-		int index = name.indexOf(':');
-		if (index <= 0)
-			return name;
-
-		return name.substring(index + 1);
-	}
-
-	public void rename(String string) {
-		name = string;
-	}
-
-
-	public static void convert( Collection c, String type, Tag parent ) {
-		for ( Iterator i=c.iterator(); i.hasNext(); ) {
-			Map	map = (Map) i.next();
-			parent.addContent( new Tag(type, map) );
-		}
-	}
-
-}
+/*
+ * $Id: Tag.java 44 2007-07-13 20:49:41Z hargrave@us.ibm.com $
+ * 
+ * Copyright (c) OSGi Alliance (2002, 2006, 2007). All Rights Reserved.
+ * 
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.osgi.impl.bundle.obr.resource;
+
+import java.io.*;
+import java.text.SimpleDateFormat;
+import java.util.*;
+
+/**
+ * The Tag class represents a minimal XML tree. It consist of a named element
+ * with a hashtable of named attributes. Methods are provided to walk the tree
+ * and get its constituents. The content of a Tag is a list that contains String
+ * objects or other Tag objects.
+ */
+public class Tag {
+	Tag						parent;
+	String					name;
+	Map						attributes	= new TreeMap();
+	Vector					content		= new Vector();
+
+	static SimpleDateFormat	format		= new SimpleDateFormat(
+												"yyyyMMddhhmmss.SSS");
+
+	/**
+	 * Construct a new Tag with a name.
+	 */
+	public Tag(String name) {
+		this.name = name;
+	}
+
+	/**
+	 * Construct a new Tag with a name.
+	 */
+	public Tag(String name, Map attributes) {
+		this.name = name;
+		this.attributes = attributes;
+	}
+
+	/**
+	 * Construct a new Tag with a name and a set of attributes. The attributes
+	 * are given as ( name, value ) ...
+	 */
+	public Tag(String name, String[] attributes) {
+		this.name = name;
+		for (int i = 0; i < attributes.length; i += 2)
+			addAttribute(attributes[i], attributes[i + 1]);
+	}
+
+	/**
+	 * Construct a new Tag with a single string as content.
+	 */
+	public Tag(String name, String content) {
+		this.name = name;
+		addContent(content);
+	}
+
+	/**
+	 * Add a new attribute.
+	 */
+	public void addAttribute(String key, String value) {
+		attributes.put(key, value);
+	}
+
+	/**
+	 * Add a new attribute.
+	 */
+	public void addAttribute(String key, Object value) {
+		if (value == null)
+			return;
+		attributes.put(key, value.toString());
+	}
+
+	/**
+	 * Add a new attribute.
+	 */
+	public void addAttribute(String key, int value) {
+		attributes.put(key, Integer.toString(value));
+	}
+
+	/**
+	 * Add a new date attribute. The date is formatted as the SimpleDateFormat
+	 * describes at the top of this class.
+	 */
+	public void addAttribute(String key, Date value) {
+		attributes.put(key, format.format(value));
+	}
+
+	/**
+	 * Add a new content string.
+	 */
+	public void addContent(String string) {
+		content.addElement(string);
+	}
+
+	/**
+	 * Add a new content tag.
+	 */
+	public void addContent(Tag tag) {
+		content.addElement(tag);
+		tag.parent = this;
+	}
+
+	/**
+	 * Return the name of the tag.
+	 */
+	public String getName() {
+		return name;
+	}
+
+	/**
+	 * Return the attribute value.
+	 */
+	public String getAttribute(String key) {
+		return (String) attributes.get(key);
+	}
+
+	/**
+	 * Return the attribute value or a default if not defined.
+	 */
+	public String getAttribute(String key, String deflt) {
+		String answer = getAttribute(key);
+		return answer == null ? deflt : answer;
+	}
+
+	/**
+	 * Answer the attributes as a Dictionary object.
+	 */
+	public Map getAttributes() {
+		return attributes;
+	}
+
+	/**
+	 * Return the contents.
+	 */
+	public Vector getContents() {
+		return content;
+	}
+
+	/**
+	 * Return a string representation of this Tag and all its children
+	 * recursively.
+	 */
+	public String toString() {
+		StringWriter sw = new StringWriter();
+		print(0, new PrintWriter(sw));
+		return sw.toString();
+	}
+
+	/**
+	 * Return only the tags of the first level of descendants that match the
+	 * name.
+	 */
+	public Vector getContents(String tag) {
+		Vector out = new Vector();
+		for (Enumeration e = content.elements(); e.hasMoreElements();) {
+			Object o = e.nextElement();
+			if (o instanceof Tag && ((Tag) o).getName().equals(tag))
+				out.addElement(o);
+		}
+		return out;
+	}
+
+	/**
+	 * Return the whole contents as a String (no tag info and attributes).
+	 */
+	public String getContentsAsString() {
+		StringBuffer sb = new StringBuffer();
+		getContentsAsString(sb);
+		return sb.toString();
+	}
+
+	/**
+	 * convenient method to get the contents in a StringBuffer.
+	 */
+	public void getContentsAsString(StringBuffer sb) {
+		for (Enumeration e = content.elements(); e.hasMoreElements();) {
+			Object o = e.nextElement();
+			if (o instanceof Tag)
+				((Tag) o).getContentsAsString(sb);
+			else
+				sb.append(o.toString());
+		}
+	}
+
+	/**
+	 * Print the tag formatted to a PrintWriter.
+	 */
+	public void print(int indent, PrintWriter pw) {
+		pw.print("\n");
+		spaces(pw, indent);
+		pw.print('<');
+		pw.print(name);
+
+		for (Iterator e = attributes.keySet().iterator(); e.hasNext();) {
+			String key = (String) e.next();
+			String value = escape((String) attributes.get(key));
+			pw.print(' ');
+			pw.print(key);
+			pw.print("=");
+			String quote = "'";
+			if (value.indexOf(quote) >= 0)
+				quote = "\"";
+			pw.print(quote);
+			pw.print(value);
+			pw.print(quote);
+		}
+
+		if (content.size() == 0)
+			pw.print('/');
+		else {
+			pw.print('>');
+			for (Enumeration e = content.elements(); e.hasMoreElements();) {
+				Object content = e.nextElement();
+				if (content instanceof String) {
+					formatted(pw, indent + 2, 60, escape((String) content));
+				}
+				else if (content instanceof Tag) {
+					Tag tag = (Tag) content;
+					tag.print(indent + 2, pw);
+				}
+			}
+			pw.print("\n");
+			spaces(pw, indent);
+			pw.print("</");
+			pw.print(name);
+		}
+		pw.print('>');
+	}
+
+	/**
+	 * Convenience method to print a string nicely and does character conversion
+	 * to entities.
+	 */
+	void formatted(PrintWriter pw, int left, int width, String s) {
+		int pos = width + 1;
+		s = s.trim();
+
+		for (int i = 0; i < s.length(); i++) {
+			char c = s.charAt(i);
+			if (i == 0 || (Character.isWhitespace(c) && pos > width - 3)) {
+				pw.print("\n");
+				spaces(pw, left);
+				pos = 0;
+			}
+			switch (c) {
+				case '<' :
+					pw.print("&lt;");
+					pos += 4;
+					break;
+				case '>' :
+					pw.print("&gt;");
+					pos += 4;
+					break;
+				case '&' :
+					pw.print("&amp;");
+					pos += 5;
+					break;
+				default :
+					pw.print(c);
+					pos++;
+					break;
+			}
+
+		}
+	}
+
+	/**
+	 * Escape a string, do entity conversion.
+	 */
+	String escape(String s) {
+		if  ( s == null )
+			return "?null?";
+		
+		StringBuffer sb = new StringBuffer();
+		for (int i = 0; i < s.length(); i++) {
+			char c = s.charAt(i);
+			switch (c) {
+				case '<' :
+					sb.append("&lt;");
+					break;
+				case '>' :
+					sb.append("&gt;");
+					break;
+				case '&' :
+					sb.append("&amp;");
+					break;
+				default :
+					sb.append(c);
+					break;
+			}
+		}
+		return sb.toString();
+	}
+
+	/**
+	 * Make spaces.
+	 */
+	void spaces(PrintWriter pw, int n) {
+		while (n-- > 0)
+			pw.print(' ');
+	}
+
+	/**
+	 * root/preferences/native/os
+	 */
+	public Tag[] select(String path) {
+		return select(path, (Tag) null);
+	}
+
+	public Tag[] select(String path, Tag mapping) {
+		Vector v = new Vector();
+		select(path, v, mapping);
+		Tag[] result = new Tag[v.size()];
+		v.copyInto(result);
+		return result;
+	}
+
+	void select(String path, Vector results, Tag mapping) {
+		if (path.startsWith("//")) {
+			int i = path.indexOf('/', 2);
+			String name = path.substring(2, i < 0 ? path.length() : i);
+
+			for (Enumeration e = content.elements(); e.hasMoreElements();) {
+				Object o = e.nextElement();
+				if (o instanceof Tag) {
+					Tag child = (Tag) o;
+					if (match(name, child, mapping))
+						results.add(child);
+					child.select(path, results, mapping);
+				}
+
+			}
+			return;
+		}
+
+		if (path.length() == 0) {
+			results.addElement(this);
+			return;
+		}
+
+		int i = path.indexOf("/");
+		String elementName = path;
+		String remainder = "";
+		if (i > 0) {
+			elementName = path.substring(0, i);
+			remainder = path.substring(i + 1);
+		}
+
+		for (Enumeration e = content.elements(); e.hasMoreElements();) {
+			Object o = e.nextElement();
+			if (o instanceof Tag) {
+				Tag child = (Tag) o;
+				if (child.getName().equals(elementName)
+						|| elementName.equals("*"))
+					child.select(remainder, results, mapping);
+			}
+		}
+	}
+
+	public boolean match(String search, Tag child, Tag mapping) {
+		String target = child.getName();
+		String sn = null;
+		String tn = null;
+
+		if (search.equals("*"))
+			return true;
+
+		int s = search.indexOf(':');
+		if (s > 0) {
+			sn = search.substring(0, s);
+			search = search.substring(s + 1);
+		}
+		int t = target.indexOf(':');
+		if (t > 0) {
+			tn = target.substring(0, t);
+			target = target.substring(t + 1);
+		}
+
+		if (!search.equals(target)) // different tag names
+			return false;
+
+		if (mapping == null) {
+			return tn == sn || (sn != null && sn.equals(tn));
+		}
+		else {
+			String suri = sn == null ? mapping.getAttribute("xmlns") : mapping
+					.getAttribute("xmlns:" + sn);
+			String turi = tn == null ? child.findRecursiveAttribute("xmlns")
+					: child.findRecursiveAttribute("xmlns:" + tn);
+			return turi == suri
+					|| (turi != null && suri != null && turi.equals(suri));
+		}
+	}
+
+	public String getString(String path) {
+		String attribute = null;
+		int index = path.indexOf("@");
+		if (index >= 0) {
+			// attribute
+			attribute = path.substring(index + 1);
+
+			if (index > 0) {
+				// prefix path
+				path = path.substring(index - 1); // skip -1
+			}
+			else
+				path = "";
+		}
+		Tag tags[] = select(path);
+		StringBuffer sb = new StringBuffer();
+		for (int i = 0; i < tags.length; i++) {
+			if (attribute == null)
+				tags[i].getContentsAsString(sb);
+			else
+				sb.append(tags[i].getAttribute(attribute));
+		}
+		return sb.toString();
+	}
+
+	public String getStringContent() {
+		StringBuffer sb = new StringBuffer();
+		for (Enumeration e = content.elements(); e.hasMoreElements();) {
+			Object c = e.nextElement();
+			if (!(c instanceof Tag))
+				sb.append(c);
+		}
+		return sb.toString();
+	}
+
+	public String getNameSpace() {
+		return getNameSpace(name);
+	}
+
+	public String getNameSpace(String name) {
+		int index = name.indexOf(':');
+		if (index > 0) {
+			String ns = name.substring(0, index);
+			return findRecursiveAttribute("xmlns:" + ns);
+		}
+		else
+			return findRecursiveAttribute("xmlns");
+	}
+
+	public String findRecursiveAttribute(String name) {
+		String value = getAttribute(name);
+		if (value != null)
+			return value;
+		if (parent != null)
+			return parent.findRecursiveAttribute(name);
+		return null;
+	}
+
+	public String getLocalName() {
+		int index = name.indexOf(':');
+		if (index <= 0)
+			return name;
+
+		return name.substring(index + 1);
+	}
+
+	public void rename(String string) {
+		name = string;
+	}
+
+
+	public static void convert( Collection c, String type, Tag parent ) {
+		for ( Iterator i=c.iterator(); i.hasNext(); ) {
+			Map	map = (Map) i.next();
+			parent.addContent( new Tag(type, map) );
+		}
+	}
+
+}