You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@karaf.apache.org by jb...@apache.org on 2014/01/17 17:00:12 UTC

git commit: [KARAF-2642] Merge jndi feature

Updated Branches:
  refs/heads/karaf-2.x 5848109c0 -> e11582a15


[KARAF-2642] Merge jndi feature


Project: http://git-wip-us.apache.org/repos/asf/karaf/repo
Commit: http://git-wip-us.apache.org/repos/asf/karaf/commit/e11582a1
Tree: http://git-wip-us.apache.org/repos/asf/karaf/tree/e11582a1
Diff: http://git-wip-us.apache.org/repos/asf/karaf/diff/e11582a1

Branch: refs/heads/karaf-2.x
Commit: e11582a158e2b4fdc306c275795602db5325eaa0
Parents: 5848109
Author: Jean-Baptiste Onofré <jb...@apache.org>
Authored: Fri Jan 17 16:58:42 2014 +0100
Committer: Jean-Baptiste Onofré <jb...@apache.org>
Committed: Fri Jan 17 16:58:42 2014 +0100

----------------------------------------------------------------------
 .../enterprise/src/main/resources/features.xml  |   3 +
 jndi/command/NOTICE                             |  71 +++++
 jndi/command/pom.xml                            |  97 ++++++
 .../apache/karaf/jndi/command/AliasCommand.java |  36 +++
 .../apache/karaf/jndi/command/BindCommand.java  |  36 +++
 .../karaf/jndi/command/ContextsCommand.java     |  46 +++
 .../karaf/jndi/command/CreateCommand.java       |  33 ++
 .../karaf/jndi/command/DeleteCommand.java       |  33 ++
 .../karaf/jndi/command/JndiCommandSupport.java  |  36 +++
 .../apache/karaf/jndi/command/NamesCommand.java |  50 +++
 .../karaf/jndi/command/UnbindCommand.java       |  33 ++
 .../command/completers/ContextsCompleter.java   |  53 ++++
 .../jndi/command/completers/NamesCompleter.java |  52 ++++
 .../command/completers/ServicesIdCompleter.java |  59 ++++
 .../OSGI-INF/blueprint/jndi-command.xml         |  99 ++++++
 .../src/main/resources/OSGI-INF/bundle.info     |  26 ++
 jndi/core/NOTICE                                |  71 +++++
 jndi/core/pom.xml                               |  95 ++++++
 .../java/org/apache/karaf/jndi/JndiMBean.java   | 104 +++++++
 .../java/org/apache/karaf/jndi/JndiService.java | 103 +++++++
 .../karaf/jndi/KarafInitialContextFactory.java  |  33 ++
 .../karaf/jndi/internal/JndiMBeanImpl.java      | 119 ++++++++
 .../karaf/jndi/internal/JndiServiceImpl.java    | 306 +++++++++++++++++++
 .../resources/OSGI-INF/blueprint/jndi-core.xml  |  55 ++++
 .../src/main/resources/OSGI-INF/bundle.info     |  19 ++
 jndi/pom.xml                                    |  41 +++
 pom.xml                                         |  16 +
 27 files changed, 1725 insertions(+)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/karaf/blob/e11582a1/assemblies/features/enterprise/src/main/resources/features.xml
----------------------------------------------------------------------
diff --git a/assemblies/features/enterprise/src/main/resources/features.xml b/assemblies/features/enterprise/src/main/resources/features.xml
index e9d3b70..1622a1a 100644
--- a/assemblies/features/enterprise/src/main/resources/features.xml
+++ b/assemblies/features/enterprise/src/main/resources/features.xml
@@ -147,11 +147,14 @@
 
     <feature name="jndi" description="OSGi Service Registry JNDI access" version="${aries.jndi.version}" resolver="(obr)">
         <details>JNDI support provided by Apache Aries JNDI ${aries.jndi.version}</details>
+        <bundle start-level="30">mvn:org.apache.xbean/xbean-naming/${xbean.version}</bundle>
+        <bundle start-level="30">mvn:org.apache.karaf.jndi/org.apache.karaf.jndi.core/${project.version}</bundle>
         <bundle start-level="30">mvn:org.apache.aries.jndi/org.apache.aries.jndi.api/${aries.jndi.api.version}</bundle>
         <bundle start-level="30">mvn:org.apache.aries.jndi/org.apache.aries.jndi.core/${aries.jndi.version}</bundle>
         <bundle start-level="30">mvn:org.apache.aries.jndi/org.apache.aries.jndi.rmi/${aries.jndi.version}</bundle>
         <bundle start-level="30">mvn:org.apache.aries.jndi/org.apache.aries.jndi.url/${aries.jndi.version}</bundle>
         <bundle start-level="30">mvn:org.apache.aries.jndi/org.apache.aries.jndi.legacy.support/${aries.jndi.version}</bundle>
+        <bundle>mvn:org.apache.karaf.jndi/org.apache.karaf.jndi.command/${project.version}</bundle>
     </feature>
 
     <feature name="openwebbeans" description="Apache OpenWebBeans CDI container support" version="${openwebbeans.version}" resolver="(obr)">

