[FELIX-4369] [FELIX-4370] Initial work towards supporting the OSGi Repository 1.0 spec
This commit provides a start for support of reading the spec-compliant Repository XML. The API for reading the XML hasn't changed, however when an XML document is encountered with the http://www.osgi.org/xmlns/repository/v1.0.0 name space it is parsed as a spec-compliant Repository XML.
This commit provides a start for supporting the Repository Service API, the actual Repository Service is not yet registered, but an implementation of this API can be obtained by wrapping the RepositoryAdmin object with the OSGiRepositoryImpl class.
Part of the work is based on and inspired by the OBR-Repository mapping as used by the Apache Aries Subsystems project (thanks!).
This work is by no means finished, it's just a start. Old clients should still work (at least the existing unit tests all pass) and new unit tests were added.
git-svn-id: https://svn.apache.org/repos/asf/felix/trunk@1563841 13f79535-47bb-0310-9956-ffa450edef68
diff --git a/bundlerepository/pom.xml b/bundlerepository/pom.xml
index 0553f45..5b5980e 100644
--- a/bundlerepository/pom.xml
+++ b/bundlerepository/pom.xml
@@ -28,7 +28,7 @@
<name>Apache Felix Bundle Repository</name>
<description>Bundle repository service.</description>
<artifactId>org.apache.felix.bundlerepository</artifactId>
- <version>1.6.7-SNAPSHOT</version>
+ <version>1.7.0-SNAPSHOT</version>
<scm>
<connection>scm:svn:http://svn.apache.org/repos/asf/felix/trunk/bundlerepository</connection>
<developerConnection>scm:svn:https://svn.apache.org/repos/asf/felix/trunk/bundlerepository</developerConnection>
@@ -46,6 +46,12 @@
<artifactId>org.osgi.service.obr</artifactId>
<version>1.0.2</version>
<optional>true</optional>
+ <exclusions>
+ <exclusion>
+ <groupId>org.apache.felix</groupId>
+ <artifactId>org.osgi.core</artifactId>
+ </exclusion>
+ </exclusions>
</dependency>
<dependency>
<groupId>${project.groupId}</groupId>
@@ -68,13 +74,13 @@
<dependency>
<groupId>org.osgi</groupId>
<artifactId>org.osgi.compendium</artifactId>
- <version>4.0.0</version>
+ <version>5.0.0</version>
<optional>true</optional>
</dependency>
<dependency>
<groupId>org.osgi</groupId>
<artifactId>org.osgi.core</artifactId>
- <version>4.1.0</version>
+ <version>5.0.0</version>
</dependency>
<dependency>
<groupId>org.codehaus.woodstox</groupId>
@@ -91,13 +97,25 @@
<build>
<plugins>
<plugin>
+ <groupId>org.apache.maven.plugins</groupId>
+ <artifactId>maven-compiler-plugin</artifactId>
+ <configuration>
+ <target>1.5</target>
+ <source>1.5</source>
+ </configuration>
+ </plugin>
+
+ <plugin>
<groupId>org.apache.felix</groupId>
<artifactId>maven-bundle-plugin</artifactId>
<version>2.3.4</version>
<extensions>true</extensions>
<configuration>
<instructions>
- <Export-Package>org.apache.felix.bundlerepository;version="2.0"</Export-Package>
+ <Export-Package>
+ org.osgi.service.repository,
+ org.apache.felix.bundlerepository;version="2.1"
+ </Export-Package>
<Private-Package>
org.kxml2.io,
org.xmlpull.v1,
diff --git a/bundlerepository/src/main/java/org/apache/felix/bundlerepository/Capability.java b/bundlerepository/src/main/java/org/apache/felix/bundlerepository/Capability.java
index 09cadff..dc17629 100644
--- a/bundlerepository/src/main/java/org/apache/felix/bundlerepository/Capability.java
+++ b/bundlerepository/src/main/java/org/apache/felix/bundlerepository/Capability.java
@@ -35,8 +35,8 @@
*/
// This document is an experimental draft to enable interoperability
-// between bundle repositories. There is currently no commitment to
-// turn this draft into an official specification.
+// between bundle repositories. There is currently no commitment to
+// turn this draft into an official specification.
package org.apache.felix.bundlerepository;
import java.util.Map;
@@ -44,12 +44,11 @@
/**
* A named set of properties representing some capability that is provided by
* its owner.
- *
+ *
* @version $Revision: 1.3 $
*/
public interface Capability
{
-
String BUNDLE = "bundle";
String FRAGMENT = "fragment";
String PACKAGE = "package";
@@ -58,24 +57,21 @@
/**
* Return the name of the capability.
- *
+ *
*/
String getName();
/**
* Return the properties of this capability
- *
+ *
* @return
*/
Property[] getProperties();
/**
* Return the map of properties.
- *
+ *
* @return a Map<String,Object>
*/
- Map getPropertiesAsMap();
-
-
-
+ Map<String, Object> getPropertiesAsMap();
}
\ No newline at end of file
diff --git a/bundlerepository/src/main/java/org/apache/felix/bundlerepository/impl/CapabilityImpl.java b/bundlerepository/src/main/java/org/apache/felix/bundlerepository/impl/CapabilityImpl.java
index e33dd40..5362a71 100644
--- a/bundlerepository/src/main/java/org/apache/felix/bundlerepository/impl/CapabilityImpl.java
+++ b/bundlerepository/src/main/java/org/apache/felix/bundlerepository/impl/CapabilityImpl.java
@@ -1,4 +1,4 @@
-/*
+/*
* 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
@@ -18,7 +18,10 @@
*/
package org.apache.felix.bundlerepository.impl;
-import java.util.*;
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
import org.apache.felix.bundlerepository.Capability;
import org.apache.felix.bundlerepository.Property;
@@ -26,8 +29,8 @@
public class CapabilityImpl implements Capability
{
private String m_name = null;
- private final Map m_map = new HashMap();
- private final List m_list = new ArrayList();
+ private final Map<String, Object> m_map = new HashMap<String, Object>();
+ private final List<Property> m_list = new ArrayList<Property>();
public CapabilityImpl()
{
@@ -57,19 +60,22 @@
m_name = name.intern();
}
- public Map getPropertiesAsMap()
+ public Map<String, Object> getPropertiesAsMap()
{
return m_map;
}
public Property[] getProperties()
{
- return (Property[]) m_list.toArray(new Property[m_list.size()]);
+ return m_list.toArray(new Property[m_list.size()]);
}
public void addProperty(Property prop)
{
- m_map.put(prop.getName().toLowerCase(), prop.getConvertedValue());
+ // m_map.put(prop.getName().toLowerCase(), prop.getConvertedValue()); // TODO is toLowerCase() on the key the right thing to do?
+ // However if we definitely need to re-enable the to-lowercasing, the Felix Util FilterImpl supports treating filters
+ // case-insensitively
+ m_map.put(prop.getName(), prop.getConvertedValue());
m_list.add(prop);
}
diff --git a/bundlerepository/src/main/java/org/apache/felix/bundlerepository/impl/FelixCapabilityAdapter.java b/bundlerepository/src/main/java/org/apache/felix/bundlerepository/impl/FelixCapabilityAdapter.java
new file mode 100644
index 0000000..4845264
--- /dev/null
+++ b/bundlerepository/src/main/java/org/apache/felix/bundlerepository/impl/FelixCapabilityAdapter.java
@@ -0,0 +1,88 @@
+/*
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.felix.bundlerepository.impl;
+
+import java.util.Collections;
+import java.util.Map;
+
+import org.osgi.framework.namespace.BundleNamespace;
+import org.osgi.namespace.service.ServiceNamespace;
+import org.osgi.resource.Capability;
+import org.osgi.resource.Resource;
+
+public class FelixCapabilityAdapter implements Capability
+{
+ private final org.apache.felix.bundlerepository.Capability capability;
+ private final Resource resource;
+
+ public FelixCapabilityAdapter(org.apache.felix.bundlerepository.Capability capability, Resource resource)
+ {
+ if (capability == null)
+ throw new NullPointerException("Missing required parameter: capability");
+ this.capability = capability;
+ this.resource = resource;
+ }
+
+ public Map<String, Object> getAttributes()
+ {
+ Map<String, Object> result = capability.getPropertiesAsMap();
+ String namespace = getNamespace();
+ if (ServiceNamespace.SERVICE_NAMESPACE.equals(namespace))
+ result.put(ServiceNamespace.CAPABILITY_OBJECTCLASS_ATTRIBUTE,
+ result.get(ServiceNamespace.CAPABILITY_OBJECTCLASS_ATTRIBUTE.toLowerCase()));
+ else if (BundleNamespace.BUNDLE_NAMESPACE.equals(namespace))
+ result.put(BundleNamespace.BUNDLE_NAMESPACE, result.get(org.apache.felix.bundlerepository.Resource.SYMBOLIC_NAME));
+ else
+ result.put(namespace, result.get(capability.getName()));
+ return result;
+ }
+
+ public Map<String, String> getDirectives()
+ {
+ return Collections.emptyMap();
+ }
+
+ public String getNamespace()
+ {
+ return NamespaceTranslator.getOSGiNamespace(capability.getName());
+ }
+
+ public Resource getResource()
+ {
+ return resource;
+ }
+
+ @Override
+ public boolean equals(Object o)
+ {
+ if (o == this)
+ return true;
+ if (!(o instanceof Capability))
+ return false;
+ Capability c = (Capability) o;
+ return c.getNamespace().equals(getNamespace()) && c.getAttributes().equals(getAttributes())
+ && c.getDirectives().equals(getDirectives()) && c.getResource().equals(getResource());
+ }
+
+ @Override
+ public int hashCode()
+ {
+ int result = 17;
+ result = 31 * result + getNamespace().hashCode();
+ result = 31 * result + getAttributes().hashCode();
+ result = 31 * result + getDirectives().hashCode();
+ result = 31 * result + getResource().hashCode();
+ return result;
+ }
+}
diff --git a/bundlerepository/src/main/java/org/apache/felix/bundlerepository/impl/FelixRequirementAdapter.java b/bundlerepository/src/main/java/org/apache/felix/bundlerepository/impl/FelixRequirementAdapter.java
new file mode 100644
index 0000000..d718b6c
--- /dev/null
+++ b/bundlerepository/src/main/java/org/apache/felix/bundlerepository/impl/FelixRequirementAdapter.java
@@ -0,0 +1,109 @@
+/*
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.felix.bundlerepository.impl;
+
+import java.util.Collections;
+import java.util.HashMap;
+import java.util.Map;
+
+import org.osgi.resource.Capability;
+import org.osgi.resource.Namespace;
+import org.osgi.resource.Requirement;
+import org.osgi.resource.Resource;
+
+public class FelixRequirementAdapter implements Requirement
+{
+ private final Map<String, String> directives;
+ private final org.apache.felix.bundlerepository.Requirement requirement;
+ private final Resource resource;
+
+ public FelixRequirementAdapter(org.apache.felix.bundlerepository.Requirement requirement, Resource resource)
+ {
+ if (requirement == null)
+ throw new NullPointerException("Missing required parameter: requirement");
+ if (resource == null)
+ throw new NullPointerException("Missing required parameter: resource");
+ this.requirement = requirement;
+ this.resource = resource;
+ directives = computeDirectives();
+ }
+
+ public Map<String, Object> getAttributes()
+ {
+ return Collections.emptyMap();
+ }
+
+ public Map<String, String> getDirectives()
+ {
+ return directives;
+ }
+
+ public String getNamespace()
+ {
+ return NamespaceTranslator.getOSGiNamespace(requirement.getName());
+ }
+
+ public Resource getResource()
+ {
+ return resource;
+ }
+
+ public boolean matches(Capability capability)
+ {
+ return requirement.isSatisfied(new OSGiCapabilityAdapter(capability));
+ }
+
+ private Map<String, String> computeDirectives()
+ {
+ Map<String, String> result = new HashMap<String, String>(3);
+ /*
+ * (1) The Felix OBR specific "mandatory:<*" syntax must be stripped out
+ * of the filter. (2) The namespace must be translated.
+ */
+ result.put(
+ Namespace.REQUIREMENT_FILTER_DIRECTIVE,
+ requirement.getFilter().replaceAll("\\(mandatory\\:\\<\\*[^\\)]*\\)", "")
+ .replaceAll("\\(service\\=[^\\)]*\\)", "").replaceAll("objectclass", "objectClass")
+ .replaceAll(requirement.getName() + '=', getNamespace() + '='));
+ result.put(Namespace.REQUIREMENT_RESOLUTION_DIRECTIVE, requirement.isOptional() ? Namespace.RESOLUTION_OPTIONAL
+ : Namespace.RESOLUTION_MANDATORY);
+ result.put(Namespace.REQUIREMENT_CARDINALITY_DIRECTIVE, requirement.isMultiple() ? Namespace.CARDINALITY_MULTIPLE
+ : Namespace.CARDINALITY_SINGLE);
+ return Collections.unmodifiableMap(result);
+ }
+
+ @Override
+ public boolean equals(Object o)
+ {
+ if (o == this)
+ return true;
+ if (!(o instanceof Requirement))
+ return false;
+ Requirement c = (Requirement) o;
+ return c.getNamespace().equals(getNamespace()) && c.getAttributes().equals(getAttributes())
+ && c.getDirectives().equals(getDirectives()) && c.getResource() != null ? c.getResource().equals(getResource())
+ : getResource() == null;
+ }
+
+ @Override
+ public int hashCode()
+ {
+ int result = 17;
+ result = 31 * result + getNamespace().hashCode();
+ result = 31 * result + getAttributes().hashCode();
+ result = 31 * result + getDirectives().hashCode();
+ result = 31 * result + (getResource() == null ? 0 : getResource().hashCode());
+ return result;
+ }
+}
diff --git a/bundlerepository/src/main/java/org/apache/felix/bundlerepository/impl/FelixResourceAdapter.java b/bundlerepository/src/main/java/org/apache/felix/bundlerepository/impl/FelixResourceAdapter.java
new file mode 100644
index 0000000..f12b2b1
--- /dev/null
+++ b/bundlerepository/src/main/java/org/apache/felix/bundlerepository/impl/FelixResourceAdapter.java
@@ -0,0 +1,158 @@
+/*
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.felix.bundlerepository.impl;
+
+import java.io.InputStream;
+import java.net.URL;
+import java.util.ArrayList;
+import java.util.Collections;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+
+import org.osgi.framework.Version;
+import org.osgi.framework.namespace.IdentityNamespace;
+import org.osgi.resource.Capability;
+import org.osgi.resource.Requirement;
+import org.osgi.resource.Resource;
+import org.osgi.service.repository.ContentNamespace;
+import org.osgi.service.repository.RepositoryContent;
+
+public class FelixResourceAdapter implements Resource, RepositoryContent
+{
+ private final org.apache.felix.bundlerepository.Resource resource;
+
+ public FelixResourceAdapter(final org.apache.felix.bundlerepository.Resource resource)
+ {
+ this.resource = resource;
+ }
+
+ public List<Capability> getCapabilities(String namespace)
+ {
+ if (namespace == null || namespace.equals(IdentityNamespace.IDENTITY_NAMESPACE))
+ {
+ Capability c = newOsgiIdentityCapability(this, resource.getSymbolicName(), resource.getVersion());
+ return Collections.singletonList(c);
+ }
+ if (namespace.equals(ContentNamespace.CONTENT_NAMESPACE))
+ {
+ Capability c = newOsgiContentCapability(this, resource.getURI(), resource.getSize());
+ return Collections.singletonList(c);
+ }
+
+ namespace = NamespaceTranslator.getFelixNamespace(namespace);
+ org.apache.felix.bundlerepository.Capability[] capabilities = resource.getCapabilities();
+ ArrayList<Capability> result = new ArrayList<Capability>(capabilities.length);
+ for (org.apache.felix.bundlerepository.Capability capability : capabilities)
+ {
+ if (namespace != null && !capability.getName().equals(namespace))
+ continue;
+ result.add(new FelixCapabilityAdapter(capability, this));
+ }
+ result.trimToSize();
+ return result;
+ }
+
+ private static Capability newOsgiIdentityCapability(Resource res, String symbolicName, Version version)
+ {
+ Map<String, Object> idAttrs = new HashMap<String, Object>();
+ idAttrs.put(IdentityNamespace.IDENTITY_NAMESPACE, symbolicName);
+ idAttrs.put(IdentityNamespace.CAPABILITY_TYPE_ATTRIBUTE, IdentityNamespace.TYPE_BUNDLE);
+ idAttrs.put(IdentityNamespace.CAPABILITY_VERSION_ATTRIBUTE, version);
+
+ return new OSGiCapabilityImpl(IdentityNamespace.IDENTITY_NAMESPACE, idAttrs, Collections.<String, String> emptyMap(), res);
+ }
+
+ private static Capability newOsgiContentCapability(Resource res, String uri, long size)
+ {
+ // TODO duplicated in OSGiRepositoryImpl
+ Map<String, Object> contentAttrs = new HashMap<String, Object>();
+ try
+ {
+ // TODO can we do this lazily?
+ contentAttrs.put(ContentNamespace.CONTENT_NAMESPACE, OSGiRepositoryImpl.getSHA256(uri));
+ } catch (Exception e)
+ {
+ // TODO handle properly. When if the sha computation can be done
+ // lazily this exception will go away...
+ throw new RuntimeException(e);
+ }
+ contentAttrs.put(ContentNamespace.CAPABILITY_MIME_ATTRIBUTE, "application/vnd.osgi.bundle");
+ contentAttrs.put(ContentNamespace.CAPABILITY_SIZE_ATTRIBUTE, size);
+ contentAttrs.put(ContentNamespace.CAPABILITY_URL_ATTRIBUTE, uri);
+ return new OSGiCapabilityImpl(ContentNamespace.CONTENT_NAMESPACE, contentAttrs, Collections.<String, String> emptyMap());
+ }
+
+ public InputStream getContent()
+ {
+ try
+ {
+ return new URL(resource.getURI()).openStream();
+ } catch (Exception e)
+ {
+ throw new RuntimeException(e);
+ }
+ }
+
+ public List<Requirement> getRequirements(String namespace)
+ {
+ namespace = NamespaceTranslator.getFelixNamespace(namespace);
+ org.apache.felix.bundlerepository.Requirement[] requirements = resource.getRequirements();
+ ArrayList<Requirement> result = new ArrayList<Requirement>(requirements.length);
+ for (final org.apache.felix.bundlerepository.Requirement requirement : requirements)
+ {
+ if (namespace == null || requirement.getName().equals(namespace))
+ result.add(new FelixRequirementAdapter(requirement, this));
+ }
+ result.trimToSize();
+ return result;
+ }
+
+ @Override
+ public boolean equals(Object o)
+ {
+ if (o == this)
+ return true;
+ if (!(o instanceof Resource))
+ return false;
+ Resource that = (Resource) o;
+ if (!OSGiResourceHelper.getTypeAttribute(that).equals(OSGiResourceHelper.getTypeAttribute(this)))
+ return false;
+ if (!OSGiResourceHelper.getSymbolicNameAttribute(that).equals(OSGiResourceHelper.getSymbolicNameAttribute(this)))
+ return false;
+ if (!OSGiResourceHelper.getVersionAttribute(that).equals(OSGiResourceHelper.getVersionAttribute(this)))
+ return false;
+ return true;
+ }
+
+ @Override
+ public int hashCode()
+ {
+ int result = 17;
+ result = 31 * result + OSGiResourceHelper.getTypeAttribute(this).hashCode();
+ result = 31 * result + OSGiResourceHelper.getSymbolicNameAttribute(this).hashCode();
+ result = 31 * result + OSGiResourceHelper.getVersionAttribute(this).hashCode();
+ return result;
+ }
+
+ @Override
+ public String toString()
+ {
+ Capability c = getCapabilities(IdentityNamespace.IDENTITY_NAMESPACE).iterator().next();
+ Map<String, Object> atts = c.getAttributes();
+ return new StringBuilder().append(atts.get(IdentityNamespace.IDENTITY_NAMESPACE)).append(';')
+ .append(atts.get(IdentityNamespace.CAPABILITY_VERSION_ATTRIBUTE)).append(';')
+ .append(atts.get(IdentityNamespace.CAPABILITY_TYPE_ATTRIBUTE)).toString();
+ }
+}
diff --git a/bundlerepository/src/main/java/org/apache/felix/bundlerepository/impl/LazyHashMap.java b/bundlerepository/src/main/java/org/apache/felix/bundlerepository/impl/LazyHashMap.java
new file mode 100644
index 0000000..9de95cb
--- /dev/null
+++ b/bundlerepository/src/main/java/org/apache/felix/bundlerepository/impl/LazyHashMap.java
@@ -0,0 +1,104 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.felix.bundlerepository.impl;
+
+import java.util.Collection;
+import java.util.HashMap;
+import java.util.Map;
+import java.util.concurrent.Callable;
+
+/**
+ * A map that can delay the computation of certain values up until the moment that they
+ * are actually needed. Useful for expensive to compute values such as the SHA-256.
+ * This map does <b>not</b> support {@code null} values.
+ */
+@SuppressWarnings("serial")
+public class LazyHashMap<K,V> extends HashMap<K,V> implements Map<K,V>
+{
+ private final Map<K, Callable<V>> lazyValuesMap = new HashMap<K, Callable<V>>();
+
+ /**
+ * This map behaves like a normal HashMap, expect for the entries passed in as lazy values.
+ * A lazy value is a Callable object associated with a key. When the key is looked up and it's
+ * one of the lazy values, the value will be computed at that point and stored in the map. If
+ * the value is looked up again, it will be served from the map as usual.
+ * @param lazyValues
+ */
+ public LazyHashMap(Collection<LazyValue<K,V>> lazyValues)
+ {
+ for (LazyValue<K,V> lv : lazyValues)
+ {
+ lazyValuesMap.put(lv.key, lv.callable);
+ }
+ }
+
+ @Override
+ // @SuppressWarnings("unchecked")
+ public V get(Object key)
+ {
+ V val = super.get(key);
+ if (val == null)
+ {
+ Callable<V> callable = lazyValuesMap.get(key);
+ if (callable != null)
+ {
+ // Invoke the lazy computation
+ try
+ {
+ val = callable.call();
+ if (val == null)
+ throw new NullPointerException("Lazy computed values may not be null");
+
+ // callable is defined for key, so we know key is of type K
+ @SuppressWarnings("unchecked")
+ K genericKey = (K) key;
+
+ put(genericKey, val);
+ } catch (Exception e)
+ {
+ throw new RuntimeException(e);
+ }
+ }
+ }
+ return val;
+ }
+
+ @Override
+ public V put(K key, V value)
+ {
+ // We cannot support the null value as this is an indication for lazy values that
+ // it hasn't been computed yet.
+ if (value == null)
+ throw new NullPointerException();
+
+ return super.put(key, value);
+ }
+
+ public static class LazyValue<K,V>
+ {
+ final K key;
+ final Callable<V> callable;
+
+ public LazyValue(K key, Callable<V> callable)
+ {
+ this.key = key;
+ this.callable = callable;
+ }
+ }
+}
diff --git a/bundlerepository/src/main/java/org/apache/felix/bundlerepository/impl/NamespaceTranslator.java b/bundlerepository/src/main/java/org/apache/felix/bundlerepository/impl/NamespaceTranslator.java
new file mode 100644
index 0000000..d1fa2c9
--- /dev/null
+++ b/bundlerepository/src/main/java/org/apache/felix/bundlerepository/impl/NamespaceTranslator.java
@@ -0,0 +1,66 @@
+/*
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.felix.bundlerepository.impl;
+
+import java.util.HashMap;
+import java.util.Map;
+
+import org.osgi.framework.namespace.BundleNamespace;
+import org.osgi.framework.namespace.HostNamespace;
+import org.osgi.framework.namespace.PackageNamespace;
+import org.osgi.namespace.service.ServiceNamespace;
+
+class NamespaceTranslator
+{
+ private static final Map<String, String> osgiToFelixMap = fillOSGiToFelixMap();
+ private static final Map<String, String> felixToOSGiMap = fillFelixToOSGiMap();
+
+ private static Map<String, String> fillOSGiToFelixMap()
+ {
+ Map<String, String> result = new HashMap<String, String>(4);
+ result.put(PackageNamespace.PACKAGE_NAMESPACE, org.apache.felix.bundlerepository.Capability.PACKAGE);
+ result.put(ServiceNamespace.SERVICE_NAMESPACE, org.apache.felix.bundlerepository.Capability.SERVICE);
+ result.put(BundleNamespace.BUNDLE_NAMESPACE, org.apache.felix.bundlerepository.Capability.BUNDLE);
+ result.put(HostNamespace.HOST_NAMESPACE, org.apache.felix.bundlerepository.Capability.FRAGMENT);
+ return result;
+ }
+
+ private static Map<String, String> fillFelixToOSGiMap()
+ {
+ Map<String, String> result = new HashMap<String, String>(4);
+ result.put(org.apache.felix.bundlerepository.Capability.PACKAGE, PackageNamespace.PACKAGE_NAMESPACE);
+ result.put(org.apache.felix.bundlerepository.Capability.SERVICE, ServiceNamespace.SERVICE_NAMESPACE);
+ result.put(org.apache.felix.bundlerepository.Capability.BUNDLE, BundleNamespace.BUNDLE_NAMESPACE);
+ result.put(org.apache.felix.bundlerepository.Capability.FRAGMENT, HostNamespace.HOST_NAMESPACE);
+ return result;
+ }
+
+ public static String getFelixNamespace(String osgiNamespace)
+ {
+ String result = osgiToFelixMap.get(osgiNamespace);
+ if (result == null)
+ return osgiNamespace;
+ else
+ return result;
+ }
+
+ public static String getOSGiNamespace(String felixNamespace)
+ {
+ String result = felixToOSGiMap.get(felixNamespace);
+ if (result == null)
+ return felixNamespace;
+ else
+ return result;
+ }
+}
diff --git a/bundlerepository/src/main/java/org/apache/felix/bundlerepository/impl/OSGiCapabilityAdapter.java b/bundlerepository/src/main/java/org/apache/felix/bundlerepository/impl/OSGiCapabilityAdapter.java
new file mode 100644
index 0000000..21eb02a
--- /dev/null
+++ b/bundlerepository/src/main/java/org/apache/felix/bundlerepository/impl/OSGiCapabilityAdapter.java
@@ -0,0 +1,132 @@
+/*
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.felix.bundlerepository.impl;
+
+import java.util.ArrayList;
+import java.util.Collection;
+import java.util.HashMap;
+import java.util.HashSet;
+import java.util.List;
+import java.util.Map;
+import java.util.Set;
+
+import org.apache.felix.bundlerepository.Capability;
+import org.apache.felix.bundlerepository.Property;
+import org.osgi.framework.Version;
+
+public class OSGiCapabilityAdapter implements Capability
+{
+ private final org.osgi.resource.Capability capability;
+
+ public OSGiCapabilityAdapter(org.osgi.resource.Capability capability)
+ {
+ this.capability = capability;
+ }
+
+ @Override
+ public boolean equals(Object o)
+ {
+ return capability.equals(o);
+ }
+
+ public String getName()
+ {
+ return NamespaceTranslator.getFelixNamespace(capability.getNamespace());
+ }
+
+ public Property[] getProperties()
+ {
+ Map<String, Object> attributes = capability.getAttributes();
+ Collection<Property> result = new ArrayList<Property>(attributes.size());
+ for (final Map.Entry<String, Object> entry : capability.getAttributes().entrySet())
+ {
+ if (entry.getKey().equals(capability.getNamespace()))
+ {
+ result.add(new FelixProperty(getName(), entry.getValue()));
+ continue;
+ }
+ result.add(new FelixProperty(entry));
+ }
+ return result.toArray(new Property[result.size()]);
+ }
+
+ public Map<String, Object> getPropertiesAsMap()
+ {
+ Map<String, Object> result = new HashMap<String, Object>(capability.getAttributes());
+ result.put(getName(), result.get(capability.getNamespace()));
+ return result;
+ }
+
+ @Override
+ public int hashCode()
+ {
+ return capability.hashCode();
+ }
+
+ static class FelixProperty implements Property
+ {
+ private static Set<?> asSet(List<?> list)
+ {
+ return new HashSet<Object>(list);
+ }
+
+ private final String name;
+ private final Object value;
+
+ public FelixProperty(String name, Object value)
+ {
+ if (name == null)
+ throw new NullPointerException("Missing required parameter: name");
+ if (value == null)
+ throw new NullPointerException("Missing required parameter: value");
+ this.name = name;
+ this.value = value;
+ }
+
+ public FelixProperty(Map.Entry<String, Object> entry)
+ {
+ this(entry.getKey(), entry.getValue());
+ }
+
+ public Object getConvertedValue()
+ {
+ if (value instanceof List)
+ return asSet((List<?>) value);
+ return value;
+ }
+
+ public String getName()
+ {
+ return name;
+ }
+
+ public String getType()
+ {
+ if (value instanceof Version)
+ return Property.VERSION;
+ if (value instanceof Long)
+ return Property.LONG;
+ if (value instanceof Double)
+ return Property.DOUBLE;
+ if (value instanceof List<?>)
+ return Property.SET;
+ return null;
+ }
+
+ public String getValue()
+ {
+ return String.valueOf(value);
+ }
+ }
+}
diff --git a/bundlerepository/src/main/java/org/apache/felix/bundlerepository/impl/OSGiCapabilityImpl.java b/bundlerepository/src/main/java/org/apache/felix/bundlerepository/impl/OSGiCapabilityImpl.java
new file mode 100644
index 0000000..655861c
--- /dev/null
+++ b/bundlerepository/src/main/java/org/apache/felix/bundlerepository/impl/OSGiCapabilityImpl.java
@@ -0,0 +1,71 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.felix.bundlerepository.impl;
+
+import java.util.Collections;
+import java.util.Map;
+
+import org.osgi.resource.Capability;
+import org.osgi.resource.Resource;
+
+class OSGiCapabilityImpl implements Capability
+{
+ private final String namespace;
+ private final Map<String, Object> attributes;
+ private final Map<String, String> directives;
+ private Resource resource;
+
+ OSGiCapabilityImpl(String ns, Map<String, Object> attrs, Map<String, String> dirs)
+ {
+ this(ns, attrs, dirs, null);
+ }
+
+ OSGiCapabilityImpl(String ns, Map<String, Object> attrs, Map<String, String> dirs, Resource res)
+ {
+ namespace = ns;
+ attributes = Collections.unmodifiableMap(attrs);
+ directives = Collections.unmodifiableMap(dirs);
+ resource = res;
+ }
+
+ public String getNamespace()
+ {
+ return namespace;
+ }
+
+ public Map<String, Object> getAttributes()
+ {
+ return attributes;
+ }
+
+ public Map<String, String> getDirectives()
+ {
+ return directives;
+ }
+
+ public Resource getResource()
+ {
+ return resource;
+ }
+
+ void setResource(Resource res)
+ {
+ resource = res;
+ }
+}
diff --git a/bundlerepository/src/main/java/org/apache/felix/bundlerepository/impl/OSGiRepositoryImpl.java b/bundlerepository/src/main/java/org/apache/felix/bundlerepository/impl/OSGiRepositoryImpl.java
new file mode 100644
index 0000000..ca7500a
--- /dev/null
+++ b/bundlerepository/src/main/java/org/apache/felix/bundlerepository/impl/OSGiRepositoryImpl.java
@@ -0,0 +1,176 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.felix.bundlerepository.impl;
+
+import java.io.IOException;
+import java.io.InputStream;
+import java.net.URL;
+import java.security.DigestInputStream;
+import java.security.MessageDigest;
+import java.security.NoSuchAlgorithmException;
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.Collection;
+import java.util.Collections;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+import java.util.concurrent.Callable;
+
+import org.apache.felix.bundlerepository.RepositoryAdmin;
+import org.apache.felix.bundlerepository.impl.LazyHashMap.LazyValue;
+import org.osgi.framework.Filter;
+import org.osgi.framework.FrameworkUtil;
+import org.osgi.framework.namespace.IdentityNamespace;
+import org.osgi.resource.Capability;
+import org.osgi.resource.Namespace;
+import org.osgi.resource.Requirement;
+import org.osgi.resource.Resource;
+import org.osgi.service.repository.ContentNamespace;
+import org.osgi.service.repository.Repository;
+
+public class OSGiRepositoryImpl implements Repository
+{
+ private final RepositoryAdmin repository;
+
+ OSGiRepositoryImpl(RepositoryAdmin repository)
+ {
+ this.repository = repository;
+ }
+
+ public Map<Requirement, Collection<Capability>> findProviders(Collection<? extends Requirement> requirements)
+ {
+ Map<Requirement, Collection<Capability>> m = new HashMap<Requirement, Collection<Capability>>();
+ for (Requirement r : requirements)
+ {
+ m.put(r, findProviders(r));
+ }
+ return m;
+ }
+
+ private Collection<Capability> findProviders(Requirement req)
+ {
+ List<Capability> caps = new ArrayList<Capability>();
+ if (IdentityNamespace.IDENTITY_NAMESPACE.equals(req.getNamespace()))
+ {
+ for(org.apache.felix.bundlerepository.Repository repo : repository.listRepositories())
+ {
+ for (org.apache.felix.bundlerepository.Resource res : repo.getResources())
+ {
+ String f = req.getDirectives().get(Namespace.REQUIREMENT_FILTER_DIRECTIVE);
+ try
+ {
+ addResourceForIdentity(res,
+ f == null ? null : FrameworkUtil.createFilter(f), caps);
+ }
+ catch (Exception e)
+ {
+ throw new RuntimeException(e);
+ }
+ }
+ }
+ }
+ else
+ {
+ org.apache.felix.bundlerepository.Resource[] resources = repository.discoverResources(
+ new org.apache.felix.bundlerepository.Requirement[] {new OSGiRequirementAdapter(req)});
+ OSGiRequirementAdapter adapter = new OSGiRequirementAdapter(req);
+ for (org.apache.felix.bundlerepository.Resource resource : resources)
+ {
+ for (org.apache.felix.bundlerepository.Capability cap : resource.getCapabilities())
+ {
+ if (adapter.isSatisfied(cap))
+ caps.add(new FelixCapabilityAdapter(cap, new FelixResourceAdapter(resource)));
+ }
+ }
+ }
+
+ return caps;
+ }
+
+ private void addResourceForIdentity(final org.apache.felix.bundlerepository.Resource res, Filter filter, List<Capability> caps)
+ throws Exception
+ {
+ Map<String, Object> idAttrs = new HashMap<String, Object>();
+ idAttrs.put(IdentityNamespace.IDENTITY_NAMESPACE, res.getSymbolicName());
+ Object type = res.getProperties().get(IdentityNamespace.CAPABILITY_TYPE_ATTRIBUTE);
+ idAttrs.put(IdentityNamespace.CAPABILITY_TYPE_ATTRIBUTE,
+ type != null ? type.toString() : IdentityNamespace.TYPE_BUNDLE);
+ idAttrs.put(IdentityNamespace.CAPABILITY_VERSION_ATTRIBUTE, res.getVersion());
+
+ if (filter != null)
+ {
+ if (!filter.matches(idAttrs))
+ return;
+ }
+
+ OSGiCapabilityImpl idCap = new OSGiCapabilityImpl(IdentityNamespace.IDENTITY_NAMESPACE, idAttrs,
+ Collections.<String, String>emptyMap());
+
+ LazyValue<String, Object> lazyValue = new LazyHashMap.LazyValue<String, Object>(ContentNamespace.CONTENT_NAMESPACE,
+ new Callable<Object>()
+ {
+ public Object call() throws Exception
+ {
+ // This is expensive to compute, so only do it if we need it...
+ return getSHA256(res.getURI());
+ }
+ });
+ Map<String, Object> contentAttrs = new LazyHashMap<String, Object>(Collections.singleton(lazyValue));
+ contentAttrs.put(ContentNamespace.CAPABILITY_MIME_ATTRIBUTE, "application/vnd.osgi.bundle");
+ contentAttrs.put(ContentNamespace.CAPABILITY_SIZE_ATTRIBUTE, res.getSize());
+ contentAttrs.put(ContentNamespace.CAPABILITY_URL_ATTRIBUTE, res.getURI());
+ OSGiCapabilityImpl contentCap = new OSGiCapabilityImpl(ContentNamespace.CONTENT_NAMESPACE, contentAttrs,
+ Collections.<String, String>emptyMap());
+
+ List<OSGiCapabilityImpl> capabilities = Arrays.<OSGiCapabilityImpl>asList(idCap, contentCap);
+ Resource resource =
+ new OSGiResourceImpl(capabilities, Collections.<Requirement>emptyList());
+
+ for (OSGiCapabilityImpl c : capabilities)
+ {
+ c.setResource(resource);
+ }
+
+ caps.add(idCap);
+ }
+
+ static String getSHA256(String uri) throws IOException, NoSuchAlgorithmException // TODO find a good place for this
+ {
+ InputStream is = new URL(uri).openStream();
+ MessageDigest md = MessageDigest.getInstance("SHA-256");
+
+ // Use a digest inputstream as using byte arrays directly to compute the SHA-256 can
+ // have big effects on memory consumption. I.e. you don't want to have to read the
+ // entire resource in memory. We rather stream it through...
+ DigestInputStream dis = new DigestInputStream(is, md);
+
+ byte[] buffer = new byte[16384];
+ while (dis.read(buffer) != -1) {
+ // we just drain the stream here to compute the Message Digest
+ }
+
+ StringBuilder sb = new StringBuilder(64); // SHA-256 is always 64 hex characters
+ for (byte b : md.digest())
+ {
+ sb.append(String.format("%02x", b));
+ }
+ return sb.toString();
+ }
+}
diff --git a/bundlerepository/src/main/java/org/apache/felix/bundlerepository/impl/OSGiRequirementAdapter.java b/bundlerepository/src/main/java/org/apache/felix/bundlerepository/impl/OSGiRequirementAdapter.java
new file mode 100644
index 0000000..19670f5
--- /dev/null
+++ b/bundlerepository/src/main/java/org/apache/felix/bundlerepository/impl/OSGiRequirementAdapter.java
@@ -0,0 +1,67 @@
+/*
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.felix.bundlerepository.impl;
+
+import org.apache.felix.bundlerepository.Capability;
+import org.apache.felix.bundlerepository.Requirement;
+import org.osgi.framework.Constants;
+import org.osgi.resource.Namespace;
+
+class OSGiRequirementAdapter implements Requirement
+{
+ private final org.osgi.resource.Requirement requirement;
+
+ public OSGiRequirementAdapter(org.osgi.resource.Requirement requirement)
+ {
+ this.requirement = requirement;
+ }
+
+ public String getComment()
+ {
+ return null;
+ }
+
+ public String getFilter()
+ {
+ return requirement.getDirectives().get(Constants.FILTER_DIRECTIVE);
+ }
+
+ public String getName()
+ {
+ return NamespaceTranslator.getFelixNamespace(requirement.getNamespace());
+ }
+
+ public boolean isExtend()
+ {
+ return false;
+ }
+
+ public boolean isMultiple()
+ {
+ String multiple = requirement.getDirectives().get(Namespace.REQUIREMENT_CARDINALITY_DIRECTIVE);
+ return Namespace.CARDINALITY_MULTIPLE.equals(multiple);
+ }
+
+ public boolean isOptional()
+ {
+ String resolution = requirement.getDirectives().get(Constants.RESOLUTION_DIRECTIVE);
+ return Constants.RESOLUTION_OPTIONAL.equals(resolution);
+ }
+
+ public boolean isSatisfied(Capability capability)
+ {
+ boolean result = OSGiResourceHelper.matches(requirement, new FelixCapabilityAdapter(capability, null));
+ return result;
+ }
+}
diff --git a/bundlerepository/src/main/java/org/apache/felix/bundlerepository/impl/OSGiRequirementImpl.java b/bundlerepository/src/main/java/org/apache/felix/bundlerepository/impl/OSGiRequirementImpl.java
new file mode 100644
index 0000000..c00aa31
--- /dev/null
+++ b/bundlerepository/src/main/java/org/apache/felix/bundlerepository/impl/OSGiRequirementImpl.java
@@ -0,0 +1,67 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.felix.bundlerepository.impl;
+
+import java.util.Collections;
+import java.util.Map;
+
+import org.osgi.resource.Namespace;
+import org.osgi.resource.Requirement;
+import org.osgi.resource.Resource;
+
+class OSGiRequirementImpl implements Requirement
+{
+ private final String namespace;
+ private final Map<String, Object> attributes;
+ private final Map<String, String> directives;
+
+ OSGiRequirementImpl(String ns, String filter)
+ {
+ this(ns, Collections.<String, Object>emptyMap(),
+ filter == null ? Collections.<String, String> emptyMap() :
+ Collections.singletonMap(Namespace.REQUIREMENT_FILTER_DIRECTIVE, filter));
+ }
+
+ OSGiRequirementImpl(String ns, Map<String, Object> attrs, Map<String, String> dirs)
+ {
+ namespace = ns;
+ attributes = attrs;
+ directives = dirs;
+ }
+
+ public String getNamespace()
+ {
+ return namespace;
+ }
+
+ public Map<String, Object> getAttributes()
+ {
+ return Collections.unmodifiableMap(attributes);
+ }
+
+ public Map<String, String> getDirectives()
+ {
+ return Collections.unmodifiableMap(directives);
+ }
+
+ public Resource getResource()
+ {
+ return null;
+ }
+}
diff --git a/bundlerepository/src/main/java/org/apache/felix/bundlerepository/impl/OSGiResourceHelper.java b/bundlerepository/src/main/java/org/apache/felix/bundlerepository/impl/OSGiResourceHelper.java
new file mode 100644
index 0000000..6d560d6
--- /dev/null
+++ b/bundlerepository/src/main/java/org/apache/felix/bundlerepository/impl/OSGiResourceHelper.java
@@ -0,0 +1,111 @@
+/*
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.felix.bundlerepository.impl;
+
+import java.util.Arrays;
+import java.util.Collection;
+import java.util.List;
+import java.util.Map;
+
+import org.apache.felix.utils.filter.FilterImpl;
+import org.osgi.framework.Constants;
+import org.osgi.framework.InvalidSyntaxException;
+import org.osgi.framework.Version;
+import org.osgi.framework.namespace.IdentityNamespace;
+import org.osgi.resource.Capability;
+import org.osgi.resource.Requirement;
+import org.osgi.resource.Resource;
+import org.osgi.service.repository.ContentNamespace;
+import org.osgi.service.repository.Repository;
+
+public class OSGiResourceHelper
+{
+ public static String getContentAttribute(Resource resource)
+ {
+ return (String) getContentAttribute(resource, ContentNamespace.CONTENT_NAMESPACE);
+ }
+
+ public static Object getContentAttribute(Resource resource, String name)
+ {
+ List<Capability> capabilities = resource.getCapabilities(ContentNamespace.CONTENT_NAMESPACE);
+ Capability capability = capabilities.get(0);
+ return capability.getAttributes().get(name);
+ }
+
+ public static Object getIdentityAttribute(Resource resource, String name)
+ {
+ List<Capability> capabilities = resource.getCapabilities(IdentityNamespace.IDENTITY_NAMESPACE);
+ Capability capability = capabilities.get(0);
+ return capability.getAttributes().get(name);
+ }
+
+ public static Resource getResource(Requirement requirement, Repository repository)
+ {
+ Map<Requirement, Collection<Capability>> map = repository.findProviders(Arrays.asList(requirement));
+ Collection<Capability> capabilities = map.get(requirement);
+ return capabilities == null ? null : capabilities.size() == 0 ? null : capabilities.iterator().next().getResource();
+ }
+
+ public static String getSymbolicNameAttribute(Resource resource)
+ {
+ return (String) getIdentityAttribute(resource, IdentityNamespace.IDENTITY_NAMESPACE);
+ }
+
+ public static String getTypeAttribute(Resource resource)
+ {
+ String result = (String) getIdentityAttribute(resource, IdentityNamespace.CAPABILITY_TYPE_ATTRIBUTE);
+ if (result == null)
+ result = IdentityNamespace.TYPE_BUNDLE;
+ return result;
+ }
+
+ public static Version getVersionAttribute(Resource resource)
+ {
+ Version result = (Version) getIdentityAttribute(resource, IdentityNamespace.CAPABILITY_VERSION_ATTRIBUTE);
+ if (result == null)
+ result = Version.emptyVersion;
+ return result;
+ }
+
+ public static boolean matches(Requirement requirement, Capability capability)
+ {
+ boolean result = false;
+ if (requirement == null && capability == null)
+ result = true;
+ else if (requirement == null || capability == null)
+ result = false;
+ else if (!capability.getNamespace().equals(requirement.getNamespace()))
+ result = false;
+ else
+ {
+ String filterStr = requirement.getDirectives().get(Constants.FILTER_DIRECTIVE);
+ if (filterStr == null)
+ result = true;
+ else
+ {
+ try
+ {
+ if (FilterImpl.newInstance(filterStr).matchCase(capability.getAttributes()))
+ result = true;
+ }
+ catch (InvalidSyntaxException e)
+ {
+ result = false;
+ }
+ }
+ }
+ // TODO Check directives.
+ return result;
+ }
+}
diff --git a/bundlerepository/src/main/java/org/apache/felix/bundlerepository/impl/OSGiResourceImpl.java b/bundlerepository/src/main/java/org/apache/felix/bundlerepository/impl/OSGiResourceImpl.java
new file mode 100644
index 0000000..2b4de89
--- /dev/null
+++ b/bundlerepository/src/main/java/org/apache/felix/bundlerepository/impl/OSGiResourceImpl.java
@@ -0,0 +1,73 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.felix.bundlerepository.impl;
+
+import java.util.ArrayList;
+import java.util.List;
+
+import org.osgi.resource.Capability;
+import org.osgi.resource.Requirement;
+import org.osgi.resource.Resource;
+
+public class OSGiResourceImpl implements Resource
+{
+ private final List<Capability> capabilities;
+ private final List<Requirement> requirements;
+
+ @SuppressWarnings("unchecked")
+ public OSGiResourceImpl(List<? extends Capability> caps, List<? extends Requirement> reqs)
+ {
+ capabilities = (List<Capability>) caps;
+ requirements = (List<Requirement>) reqs;
+ }
+
+ public List<Capability> getCapabilities(String namespace)
+ {
+ if (namespace == null)
+ return capabilities;
+
+ List<Capability> caps = new ArrayList<Capability>();
+ for(Capability cap : capabilities)
+ {
+ if (namespace.equals(cap.getNamespace()))
+ {
+ caps.add(cap);
+ }
+ }
+ return caps;
+ }
+
+ public List<Requirement> getRequirements(String namespace)
+ {
+ if (namespace == null)
+ return requirements;
+
+ List<Requirement> reqs = new ArrayList<Requirement>();
+ for(Requirement req : requirements)
+ {
+ if (namespace.equals(req.getNamespace()))
+ {
+ reqs.add(req);
+ }
+ }
+ return reqs;
+ }
+
+ // TODO implement equals and hashcode
+}
diff --git a/bundlerepository/src/main/java/org/apache/felix/bundlerepository/impl/PullParser.java b/bundlerepository/src/main/java/org/apache/felix/bundlerepository/impl/PullParser.java
index 09749f1..a187133 100644
--- a/bundlerepository/src/main/java/org/apache/felix/bundlerepository/impl/PullParser.java
+++ b/bundlerepository/src/main/java/org/apache/felix/bundlerepository/impl/PullParser.java
@@ -39,18 +39,32 @@
public RepositoryImpl parseRepository(InputStream is) throws Exception
{
XmlPullParser reader = new KXmlParser();
+
+ // The spec-based Repository XML uses namespaces, so switch this on...
+ reader.setFeature(XmlPullParser.FEATURE_PROCESS_NAMESPACES, true);
+
reader.setInput(is, null);
int event = reader.nextTag();
if (event != XmlPullParser.START_TAG || !REPOSITORY.equals(reader.getName()))
{
throw new Exception("Expected element 'repository' at the root of the document");
}
- return parse(reader);
+
+ if ("http://www.osgi.org/xmlns/repository/v1.0.0".equals(reader.getNamespace()))
+ // TODO there are a bunch of other methods here that create a parser, should they be updated too?
+ // at the very least they should be made namespace-aware too, so that parsing is the same no matter
+ // how its initiated.
+ return SpecXMLPullParser.parse(reader);
+ else
+ // We're parsing the old
+ return parse(reader);
}
public RepositoryImpl parseRepository(Reader r) throws Exception
{
XmlPullParser reader = new KXmlParser();
+ reader.setFeature(XmlPullParser.FEATURE_PROCESS_NAMESPACES, true);
+
reader.setInput(r);
int event = reader.nextTag();
if (event != XmlPullParser.START_TAG || !REPOSITORY.equals(reader.getName()))
@@ -63,6 +77,8 @@
public ResourceImpl parseResource(Reader r) throws Exception
{
XmlPullParser reader = new KXmlParser();
+ reader.setFeature(XmlPullParser.FEATURE_PROCESS_NAMESPACES, true);
+
reader.setInput(r);
int event = reader.nextTag();
if (event != XmlPullParser.START_TAG || !RESOURCE.equals(reader.getName()))
@@ -75,6 +91,8 @@
public CapabilityImpl parseCapability(Reader r) throws Exception
{
XmlPullParser reader = new KXmlParser();
+ reader.setFeature(XmlPullParser.FEATURE_PROCESS_NAMESPACES, true);
+
reader.setInput(r);
int event = reader.nextTag();
if (event != XmlPullParser.START_TAG || !CAPABILITY.equals(reader.getName()))
@@ -87,6 +105,8 @@
public PropertyImpl parseProperty(Reader r) throws Exception
{
XmlPullParser reader = new KXmlParser();
+ reader.setFeature(XmlPullParser.FEATURE_PROCESS_NAMESPACES, true);
+
reader.setInput(r);
int event = reader.nextTag();
if (event != XmlPullParser.START_TAG || !P.equals(reader.getName()))
@@ -99,6 +119,8 @@
public RequirementImpl parseRequirement(Reader r) throws Exception
{
XmlPullParser reader = new KXmlParser();
+ reader.setFeature(XmlPullParser.FEATURE_PROCESS_NAMESPACES, true);
+
reader.setInput(r);
int event = reader.nextTag();
if (event != XmlPullParser.START_TAG || !REQUIRE.equals(reader.getName()))
@@ -148,7 +170,7 @@
return repository;
}
- private void sanityCheckEndElement(XmlPullParser reader, int event, String element)
+ static void sanityCheckEndElement(XmlPullParser reader, int event, String element)
{
if (event != XmlPullParser.END_TAG || !element.equals(reader.getName()))
{
@@ -367,7 +389,7 @@
return requirement;
}
- public void ignoreTag(XmlPullParser reader) throws IOException, XmlPullParserException {
+ static void ignoreTag(XmlPullParser reader) throws IOException, XmlPullParserException {
int level = 1;
while (level > 0)
{
diff --git a/bundlerepository/src/main/java/org/apache/felix/bundlerepository/impl/ResolverImpl.java b/bundlerepository/src/main/java/org/apache/felix/bundlerepository/impl/ResolverImpl.java
index 1671900..3245b09 100644
--- a/bundlerepository/src/main/java/org/apache/felix/bundlerepository/impl/ResolverImpl.java
+++ b/bundlerepository/src/main/java/org/apache/felix/bundlerepository/impl/ResolverImpl.java
@@ -19,13 +19,27 @@
package org.apache.felix.bundlerepository.impl;
import java.net.URL;
-import java.util.*;
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.HashMap;
+import java.util.HashSet;
+import java.util.Iterator;
+import java.util.List;
+import java.util.Map;
+import java.util.Set;
-import org.apache.felix.bundlerepository.*;
+import org.apache.felix.bundlerepository.Capability;
+import org.apache.felix.bundlerepository.Reason;
+import org.apache.felix.bundlerepository.Repository;
+import org.apache.felix.bundlerepository.Requirement;
import org.apache.felix.bundlerepository.Resolver;
-import org.apache.felix.bundlerepository.impl.ResourceImpl;
+import org.apache.felix.bundlerepository.Resource;
import org.apache.felix.utils.log.Logger;
-import org.osgi.framework.*;
+import org.osgi.framework.Bundle;
+import org.osgi.framework.BundleContext;
+import org.osgi.framework.BundleException;
+import org.osgi.framework.Constants;
+import org.osgi.framework.Version;
public class ResolverImpl implements Resolver
{
@@ -446,7 +460,7 @@
{
// If there is no best version or if the current
// resource's version is lower, then select it.
- if ((bestVersion == null) || (bestVersion.compareTo(v) < 0))
+ if ((bestVersion == null) || (bestVersion.compareTo((Version) v) < 0))
{
best = current;
bestLocal = isCurrentLocal;
@@ -454,7 +468,7 @@
}
// If the current resource version is equal to the
// best
- else if ((bestVersion != null) && (bestVersion.compareTo(v) == 0))
+ else if ((bestVersion != null) && (bestVersion.compareTo((Version) v) == 0))
{
// If the symbolic name is the same, use the highest
// bundle version.
@@ -789,7 +803,7 @@
public static String getBundleName(Bundle bundle)
{
- String name = (String) bundle.getHeaders().get(Constants.BUNDLE_NAME);
+ String name = bundle.getHeaders().get(Constants.BUNDLE_NAME);
return (name == null)
? "Bundle " + Long.toString(bundle.getBundleId())
: name;
diff --git a/bundlerepository/src/main/java/org/apache/felix/bundlerepository/impl/SpecXMLPullParser.java b/bundlerepository/src/main/java/org/apache/felix/bundlerepository/impl/SpecXMLPullParser.java
new file mode 100644
index 0000000..295f083
--- /dev/null
+++ b/bundlerepository/src/main/java/org/apache/felix/bundlerepository/impl/SpecXMLPullParser.java
@@ -0,0 +1,240 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.felix.bundlerepository.impl;
+
+import java.io.IOException;
+import java.util.HashMap;
+import java.util.Map;
+
+import org.apache.felix.bundlerepository.Capability;
+import org.apache.felix.bundlerepository.Requirement;
+import org.apache.felix.bundlerepository.Resource;
+import org.osgi.framework.namespace.IdentityNamespace;
+import org.osgi.resource.Namespace;
+import org.osgi.service.repository.ContentNamespace;
+import org.xmlpull.v1.XmlPullParser;
+import org.xmlpull.v1.XmlPullParserException;
+
+public class SpecXMLPullParser
+{
+ private static final String ATTRIBUTE = "attribute";
+ private static final String CAPABILITY = "capability";
+ private static final String DIRECTIVE = "directive";
+ private static final String INCREMENT = "increment";
+ private static final String NAME = "name";
+ private static final String NAMESPACE = "namespace";
+ private static final String REFERRAL = "referral";
+ private static final String REPOSITORY = "repository";
+ private static final String REQUIREMENT = "requirement";
+ private static final String RESOURCE = "resource";
+
+ public static RepositoryImpl parse(XmlPullParser reader) throws Exception
+ {
+ RepositoryImpl repository = new RepositoryImpl();
+
+ for (int i = 0, ac = reader.getAttributeCount(); i < ac; i++)
+ {
+ String name = reader.getAttributeName(i);
+ String value = reader.getAttributeValue(i);
+ if (NAME.equals(name))
+ repository.setName(value);
+ else if (INCREMENT.equals(name))
+ repository.setLastModified(value); // TODO increment is not necessarily a timestamp
+ }
+
+ int event;
+ while ((event = reader.nextTag()) == XmlPullParser.START_TAG)
+ {
+ String element = reader.getName();
+ if (REFERRAL.equals(element))
+ {
+ // TODO
+ }
+ else if (RESOURCE.equals(element))
+ {
+ Resource resource = parseResource(reader);
+ repository.addResource(resource);
+ }
+ else
+ {
+ PullParser.ignoreTag(reader);
+ }
+ }
+
+ PullParser.sanityCheckEndElement(reader, event, REPOSITORY);
+ return repository;
+ }
+
+ private static Resource parseResource(XmlPullParser reader) throws Exception
+ {
+ ResourceImpl resource = new ResourceImpl();
+ try
+ {
+ int event;
+ while ((event = reader.nextTag()) == XmlPullParser.START_TAG)
+ {
+ String element = reader.getName();
+ if (CAPABILITY.equals(element))
+ {
+ Capability capability = parseCapability(reader, resource);
+ if (capability != null)
+ resource.addCapability(capability);
+ }
+ else if (REQUIREMENT.equals(element))
+ {
+ Requirement requirement = parseRequirement(reader);
+ resource.addRequire(requirement);
+ }
+ else
+ {
+ PullParser.ignoreTag(reader);
+ }
+ }
+
+ PullParser.sanityCheckEndElement(reader, event, RESOURCE);
+ return resource;
+ }
+ catch (Exception e)
+ {
+ throw new Exception("Error while parsing resource " + resource.getId() + " at line " + reader.getLineNumber() + " and column " + reader.getColumnNumber(), e);
+ }
+ }
+
+ private static Capability parseCapability(XmlPullParser reader, ResourceImpl resource) throws Exception
+ {
+ String namespace = reader.getAttributeValue(null, NAMESPACE);
+ if (IdentityNamespace.IDENTITY_NAMESPACE.equals(namespace))
+ {
+ parseIdentityNamespace(reader, resource);
+ return null;
+ }
+ if (ContentNamespace.CONTENT_NAMESPACE.equals(namespace))
+ {
+ parseContentNamespace(reader, resource);
+ return null;
+ }
+
+ CapabilityImpl capability = new CapabilityImpl();
+ if (!namespace.equals(NamespaceTranslator.getOSGiNamespace(namespace)))
+ throw new Exception("Namespace conflict. Namespace not allowed: " + namespace);
+
+ capability.setName(NamespaceTranslator.getFelixNamespace(namespace));
+ Map<String, Object> attributes = new HashMap<String, Object>();
+ parseAttributesDirectives(reader, attributes, CAPABILITY);
+
+ for (Map.Entry<String, Object> entry : attributes.entrySet())
+ {
+ capability.addProperty(entry.getKey(), "" + entry.getValue()); // TODO handle non-string data types
+ }
+
+ return capability;
+ }
+
+ private static void parseIdentityNamespace(XmlPullParser reader, ResourceImpl resource) throws Exception
+ {
+ Map<String, Object> attributes = new HashMap<String, Object>();
+ parseAttributesDirectives(reader, attributes, CAPABILITY);
+
+ for (Map.Entry<String, Object> entry : attributes.entrySet())
+ {
+ if (IdentityNamespace.IDENTITY_NAMESPACE.equals(entry.getKey()))
+ resource.put(Resource.SYMBOLIC_NAME, entry.getValue());
+ else
+ resource.put(entry.getKey(), entry.getValue());
+ }
+ }
+
+ private static void parseContentNamespace(XmlPullParser reader, ResourceImpl resource) throws Exception
+ {
+ Map<String, Object> attributes = new HashMap<String, Object>();
+ parseAttributesDirectives(reader, attributes, CAPABILITY);
+
+ for (Map.Entry<String, Object> entry : attributes.entrySet())
+ {
+ if (ContentNamespace.CONTENT_NAMESPACE.equals(entry.getKey()))
+ // TODO we should really check the SHA
+ continue;
+ else if (ContentNamespace.CAPABILITY_URL_ATTRIBUTE.equals(entry.getKey()))
+ resource.put(Resource.URI, entry.getValue());
+ else
+ resource.put(entry.getKey(), entry.getValue());
+ }
+ }
+
+ private static void parseAttributesDirectives(XmlPullParser reader, Map<String, Object> attributes, String parentTag) throws XmlPullParserException, IOException
+ {
+ int event;
+ while ((event = reader.nextTag()) == XmlPullParser.START_TAG)
+ {
+ String element = reader.getName();
+ if (ATTRIBUTE.equals(element))
+ {
+ String name = reader.getAttributeValue(null, "name");
+ String type = reader.getAttributeValue(null, "type"); // TODO handle
+ String value = reader.getAttributeValue(null, "value");
+ attributes.put(name, value);
+ PullParser.sanityCheckEndElement(reader, reader.nextTag(), ATTRIBUTE);
+ }
+ else
+ {
+ PullParser.ignoreTag(reader);
+ }
+ }
+ PullParser.sanityCheckEndElement(reader, event, parentTag);
+ }
+
+ private static Requirement parseRequirement(XmlPullParser reader) throws Exception
+ {
+ RequirementImpl requirement = new RequirementImpl();
+ String namespace = reader.getAttributeValue(null, NAMESPACE);
+ if (!namespace.equals(NamespaceTranslator.getOSGiNamespace(namespace)))
+ throw new Exception("Namespace conflict. Namespace not allowed: " + namespace);
+
+ requirement.setName(NamespaceTranslator.getFelixNamespace(namespace));
+
+ Map<String, String> directives = new HashMap<String, String>();
+ int event;
+ while ((event = reader.nextTag()) == XmlPullParser.START_TAG)
+ {
+ String element = reader.getName();
+ if (DIRECTIVE.equals(element))
+ {
+ String name = reader.getAttributeValue(null, "name");
+ String value = reader.getAttributeValue(null, "value");
+ directives.put(name, value);
+ PullParser.sanityCheckEndElement(reader, reader.nextTag(), DIRECTIVE);
+ }
+ else
+ {
+ PullParser.ignoreTag(reader);
+ }
+ }
+
+ requirement.setExtend(false);
+ // TODO transform the namespaces in the filter!
+ requirement.setFilter(directives.get(Namespace.REQUIREMENT_FILTER_DIRECTIVE));
+ requirement.setMultiple(Namespace.CARDINALITY_MULTIPLE.equals(
+ directives.get(Namespace.REQUIREMENT_CARDINALITY_DIRECTIVE)));
+ requirement.setOptional(Namespace.RESOLUTION_OPTIONAL.equals(
+ directives.get(Namespace.REQUIREMENT_RESOLUTION_DIRECTIVE)));
+
+ PullParser.sanityCheckEndElement(reader, event, REQUIREMENT);
+ return requirement;
+ }
+}
diff --git a/bundlerepository/src/test/java/org/apache/felix/bundlerepository/impl/LazyHashMapTest.java b/bundlerepository/src/test/java/org/apache/felix/bundlerepository/impl/LazyHashMapTest.java
new file mode 100644
index 0000000..285615c
--- /dev/null
+++ b/bundlerepository/src/test/java/org/apache/felix/bundlerepository/impl/LazyHashMapTest.java
@@ -0,0 +1,74 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.felix.bundlerepository.impl;
+
+import java.util.ArrayList;
+import java.util.Collection;
+import java.util.HashMap;
+import java.util.concurrent.Callable;
+import java.util.concurrent.atomic.AtomicInteger;
+
+import junit.framework.TestCase;
+
+import org.apache.felix.bundlerepository.impl.LazyHashMap.LazyValue;
+
+public class LazyHashMapTest extends TestCase
+{
+ public void testLazyHashMap() {
+ final AtomicInteger lv1Computed = new AtomicInteger(0);
+ LazyValue<String, Long> lv1 = new LazyValue<String, Long>("42", new Callable<Long>()
+ {
+ public Long call() throws Exception
+ {
+ lv1Computed.incrementAndGet();
+ return 24L;
+ }
+ });
+
+ final AtomicInteger lv2Computed = new AtomicInteger(0);
+ LazyValue<String, Long> lv2 = new LazyValue<String, Long>("zero", new Callable<Long>()
+ {
+ public Long call() throws Exception
+ {
+ lv2Computed.incrementAndGet();
+ return 0L;
+ }
+ });
+
+ Collection<LazyValue<String, Long>> lazyValues = new ArrayList<LazyHashMap.LazyValue<String,Long>>();
+ lazyValues.add(lv1);
+ lazyValues.add(lv2);
+ HashMap<String, Long> lhm = new LazyHashMap<String, Long>(lazyValues);
+ lhm.put("1", 2L);
+
+ assertEquals(new Long(2L), lhm.get("1"));
+ assertEquals("No computation should have happened yet", 0, lv1Computed.get());
+ assertEquals("No computation should have happened yet", 0, lv2Computed.get());
+
+ assertEquals(new Long(24L), lhm.get("42"));
+ assertEquals("lv1 should have been computed", 1, lv1Computed.get());
+ assertEquals("No computation should have happened yet for lv2", 0, lv2Computed.get());
+
+ lhm.put("zero", -1L);
+ assertEquals(new Long(-1L), lhm.get("zero"));
+ assertEquals("lv1 should have been computed", 1, lv1Computed.get());
+ assertEquals("No computation should have happened for lv2, as we put a value in for it",
+ 0, lv2Computed.get());
+ }
+}
diff --git a/bundlerepository/src/test/java/org/apache/felix/bundlerepository/impl/OSGiRepositoryImplTest.java b/bundlerepository/src/test/java/org/apache/felix/bundlerepository/impl/OSGiRepositoryImplTest.java
new file mode 100644
index 0000000..1c25735
--- /dev/null
+++ b/bundlerepository/src/test/java/org/apache/felix/bundlerepository/impl/OSGiRepositoryImplTest.java
@@ -0,0 +1,163 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.felix.bundlerepository.impl;
+
+import java.net.URL;
+import java.util.Arrays;
+import java.util.Collection;
+import java.util.Collections;
+import java.util.HashSet;
+import java.util.Hashtable;
+import java.util.Map;
+import java.util.Set;
+
+import junit.framework.TestCase;
+
+import org.apache.felix.utils.log.Logger;
+import org.mockito.Mockito;
+import org.osgi.framework.Bundle;
+import org.osgi.framework.BundleContext;
+import org.osgi.framework.Version;
+import org.osgi.framework.namespace.IdentityNamespace;
+import org.osgi.resource.Capability;
+import org.osgi.resource.Requirement;
+import org.osgi.resource.Resource;
+import org.osgi.service.repository.ContentNamespace;
+import org.osgi.service.repository.Repository;
+
+public class OSGiRepositoryImplTest extends TestCase
+{
+ public void testIdentityAndContentCapabilities() throws Exception
+ {
+ RepositoryAdminImpl repoAdmin = createRepositoryAdmin();
+ URL url = getClass().getResource("/another_repository.xml");
+ repoAdmin.addRepository(url);
+
+ Repository repo = new OSGiRepositoryImpl(repoAdmin);
+ Requirement req = new OSGiRequirementImpl("osgi.identity", null);
+
+ Map<Requirement, Collection<Capability>> result = repo.findProviders(Collections.singleton(req));
+ assertEquals(1, result.size());
+ Collection<Capability> caps = result.values().iterator().next();
+ assertEquals(2, caps.size());
+
+ Capability tf1Cap = null;
+ for (Capability cap : caps)
+ {
+ if ("test_file_1".equals(cap.getAttributes().get(IdentityNamespace.IDENTITY_NAMESPACE))) {
+ tf1Cap = cap;
+ break;
+ }
+ }
+
+ assertEquals(Version.parseVersion("1.0.0.SNAPSHOT"), tf1Cap.getAttributes().get(IdentityNamespace.CAPABILITY_VERSION_ATTRIBUTE));
+ assertEquals(IdentityNamespace.TYPE_BUNDLE, tf1Cap.getAttributes().get(IdentityNamespace.CAPABILITY_TYPE_ATTRIBUTE));
+
+ Resource res = tf1Cap.getResource();
+ assertEquals(0, res.getRequirements(null).size());
+ assertEquals(1, res.getCapabilities(IdentityNamespace.IDENTITY_NAMESPACE).size());
+ assertEquals(1, res.getCapabilities(ContentNamespace.CONTENT_NAMESPACE).size());
+ assertEquals(2, res.getCapabilities(null).size());
+
+ Capability contentCap = res.getCapabilities(ContentNamespace.CONTENT_NAMESPACE).iterator().next();
+ assertEquals("4b68ab3847feda7d6c62c1fbcbeebfa35eab7351ed5e78f4ddadea5df64b8015",
+ contentCap.getAttributes().get(ContentNamespace.CONTENT_NAMESPACE));
+ assertEquals(getClass().getResource("/repo_files/test_file_1.jar").toExternalForm(),
+ contentCap.getAttributes().get(ContentNamespace.CAPABILITY_URL_ATTRIBUTE));
+ assertEquals(1L, contentCap.getAttributes().get(ContentNamespace.CAPABILITY_SIZE_ATTRIBUTE));
+ assertEquals("application/vnd.osgi.bundle", contentCap.getAttributes().get(ContentNamespace.CAPABILITY_MIME_ATTRIBUTE));
+ }
+
+ public void testIdentityCapabilityFilter() throws Exception
+ {
+ RepositoryAdminImpl repoAdmin = createRepositoryAdmin();
+ URL url = getClass().getResource("/another_repository.xml");
+ repoAdmin.addRepository(url);
+
+ Repository repo = new OSGiRepositoryImpl(repoAdmin);
+ Requirement req = new OSGiRequirementImpl("osgi.identity", "(osgi.identity=test_file_2)");
+
+ Map<Requirement, Collection<Capability>> result = repo.findProviders(Collections.singleton(req));
+ assertEquals(1, result.size());
+ Collection<Capability> caps = result.values().iterator().next();
+ assertEquals(1, caps.size());
+ Capability cap = caps.iterator().next();
+
+ assertEquals("test_file_2", cap.getAttributes().get(IdentityNamespace.IDENTITY_NAMESPACE));
+ assertEquals(Version.parseVersion("1.0.0"), cap.getAttributes().get(IdentityNamespace.CAPABILITY_VERSION_ATTRIBUTE));
+ assertEquals(IdentityNamespace.TYPE_BUNDLE, cap.getAttributes().get(IdentityNamespace.CAPABILITY_TYPE_ATTRIBUTE));
+ }
+
+ public void testFilterOnCapability() throws Exception
+ {
+ RepositoryAdminImpl repoAdmin = createRepositoryAdmin();
+ URL url = getClass().getResource("/another_repository.xml");
+ repoAdmin.addRepository(url);
+
+ Repository repo = new OSGiRepositoryImpl(repoAdmin);
+ Requirement req = new OSGiRequirementImpl("foo", "(someKey=someOtherVal)");
+
+ Map<Requirement, Collection<Capability>> result = repo.findProviders(Collections.singleton(req));
+ assertEquals(1, result.size());
+ Collection<Capability> caps = result.values().iterator().next();
+ assertEquals(1, caps.size());
+
+ Resource res = caps.iterator().next().getResource();
+ assertEquals("test_file_2",
+ res.getCapabilities(IdentityNamespace.IDENTITY_NAMESPACE).iterator().next().
+ getAttributes().get(IdentityNamespace.IDENTITY_NAMESPACE));
+ }
+
+ public void testFilterOnCapabilityExistence() throws Exception
+ {
+ RepositoryAdminImpl repoAdmin = createRepositoryAdmin();
+ URL url = getClass().getResource("/another_repository.xml");
+ repoAdmin.addRepository(url);
+
+ Repository repo = new OSGiRepositoryImpl(repoAdmin);
+ Requirement req = new OSGiRequirementImpl("foo", "(someKey=*)");
+
+ Map<Requirement, Collection<Capability>> result = repo.findProviders(Collections.singleton(req));
+ assertEquals(1, result.size());
+ Collection<Capability> caps = result.values().iterator().next();
+ assertEquals(2, caps.size());
+
+ Set<Object> identities = new HashSet<Object>();
+ for (Capability cap : caps)
+ {
+ identities.add(cap.getResource().getCapabilities(IdentityNamespace.IDENTITY_NAMESPACE).
+ iterator().next().getAttributes().get(IdentityNamespace.IDENTITY_NAMESPACE));
+ }
+
+ Set<String> expected = new HashSet<String>(Arrays.asList("test_file_1", "test_file_2"));
+ assertEquals(expected, identities);
+ }
+
+ private RepositoryAdminImpl createRepositoryAdmin() throws Exception
+ {
+ Bundle sysBundle = Mockito.mock(Bundle.class);
+ Mockito.when(sysBundle.getHeaders()).thenReturn(new Hashtable<String, String>());
+
+ BundleContext bc = Mockito.mock(BundleContext.class);
+ Mockito.when(bc.getBundle(0)).thenReturn(sysBundle);
+ Mockito.when(sysBundle.getBundleContext()).thenReturn(bc);
+
+ return new RepositoryAdminImpl(bc, new Logger(bc));
+ }
+}
diff --git a/bundlerepository/src/test/java/org/apache/felix/bundlerepository/impl/OSGiRepositoryXMLTest.java b/bundlerepository/src/test/java/org/apache/felix/bundlerepository/impl/OSGiRepositoryXMLTest.java
new file mode 100644
index 0000000..c299c2a
--- /dev/null
+++ b/bundlerepository/src/test/java/org/apache/felix/bundlerepository/impl/OSGiRepositoryXMLTest.java
@@ -0,0 +1,72 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.felix.bundlerepository.impl;
+
+import java.net.URL;
+import java.util.Collection;
+import java.util.Collections;
+import java.util.Hashtable;
+import java.util.Map;
+
+import junit.framework.TestCase;
+
+import org.apache.felix.utils.log.Logger;
+import org.mockito.Mockito;
+import org.osgi.framework.Bundle;
+import org.osgi.framework.BundleContext;
+import org.osgi.framework.Version;
+import org.osgi.framework.namespace.IdentityNamespace;
+import org.osgi.resource.Capability;
+import org.osgi.resource.Requirement;
+import org.osgi.service.repository.Repository;
+
+public class OSGiRepositoryXMLTest extends TestCase
+{
+ public void testParseStandardRepositoryXML() throws Exception
+ {
+ RepositoryAdminImpl repoAdmin = createRepositoryAdmin();
+ URL url = getClass().getResource("/spec_repository.xml");
+ repoAdmin.addRepository(url);
+
+ Repository repo = new OSGiRepositoryImpl(repoAdmin);
+ Requirement req = new OSGiRequirementImpl("osgi.identity", "(osgi.identity=cdi-subsystem)");
+
+ Map<Requirement, Collection<Capability>> result = repo.findProviders(Collections.singleton(req));
+ assertEquals(1, result.size());
+ Collection<Capability> caps = result.values().iterator().next();
+ assertEquals(1, caps.size());
+ Capability cap = caps.iterator().next();
+
+ assertEquals("cdi-subsystem", cap.getAttributes().get(IdentityNamespace.IDENTITY_NAMESPACE));
+ assertEquals(Version.parseVersion("0.5.0"), cap.getAttributes().get(IdentityNamespace.CAPABILITY_VERSION_ATTRIBUTE));
+ assertEquals("osgi.subsystem.feature", cap.getAttributes().get(IdentityNamespace.CAPABILITY_TYPE_ATTRIBUTE));
+ }
+
+ private RepositoryAdminImpl createRepositoryAdmin() throws Exception
+ {
+ Bundle sysBundle = Mockito.mock(Bundle.class);
+ Mockito.when(sysBundle.getHeaders()).thenReturn(new Hashtable<String, String>());
+
+ BundleContext bc = Mockito.mock(BundleContext.class);
+ Mockito.when(bc.getBundle(0)).thenReturn(sysBundle);
+ Mockito.when(sysBundle.getBundleContext()).thenReturn(bc);
+
+ return new RepositoryAdminImpl(bc, new Logger(bc));
+ }
+}
diff --git a/bundlerepository/src/test/java/org/apache/felix/bundlerepository/impl/RepositoryImplTest.java b/bundlerepository/src/test/java/org/apache/felix/bundlerepository/impl/RepositoryImplTest.java
index 7481cdc..5e4b459 100644
--- a/bundlerepository/src/test/java/org/apache/felix/bundlerepository/impl/RepositoryImplTest.java
+++ b/bundlerepository/src/test/java/org/apache/felix/bundlerepository/impl/RepositoryImplTest.java
@@ -21,8 +21,10 @@
import java.net.URL;
import java.util.Dictionary;
import java.util.Hashtable;
+import java.util.Map;
import junit.framework.TestCase;
+
import org.apache.felix.bundlerepository.Repository;
import org.apache.felix.bundlerepository.Resource;
import org.apache.felix.utils.log.Logger;
@@ -70,7 +72,7 @@
URL url = getClass().getResource("/referral1_repository.xml");
RepositoryAdminImpl repoAdmin = createRepositoryAdmin();
- RepositoryImpl repo = (RepositoryImpl) repoAdmin.addRepository(url, 1);
+ RepositoryImpl repo = repoAdmin.addRepository(url, 1);
Referral[] refs = repo.getReferrals();
assertNotNull("Expect referrals", refs);
@@ -92,8 +94,8 @@
private RepositoryAdminImpl createRepositoryAdmin() throws Exception
{
- BundleContext bundleContext = (BundleContext) EasyMock.createMock(BundleContext.class);
- Bundle systemBundle = (Bundle) EasyMock.createMock(Bundle.class);
+ BundleContext bundleContext = EasyMock.createMock(BundleContext.class);
+ Bundle systemBundle = EasyMock.createMock(Bundle.class);
Activator.setContext(bundleContext);
EasyMock.expect(bundleContext.getProperty((String) EasyMock.anyObject())).andReturn(null).anyTimes();
@@ -115,6 +117,9 @@
public boolean matchCase(Dictionary dictionary) {
return true;
}
+ public boolean matches(Map<String, ?> map) {
+ return true;
+ }
}).anyTimes();
EasyMock.replay(new Object[] { bundleContext, systemBundle });
diff --git a/bundlerepository/src/test/resources/another_repository.xml b/bundlerepository/src/test/resources/another_repository.xml
new file mode 100644
index 0000000..749d9b5
--- /dev/null
+++ b/bundlerepository/src/test/resources/another_repository.xml
@@ -0,0 +1,81 @@
+<?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.
+-->
+<repository lastmodified="20140130073223" name="AnotherRepository">
+
+ <resource id="test_file_1/1.0.0.SNAPSHOT"
+ symbolicname="test_file_1"
+ uri="repo_files/test_file_1.jar"
+ version="1.0.0.SNAPSHOT">
+ <size>1</size>
+ <capability name="bundle">
+ <p n="manifestversion" v="2" />
+ <p n="presentationname"
+ v="Unnamed - dummy" />
+ <p n="symbolicname" v="dummy" />
+ <p n="version" t="version" v="1.0.0.SNAPSHOT" />
+ </capability>
+ <capability name="package">
+ <p n="package" v="javax.naming" />
+ <p n="version" t="version" v="0.0.0" />
+ </capability>
+ <capability name="package">
+ <p n="package" v="javax.naming.event" />
+ <p n="version" t="version" v="0.0.0" />
+ </capability>
+ <capability name="package">
+ <p n="package" v="javax.naming.spi" />
+ <p n="version" t="version" v="0.0.0" />
+ </capability>
+ <capability name="package">
+ <p n="package" v="javax.sql" />
+ <p n="version" t="version" v="0.0.0" />
+ </capability>
+ <capability name="package">
+ <p n="package" v="org.xml.sax" />
+ <p n="version" t="version" v="0.0.0" />
+ </capability>
+ <capability name="package">
+ <p n="package" v="org.xml.sax.ext" />
+ <p n="version" t="version" v="0.0.0" />
+ </capability>
+ <capability name="package">
+ <p n="package" v="org.xml.sax.helpers" />
+ <p n="version" t="version" v="0.0.0" />
+ </capability>
+ <capability name="package">
+ <p n="package" v="org.apache.commons.logging" />
+ <p n="version" t="version" v="1.0.4" />
+ </capability>
+ <capability name="foo">
+ <p n="someKey" v="someVal"/>
+ </capability>
+ </resource>
+
+ <resource id="test_file_2/1.0.0"
+ symbolicname="test_file_2"
+ uri="repo_files/test_file_2.jar"
+ version="1.0.0">
+ <size>2</size>
+
+ <capability name="foo">
+ <p n="someKey" v="someOtherVal"/>
+ </capability>
+ </resource>
+</repository>
diff --git a/bundlerepository/src/test/resources/repo_files/test_file_1.jar b/bundlerepository/src/test/resources/repo_files/test_file_1.jar
new file mode 100644
index 0000000..500c070
--- /dev/null
+++ b/bundlerepository/src/test/resources/repo_files/test_file_1.jar
@@ -0,0 +1 @@
+X
\ No newline at end of file
diff --git a/bundlerepository/src/test/resources/repo_files/test_file_2.jar b/bundlerepository/src/test/resources/repo_files/test_file_2.jar
new file mode 100644
index 0000000..dfc9179
--- /dev/null
+++ b/bundlerepository/src/test/resources/repo_files/test_file_2.jar
@@ -0,0 +1 @@
+AB
\ No newline at end of file
diff --git a/bundlerepository/src/test/resources/spec_repository.xml b/bundlerepository/src/test/resources/spec_repository.xml
new file mode 100644
index 0000000..ffd6c2e
--- /dev/null
+++ b/bundlerepository/src/test/resources/spec_repository.xml
@@ -0,0 +1,899 @@
+<?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.
+-->
+<repository increment='1389802088217' name='Untitled' xmlns='http://www.osgi.org/xmlns/repository/v1.0.0'>
+ <resource>
+ <capability namespace='osgi.identity'>
+ <attribute name='osgi.identity' value='org.apache.sshd.core'/>
+ <attribute name='type' value='osgi.bundle'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ </capability>
+ <capability namespace='osgi.content'>
+ <attribute name='osgi.content' value='a1c64578808c38a63cd6563e9936f025638aeaf9de70f36765367db81c0afc38'/>
+ <attribute name='url' value='local-repo/sshd-core-0.9.0.jar'/>
+ <attribute name='size' type='Long' value='464733'/>
+ <attribute name='mime' value='application/vnd.osgi.bundle'/>
+ </capability>
+ <capability namespace='osgi.wiring.bundle'>
+ <attribute name='osgi.wiring.bundle' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.0'/>
+ </capability>
+ <capability namespace='osgi.wiring.host'>
+ <attribute name='osgi.wiring.host' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.0'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.common.io.nio2'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.0'/>
+ <directive name='uses' value='org.apache.sshd.common.io,org.slf4j,org.apache.sshd.common,org.apache.sshd.common.future,org.apache.sshd.common.util'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.common'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.0'/>
+ <directive name='uses' value='org.apache.sshd.common.io,org.apache.sshd.agent,org.apache.sshd.common.file,org.slf4j,org.apache.sshd.common.future,org.apache.sshd.common.util,org.apache.sshd.common.session,org.apache.sshd.client.future,org.apache.sshd.common.channel'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.common.kex'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.0'/>
+ <directive name='uses' value='javax.crypto.interfaces,org.apache.sshd.common.util,javax.crypto.spec,javax.crypto'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.common.keyprovider'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.0'/>
+ <directive name='uses' value='org.apache.sshd.common,org.slf4j,org.apache.sshd.common.util,org.bouncycastle.openssl'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.common.session'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.0'/>
+ <directive name='uses' value='org.apache.sshd.common.future,org.apache.sshd.common.io,org.slf4j,org.apache.sshd.common,org.apache.sshd.common.util,org.apache.sshd.client.channel'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.client.future'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.0'/>
+ <directive name='uses' value='org.apache.sshd.common.future,org.apache.sshd,org.apache.sshd.common'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.common.future'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.0'/>
+ <directive name='uses' value='org.slf4j'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.client.keyverifier'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.0'/>
+ <directive name='uses' value='org.apache.sshd.common.util,org.apache.sshd.client,org.apache.sshd,org.slf4j'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.server.channel'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.0'/>
+ <directive name='uses' value='org.apache.sshd.common.util,org.apache.sshd.common,org.apache.sshd.client.future,org.slf4j,org.apache.sshd.common.channel,org.apache.sshd.common.future,org.apache.sshd.server,org.apache.sshd.common.file,org.apache.sshd.agent,org.apache.sshd.server.session'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.server.shell'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.0'/>
+ <directive name='uses' value='org.apache.sshd.server,org.apache.sshd.server.session,org.apache.sshd.common.util,org.slf4j,org.apache.sshd.common'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.agent'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.0'/>
+ <directive name='uses' value='org.apache.sshd.common'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.client.scp'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.0'/>
+ <directive name='uses' value='org.apache.sshd.common.future,org.apache.sshd.common.scp,org.apache.sshd.common,org.apache.sshd.client,org.apache.sshd.client.future,org.apache.sshd,org.apache.sshd.common.file,org.apache.sshd.client.channel'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.server.kex'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.0'/>
+ <directive name='uses' value='org.apache.sshd.common.io,org.apache.sshd.common.util,org.apache.sshd.common,org.apache.sshd.common.kex,org.apache.sshd.common.session,org.apache.sshd.server.session,org.apache.sshd.common.digest,org.slf4j'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.client.session'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.0'/>
+ <directive name='uses' value='org.apache.sshd.common.io,org.apache.sshd.common.future,org.apache.sshd.common.util,org.apache.sshd.server.channel,org.apache.sshd.common,org.apache.sshd.client.future,org.apache.sshd.common.channel,org.apache.sshd.client,org.apache.sshd.common.session,org.apache.sshd.client.channel,org.slf4j,org.apache.sshd.client.sftp,org.apache.sshd.agent,org.apache.sshd.client.scp,org.apache.sshd,org.apache.sshd.client.auth'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.server.command'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.0'/>
+ <directive name='uses' value='org.apache.sshd.common.scp,org.apache.sshd.server,org.apache.sshd.common.file,org.slf4j'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.client.auth'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.0'/>
+ <directive name='uses' value='org.apache.sshd.client,org.apache.sshd.client.session,org.slf4j,org.apache.sshd.common,org.apache.sshd.common.io,org.apache.sshd.common.util,org.apache.sshd.agent'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.common.random'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.0'/>
+ <directive name='uses' value='org.apache.sshd.common,org.bouncycastle.crypto.prng'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.common.scp'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.0'/>
+ <directive name='uses' value='org.apache.sshd.common.file,org.apache.sshd.common.util,org.apache.sshd.common,org.slf4j'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.agent.local'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.0'/>
+ <directive name='uses' value='org.apache.sshd.common.future,org.apache.sshd.common.util,org.apache.sshd.agent,org.apache.sshd.agent.common,org.apache.sshd.common,org.apache.sshd.client.future,org.slf4j,org.apache.sshd.client.channel,org.apache.sshd.common.channel,org.apache.sshd.common.signature,org.apache.sshd.server.session,org.apache.sshd.server.channel'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.common.forward'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.0'/>
+ <directive name='uses' value='org.apache.sshd.common.io,org.apache.sshd.common.future,org.apache.sshd.common,org.apache.sshd.client.future,org.apache.sshd.common.util,org.slf4j,org.apache.sshd.common.channel,org.apache.sshd.client.channel,org.apache.sshd.server.channel'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.agent.unix'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.0'/>
+ <directive name='uses' value='org.apache.sshd.common.util,org.apache.sshd.common,org.apache.sshd.agent.common,org.apache.tomcat.jni,org.apache.sshd.common.future,org.apache.sshd.client.future,org.slf4j,org.apache.sshd.common.channel,org.apache.sshd.client.channel,org.apache.sshd.agent,org.apache.sshd.agent.local,org.apache.sshd.server.session,org.apache.sshd.server.channel'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.server.auth.gss'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.0'/>
+ <directive name='uses' value='javax.security.auth.login,org.ietf.jgss,javax.security.auth.callback,javax.security.auth,org.apache.sshd.server.session,org.apache.sshd.common,org.apache.sshd.server,org.apache.sshd.common.io,org.apache.sshd.common.util,org.apache.sshd.server.auth,org.slf4j'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.agent.common'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.0'/>
+ <directive name='uses' value='org.apache.sshd.common.util,org.apache.sshd.agent,org.apache.sshd.common,org.apache.sshd.server.session,org.slf4j'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.common.compression'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.0'/>
+ <directive name='uses' value='org.apache.sshd.common,org.apache.sshd.common.util,com.jcraft.jzlib'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.common.cipher'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.0'/>
+ <directive name='uses' value='org.apache.sshd.common,javax.crypto,org.apache.sshd.common.util,javax.crypto.spec'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.common.signature'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.0'/>
+ <directive name='uses' value='org.apache.sshd.common.util,org.apache.sshd.common'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.common.file.nativefs'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.0'/>
+ <directive name='uses' value='org.apache.sshd.common,org.slf4j,org.apache.sshd.common.file'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.common.file'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.0'/>
+ <directive name='uses' value='org.apache.sshd.common'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.client.channel'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.0'/>
+ <directive name='uses' value='org.apache.sshd.common.future,org.apache.sshd.client.future,org.apache.sshd.common.util,org.apache.sshd.common,org.apache.sshd,org.slf4j,org.apache.sshd.common.channel'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.server.auth'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.0'/>
+ <directive name='uses' value='org.apache.sshd.common.util,org.apache.sshd.server,org.apache.sshd.server.session,org.slf4j,org.apache.sshd.common,org.apache.sshd.common.io'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.common.io'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.0'/>
+ <directive name='uses' value='org.apache.sshd.common,org.slf4j,org.apache.sshd.common.future,org.apache.sshd.common.util'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.common.util'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.0'/>
+ <directive name='uses' value='org.apache.sshd.common,org.slf4j,org.bouncycastle.jce.provider,javax.crypto'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.server.keyprovider'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.0'/>
+ <directive name='uses' value='org.apache.sshd.common.util,org.apache.sshd.common.keyprovider,org.slf4j,org.bouncycastle.openssl'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.common.mac'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.0'/>
+ <directive name='uses' value='org.apache.sshd.common.util,javax.crypto.spec,org.apache.sshd.common,javax.crypto'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.server.x11'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.0'/>
+ <directive name='uses' value='org.apache.sshd.common.io,org.apache.sshd.common.future,org.apache.sshd.common.util,org.apache.sshd.common,org.apache.sshd.client.future,org.apache.sshd.client.channel,org.slf4j,org.apache.sshd.common.channel,org.apache.sshd.server.session'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.server.jaas'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.0'/>
+ <directive name='uses' value='javax.security.auth.callback,javax.security.auth.login,org.apache.sshd.server,org.apache.sshd.server.session,javax.security.auth,org.slf4j'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.client.kex'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.0'/>
+ <directive name='uses' value='org.apache.sshd.common.io,org.apache.sshd.common.util,org.apache.sshd.common,org.apache.sshd.common.kex,org.apache.sshd.common.session,org.apache.sshd.client.session,org.apache.sshd.common.digest,org.slf4j'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.client.sftp'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.0'/>
+ <directive name='uses' value='org.apache.sshd,org.apache.sshd.client,org.apache.sshd.common.future,org.apache.sshd.common.util,org.apache.sshd.common,org.apache.sshd.client.future,org.apache.sshd.client.channel'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.client'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.0'/>
+ <directive name='uses' value='org.apache.sshd.common,org.apache.sshd,org.apache.sshd.common.io,org.apache.sshd.common.session,org.apache.sshd.client.session,org.apache.sshd.common.util'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.server'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.0'/>
+ <directive name='uses' value='org.apache.sshd.server.channel,org.apache.sshd.server.session,org.apache.sshd.common,org.apache.sshd.server.auth.gss,org.apache.sshd.common.util'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.common.io.mina'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.0'/>
+ <directive name='uses' value='org.apache.sshd.common.io,org.apache.mina.core.session,org.apache.sshd.common,org.apache.mina.core.service,org.apache.mina.transport.socket.nio,org.apache.mina.transport.socket,org.slf4j,org.apache.mina.core.future,org.apache.sshd.common.future,org.apache.sshd.common.util,org.apache.mina.core.buffer'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.server.sftp'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.0'/>
+ <directive name='uses' value='org.apache.sshd.common.file,org.apache.sshd.common,org.apache.sshd.server,org.apache.sshd.common.util,org.apache.sshd.server.session,org.slf4j'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.server.session'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.0'/>
+ <directive name='uses' value='org.apache.sshd.common.io,org.apache.sshd.common.future,org.apache.sshd.common.util,org.apache.sshd.server.channel,org.apache.sshd.common,org.apache.sshd.client.future,org.apache.sshd.common.channel,org.apache.sshd.common.session,org.apache.sshd.agent.common,org.slf4j,org.apache.sshd.server.x11,org.apache.sshd.server'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.common.digest'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.0'/>
+ <directive name='uses' value='org.apache.sshd.common.util,org.apache.sshd.common'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.0'/>
+ <directive name='uses' value='org.apache.sshd.common.future,org.apache.sshd.client.future,org.apache.sshd.common,org.apache.sshd.client,org.apache.sshd.client.channel,org.apache.sshd.common.io,org.apache.sshd.common.session,org.apache.sshd.client.session,org.apache.sshd.client.keyverifier,org.apache.sshd.agent,org.apache.sshd.common.random,org.apache.sshd.common.forward,org.apache.sshd.common.compression,org.apache.sshd.common.cipher,org.apache.sshd.common.signature,org.apache.sshd.common.file.nativefs,org.apache.sshd.common.file,org.apache.sshd.common.util,org.apache.sshd.common.mac,org.apache.sshd.client.kex,org.apache.sshd.server,org.apache.sshd.server.session,org.apache.sshd.common.io.nio2,org.apache.sshd.server.channel,org.apache.sshd.server.shell,org.apache.sshd.server.kex,org.apache.sshd.server.command,org.apache.sshd.server.auth.gss,org.slf4j,org.apache.sshd.server.auth,org.apache.sshd.server.keyprovider,org.apache.sshd.common.io.mina,org.apache.sshd.server.sftp'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.common.channel'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.0'/>
+ <directive name='uses' value='org.apache.sshd.common.future,org.apache.sshd.common,org.apache.sshd.common.io,org.slf4j,org.apache.sshd.common.util'/>
+ </capability>
+ <requirement namespace='osgi.wiring.package'>
+ <directive name='filter' value='(osgi.wiring.package=com.jcraft.jzlib)'/>
+ <directive name='resolution' value='optional'/>
+ </requirement>
+ <requirement namespace='osgi.wiring.package'>
+ <directive name='filter' value='(osgi.wiring.package=javax.crypto)'/>
+ </requirement>
+ <requirement namespace='osgi.wiring.package'>
+ <directive name='filter' value='(osgi.wiring.package=javax.crypto.interfaces)'/>
+ </requirement>
+ <requirement namespace='osgi.wiring.package'>
+ <directive name='filter' value='(osgi.wiring.package=javax.crypto.spec)'/>
+ </requirement>
+ <requirement namespace='osgi.wiring.package'>
+ <directive name='filter' value='(osgi.wiring.package=javax.security.auth)'/>
+ </requirement>
+ <requirement namespace='osgi.wiring.package'>
+ <directive name='filter' value='(osgi.wiring.package=javax.security.auth.callback)'/>
+ </requirement>
+ <requirement namespace='osgi.wiring.package'>
+ <directive name='filter' value='(osgi.wiring.package=javax.security.auth.login)'/>
+ </requirement>
+ <requirement namespace='osgi.wiring.package'>
+ <directive name='filter' value='(&(osgi.wiring.package=org.apache.mina.core.buffer)(version>=2.0.0)(!(version>=3.0.0)))'/>
+ <directive name='resolution' value='optional'/>
+ </requirement>
+ <requirement namespace='osgi.wiring.package'>
+ <directive name='filter' value='(&(osgi.wiring.package=org.apache.mina.core.future)(version>=2.0.0)(!(version>=3.0.0)))'/>
+ <directive name='resolution' value='optional'/>
+ </requirement>
+ <requirement namespace='osgi.wiring.package'>
+ <directive name='filter' value='(&(osgi.wiring.package=org.apache.mina.core.service)(version>=2.0.0)(!(version>=3.0.0)))'/>
+ <directive name='resolution' value='optional'/>
+ </requirement>
+ <requirement namespace='osgi.wiring.package'>
+ <directive name='filter' value='(&(osgi.wiring.package=org.apache.mina.core.session)(version>=2.0.0)(!(version>=3.0.0)))'/>
+ <directive name='resolution' value='optional'/>
+ </requirement>
+ <requirement namespace='osgi.wiring.package'>
+ <directive name='filter' value='(&(osgi.wiring.package=org.apache.mina.transport.socket)(version>=2.0.0)(!(version>=3.0.0)))'/>
+ <directive name='resolution' value='optional'/>
+ </requirement>
+ <requirement namespace='osgi.wiring.package'>
+ <directive name='filter' value='(&(osgi.wiring.package=org.apache.mina.transport.socket.nio)(version>=2.0.0)(!(version>=3.0.0)))'/>
+ <directive name='resolution' value='optional'/>
+ </requirement>
+ <requirement namespace='osgi.wiring.package'>
+ <directive name='filter' value='(osgi.wiring.package=org.apache.tomcat.jni)'/>
+ <directive name='resolution' value='optional'/>
+ </requirement>
+ <requirement namespace='osgi.wiring.package'>
+ <directive name='filter' value='(osgi.wiring.package=org.bouncycastle.crypto.prng)'/>
+ <directive name='resolution' value='optional'/>
+ </requirement>
+ <requirement namespace='osgi.wiring.package'>
+ <directive name='filter' value='(osgi.wiring.package=org.bouncycastle.jce.provider)'/>
+ <directive name='resolution' value='optional'/>
+ </requirement>
+ <requirement namespace='osgi.wiring.package'>
+ <directive name='filter' value='(osgi.wiring.package=org.bouncycastle.openssl)'/>
+ <directive name='resolution' value='optional'/>
+ </requirement>
+ <requirement namespace='osgi.wiring.package'>
+ <directive name='filter' value='(osgi.wiring.package=org.ietf.jgss)'/>
+ </requirement>
+ <requirement namespace='osgi.wiring.package'>
+ <directive name='filter' value='(&(osgi.wiring.package=org.slf4j)(version>=1.6.0)(!(version>=2.0.0)))'/>
+ </requirement>
+ </resource>
+ <resource>
+ <capability namespace='osgi.identity'>
+ <attribute name='osgi.identity' value='org.apache.sshd.core'/>
+ <attribute name='type' value='osgi.bundle'/>
+ <attribute name='version' type='Version' value='0.9.1'/>
+ </capability>
+ <capability namespace='osgi.content'>
+ <attribute name='osgi.content' value='6e60da106b050e88c06a476c1f3462637e864826be4b31ee77502b62d0bc59a0'/>
+ <attribute name='url' value='local-repo/sshd-core-0.9.1.jar'/>
+ <attribute name='size' type='Long' value='470632'/>
+ <attribute name='mime' value='application/vnd.osgi.bundle'/>
+ </capability>
+ <capability namespace='osgi.wiring.bundle'>
+ <attribute name='osgi.wiring.bundle' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.1'/>
+ </capability>
+ <capability namespace='osgi.wiring.host'>
+ <attribute name='osgi.wiring.host' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.1'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.common.io.nio2'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.1'/>
+ <directive name='uses' value='org.apache.sshd.common.io,org.slf4j,org.apache.sshd.common,org.apache.sshd.common.future,org.apache.sshd.common.util'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.common'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.1'/>
+ <directive name='uses' value='org.apache.sshd.common.io,org.apache.sshd.agent,org.apache.sshd.common.file,org.slf4j,org.apache.sshd.common.future,org.apache.sshd.common.util,org.apache.sshd.common.session,org.apache.sshd.client.future,org.apache.sshd.common.channel'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.common.kex'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.1'/>
+ <directive name='uses' value='javax.crypto.interfaces,org.apache.sshd.common.util,javax.crypto.spec,javax.crypto'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.common.keyprovider'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.1'/>
+ <directive name='uses' value='org.apache.sshd.common,org.slf4j,org.apache.sshd.common.util,org.bouncycastle.openssl'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.common.session'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.1'/>
+ <directive name='uses' value='org.apache.sshd.common.future,org.apache.sshd.common.io,org.slf4j,org.apache.sshd.common,org.apache.sshd.common.util,org.apache.sshd.client.channel'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.client.future'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.1'/>
+ <directive name='uses' value='org.apache.sshd.common.future,org.apache.sshd,org.apache.sshd.common'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.common.future'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.1'/>
+ <directive name='uses' value='org.slf4j'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.client.keyverifier'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.1'/>
+ <directive name='uses' value='org.apache.sshd.common.util,org.apache.sshd.client,org.apache.sshd,org.slf4j'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.server.channel'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.1'/>
+ <directive name='uses' value='org.apache.sshd.common.util,org.apache.sshd.common,org.apache.sshd.client.future,org.slf4j,org.apache.sshd.common.channel,org.apache.sshd.common.future,org.apache.sshd.server,org.apache.sshd.common.file,org.apache.sshd.agent,org.apache.sshd.server.session'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.server.shell'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.1'/>
+ <directive name='uses' value='org.apache.sshd.server,org.apache.sshd.server.session,org.apache.sshd.common.util,org.slf4j,org.apache.sshd.common'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.agent'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.1'/>
+ <directive name='uses' value='org.apache.sshd.common'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.client.scp'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.1'/>
+ <directive name='uses' value='org.apache.sshd.common.future,org.apache.sshd.common.scp,org.apache.sshd.common,org.apache.sshd.client,org.apache.sshd.client.future,org.apache.sshd,org.apache.sshd.common.file,org.apache.sshd.client.channel'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.server.kex'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.1'/>
+ <directive name='uses' value='org.apache.sshd.common.io,org.apache.sshd.common.util,org.apache.sshd.common,org.apache.sshd.common.kex,org.apache.sshd.common.session,org.apache.sshd.server.session,org.apache.sshd.common.digest,org.slf4j'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.client.session'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.1'/>
+ <directive name='uses' value='org.apache.sshd.common.io,org.apache.sshd.common.future,org.apache.sshd.common.util,org.apache.sshd.server.channel,org.apache.sshd.common,org.apache.sshd.client.future,org.apache.sshd.common.channel,org.apache.sshd.client,org.apache.sshd.common.session,org.apache.sshd.client.channel,org.slf4j,org.apache.sshd.client.sftp,org.apache.sshd.agent,org.apache.sshd.client.scp,org.apache.sshd,org.apache.sshd.client.auth'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.server.command'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.1'/>
+ <directive name='uses' value='org.apache.sshd.common.scp,org.apache.sshd.server,org.apache.sshd.common.file,org.slf4j'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.client.auth'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.1'/>
+ <directive name='uses' value='org.apache.sshd.client,org.apache.sshd.client.session,org.slf4j,org.apache.sshd.common,org.apache.sshd.common.io,org.apache.sshd.common.util,org.apache.sshd.agent'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.common.random'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.1'/>
+ <directive name='uses' value='org.apache.sshd.common,org.bouncycastle.crypto.prng'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.common.scp'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.1'/>
+ <directive name='uses' value='org.apache.sshd.common.file,org.apache.sshd.common.util,org.apache.sshd.common,org.slf4j'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.agent.local'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.1'/>
+ <directive name='uses' value='org.apache.sshd.common.future,org.apache.sshd.common.util,org.apache.sshd.agent,org.apache.sshd.agent.common,org.apache.sshd.common,org.apache.sshd.client.future,org.slf4j,org.apache.sshd.client.channel,org.apache.sshd.common.channel,org.apache.sshd.common.signature,org.apache.sshd.server.session,org.apache.sshd.server.channel'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.common.forward'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.1'/>
+ <directive name='uses' value='org.apache.sshd.common.io,org.apache.sshd.common.future,org.apache.sshd.common,org.apache.sshd.client.future,org.apache.sshd.common.util,org.slf4j,org.apache.sshd.common.channel,org.apache.sshd.client.channel,org.apache.sshd.server.channel'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.agent.unix'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.1'/>
+ <directive name='uses' value='org.apache.sshd.common.util,org.apache.sshd.common,org.apache.sshd.agent.common,org.apache.tomcat.jni,org.apache.sshd.common.future,org.apache.sshd.client.future,org.slf4j,org.apache.sshd.common.channel,org.apache.sshd.client.channel,org.apache.sshd.agent,org.apache.sshd.agent.local,org.apache.sshd.server.session,org.apache.sshd.server.channel'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.server.auth.gss'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.1'/>
+ <directive name='uses' value='javax.security.auth.login,org.ietf.jgss,javax.security.auth.callback,javax.security.auth,org.apache.sshd.server.session,org.apache.sshd.common,org.apache.sshd.server,org.apache.sshd.common.io,org.apache.sshd.common.util,org.apache.sshd.server.auth,org.slf4j'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.agent.common'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.1'/>
+ <directive name='uses' value='org.apache.sshd.common.util,org.apache.sshd.agent,org.apache.sshd.common,org.apache.sshd.server.session,org.slf4j'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.common.compression'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.1'/>
+ <directive name='uses' value='org.apache.sshd.common,org.apache.sshd.common.util,com.jcraft.jzlib'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.common.cipher'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.1'/>
+ <directive name='uses' value='org.apache.sshd.common,javax.crypto,org.apache.sshd.common.util,javax.crypto.spec'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.common.signature'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.1'/>
+ <directive name='uses' value='org.apache.sshd.common.util,org.apache.sshd.common'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.common.file.nativefs'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.1'/>
+ <directive name='uses' value='org.apache.sshd.common,org.slf4j,org.apache.sshd.common.file'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.common.file'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.1'/>
+ <directive name='uses' value='org.apache.sshd.common'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.client.channel'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.1'/>
+ <directive name='uses' value='org.apache.sshd.common.future,org.apache.sshd.client.future,org.apache.sshd.common.util,org.apache.sshd.common,org.apache.sshd,org.slf4j,org.apache.sshd.common.channel'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.server.auth'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.1'/>
+ <directive name='uses' value='org.apache.sshd.common.util,org.apache.sshd.server,org.apache.sshd.server.session,org.slf4j,org.apache.sshd.common,org.apache.sshd.common.io'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.common.io'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.1'/>
+ <directive name='uses' value='org.apache.sshd.common,org.slf4j,org.apache.sshd.common.future,org.apache.sshd.common.util'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.common.util'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.1'/>
+ <directive name='uses' value='org.apache.sshd.common,org.slf4j,org.bouncycastle.jce.provider,javax.crypto'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.server.keyprovider'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.1'/>
+ <directive name='uses' value='org.apache.sshd.common.util,org.apache.sshd.common.keyprovider,org.slf4j,org.bouncycastle.openssl'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.common.mac'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.1'/>
+ <directive name='uses' value='org.apache.sshd.common.util,javax.crypto.spec,org.apache.sshd.common,javax.crypto'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.server.x11'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.1'/>
+ <directive name='uses' value='org.apache.sshd.common.io,org.apache.sshd.common.future,org.apache.sshd.common.util,org.apache.sshd.common,org.apache.sshd.client.future,org.apache.sshd.client.channel,org.slf4j,org.apache.sshd.common.channel,org.apache.sshd.server.session'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.server.jaas'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.1'/>
+ <directive name='uses' value='javax.security.auth.callback,javax.security.auth.login,org.apache.sshd.server,org.apache.sshd.server.session,javax.security.auth,org.slf4j'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.client.kex'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.1'/>
+ <directive name='uses' value='org.apache.sshd.common.io,org.apache.sshd.common.util,org.apache.sshd.common,org.apache.sshd.common.kex,org.apache.sshd.common.session,org.apache.sshd.client.session,org.apache.sshd.common.digest,org.slf4j'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.client.sftp'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.1'/>
+ <directive name='uses' value='org.apache.sshd,org.apache.sshd.client,org.apache.sshd.common.future,org.apache.sshd.common.util,org.apache.sshd.common,org.apache.sshd.client.future,org.apache.sshd.client.channel'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.client'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.1'/>
+ <directive name='uses' value='org.apache.sshd.common,org.apache.sshd,org.apache.sshd.common.io,org.apache.sshd.common.session,org.apache.sshd.client.session,org.apache.sshd.common.util'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.server'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.1'/>
+ <directive name='uses' value='org.apache.sshd.server.channel,org.apache.sshd.server.session,org.apache.sshd.common,org.apache.sshd.server.auth.gss,org.apache.sshd.common.util'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.common.io.mina'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.1'/>
+ <directive name='uses' value='org.apache.sshd.common.io,org.apache.mina.core.session,org.apache.sshd.common,org.apache.mina.core.service,org.apache.mina.transport.socket.nio,org.apache.mina.transport.socket,org.slf4j,org.apache.mina.core.future,org.apache.sshd.common.future,org.apache.sshd.common.util,org.apache.mina.core.buffer'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.server.sftp'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.1'/>
+ <directive name='uses' value='org.apache.sshd.common.file,org.apache.sshd.common,org.apache.sshd.server,org.apache.sshd.common.util,org.apache.sshd.server.session,org.slf4j'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.server.session'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.1'/>
+ <directive name='uses' value='org.apache.sshd.common.io,org.apache.sshd.common.future,org.apache.sshd.common.util,org.apache.sshd.server.channel,org.apache.sshd.common,org.apache.sshd.client.future,org.apache.sshd.common.channel,org.apache.sshd.common.session,org.apache.sshd.agent.common,org.slf4j,org.apache.sshd.server.x11,org.apache.sshd.server'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.common.digest'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.1'/>
+ <directive name='uses' value='org.apache.sshd.common.util,org.apache.sshd.common'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.1'/>
+ <directive name='uses' value='org.apache.sshd.common.future,org.apache.sshd.client.future,org.apache.sshd.common,org.apache.sshd.client,org.apache.sshd.client.channel,org.apache.sshd.common.io,org.apache.sshd.common.session,org.apache.sshd.client.session,org.apache.sshd.client.keyverifier,org.apache.sshd.agent,org.apache.sshd.common.random,org.apache.sshd.common.forward,org.apache.sshd.common.compression,org.apache.sshd.common.cipher,org.apache.sshd.common.signature,org.apache.sshd.common.file.nativefs,org.apache.sshd.common.file,org.apache.sshd.common.util,org.apache.sshd.common.mac,org.apache.sshd.client.kex,org.apache.sshd.server,org.apache.sshd.server.session,org.apache.sshd.common.io.nio2,org.apache.sshd.server.channel,org.apache.sshd.server.shell,org.apache.sshd.server.kex,org.apache.sshd.server.command,org.apache.sshd.server.auth.gss,org.slf4j,org.apache.sshd.server.auth,org.apache.sshd.server.keyprovider,org.apache.sshd.common.io.mina,org.apache.sshd.server.sftp'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.apache.sshd.common.channel'/>
+ <attribute name='version' type='Version' value='0.9.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.sshd.core'/>
+ <attribute name='bundle-version' type='Version' value='0.9.1'/>
+ <directive name='uses' value='org.apache.sshd.common.future,org.apache.sshd.common,org.apache.sshd.common.io,org.slf4j,org.apache.sshd.common.util'/>
+ </capability>
+ <requirement namespace='osgi.wiring.package'>
+ <directive name='filter' value='(osgi.wiring.package=com.jcraft.jzlib)'/>
+ <directive name='resolution' value='optional'/>
+ </requirement>
+ <requirement namespace='osgi.wiring.package'>
+ <directive name='filter' value='(osgi.wiring.package=javax.crypto)'/>
+ </requirement>
+ <requirement namespace='osgi.wiring.package'>
+ <directive name='filter' value='(osgi.wiring.package=javax.crypto.interfaces)'/>
+ </requirement>
+ <requirement namespace='osgi.wiring.package'>
+ <directive name='filter' value='(osgi.wiring.package=javax.crypto.spec)'/>
+ </requirement>
+ <requirement namespace='osgi.wiring.package'>
+ <directive name='filter' value='(osgi.wiring.package=javax.security.auth)'/>
+ </requirement>
+ <requirement namespace='osgi.wiring.package'>
+ <directive name='filter' value='(osgi.wiring.package=javax.security.auth.callback)'/>
+ </requirement>
+ <requirement namespace='osgi.wiring.package'>
+ <directive name='filter' value='(osgi.wiring.package=javax.security.auth.login)'/>
+ </requirement>
+ <requirement namespace='osgi.wiring.package'>
+ <directive name='filter' value='(&(osgi.wiring.package=org.apache.mina.core.buffer)(version>=2.0.0)(!(version>=3.0.0)))'/>
+ <directive name='resolution' value='optional'/>
+ </requirement>
+ <requirement namespace='osgi.wiring.package'>
+ <directive name='filter' value='(&(osgi.wiring.package=org.apache.mina.core.future)(version>=2.0.0)(!(version>=3.0.0)))'/>
+ <directive name='resolution' value='optional'/>
+ </requirement>
+ <requirement namespace='osgi.wiring.package'>
+ <directive name='filter' value='(&(osgi.wiring.package=org.apache.mina.core.service)(version>=2.0.0)(!(version>=3.0.0)))'/>
+ <directive name='resolution' value='optional'/>
+ </requirement>
+ <requirement namespace='osgi.wiring.package'>
+ <directive name='filter' value='(&(osgi.wiring.package=org.apache.mina.core.session)(version>=2.0.0)(!(version>=3.0.0)))'/>
+ <directive name='resolution' value='optional'/>
+ </requirement>
+ <requirement namespace='osgi.wiring.package'>
+ <directive name='filter' value='(&(osgi.wiring.package=org.apache.mina.transport.socket)(version>=2.0.0)(!(version>=3.0.0)))'/>
+ <directive name='resolution' value='optional'/>
+ </requirement>
+ <requirement namespace='osgi.wiring.package'>
+ <directive name='filter' value='(&(osgi.wiring.package=org.apache.mina.transport.socket.nio)(version>=2.0.0)(!(version>=3.0.0)))'/>
+ <directive name='resolution' value='optional'/>
+ </requirement>
+ <requirement namespace='osgi.wiring.package'>
+ <directive name='filter' value='(osgi.wiring.package=org.apache.tomcat.jni)'/>
+ <directive name='resolution' value='optional'/>
+ </requirement>
+ <requirement namespace='osgi.wiring.package'>
+ <directive name='filter' value='(osgi.wiring.package=org.bouncycastle.crypto.prng)'/>
+ <directive name='resolution' value='optional'/>
+ </requirement>
+ <requirement namespace='osgi.wiring.package'>
+ <directive name='filter' value='(osgi.wiring.package=org.bouncycastle.jce.provider)'/>
+ <directive name='resolution' value='optional'/>
+ </requirement>
+ <requirement namespace='osgi.wiring.package'>
+ <directive name='filter' value='(osgi.wiring.package=org.bouncycastle.openssl)'/>
+ <directive name='resolution' value='optional'/>
+ </requirement>
+ <requirement namespace='osgi.wiring.package'>
+ <directive name='filter' value='(osgi.wiring.package=org.ietf.jgss)'/>
+ </requirement>
+ <requirement namespace='osgi.wiring.package'>
+ <directive name='filter' value='(&(osgi.wiring.package=org.slf4j)(version>=1.6.0)(!(version>=2.0.0)))'/>
+ </requirement>
+ </resource>
+ <resource>
+ <capability namespace='osgi.identity'>
+ <attribute name='osgi.identity' value='cdi-subsystem'/>
+ <attribute name='type' value='osgi.subsystem.feature'/>
+ <attribute name='version' type='Version' value='0.5.0'/>
+ </capability>
+ <capability namespace='osgi.content'>
+ <attribute name='osgi.content' value='cf437416541f1c04a503b4c4db9127c805a0d1989db6e71c3245e09d3b572d41'/>
+ <attribute name='url' value='local-repo/cdi.esa'/>
+ <attribute name='size' type='Long' value='5060942'/>
+ <attribute name='mime' value='application/vnd.osgi.subsystem'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.osgi.service.cdi'/>
+ <attribute name='version' type='Version' value='1.0.0'/>
+ <attribute name='bundle-symbolic-name' value='org.ops4j.pax.cdi.api'/>
+ <attribute name='bundle-version' type='Version' value='0.5.0.ri-SNAPSHOT'/>
+ <directive name='uses' value='org.osgi.framework,javax.enterprise.util,javax.inject'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='org.osgi.service.http'/>
+ <attribute name='version' type='Version' value='1.2.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.felix.http.jetty'/>
+ <attribute name='bundle-version' type='Version' value='2.2.2'/>
+ <directive name='uses' value='javax.servlet.http,javax.servlet'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='javax.servlet'/>
+ <attribute name='version' type='Version' value='2.5.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.felix.http.jetty'/>
+ <attribute name='bundle-version' type='Version' value='2.2.2'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='javax.servlet.http'/>
+ <attribute name='version' type='Version' value='2.5.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.felix.http.jetty'/>
+ <attribute name='bundle-version' type='Version' value='2.2.2'/>
+ <directive name='uses' value='javax.servlet'/>
+ </capability>
+ <capability namespace='osgi.wiring.package'>
+ <attribute name='osgi.wiring.package' value='javax.inject'/>
+ <attribute name='version' type='Version' value='1.0.0'/>
+ <attribute name='bundle-symbolic-name' value='org.apache.geronimo.specs.geronimo-atinject_1.0_spec'/>
+ <attribute name='bundle-version' type='Version' value='1.0.0'/>
+ </capability>
+ <capability namespace='osgi.extender'>
+ <attribute name='osgi.extender' value='osgi.cdi'/>
+ <attribute name='version' type='Version' value='1.0.0'/>
+ <directive name='uses' value='org.osgi.service.cdi,javax.enterprise.inject.spi'/>
+ </capability>
+ <capability namespace='osgi.whiteboard'>
+ <attribute name='osgi.whiteboard' value='osgi.http'/>
+ <attribute name='version' type='Version' value='1.2.0'/>
+ <directive name='uses' value='javax.servlet,javax.servlet.http'/>
+ </capability>
+ </resource>
+</repository>