Add support for Gogo. (FELIX-2544)
git-svn-id: https://svn.apache.org/repos/asf/felix/trunk@986336 13f79535-47bb-0310-9956-ffa450edef68
diff --git a/shell.remote/pom.xml b/shell.remote/pom.xml
index 5f6b3c7..9aa49e5 100644
--- a/shell.remote/pom.xml
+++ b/shell.remote/pom.xml
@@ -27,7 +27,7 @@
<packaging>bundle</packaging>
<name>Apache Felix Remote Shell</name>
<description>
- A simple remote textual user interface for Felix' shell service.
+ Provide remote access to Felix Shell or Gogo.
</description>
<version>1.0.5-SNAPSHOT</version>
<artifactId>org.apache.felix.shell.remote</artifactId>
@@ -47,6 +47,11 @@
<artifactId>org.apache.felix.shell</artifactId>
<version>1.0.0</version>
</dependency>
+ <dependency>
+ <groupId>${pom.groupId}</groupId>
+ <artifactId>org.apache.felix.gogo.runtime</artifactId>
+ <version>0.6.0</version>
+ </dependency>
</dependencies>
<build>
<plugins>
@@ -65,9 +70,9 @@
<Private-Package>
org.apache.felix.shell.remote.*
</Private-Package>
- <Import-Package>
- org.osgi.service.log;resolution:=optional,*
- </Import-Package>
+ <DynamicImport-Package>
+ org.apache.felix.service.command,org.apache.felix.shell,org.osgi.service.log
+ </DynamicImport-Package>
</instructions>
</configuration>
</plugin>
diff --git a/shell.remote/src/main/java/org/apache/felix/shell/remote/ServiceMediator.java b/shell.remote/src/main/java/org/apache/felix/shell/remote/ServiceMediator.java
index 994a4ff..f28fa99 100644
--- a/shell.remote/src/main/java/org/apache/felix/shell/remote/ServiceMediator.java
+++ b/shell.remote/src/main/java/org/apache/felix/shell/remote/ServiceMediator.java
@@ -16,14 +16,7 @@
*/
package org.apache.felix.shell.remote;
-import org.apache.felix.shell.ShellService;
-import org.osgi.framework.Bundle;
import org.osgi.framework.BundleContext;
-import org.osgi.framework.Constants;
-import org.osgi.framework.InvalidSyntaxException;
-import org.osgi.framework.ServiceEvent;
-import org.osgi.framework.ServiceListener;
-import org.osgi.framework.ServiceReference;
import org.osgi.service.log.LogService;
import org.osgi.util.tracker.ServiceTracker;
@@ -37,6 +30,7 @@
private final BundleContext m_context;
private final ServiceTracker m_logTracker;
private final ServiceTracker m_shellTracker;
+ private final ServiceTracker m_cpTracker;
ServiceMediator(BundleContext context)
{
@@ -45,21 +39,36 @@
? m_context.getBundle().getLocation()
: m_context.getBundle().getSymbolicName();
m_bundleId = m_context.getBundle().getBundleId();
- ServiceTracker logTracker = null;
+ m_logTracker = new ServiceTracker(
+ m_context, "org.osgi.service.log.LogService", null);
+ m_logTracker.open();
+ m_shellTracker = new ServiceTracker(
+ m_context, "org.apache.felix.shell.ShellService", null);
+ m_shellTracker.open();
+ m_cpTracker = new ServiceTracker(
+ m_context, "org.apache.felix.service.command.CommandProcessor", null);
+ m_cpTracker.open();
+ }
+
+ public Object getCommandProcessor(long wait)
+ {
+ Object svcObj = null;
try
{
- logTracker = new ServiceTracker(m_context, LogService.class.getName(), null);
- logTracker.open();
+ if (wait < 0)
+ {
+ svcObj = m_cpTracker.getService();
+ }
+ else
+ {
+ svcObj = m_cpTracker.waitForService(wait);
+ }
}
- catch (Throwable ex)
+ catch (InterruptedException e)
{
- // This means we don't have access to the log service package since it
- // is optional, so don't track log services.
- logTracker = null;
+ e.printStackTrace(System.err);
}
- m_logTracker = logTracker;
- m_shellTracker = new ServiceTracker(m_context, ShellService.class.getName(), null);
- m_shellTracker.open();
+ return svcObj;
}
/**
@@ -68,55 +77,53 @@
* @param wait time in milliseconds to wait for the reference if it isn't available.
* @return the reference to the <tt>ShellService</tt> as obtained from the OSGi service layer.
*/
- public ShellService getFelixShellService(long wait)
+ public Object getShellService(long wait)
{
- ShellService shell = null;
+ Object svcObj = null;
try
{
if (wait < 0)
{
- shell = (ShellService) m_shellTracker.getService();
+ svcObj = m_shellTracker.getService();
}
else
{
- shell = (ShellService) m_shellTracker.waitForService(wait);
+ svcObj = m_shellTracker.waitForService(wait);
+ }
+
+ return svcObj;
+ }
+ catch (InterruptedException e)
+ {
+ e.printStackTrace(System.err);
+ }
+ return svcObj;
+ }//getFelixShellService
+
+ public Object getLogService(long wait)
+ {
+ Object svcObj = null;
+ try
+ {
+ if (wait < 0)
+ {
+ svcObj = m_logTracker.getService();
+ }
+ else
+ {
+ svcObj = m_logTracker.waitForService(wait);
}
}
catch (InterruptedException e)
{
e.printStackTrace(System.err);
}
-
- return shell;
- }//getFelixShellService
-
- public Object getLogServiceLatch(long wait)
- {
- Object log = null;
- if (m_logTracker != null)
- {
- try
- {
- if (wait < 0)
- {
- log = m_logTracker.getService();
- }
- else
- {
- log = m_logTracker.waitForService(wait);
- }
- }
- catch (InterruptedException e)
- {
- e.printStackTrace(System.err);
- }
- }
- return log;
+ return svcObj;
}//getLogService
public void info(String msg)
{
- Object log = getLogServiceLatch(NO_WAIT);
+ Object log = getLogService(NO_WAIT);
if (log != null)
{
((LogService) log).log(LogService.LOG_INFO, msg);
@@ -129,7 +136,7 @@
public void error(String msg, Throwable t)
{
- Object log = getLogServiceLatch(NO_WAIT);
+ Object log = getLogService(NO_WAIT);
if (log != null)
{
((LogService) log).log(LogService.LOG_ERROR, msg);
@@ -142,7 +149,7 @@
public void error(String msg)
{
- Object log = getLogServiceLatch(NO_WAIT);
+ Object log = getLogService(NO_WAIT);
if (log != null)
{
((LogService) log).log(LogService.LOG_ERROR, msg);
@@ -155,7 +162,7 @@
public void debug(String msg)
{
- Object log = getLogServiceLatch(NO_WAIT);
+ Object log = getLogService(NO_WAIT);
if (log != null)
{
((LogService) log).log(LogService.LOG_DEBUG, msg);
@@ -168,7 +175,7 @@
public void warn(String msg)
{
- Object log = getLogServiceLatch(NO_WAIT);
+ Object log = getLogService(NO_WAIT);
if (log != null)
{
((LogService) log).log(LogService.LOG_WARNING, msg);
@@ -219,6 +226,7 @@
m_logTracker.close();
}
m_shellTracker.close();
+ m_cpTracker.close();
}//deactivate
public static long WAIT_UNLIMITED = 0;
diff --git a/shell.remote/src/main/java/org/apache/felix/shell/remote/Shell.java b/shell.remote/src/main/java/org/apache/felix/shell/remote/Shell.java
index 6530aa3..43e230c 100644
--- a/shell.remote/src/main/java/org/apache/felix/shell/remote/Shell.java
+++ b/shell.remote/src/main/java/org/apache/felix/shell/remote/Shell.java
@@ -18,8 +18,9 @@
import java.io.BufferedReader;
import java.io.IOException;
-import java.io.PrintStream;
import java.net.Socket;
+import org.apache.felix.service.command.CommandProcessor;
+import org.apache.felix.service.command.CommandSession;
import org.apache.felix.shell.ShellService;
@@ -62,61 +63,32 @@
{
m_owner.registerConnection(this);
+ String msg = null;
+
try
{
m_out = new TerminalPrintStream(
m_owner.getServices(), m_socket.getOutputStream());
- BufferedReader in = new BufferedReader(
- new TerminalReader(m_socket.getInputStream(), m_out));
- ReentrantLock lock = new ReentrantLock();
- // Print welcome banner.
- m_out.println();
- m_out.println("Felix Remote Shell Console:");
- m_out.println("============================");
- m_out.println("");
+ Object obj = null;
- do
+ if ((obj = m_owner.getServices().getCommandProcessor(ServiceMediator.NO_WAIT))
+ != null)
{
- String line = "";
- try
- {
- m_out.print("-> ");
- line = in.readLine();
- //make sure to capture end of stream
- if (line == null)
- {
- m_out.println("exit");
- return;
- }
- }
- catch (Exception ex)
- {
- return;
- }
-
- line = line.trim();
- if (line.equalsIgnoreCase("exit") || line.equalsIgnoreCase("disconnect"))
- {
- return;
- }
-
- ShellService shs = m_owner.getServices().getFelixShellService(ServiceMediator.NO_WAIT);
- try
- {
- lock.acquire();
- shs.executeCommand(line, m_out, m_out);
- }
- catch (Exception ex)
- {
- m_owner.getServices().error("Shell::run()", ex);
- }
- finally
- {
- lock.release();
- }
+ CommandProcessor cp = (CommandProcessor) obj;
+ CommandSession session =
+ cp.createSession(m_socket.getInputStream(), m_out, m_out);
+ startGogoShell(session);
}
- while (true);
+ else if ((obj = m_owner.getServices().getShellService(ServiceMediator.NO_WAIT))
+ != null)
+ {
+ startFelixShell();
+ }
+ else
+ {
+ msg = "No shell services available...exiting.";
+ }
}
catch (IOException ex)
{
@@ -125,10 +97,82 @@
finally
{
// no need to clean up in/out, since exit does it all
- exit(null);
+ exit(msg);
}
}//run
+ private void startGogoShell(CommandSession session)
+ {
+ try
+ {
+ session.execute("gosh --login --noshutdown");
+ }
+ catch (Exception e)
+ {
+ e.printStackTrace();
+ }
+ finally
+ {
+ session.close();
+ }
+ }
+
+ private void startFelixShell() throws IOException
+ {
+ BufferedReader in = new BufferedReader(
+ new TerminalReader(m_socket.getInputStream(), m_out));
+ ReentrantLock lock = new ReentrantLock();
+
+ // Print welcome banner.
+ m_out.println();
+ m_out.println("Felix Remote Shell Console:");
+ m_out.println("============================");
+ m_out.println("");
+
+ do
+ {
+ String line = "";
+ try
+ {
+ m_out.print("-> ");
+ line = in.readLine();
+ //make sure to capture end of stream
+ if (line == null)
+ {
+ m_out.println("exit");
+ return;
+ }
+ }
+ catch (Exception ex)
+ {
+ return;
+ }
+
+ line = line.trim();
+ if (line.equalsIgnoreCase("exit") || line.equalsIgnoreCase("disconnect"))
+ {
+ return;
+ }
+
+ ShellService shs = (ShellService)
+ m_owner.getServices().getShellService(ServiceMediator.NO_WAIT);
+ try
+ {
+ lock.acquire();
+ shs.executeCommand(line, m_out, m_out);
+ }
+ catch (Exception ex)
+ {
+ m_owner.getServices().error("Shell::run()", ex);
+ }
+ finally
+ {
+ lock.release();
+ }
+ }
+ while (true);
+ }
+
private void exit(String message)
{
// farewell message