http://git-wip-us.apache.org/repos/asf/karaf/blob/e11582a1/jndi/command/NOTICE
----------------------------------------------------------------------
diff --git a/jndi/command/NOTICE b/jndi/command/NOTICE
new file mode 100644
index 0000000..de8d101
--- /dev/null
+++ b/jndi/command/NOTICE
@@ -0,0 +1,71 @@
+Apache Karaf
+Copyright 2010-2013 The Apache Software Foundation
+
+
+I. Included Software
+
+This product includes software developed at
+The Apache Software Foundation (http://www.apache.org/).
+Licensed under the Apache License 2.0.
+
+This product uses software developed at
+The OSGi Alliance (http://www.osgi.org/).
+Copyright (c) OSGi Alliance (2000, 2010).
+Licensed under the Apache License 2.0.
+
+This product includes software developed at
+OW2 (http://www.ow2.org/).
+Licensed under the BSD License.
+
+This product includes software developed at
+OPS4J (http://www.ops4j.org/).
+Licensed under the Apache License 2.0.
+
+This product includes software developed at
+Eclipse Foundation (http://www.eclipse.org/).
+Licensed under the EPL.
+
+This product includes software written by
+Antony Lesuisse.
+Licensed under Public Domain.
+
+
+II. Used Software
+
+This product uses software developed at
+FUSE Source (http://www.fusesource.org/).
+Licensed under the Apache License 2.0.
+
+This product uses software developed at
+AOP Alliance (http://aopalliance.sourceforge.net/).
+Licensed under the Public Domain.
+
+This product uses software developed at
+Tanuki Software (http://www.tanukisoftware.com/).
+Licensed under the Apache License 2.0.
+
+This product uses software developed at
+Jasypt (http://jasypt.sourceforge.net/).
+Licensed under the Apache License 2.0.
+
+This product uses software developed at
+JLine (http://jline.sourceforge.net).
+Licensed under the BSD License.
+
+This product uses software developed at
+SLF4J (http://www.slf4j.org/).
+Licensed under the MIT License.
+
+This product uses software developed at
+SpringSource (http://www.springsource.org/).
+Licensed under the Apache License 2.0.
+
+This product includes software from http://www.json.org.
+Copyright (c) 2002 JSON.org
+
+
+III. License Summary
+- Apache License 2.0
+- BSD License
+- EPL License
+- MIT License

http://git-wip-us.apache.org/repos/asf/karaf/blob/e11582a1/jndi/command/pom.xml
----------------------------------------------------------------------
diff --git a/jndi/command/pom.xml b/jndi/command/pom.xml
new file mode 100644
index 0000000..a2072fb
--- /dev/null
+++ b/jndi/command/pom.xml
@@ -0,0 +1,97 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
+
+    <!--
+
+        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.
+    -->
+
+    <modelVersion>4.0.0</modelVersion>
+
+    <parent>
+        <groupId>org.apache.karaf.jndi</groupId>
+        <artifactId>jndi</artifactId>
+        <version>2.4.0-SNAPSHOT</version>
+        <relativePath>../pom.xml</relativePath>
+    </parent>
+
+    <artifactId>org.apache.karaf.jndi.command</artifactId>
+    <packaging>bundle</packaging>
+    <name>Apache Karaf :: JNDI :: Command</name>
+    <description>This bundle provides a set of commands to manipulate JNDI service.</description>
+
+    <properties>
+        <appendedResourcesDirectory>${basedir}/../../etc/appended-resources</appendedResourcesDirectory>
+    </properties>
+
+    <dependencies>
+        <dependency>
+            <groupId>org.apache.karaf.jndi</groupId>
+            <artifactId>org.apache.karaf.jndi.core</artifactId>
+        </dependency>
+
+        <dependency>
+            <groupId>org.osgi</groupId>
+            <artifactId>org.osgi.core</artifactId>
+        </dependency>
+
+        <dependency>
+            <groupId>org.apache.felix</groupId>
+            <artifactId>org.apache.felix.gogo.runtime</artifactId>
+            <scope>provided</scope>
+        </dependency>
+
+        <dependency>
+            <groupId>org.apache.karaf.shell</groupId>
+            <artifactId>org.apache.karaf.shell.console</artifactId>
+        </dependency>
+    </dependencies>
+
+    <build>
+        <resources>
+            <resource>
+                <directory>${project.basedir}/src/main/resources</directory>
+                <includes>
+                    <include>**/*</include>
+                </includes>
+            </resource>
+            <resource>
+                <directory>${project.basedir}/src/main/resources</directory>
+                <filtering>true</filtering>
+                <includes>
+                    <include>**/*.info</include>
+                </includes>
+            </resource>
+        </resources>
+        <plugins>
+            <plugin>
+                <groupId>org.apache.felix</groupId>
+                <artifactId>maven-bundle-plugin</artifactId>
+                <configuration>
+                    <instructions>
+                        <Import-Package>
+                            org.apache.felix.service.command,
+                            org.apache.felix.gogo.commands,
+                            org.apache.karaf.shell.console,
+                            *
+                        </Import-Package>
+                    </instructions>
+                </configuration>
+            </plugin>
+        </plugins>
+    </build>
+
+</project>
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/karaf/blob/e11582a1/jndi/command/src/main/java/org/apache/karaf/jndi/command/AliasCommand.java
----------------------------------------------------------------------
diff --git a/jndi/command/src/main/java/org/apache/karaf/jndi/command/AliasCommand.java b/jndi/command/src/main/java/org/apache/karaf/jndi/command/AliasCommand.java
new file mode 100644
index 0000000..aa7c2c9
--- /dev/null
+++ b/jndi/command/src/main/java/org/apache/karaf/jndi/command/AliasCommand.java
@@ -0,0 +1,36 @@
+/*
+ * 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.karaf.jndi.command;
+
+import org.apache.felix.gogo.commands.Argument;
+import org.apache.felix.gogo.commands.Command;
+
+@Command(scope = "jndi", name = "alias", description = "Create a JNDI alias on a given name.")
+public class AliasCommand extends JndiCommandSupport {
+
+    @Argument(index = 0, name = "name", description = "The JNDI name", required = true, multiValued = false)
+    String name;
+
+    @Argument(index = 1, name = "alias", description = "The JNDI alias", required = true, multiValued = false)
+    String alias;
+
+    public Object doExecute() throws Exception {
+        getJndiService().alias(name, alias);
+        return null;
+    }
+
+}

http://git-wip-us.apache.org/repos/asf/karaf/blob/e11582a1/jndi/command/src/main/java/org/apache/karaf/jndi/command/BindCommand.java
----------------------------------------------------------------------
diff --git a/jndi/command/src/main/java/org/apache/karaf/jndi/command/BindCommand.java b/jndi/command/src/main/java/org/apache/karaf/jndi/command/BindCommand.java
new file mode 100644
index 0000000..f280069
--- /dev/null
+++ b/jndi/command/src/main/java/org/apache/karaf/jndi/command/BindCommand.java
@@ -0,0 +1,36 @@
+/*
+ * 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.karaf.jndi.command;
+
+import org.apache.felix.gogo.commands.Argument;
+import org.apache.felix.gogo.commands.Command;
+
+@Command(scope = "jndi", name = "bind", description = "Bind an OSGi service in the JNDI context")
+public class BindCommand extends JndiCommandSupport {
+
+    @Argument(index = 0, name = "service", description = "The ID of the OSGi service to bind", required = true, multiValued = false)
+    Long serviceId;
+
+    @Argument(index = 1, name = "name", description = "The JNDI name to bind the OSGi service", required = true, multiValued = false)
+    String name;
+
+    public Object doExecute() throws Exception {
+        this.getJndiService().bind(serviceId, name);
+        return null;
+    }
+
+}

http://git-wip-us.apache.org/repos/asf/karaf/blob/e11582a1/jndi/command/src/main/java/org/apache/karaf/jndi/command/ContextsCommand.java
----------------------------------------------------------------------
diff --git a/jndi/command/src/main/java/org/apache/karaf/jndi/command/ContextsCommand.java b/jndi/command/src/main/java/org/apache/karaf/jndi/command/ContextsCommand.java
new file mode 100644
index 0000000..9a10b0a
--- /dev/null
+++ b/jndi/command/src/main/java/org/apache/karaf/jndi/command/ContextsCommand.java
@@ -0,0 +1,46 @@
+/*
+ * 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.karaf.jndi.command;
+
+import org.apache.felix.gogo.commands.Argument;
+import org.apache.felix.gogo.commands.Command;
+
+import java.util.List;
+
+@Command(scope = "jndi", name = "contexts", description = "List the JNDI sub-contexts.")
+public class ContextsCommand extends JndiCommandSupport {
+
+    @Argument(index = 0, name = "context", description = "The base JNDI context", required = false, multiValued = false)
+    String context;
+
+    public Object doExecute() throws Exception {
+
+        List<String> contexts;
+        if (context == null) {
+            contexts = this.getJndiService().contexts();
+        } else {
+            contexts = this.getJndiService().contexts(context);
+        }
+
+        for (String c : contexts) {
+            System.out.println(c);
+        }
+
+        return null;
+    }
+
+}

http://git-wip-us.apache.org/repos/asf/karaf/blob/e11582a1/jndi/command/src/main/java/org/apache/karaf/jndi/command/CreateCommand.java
----------------------------------------------------------------------
diff --git a/jndi/command/src/main/java/org/apache/karaf/jndi/command/CreateCommand.java b/jndi/command/src/main/java/org/apache/karaf/jndi/command/CreateCommand.java
new file mode 100644
index 0000000..d963c51
--- /dev/null
+++ b/jndi/command/src/main/java/org/apache/karaf/jndi/command/CreateCommand.java
@@ -0,0 +1,33 @@
+/*
+ * 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.karaf.jndi.command;
+
+import org.apache.felix.gogo.commands.Argument;
+import org.apache.felix.gogo.commands.Command;
+
+@Command(scope = "jndi",  name = "create", description = "Create a new JNDI sub-context.")
+public class CreateCommand extends JndiCommandSupport {
+
+    @Argument(index = 0, name = "context", description = "The JNDI sub-context name", required = true, multiValued = false)
+    String context;
+
+    public Object doExecute() throws Exception {
+        this.getJndiService().create(context);
+        return null;
+    }
+
+}

http://git-wip-us.apache.org/repos/asf/karaf/blob/e11582a1/jndi/command/src/main/java/org/apache/karaf/jndi/command/DeleteCommand.java
----------------------------------------------------------------------
diff --git a/jndi/command/src/main/java/org/apache/karaf/jndi/command/DeleteCommand.java b/jndi/command/src/main/java/org/apache/karaf/jndi/command/DeleteCommand.java
new file mode 100644
index 0000000..3425fdf
--- /dev/null
+++ b/jndi/command/src/main/java/org/apache/karaf/jndi/command/DeleteCommand.java
@@ -0,0 +1,33 @@
+/*
+ * 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.karaf.jndi.command;
+
+import org.apache.felix.gogo.commands.Argument;
+import org.apache.felix.gogo.commands.Command;
+
+@Command(scope = "jndi", name = "delete", description = "Delete a JNDI sub-context.")
+public class DeleteCommand extends JndiCommandSupport {
+
+    @Argument(index = 0, name = "context", description = "The JNDI sub-context name", required = true, multiValued = false)
+    String context;
+
+    public Object doExecute() throws Exception {
+        this.getJndiService().delete(context);
+        return null;
+    }
+
+}

http://git-wip-us.apache.org/repos/asf/karaf/blob/e11582a1/jndi/command/src/main/java/org/apache/karaf/jndi/command/JndiCommandSupport.java
----------------------------------------------------------------------
diff --git a/jndi/command/src/main/java/org/apache/karaf/jndi/command/JndiCommandSupport.java b/jndi/command/src/main/java/org/apache/karaf/jndi/command/JndiCommandSupport.java
new file mode 100644
index 0000000..0e46be3
--- /dev/null
+++ b/jndi/command/src/main/java/org/apache/karaf/jndi/command/JndiCommandSupport.java
@@ -0,0 +1,36 @@
+/*
+ * 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.karaf.jndi.command;
+
+import org.apache.karaf.jndi.JndiService;
+import org.apache.karaf.shell.console.OsgiCommandSupport;
+
+public abstract class JndiCommandSupport extends OsgiCommandSupport {
+
+    private JndiService jndiService;
+
+    public JndiService getJndiService() {
+        return jndiService;
+    }
+
+    public void setJndiService(JndiService jndiService) {
+        this.jndiService = jndiService;
+    }
+
+    public abstract Object doExecute() throws Exception;
+
+}

http://git-wip-us.apache.org/repos/asf/karaf/blob/e11582a1/jndi/command/src/main/java/org/apache/karaf/jndi/command/NamesCommand.java
----------------------------------------------------------------------
diff --git a/jndi/command/src/main/java/org/apache/karaf/jndi/command/NamesCommand.java b/jndi/command/src/main/java/org/apache/karaf/jndi/command/NamesCommand.java
new file mode 100644
index 0000000..47c7a4f
--- /dev/null
+++ b/jndi/command/src/main/java/org/apache/karaf/jndi/command/NamesCommand.java
@@ -0,0 +1,50 @@
+/*
+ * 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.karaf.jndi.command;
+
+import org.apache.felix.gogo.commands.Argument;
+import org.apache.felix.gogo.commands.Command;
+
+import java.util.Map;
+
+@Command(scope = "jndi", name = "names", description = "List the JNDI names.")
+public class NamesCommand extends JndiCommandSupport {
+
+    private static final String NAMES_STRING_FORMAT = "%-20s %-60s";
+
+    @Argument(index = 0, name = "context", description = "The JNDI context to display the names", required = false, multiValued = false)
+    String context;
+
+    public Object doExecute() throws Exception {
+
+        System.out.println(String.format(NAMES_STRING_FORMAT, "JNDI Name", "Class Name"));
+
+        Map<String, String> names;
+        if (context == null) {
+            names = this.getJndiService().names();
+        } else {
+            names = this.getJndiService().names(context);
+        }
+
+        for (String name : names.keySet()) {
+            System.out.println(String.format(NAMES_STRING_FORMAT, name, names.get(name)));
+        }
+
+        return null;
+    }
+
+}

http://git-wip-us.apache.org/repos/asf/karaf/blob/e11582a1/jndi/command/src/main/java/org/apache/karaf/jndi/command/UnbindCommand.java
----------------------------------------------------------------------
diff --git a/jndi/command/src/main/java/org/apache/karaf/jndi/command/UnbindCommand.java b/jndi/command/src/main/java/org/apache/karaf/jndi/command/UnbindCommand.java
new file mode 100644
index 0000000..91283fb
--- /dev/null
+++ b/jndi/command/src/main/java/org/apache/karaf/jndi/command/UnbindCommand.java
@@ -0,0 +1,33 @@
+/*
+ * 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.karaf.jndi.command;
+
+import org.apache.felix.gogo.commands.Argument;
+import org.apache.felix.gogo.commands.Command;
+
+@Command(scope = "jndi", name = "unbind", description = "Unbind a JNDI name.")
+public class UnbindCommand extends JndiCommandSupport {
+
+    @Argument(index = 0, name = "name", description = "The JNDI name to unbind", required = true, multiValued = false)
+    String name;
+
+    public Object doExecute() throws Exception {
+        getJndiService().unbind(name);
+        return null;
+    }
+
+}

http://git-wip-us.apache.org/repos/asf/karaf/blob/e11582a1/jndi/command/src/main/java/org/apache/karaf/jndi/command/completers/ContextsCompleter.java
----------------------------------------------------------------------
diff --git a/jndi/command/src/main/java/org/apache/karaf/jndi/command/completers/ContextsCompleter.java b/jndi/command/src/main/java/org/apache/karaf/jndi/command/completers/ContextsCompleter.java
new file mode 100644
index 0000000..88705c0
--- /dev/null
+++ b/jndi/command/src/main/java/org/apache/karaf/jndi/command/completers/ContextsCompleter.java
@@ -0,0 +1,53 @@
+/*
+ * 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.karaf.jndi.command.completers;
+
+import org.apache.karaf.jndi.JndiService;
+import org.apache.karaf.shell.console.Completer;
+import org.apache.karaf.shell.console.completer.StringsCompleter;
+
+import java.util.List;
+
+/**
+ * Completers on the JNDI contexts.
+ */
+public class ContextsCompleter implements Completer {
+
+    private JndiService jndiService;
+
+    public int complete(String buffer, int cursor, List candidates) {
+        StringsCompleter delegate = new StringsCompleter();
+        try {
+            List<String> contexts = jndiService.contexts();
+            for (String context : contexts) {
+                delegate.getStrings().add(context);
+            }
+        } catch (Exception e) {
+            // nothing to do
+        }
+        return delegate.complete(buffer, cursor, candidates);
+    }
+
+    public JndiService getJndiService() {
+        return jndiService;
+    }
+
+    public void setJndiService(JndiService jndiService) {
+        this.jndiService = jndiService;
+    }
+
+}

http://git-wip-us.apache.org/repos/asf/karaf/blob/e11582a1/jndi/command/src/main/java/org/apache/karaf/jndi/command/completers/NamesCompleter.java
----------------------------------------------------------------------
diff --git a/jndi/command/src/main/java/org/apache/karaf/jndi/command/completers/NamesCompleter.java b/jndi/command/src/main/java/org/apache/karaf/jndi/command/completers/NamesCompleter.java
new file mode 100644
index 0000000..33aef6b
--- /dev/null
+++ b/jndi/command/src/main/java/org/apache/karaf/jndi/command/completers/NamesCompleter.java
@@ -0,0 +1,52 @@
+/*
+ * 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.karaf.jndi.command.completers;
+
+import org.apache.karaf.jndi.JndiService;
+import org.apache.karaf.shell.console.Completer;
+import org.apache.karaf.shell.console.completer.StringsCompleter;
+
+import java.util.List;
+
+/**
+ * Completer to the JNDI names.
+ */
+public class NamesCompleter implements Completer {
+
+    private JndiService jndiService;
+
+    public int complete(String buffer, int cursor, List candidates) {
+        StringsCompleter delegate = new StringsCompleter();
+        try {
+            for (String name : jndiService.names().keySet()) {
+                delegate.getStrings().add(name);
+            }
+        } catch (Exception e) {
+            // nothing to do
+        }
+        return delegate.complete(buffer, cursor, candidates);
+    }
+
+    public JndiService getJndiService() {
+        return jndiService;
+    }
+
+    public void setJndiService(JndiService jndiService) {
+        this.jndiService = jndiService;
+    }
+
+}

http://git-wip-us.apache.org/repos/asf/karaf/blob/e11582a1/jndi/command/src/main/java/org/apache/karaf/jndi/command/completers/ServicesIdCompleter.java
----------------------------------------------------------------------
diff --git a/jndi/command/src/main/java/org/apache/karaf/jndi/command/completers/ServicesIdCompleter.java b/jndi/command/src/main/java/org/apache/karaf/jndi/command/completers/ServicesIdCompleter.java
new file mode 100644
index 0000000..e1673cd
--- /dev/null
+++ b/jndi/command/src/main/java/org/apache/karaf/jndi/command/completers/ServicesIdCompleter.java
@@ -0,0 +1,59 @@
+/*
+ * 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.karaf.jndi.command.completers;
+
+import org.apache.karaf.shell.console.Completer;
+import org.apache.karaf.shell.console.completer.StringsCompleter;
+import org.osgi.framework.Bundle;
+import org.osgi.framework.BundleContext;
+import org.osgi.framework.Constants;
+import org.osgi.framework.ServiceReference;
+
+import java.util.List;
+
+/**
+ * Completer on the OSGi services ID.
+ */
+public class ServicesIdCompleter implements Completer {
+
+    private BundleContext bundleContext;
+
+    public int complete(String buffer, int cursor, List candidates) {
+        StringsCompleter delegate = new StringsCompleter();
+        Bundle[] bundles = bundleContext.getBundles();
+        for (Bundle bundle : bundles) {
+            ServiceReference[] references = bundle.getRegisteredServices();
+            if (references != null) {
+                for (ServiceReference reference : references) {
+                    if (reference.getProperty(Constants.SERVICE_ID) != null) {
+                        delegate.getStrings().add(reference.getProperty(Constants.SERVICE_ID).toString());
+                    }
+                }
+            }
+        }
+        return delegate.complete(buffer, cursor, candidates);
+    }
+
+    public BundleContext getBundleContext() {
+        return bundleContext;
+    }
+
+    public void setBundleContext(BundleContext bundleContext) {
+        this.bundleContext = bundleContext;
+    }
+
+}

http://git-wip-us.apache.org/repos/asf/karaf/blob/e11582a1/jndi/command/src/main/resources/OSGI-INF/blueprint/jndi-command.xml
----------------------------------------------------------------------
diff --git a/jndi/command/src/main/resources/OSGI-INF/blueprint/jndi-command.xml b/jndi/command/src/main/resources/OSGI-INF/blueprint/jndi-command.xml
new file mode 100644
index 0000000..e05d0bb
--- /dev/null
+++ b/jndi/command/src/main/resources/OSGI-INF/blueprint/jndi-command.xml
@@ -0,0 +1,99 @@
+<?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.
+    -->
+<blueprint xmlns="http://www.osgi.org/xmlns/blueprint/v1.0.0" default-activation="lazy">
+
+    <reference id="jndiService" interface="org.apache.karaf.jndi.JndiService" />
+
+    <command-bundle xmlns="http://karaf.apache.org/xmlns/shell/v1.0.0">
+        <command name="jndi/alias">
+            <action class="org.apache.karaf.jndi.command.AliasCommand">
+                <property name="jndiService" ref="jndiService" />
+            </action>
+            <completers>
+                <ref component-id="namesCompleter" />
+                <ref component-id="contextsCompleter" />
+                <null />
+            </completers>
+        </command>
+        <command name="jndi/contexts">
+            <action class="org.apache.karaf.jndi.command.ContextsCommand">
+                <property name="jndiService" ref="jndiService" />
+            </action>
+            <completers>
+                <ref component-id="contextsCompleter" />
+                <null />
+            </completers>
+        </command>
+        <command name="jndi/names">
+            <action class="org.apache.karaf.jndi.command.NamesCommand">
+                <property name="jndiService" ref="jndiService" />
+            </action>
+            <completers>
+                <ref component-id="contextsCompleter" />
+                <null />
+            </completers>
+        </command>
+        <command name="jndi/create">
+            <action class="org.apache.karaf.jndi.command.CreateCommand">
+                <property name="jndiService" ref="jndiService"/>
+            </action>
+            <completers>
+                <ref component-id="contextsCompleter" />
+                <null />
+            </completers>
+        </command>
+        <command name="jndi/delete">
+            <action class="org.apache.karaf.jndi.command.DeleteCommand">
+                <property name="jndiService" ref="jndiService"/>
+            </action>
+            <completers>
+                <ref component-id="contextsCompleter" />
+                <null />
+            </completers>
+        </command>
+        <command name="jndi/bind">
+            <action class="org.apache.karaf.jndi.command.BindCommand">
+                <property name="jndiService" ref="jndiService"/>
+            </action>
+            <completers>
+                <ref component-id="servicesIdCompleter" />
+                <ref component-id="contextsCompleter" />
+                <null />
+            </completers>
+        </command>
+        <command name="jndi/unbind">
+            <action class="org.apache.karaf.jndi.command.UnbindCommand">
+                <property name="jndiService" ref="jndiService" />
+            </action>
+            <completers>
+                <ref component-id="namesCompleter" />
+            </completers>
+        </command>
+    </command-bundle>
+
+    <bean id="namesCompleter" class="org.apache.karaf.jndi.command.completers.NamesCompleter">
+        <property name="jndiService" ref="jndiService" />
+    </bean>
+    <bean id="contextsCompleter" class="org.apache.karaf.jndi.command.completers.ContextsCompleter">
+        <property name="jndiService" ref="jndiService" />
+    </bean>
+    <bean id="servicesIdCompleter" class="org.apache.karaf.jndi.command.completers.ServicesIdCompleter">
+        <property name="bundleContext" ref="blueprintBundleContext" />
+    </bean>
+
+</blueprint>
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/karaf/blob/e11582a1/jndi/command/src/main/resources/OSGI-INF/bundle.info
----------------------------------------------------------------------
diff --git a/jndi/command/src/main/resources/OSGI-INF/bundle.info b/jndi/command/src/main/resources/OSGI-INF/bundle.info
new file mode 100644
index 0000000..d97d132
--- /dev/null
+++ b/jndi/command/src/main/resources/OSGI-INF/bundle.info
@@ -0,0 +1,26 @@
+h1. Synopsis
+
+${project.name}
+
+${project.description}
+
+Maven URL:
+[mvn:${project.groupId}/${project.artifactId}/${project.version}]
+
+h1. Description
+
+This bundle provides the shell commands to manipulate the JNDI service.
+
+The following commands are available:
+
+* jndi:alias
+* jndi:bind
+* jndi:create
+* jndi:contexts
+* jndi:delete
+* jndi:names
+* jndi:unbind
+
+h1. See also
+
+JNDI - section of the Karaf User Guide
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/karaf/blob/e11582a1/jndi/core/NOTICE
----------------------------------------------------------------------
diff --git a/jndi/core/NOTICE b/jndi/core/NOTICE
new file mode 100644
index 0000000..de8d101
--- /dev/null
+++ b/jndi/core/NOTICE
@@ -0,0 +1,71 @@
+Apache Karaf
+Copyright 2010-2013 The Apache Software Foundation
+
+
+I. Included Software
+
+This product includes software developed at
+The Apache Software Foundation (http://www.apache.org/).
+Licensed under the Apache License 2.0.
+
+This product uses software developed at
+The OSGi Alliance (http://www.osgi.org/).
+Copyright (c) OSGi Alliance (2000, 2010).
+Licensed under the Apache License 2.0.
+
+This product includes software developed at
+OW2 (http://www.ow2.org/).
+Licensed under the BSD License.
+
+This product includes software developed at
+OPS4J (http://www.ops4j.org/).
+Licensed under the Apache License 2.0.
+
+This product includes software developed at
+Eclipse Foundation (http://www.eclipse.org/).
+Licensed under the EPL.
+
+This product includes software written by
+Antony Lesuisse.
+Licensed under Public Domain.
+
+
+II. Used Software
+
+This product uses software developed at
+FUSE Source (http://www.fusesource.org/).
+Licensed under the Apache License 2.0.
+
+This product uses software developed at
+AOP Alliance (http://aopalliance.sourceforge.net/).
+Licensed under the Public Domain.
+
+This product uses software developed at
+Tanuki Software (http://www.tanukisoftware.com/).
+Licensed under the Apache License 2.0.
+
+This product uses software developed at
+Jasypt (http://jasypt.sourceforge.net/).
+Licensed under the Apache License 2.0.
+
+This product uses software developed at
+JLine (http://jline.sourceforge.net).
+Licensed under the BSD License.
+
+This product uses software developed at
+SLF4J (http://www.slf4j.org/).
+Licensed under the MIT License.
+
+This product uses software developed at
+SpringSource (http://www.springsource.org/).
+Licensed under the Apache License 2.0.
+
+This product includes software from http://www.json.org.
+Copyright (c) 2002 JSON.org
+
+
+III. License Summary
+- Apache License 2.0
+- BSD License
+- EPL License
+- MIT License

http://git-wip-us.apache.org/repos/asf/karaf/blob/e11582a1/jndi/core/pom.xml
----------------------------------------------------------------------
diff --git a/jndi/core/pom.xml b/jndi/core/pom.xml
new file mode 100644
index 0000000..1c11648
--- /dev/null
+++ b/jndi/core/pom.xml
@@ -0,0 +1,95 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
+
+    <!--
+
+        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.
+    -->
+
+    <modelVersion>4.0.0</modelVersion>
+
+    <parent>
+        <groupId>org.apache.karaf.jndi</groupId>
+        <artifactId>jndi</artifactId>
+        <version>2.4.0-SNAPSHOT</version>
+        <relativePath>../pom.xml</relativePath>
+    </parent>
+
+    <artifactId>org.apache.karaf.jndi.core</artifactId>
+    <packaging>bundle</packaging>
+    <name>Apache Karaf :: JNDI :: Core</name>
+    <description>This bundle provides core implementation of the JNDI management service.</description>
+
+    <properties>
+        <appendedResourcesDirectory>${basedir}/../../etc/appended-resources</appendedResourcesDirectory>
+    </properties>
+
+    <dependencies>
+        <dependency>
+            <groupId>org.apache.xbean</groupId>
+            <artifactId>xbean-naming</artifactId>
+        </dependency>
+        <dependency>
+            <groupId>org.osgi</groupId>
+            <artifactId>org.osgi.core</artifactId>
+        </dependency>
+        <dependency>
+            <groupId>org.apache.aries.proxy</groupId>
+            <artifactId>org.apache.aries.proxy.api</artifactId>
+        </dependency>
+    </dependencies>
+
+    <build>
+        <resources>
+            <resource>
+                <directory>${project.basedir}/src/main/resources</directory>
+                <includes>
+                    <include>**/*</include>
+                </includes>
+            </resource>
+            <resource>
+                <directory>${project.basedir}/src/main/resources</directory>
+                <filtering>true</filtering>
+                <includes>
+                    <include>**/*.info</include>
+                </includes>
+            </resource>
+        </resources>
+        <plugins>
+            <plugin>
+                <groupId>org.apache.felix</groupId>
+                <artifactId>maven-bundle-plugin</artifactId>
+                <configuration>
+                    <instructions>
+                        <Export-Package>
+                            org.apache.karaf.jndi
+                        </Export-Package>
+                        <Import-Package>
+                            javax.management,
+                            javax.management.loading,
+                            org.apache.karaf.management;version=${project.version},
+                            *
+                        </Import-Package>
+                        <Private-Package>
+                            org.apache.karaf.jndi.internal
+                        </Private-Package>
+                    </instructions>
+                </configuration>
+            </plugin>
+        </plugins>
+    </build>
+
+</project>
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/karaf/blob/e11582a1/jndi/core/src/main/java/org/apache/karaf/jndi/JndiMBean.java
----------------------------------------------------------------------
diff --git a/jndi/core/src/main/java/org/apache/karaf/jndi/JndiMBean.java b/jndi/core/src/main/java/org/apache/karaf/jndi/JndiMBean.java
new file mode 100644
index 0000000..0b2be41
--- /dev/null
+++ b/jndi/core/src/main/java/org/apache/karaf/jndi/JndiMBean.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.karaf.jndi;
+
+import javax.management.MBeanException;
+import java.util.List;
+import java.util.Map;
+
+/**
+ * JNDI Service MBean
+ */
+public interface JndiMBean {
+
+    /**
+     * Get a map of JNDI names/class names (as attribute).
+     *
+     * @return the MBean attribute containing the map of names/class names.
+     * @throws MBeanException
+     */
+    public Map<String, String> getNames() throws MBeanException;
+
+    /**
+     * Get a list of JNDI sub-contexts (as attribute).
+     *
+     * @return the MBean attribute containing the list of sub-contexts.
+     * @throws MBeanException
+     */
+    public List<String> getContexts() throws MBeanException;
+
+    /**
+     * Get a map of JNDI names/class names children of a given base context.
+     *
+     * @param context the base context.
+     * @return the map of names/class names.
+     * @throws MBeanException
+     */
+    public Map<String, String> getNames(String context) throws MBeanException;
+
+    /**
+     * Get a list of JNDI sub-contexts children of a given base context.
+     *
+     * @param context the base context.
+     * @return the list of sub-contexts.
+     * @throws MBeanException
+     */
+    public List<String> getContexts(String context) throws MBeanException;
+
+    /**
+     * Create a JNDI sub-context.
+     *
+     * @param context the JNDI sub-context name.
+     * @throws MBeanException
+     */
+    public void create(String context) throws MBeanException;
+
+    /**
+     * Delete a JNDI sub-context.
+     *
+     * @param context the JNDI sub-context name.
+     * @throws MBeanException
+     */
+    public void delete(String context) throws MBeanException;
+
+    /**
+     * Create another JNDI name (alias) for a given one.
+     *
+     * @param name the "source" JNDI name.
+     * @param alias the JNDI alias name.
+     * @throws MBeanException
+     */
+    public void alias(String name, String alias) throws MBeanException;
+
+    /**
+     * Bind an OSGi service with a JNDI name.
+     *
+     * @param serviceId the OSGi service id (service.id property on the service, created by the framework).
+     * @param name the JNDI name.
+     * @throws MBeanException
+     */
+    public void bind(Long serviceId, String name) throws MBeanException;
+
+    /**
+     * Unbind a given JNDI name.
+     *
+     * @param name the JNDI name.
+     * @throws MBeanException
+     */
+    public void unbind(String name) throws MBeanException;
+
+}

http://git-wip-us.apache.org/repos/asf/karaf/blob/e11582a1/jndi/core/src/main/java/org/apache/karaf/jndi/JndiService.java
----------------------------------------------------------------------
diff --git a/jndi/core/src/main/java/org/apache/karaf/jndi/JndiService.java b/jndi/core/src/main/java/org/apache/karaf/jndi/JndiService.java
new file mode 100644
index 0000000..c9f9c57
--- /dev/null
+++ b/jndi/core/src/main/java/org/apache/karaf/jndi/JndiService.java
@@ -0,0 +1,103 @@
+/*
+ * 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.karaf.jndi;
+
+import java.util.List;
+import java.util.Map;
+
+/**
+ * JNDI Service.
+ */
+public interface JndiService {
+
+    /**
+     * List the current JNDI names (with the bound class name).
+     *
+     * @return the JNDI names.
+     * @throws Exception
+     */
+    Map<String, String> names() throws Exception;
+
+    /**
+     * List the current JNDI names in the given context.
+     *
+     * @param context the JNDI context.
+     * @return the JNDI names in the context.
+     * @throws Exception
+     */
+    Map<String, String> names(String context) throws Exception;
+
+    /**
+     * List all JNDI sub-contexts.
+     *
+     * @return a list containing the sub-context names.
+     * @throws Exception
+     */
+    List<String> contexts() throws Exception;
+
+    /**
+     * List the JNDI sub-context from a given context.
+     *
+     * @param context the base JNDI context.
+     * @return a list containing the sub-context names.
+     * @throws Exception
+     */
+    List<String> contexts(String context) throws Exception;
+
+    /**
+     * Create a sub-context.
+     *
+     * @param context the new sub-context name to create.
+     * @throws Exception
+     */
+    void create(String context) throws Exception;
+
+    /**
+     * Delete a sub-context.
+     *
+     * @param context the sub-context name to delete.
+     * @throws Exception
+     */
+    void delete(String context) throws Exception;
+
+    /**
+     * Create an alias on a given JNDI name.
+     *
+     * @param name the JNDI name.
+     * @param alias the alias.
+     * @throws Exception
+     */
+    void alias(String name, String alias) throws Exception;
+
+    /**
+     * Bind a given OSGi service to a JNDI name.
+     *
+     * @param serviceId the OSGi service ID.
+     * @param name the JNDI name.
+     * @throws Exception
+     */
+    void bind(long serviceId, String name) throws Exception;
+
+    /**
+     * Unbind an existing name.
+     *
+     * @param name the JNDI name to unbind.
+     * @throws Exception
+     */
+    void unbind(String name) throws Exception;
+
+}

http://git-wip-us.apache.org/repos/asf/karaf/blob/e11582a1/jndi/core/src/main/java/org/apache/karaf/jndi/KarafInitialContextFactory.java
----------------------------------------------------------------------
diff --git a/jndi/core/src/main/java/org/apache/karaf/jndi/KarafInitialContextFactory.java b/jndi/core/src/main/java/org/apache/karaf/jndi/KarafInitialContextFactory.java
new file mode 100644
index 0000000..a540556
--- /dev/null
+++ b/jndi/core/src/main/java/org/apache/karaf/jndi/KarafInitialContextFactory.java
@@ -0,0 +1,33 @@
+/*
+ * 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.karaf.jndi;
+
+import org.apache.xbean.naming.context.WritableContext;
+import org.apache.xbean.naming.global.GlobalContextManager;
+
+/**
+ * A very simple writable initial context factory.
+ * @see org.apache.xbean.naming.context.WritableContext for details.
+ */
+public class KarafInitialContextFactory extends GlobalContextManager {
+
+    public KarafInitialContextFactory() throws Exception {
+        super();
+        setGlobalContext(new WritableContext());
+    }
+
+}

http://git-wip-us.apache.org/repos/asf/karaf/blob/e11582a1/jndi/core/src/main/java/org/apache/karaf/jndi/internal/JndiMBeanImpl.java
----------------------------------------------------------------------
diff --git a/jndi/core/src/main/java/org/apache/karaf/jndi/internal/JndiMBeanImpl.java b/jndi/core/src/main/java/org/apache/karaf/jndi/internal/JndiMBeanImpl.java
new file mode 100644
index 0000000..ba1b069
--- /dev/null
+++ b/jndi/core/src/main/java/org/apache/karaf/jndi/internal/JndiMBeanImpl.java
@@ -0,0 +1,119 @@
+/*
+ * 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.karaf.jndi.internal;
+
+import org.apache.karaf.jndi.JndiService;
+import org.apache.karaf.jndi.JndiMBean;
+
+import javax.management.MBeanException;
+import javax.management.NotCompliantMBeanException;
+import javax.management.StandardMBean;
+import java.util.List;
+import java.util.Map;
+
+/**
+ * Implementation of the JndiMBean
+ */
+public class JndiMBeanImpl extends StandardMBean implements JndiMBean {
+
+    private JndiService jndiService;
+
+    public JndiMBeanImpl() throws NotCompliantMBeanException {
+        super(JndiMBean.class);
+    }
+
+    public Map<String, String> getNames() throws MBeanException {
+        try {
+            return this.jndiService.names();
+        } catch (Throwable t) {
+            throw new MBeanException(null, t.getMessage());
+        }
+    }
+
+    public List<String> getContexts() throws MBeanException {
+        try {
+            return this.jndiService.contexts();
+        } catch (Throwable t) {
+            throw new MBeanException(null, t.getMessage());
+        }
+    }
+
+    public Map<String, String> getNames(String context) throws MBeanException {
+        try {
+            return this.jndiService.names(context);
+        } catch (Throwable t) {
+            throw new MBeanException(null, t.getMessage());
+        }
+    }
+
+    public List<String> getContexts(String context) throws MBeanException {
+        try {
+            return this.jndiService.contexts(context);
+        } catch (Throwable t) {
+            throw new MBeanException(null, t.getMessage());
+        }
+    }
+
+    public void alias(String name, String alias) throws MBeanException {
+        try {
+            this.jndiService.alias(name, alias);
+        } catch (Throwable t) {
+            throw new MBeanException(null, t.getMessage());
+        }
+    }
+
+    public void bind(Long serviceId, String name) throws MBeanException {
+        try {
+            this.jndiService.bind(serviceId, name);
+        } catch (Throwable t) {
+            throw new MBeanException(null, t.getMessage());
+        }
+    }
+
+    public void unbind(String name) throws MBeanException {
+        try {
+            this.jndiService.unbind(name);
+        } catch (Throwable t) {
+            throw new MBeanException(null, t.getMessage());
+        }
+    }
+
+    public void create(String context) throws MBeanException {
+        try {
+            this.jndiService.create(context);
+        } catch (Throwable t) {
+            throw new MBeanException(null, t.getMessage());
+        }
+    }
+
+    public void delete(String context) throws MBeanException {
+        try {
+            this.jndiService.delete(context);
+        } catch (Throwable t) {
+            throw new MBeanException(null, t.getMessage());
+        }
+    }
+
+    public JndiService getJndiService() {
+        return jndiService;
+    }
+
+    public void setJndiService(JndiService jndiService) {
+        this.jndiService = jndiService;
+    }
+
+}

http://git-wip-us.apache.org/repos/asf/karaf/blob/e11582a1/jndi/core/src/main/java/org/apache/karaf/jndi/internal/JndiServiceImpl.java
----------------------------------------------------------------------
diff --git a/jndi/core/src/main/java/org/apache/karaf/jndi/internal/JndiServiceImpl.java b/jndi/core/src/main/java/org/apache/karaf/jndi/internal/JndiServiceImpl.java
new file mode 100644
index 0000000..d7ba7e4
--- /dev/null
+++ b/jndi/core/src/main/java/org/apache/karaf/jndi/internal/JndiServiceImpl.java
@@ -0,0 +1,306 @@
+/*
+ * 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.karaf.jndi.internal;
+
+import org.apache.aries.proxy.ProxyManager;
+import org.apache.karaf.jndi.JndiService;
+import org.osgi.framework.Bundle;
+import org.osgi.framework.BundleContext;
+import org.osgi.framework.Constants;
+import org.osgi.framework.ServiceReference;
+
+import javax.naming.*;
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+
+/**
+ * Implementation of the JNDI Service.
+ */
+public class JndiServiceImpl implements JndiService {
+
+    private BundleContext bundleContext;
+    private ProxyManager proxyManager;
+
+    private final static String OSGI_JNDI_CONTEXT_PREFIX = "osgi:service/";
+    private final static String OSGI_JNDI_SERVICE_PROPERTY = "osgi.jndi.service.name";
+
+    public Map<String, String> names() throws Exception {
+        Map<String, String> result = names("/");
+        result.putAll(names(OSGI_JNDI_CONTEXT_PREFIX));
+        return result;
+    }
+
+    public Map<String, String> names(String name) throws Exception {
+        Map<String, String> map = new HashMap<String, String>();
+        if (name.startsWith(OSGI_JNDI_CONTEXT_PREFIX)) {
+            // OSGi service binding
+            // make a lookup using directly the OSGi service
+            Bundle[] bundles = bundleContext.getBundles();
+            for (Bundle bundle : bundles) {
+                ServiceReference<?>[] services = bundle.getRegisteredServices();
+                if (services != null) {
+                    for (ServiceReference service : services) {
+                        if (service.getProperty(OSGI_JNDI_SERVICE_PROPERTY) != null) {
+                            Object actualService = bundleContext.getService(service);
+                            if (proxyManager.isProxy(actualService)) {
+                                actualService = proxyManager.unwrap(actualService).call();
+                            }
+                            map.put(OSGI_JNDI_CONTEXT_PREFIX + service.getProperty(OSGI_JNDI_SERVICE_PROPERTY), actualService.getClass().getName());
+                            bundleContext.ungetService(service);
+                        }
+                    }
+                }
+            }
+        } else {
+            // "real" JNDI lookup
+            Context context = new InitialContext();
+            NamingEnumeration<NameClassPair> pairs = context.list(name);
+            while (pairs.hasMoreElements()) {
+                NameClassPair pair = pairs.nextElement();
+                Object o;
+                if (name != null) {
+                    o = context.lookup(name + "/" + pair.getName());
+                } else {
+                    o = context.lookup(pair.getName());
+                }
+                if (o instanceof Context) {
+                    StringBuilder sb = new StringBuilder();
+                    sb.append("/" + pair.getName());
+                    names((Context) o, sb, map);
+                } else {
+                    map.put("/" + pair.getName(), pair.getClassName());
+                }
+            }
+        }
+        return map;
+    }
+
+    public List<String> contexts() throws Exception {
+        return contexts("/");
+    }
+
+    public List<String> contexts(String name) throws Exception {
+        List<String> contexts = new ArrayList<String>();
+        Context context = new InitialContext();
+        NamingEnumeration<NameClassPair> pairs = context.list(name);
+        while (pairs.hasMoreElements()) {
+            NameClassPair pair = pairs.nextElement();
+            Object o;
+            if (name != null) {
+                o = context.lookup(name + "/" + pair.getName());
+            } else {
+                o = context.lookup(pair.getName());
+            }
+            if (o instanceof Context) {
+                StringBuilder sb = new StringBuilder();
+                sb.append("/" + pair.getName());
+                contexts((Context) o, sb, contexts);
+            }
+        }
+        return contexts;
+    }
+
+    private void contexts(Context context, StringBuilder sb, List<String> contexts) throws Exception {
+        NamingEnumeration list = context.listBindings("");
+        while (list.hasMore()) {
+            Binding item = (Binding) list.next();
+            String name = item.getName();
+            Object o = item.getObject();
+            if (o instanceof Context) {
+                if (((Context) o).list("").hasMoreElements()) {
+                    sb.append("/").append(name);
+                    contexts((Context) o, sb, contexts);
+                } else {
+                    contexts.add(sb.toString() + "/" + name);
+                }
+            }
+        }
+    }
+
+    /**
+     * Recursively list a context/names
+     *
+     * @param ctx the startup context.
+     * @param sb the string builder where to construct the full qualified name.
+     * @param map the final map containing name/class name pairs.
+     * @throws Exception
+     */
+    private static final void names(Context ctx, StringBuilder sb, Map<String, String> map) throws Exception {
+        NamingEnumeration list = ctx.listBindings("");
+        while (list.hasMore()) {
+            Binding item = (Binding) list.next();
+            String className = item.getClassName();
+            String name = item.getName();
+            Object o = item.getObject();
+            if (o instanceof Context) {
+                sb.append("/").append(name);
+                names((Context) o, sb, map);
+            } else {
+                map.put(sb.toString() + "/" + name, className);
+            }
+        }
+    }
+
+    public void create(String name) throws Exception {
+        Context context = new InitialContext();
+        String[] splitted = name.split("/");
+        if (splitted.length > 0) {
+            for (int i = 0; i < splitted.length; i++) {
+                try {
+                    Object o = context.lookup(splitted[i]);
+                    if (!(o instanceof Context)) {
+                        throw new NamingException("Name " + splitted[i] + " already exists");
+                    }
+                } catch (NameNotFoundException e) {
+                    context.createSubcontext(splitted[i]);
+                }
+                context = (Context) context.lookup(splitted[i]);
+            }
+        } else {
+            context.createSubcontext(name);
+        }
+    }
+
+    public void delete(String name) throws Exception {
+        Context context = new InitialContext();
+        context.destroySubcontext(name);
+    }
+
+    public void bind(long serviceId, String name) throws Exception {
+        Context context = new InitialContext();
+        Bundle[] bundles = bundleContext.getBundles();
+        for (Bundle bundle : bundles) {
+            ServiceReference<?>[] services = bundle.getRegisteredServices();
+            if (services != null) {
+                for (ServiceReference service : services) {
+                    if (service.getProperty(Constants.SERVICE_ID) != null && ((Long) service.getProperty(Constants.SERVICE_ID)) == serviceId) {
+                        Object actualService = bundleContext.getService(service);
+                        if (proxyManager.isProxy(actualService)) {
+                            actualService = proxyManager.unwrap(actualService).call();
+                        }
+                        try {
+                            String[] splitted = name.split("/");
+                            if (splitted.length > 0) {
+                                for (int i = 0; i < splitted.length - 1; i++) {
+                                    try {
+                                        Object o = context.lookup(splitted[i]);
+                                        if (!(o instanceof Context)) {
+                                            throw new NamingException("Name " + splitted[i] + " already exists");
+                                        }
+                                    } catch (NameNotFoundException nnfe) {
+                                        context.createSubcontext(splitted[i]);
+                                    }
+                                    context = (Context) context.lookup(splitted[i]);
+                                }
+                                name = splitted[splitted.length - 1];
+                            }
+                            context.bind(name, actualService);
+                        } finally {
+                            bundleContext.ungetService(service);
+                        }
+                    }
+                }
+            }
+        }
+    }
+
+    public void alias(String name, String alias) throws Exception {
+        Context context = new InitialContext();
+        if (name.startsWith(OSGI_JNDI_CONTEXT_PREFIX)) {
+            // get the object
+            Bundle[] bundles = bundleContext.getBundles();
+            for (Bundle bundle : bundles) {
+                ServiceReference<?>[] services = bundle.getRegisteredServices();
+                if (services != null) {
+                    for (ServiceReference service : services) {
+                        if (service.getProperty(OSGI_JNDI_SERVICE_PROPERTY) != null && ((String) service.getProperty(OSGI_JNDI_SERVICE_PROPERTY)).equals(name.substring(OSGI_JNDI_CONTEXT_PREFIX.length()))) {
+                            Object actualService = bundleContext.getService(service);
+                            try {
+                                if (proxyManager.isProxy(actualService)) {
+                                    actualService = proxyManager.unwrap(actualService).call();
+                                }
+                                String[] splitted = alias.split("/");
+                                if (splitted.length > 0) {
+                                    for (int i = 0; i < splitted.length - 1; i++) {
+                                        try {
+                                            Object o = context.lookup(splitted[i]);
+                                            if (!(o instanceof Context)) {
+                                                throw new NamingException("Name " + splitted[i] + " already exists");
+                                            }
+                                        } catch (NameNotFoundException nnfe) {
+                                            context.createSubcontext(splitted[i]);
+                                        }
+                                        context = (Context) context.lookup(splitted[i]);
+                                    }
+                                    alias = splitted[splitted.length -1];
+                                }
+                                context.bind(alias, actualService);
+                            } finally {
+                                bundleContext.ungetService(service);
+                            }
+                        }
+                    }
+                }
+            }
+        } else {
+            Object object = context.lookup(name);
+            String[] splitted = alias.split("/");
+            if (splitted.length > 0) {
+                for (int i = 0; i < splitted.length - 1; i++) {
+                    try {
+                        Object o = context.lookup(splitted[i]);
+                        if (!(o instanceof Context)) {
+                            throw new NamingException("Name " + splitted[i] + " already exists");
+                        }
+                    } catch (NameNotFoundException nnfe) {
+                        context.createSubcontext(splitted[i]);
+                    }
+                    context = (Context) context.lookup(splitted[i]);
+                }
+                alias = splitted[splitted.length - 1];
+            }
+            context.bind(alias, object);
+        }
+    }
+
+    public void unbind(String name) throws Exception {
+        InitialContext context = new InitialContext();
+        if (name.startsWith(OSGI_JNDI_CONTEXT_PREFIX)) {
+            throw new IllegalArgumentException("You can't unbind a name from the " + OSGI_JNDI_CONTEXT_PREFIX + " JNDI context.");
+        }
+        context.unbind(name);
+    }
+
+    public BundleContext getBundleContext() {
+        return bundleContext;
+    }
+
+    public void setBundleContext(BundleContext bundleContext) {
+        this.bundleContext = bundleContext;
+    }
+
+    public ProxyManager getProxyManager() {
+        return proxyManager;
+    }
+
+    public void setProxyManager(ProxyManager proxyManager) {
+        this.proxyManager = proxyManager;
+    }
+
+}

http://git-wip-us.apache.org/repos/asf/karaf/blob/e11582a1/jndi/core/src/main/resources/OSGI-INF/blueprint/jndi-core.xml
----------------------------------------------------------------------
diff --git a/jndi/core/src/main/resources/OSGI-INF/blueprint/jndi-core.xml b/jndi/core/src/main/resources/OSGI-INF/blueprint/jndi-core.xml
new file mode 100644
index 0000000..b2b0b1b
--- /dev/null
+++ b/jndi/core/src/main/resources/OSGI-INF/blueprint/jndi-core.xml
@@ -0,0 +1,55 @@
+<?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.
+    -->
+<blueprint xmlns="http://www.osgi.org/xmlns/blueprint/v1.0.0">
+
+    <bean id="karafInitialContextFactory" class="org.apache.karaf.jndi.KarafInitialContextFactory"/>
+
+    <reference id="proxyManager" interface="org.apache.aries.proxy.ProxyManager"/>
+
+    <service ref="karafInitialContextFactory" interface="javax.naming.spi.InitialContextFactory"/>
+
+    <bean id="jndiService" class="org.apache.karaf.jndi.internal.JndiServiceImpl">
+        <property name="bundleContext" ref="blueprintBundleContext"/>
+        <property name="proxyManager" ref="proxyManager"/>
+    </bean>
+
+    <service ref="jndiService" interface="org.apache.karaf.jndi.JndiService">
+        <service-properties>
+            <!-- bind the JNDI service itself in the JNDI context -->
+            <entry key="osgi.jndi.service.name" value="jndi"/>
+        </service-properties>
+    </service>
+
+    <!-- Management -->
+    <bean id="jndiMBeanImpl" class="org.apache.karaf.jndi.internal.JndiMBeanImpl">
+        <property name="jndiService" ref="jndiService"/>
+    </bean>
+
+    <reference id="mbeanServer" interface="javax.management.MBeanServer">
+        <reference-listener ref="mbeanRegister" bind-method="registerMBeanServer" unbind-method="unregisterMBeanServer" />
+    </reference>
+
+    <bean id="mbeanRegister" class="org.apache.karaf.management.MBeanRegistrer" init-method="init"  destroy-method="destroy">
+        <property name="mbeans">
+            <map>
+                <entry value="org.apache.karaf:type=jndi,name=${karaf.name}" key-ref="jndiMBeanImpl" />
+            </map>
+        </property>
+    </bean>
+
+</blueprint>
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/karaf/blob/e11582a1/jndi/core/src/main/resources/OSGI-INF/bundle.info
----------------------------------------------------------------------
diff --git a/jndi/core/src/main/resources/OSGI-INF/bundle.info b/jndi/core/src/main/resources/OSGI-INF/bundle.info
new file mode 100644
index 0000000..4a7a606
--- /dev/null
+++ b/jndi/core/src/main/resources/OSGI-INF/bundle.info
@@ -0,0 +1,19 @@
+h1. Synopsis
+
+${project.name}
+
+${project.description}
+
+Maven URL:
+[mvn:${project.groupId}/${project.artifactId}/${project.version}]
+
+h1. Description
+
+This bundle is the core implementation of the JNDI service support.
+
+JNDI allows to expose any OSGi services as JNDI names. Karaf JNDI also provides a set of commands and a MBean to list
+the current JNDI names, create JNDI aliases, ...
+
+h1. See also
+
+JNDI - section of the Karaf User Guide

http://git-wip-us.apache.org/repos/asf/karaf/blob/e11582a1/jndi/pom.xml
----------------------------------------------------------------------
diff --git a/jndi/pom.xml b/jndi/pom.xml
new file mode 100644
index 0000000..dafd873
--- /dev/null
+++ b/jndi/pom.xml
@@ -0,0 +1,41 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
+
+    <!--
+
+        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.
+    -->
+
+    <modelVersion>4.0.0</modelVersion>
+
+    <parent>
+        <groupId>org.apache.karaf</groupId>
+        <artifactId>karaf</artifactId>
+        <version>2.4.0-SNAPSHOT</version>
+        <relativePath>../pom.xml</relativePath>
+    </parent>
+
+    <groupId>org.apache.karaf.jndi</groupId>
+    <artifactId>jndi</artifactId>
+    <packaging>pom</packaging>
+    <name>Apache Karaf :: JNDI</name>
+
+    <modules>
+        <module>core</module>
+        <module>command</module>
+    </modules>
+
+</project>
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/karaf/blob/e11582a1/pom.xml
----------------------------------------------------------------------
diff --git a/pom.xml b/pom.xml
index 873a9bc..d207b35 100644
--- a/pom.xml
+++ b/pom.xml
@@ -45,6 +45,7 @@
         <module>jaas</module>
         <module>client</module>
         <module>management</module>
+        <module>jndi</module>
         <module>webconsole</module>
         <module>exception</module>
         <module>assemblies</module>
@@ -461,6 +462,16 @@
                 <version>${project.version}</version>
             </dependency>
             <dependency>
+                <groupId>org.apache.karaf.jndi</groupId>
+                <artifactId>org.apache.karaf.jndi.core</artifactId>
+                <version>${project.version}</version>
+            </dependency>
+            <dependency>
+                <groupId>org.apache.karaf.jndi</groupId>
+                <artifactId>org.apache.karaf.jndi.command</artifactId>
+                <version>${project.version}</version>
+            </dependency>
+            <dependency>
                 <groupId>org.apache.karaf.webconsole</groupId>
                 <artifactId>org.apache.karaf.webconsole.admin</artifactId>
                 <version>${project.version}</version>
@@ -1161,6 +1172,11 @@
                 <version>${xbean.version}</version>
             </dependency>
             <dependency>
+                <groupId>org.apache.xbean</groupId>
+                <artifactId>xbean-naming</artifactId>
+                <version>${xbean.version}</version>
+            </dependency>
+            <dependency>
                 <groupId>tanukisoft</groupId>
                 <artifactId>wrapper</artifactId>
                 <version>${jsw.version}</version>