Yes, I've checked that in yesterday or so:
https://svn.apache.org/repos/asf/servicemix/smx4/kernel/trunk/gshell/gshell-core/src/main/java/org/apache/servicemix/kernel/gshell/core/sshd/
https://svn.apache.org/repos/asf/servicemix/smx4/kernel/trunk/gshell/gshell-core/src/main/resources/META-INF/spring/gshell-remote.xml
On Fri, Nov 21, 2008 at 7:08 AM, Jason Dillon <[EMAIL PROTECTED]> wrote:
> Hey, do you have "org.apache.servicemix.kernel.gshell.core.sshd" checked in
> somewhere?
>
> --jason
>
>
> On Nov 13, 2008, at 5:58 AM, Guillaume Nodet wrote:
>
>> I've just done a real quick prototype to plug into smx kernel and I've
>> been able to log in into smx kernel using an ssh client and issue a
>> few commands.
>> Following is the class that does everything and the spring config to
>> start the ssh server.
>> The BogusPasswordAuthenticator is a dummy class which I pasted below too.
>>
>> Notice the use of stream filters to convert CR / CRLF stuff. I think
>> this is because both sshd and the geronimo gshell do not handle well
>> the pty request and/or VT100 stuff. But I'm still not sure where the
>> conversion should happen exactly.
>>
>> Also note that i've redefined the ConsoleErrorHandlerImpl, because the
>> default one uses the application.getIO() for displaying errors so they
>> are not available remotely.
>>
>> Let me know what you think, but it basically makes the whole remote
>> bits of gshell unused.
>> I have not implemented the ssh command which should be easy using jsch
>> lib.
>>
>> Let me know if / how I can help you with that bits.
>>
>> ==================================================
>> package org.apache.servicemix.kernel.gshell.core.sshd;
>>
>> import com.google.code.sshd.PasswordAuthenticator;
>>
>> public class BogusPasswordAuthenticator implements PasswordAuthenticator {
>>
>> public Object authenticate(String username, String password) {
>> return (username != null && username.equals(password)) ?
>> username : null;
>> }
>> }
>>
>>
>> ==================================================
>> <bean name="sshServer" class="com.google.code.sshd.SshServer"
>> init-method="start" destroy-method="stop">
>> <property name="port" value="8000" />
>> <property name="shellFactory">
>> <bean
>> class="org.apache.servicemix.kernel.gshell.core.sshd.GShellShellFactory">
>> <property name="branding" ref="branding" />
>> <property name="completers">
>> <list>
>> <ref bean="commandsCompleter"/>
>> <ref bean="aliasNameCompleter"/>
>> </list>
>> </property>
>> <property name="executor" ref="commandLineExecutor" />
>> <property name="history">
>> <bean
>> class="org.apache.geronimo.gshell.wisdom.shell.HistoryImpl">
>> <constructor-arg ref="application"/>
>> </bean>
>> </property>
>> <property name="prompter">
>> <bean
>> class="org.apache.geronimo.gshell.wisdom.shell.ConsolePrompterImpl">
>> <constructor-arg ref="application"/>
>> </bean>
>> </property>
>> </bean>
>> </property>
>> <property name="hostKeyProvider">
>> <bean class="com.google.code.sshd.hostkeys.FileHostKeyProvider">
>> <constructor-arg>
>> <list>
>> <value>${hostKey}</value>
>> </list>
>> </constructor-arg>
>> </bean>
>> </property>
>> <property name="passwordAuthenticator">
>> <!-- TODO: provide real authentication -->
>> <bean
>>
>> class="org.apache.servicemix.kernel.gshell.core.sshd.BogusPasswordAuthenticator"
>> />
>> </property>
>> <!-- Do not use public keys for now
>> <property name="publickeyAuthenticator">
>> <bean class="com.google.code.sshd.BogusPublickeyAuthenticator"
>> />
>> </property>
>> -->
>> <!-- Standard properties -->
>> <property name="channelFactories">
>> <list>
>> <bean
>> class="com.google.code.sshd.channel.ChannelSession$Factory" />
>> </list>
>> </property>
>> <property name="cipherFactories">
>> <list>
>> <bean class="com.google.code.sshd.cipher.AES128CBC$Factory"
>> />
>> <bean
>> class="com.google.code.sshd.cipher.TripleDESCBC$Factory" />
>> <bean
>> class="com.google.code.sshd.cipher.BlowfishCBC$Factory" />
>> <bean class="com.google.code.sshd.cipher.AES192CBC$Factory"
>> />
>> <bean class="com.google.code.sshd.cipher.AES256CBC$Factory"
>> />
>> </list>
>> </property>
>> <property name="compressionFactories">
>> <list>
>> <bean
>> class="com.google.code.sshd.compression.CompressionNone$Factory" />
>> </list>
>> </property>
>> <property name="keyExchangeFactories">
>> <list>
>> <bean class="com.google.code.sshd.kex.DHG1$Factory" />
>> </list>
>> </property>
>> <property name="macFactories">
>> <list>
>> <bean class="com.google.code.sshd.mac.HMACMD5$Factory" />
>> <bean class="com.google.code.sshd.mac.HMACSHA1$Factory" />
>> <bean class="com.google.code.sshd.mac.HMACMD596$Factory" />
>> <bean class="com.google.code.sshd.mac.HMACSHA196$Factory" />
>> </list>
>> </property>
>> <property name="randomFactory">
>> <bean class="com.google.code.sshd.random.JceRandom$Factory" />
>> </property>
>> <property name="userAuthFactories">
>> <list>
>> <bean
>> class="com.google.code.sshd.auth.UserAuthPublicKey$Factory" />
>> <bean
>> class="com.google.code.sshd.auth.UserAuthPassword$Factory" />
>> </list>
>> </property>
>> <property name="signatureFactories">
>> <list>
>> <bean
>> class="com.google.code.sshd.signature.SignatureDSA$Factory" />
>> <bean
>> class="com.google.code.sshd.signature.SignatureRSA$Factory" />
>> </list>
>> </property>
>> </bean>
>>
>>
>>
>> ===================================================
>> package org.apache.servicemix.kernel.gshell.core.sshd;
>>
>> import java.util.Map;
>> import java.util.List;
>> import java.io.OutputStream;
>> import java.io.InputStream;
>> import java.io.Closeable;
>> import java.io.IOException;
>>
>> import com.google.code.sshd.ShellFactory;
>> import com.google.code.sshd.shell.CrLfFilterInputStream;
>> import org.apache.geronimo.gshell.shell.ShellContext;
>> import org.apache.geronimo.gshell.io.IO;
>> import org.apache.geronimo.gshell.command.Variables;
>> import org.apache.geronimo.gshell.console.Console;
>> import org.apache.geronimo.gshell.console.JLineConsole;
>> import org.apache.geronimo.gshell.console.completer.AggregateCompleter;
>> import org.apache.geronimo.gshell.notification.ExitNotification;
>> import org.apache.geronimo.gshell.notification.ErrorNotification;
>> import org.apache.geronimo.gshell.application.model.Branding;
>> import org.apache.geronimo.gshell.commandline.CommandLineExecutor;
>> import org.apache.geronimo.gshell.ansi.AnsiRenderer;
>> import org.slf4j.LoggerFactory;
>> import org.slf4j.Logger;
>> import jline.History;
>> import jline.Completor;
>>
>> public class GShellShellFactory implements ShellFactory {
>>
>> private Logger logger = LoggerFactory.getLogger(getClass());
>> private Branding branding;
>> private Console.Prompter prompter;
>> private CommandLineExecutor executor;
>> private History history;
>> private List<Completor> completers;
>>
>> public Branding getBranding() {
>> return branding;
>> }
>>
>> public void setBranding(Branding branding) {
>> this.branding = branding;
>> }
>>
>> public Console.Prompter getPrompter() {
>> return prompter;
>> }
>>
>> public void setPrompter(Console.Prompter prompter) {
>> this.prompter = prompter;
>> }
>>
>> public CommandLineExecutor getExecutor() {
>> return executor;
>> }
>>
>> public void setExecutor(CommandLineExecutor executor) {
>> this.executor = executor;
>> }
>>
>> public History getHistory() {
>> return history;
>> }
>>
>> public void setHistory(History history) {
>> this.history = history;
>> }
>>
>> public List<Completor> getCompleters() {
>> return completers;
>> }
>>
>> public void setCompleters(List<Completor> completers) {
>> this.completers = completers;
>> }
>>
>> public Shell createShell() {
>> return new ShellImpl();
>> }
>>
>> public class ShellImpl implements ShellFactory.DirectShell,
>> org.apache.geronimo.gshell.shell.Shell {
>>
>> private InputStream in;
>> private OutputStream out;
>> private OutputStream err;
>> private IO io;
>> private Variables variables;
>> private ShellContext context;
>> private boolean closed;
>>
>> public ShellImpl() {
>> }
>>
>> public void setInputStream(InputStream in) {
>> this.in = in;
>> }
>>
>> public void setOutputStream(OutputStream out) {
>> this.out = out;
>> }
>>
>> public void setErrorStream(OutputStream err) {
>> this.err = err;
>> }
>>
>> public void start(Map<String,String> env) throws Exception {
>> this.io = new IO(new CrLfFilterInputStream(in, "IN: ", logger),
>> new LfToCrLfFilterOutputStream(out,
>> "OUT:", logger),
>> new LfToCrLfFilterOutputStream(err,
>> "ERR:", logger),
>> false);
>> this.variables = new Variables((Map) env);
>> this.context = new ShellContext() {
>> public org.apache.geronimo.gshell.shell.Shell getShell() {
>> return ShellImpl.this;
>> }
>> public IO getIo() {
>> return ShellImpl.this.io;
>> }
>> public Variables getVariables() {
>> return ShellImpl.this.variables;
>> }
>> };
>> new Thread() {
>> public void run() {
>> try {
>> ShellImpl.this.run();
>> } catch (Exception e) {
>> e.printStackTrace();
>> } finally {
>> close();
>> }
>> }
>> }.start();
>> }
>>
>> public boolean isAlive() {
>> return !closed;
>> }
>>
>> public int exitValue() {
>> if (!closed) {
>> throw new IllegalThreadStateException();
>> }
>> return 0;
>> }
>>
>> public void destroy() {
>> close();
>> }
>>
>> public ShellContext getContext() {
>> return context;
>> }
>>
>> public Object execute(String line) throws Exception {
>> return executor.execute(getContext(), line);
>> }
>>
>> public Object execute(String command, Object[] args) throws
>> Exception {
>> return executor.execute(getContext(), args);
>> }
>>
>> public Object execute(Object... args) throws Exception {
>> return executor.execute(getContext(), args);
>> }
>>
>> public boolean isOpened() {
>> return !closed;
>> }
>>
>> public void close() {
>> closed = true;
>> close(in);
>> close(out);
>> close(err);
>> }
>>
>> public boolean isInteractive() {
>> return false;
>> }
>>
>> public void run(Object... args) throws Exception {
>> Console.Executor executor = new Console.Executor() {
>> public Result execute(final String line) throws Exception {
>> assert line != null;
>> try {
>> ShellImpl.this.execute(line);
>> }
>> catch (ExitNotification n) {
>> return Result.STOP;
>> }
>> return Result.CONTINUE;
>> }
>> };
>>
>> IO io = getContext().getIo();
>>
>> // Setup the console runner
>> JLineConsole console = new JLineConsole(executor, io);
>> console.setPrompter(getPrompter());
>> console.setErrorHandler(new ConsoleErrorHandlerImpl(io));
>> console.setHistory(getHistory());
>> if (completers != null) {
>> // Have to use aggregate here to get the completion
>> list to update properly
>> console.addCompleter(new AggregateCompleter(completers));
>> }
>> console.run();
>> }
>>
>> private void close(Closeable c) {
>> try {
>> c.close();
>> } catch (IOException e) {
>> // Ignore
>> }
>> }
>>
>> }
>>
>> public static class ConsoleErrorHandlerImpl implements
>> Console.ErrorHandler {
>> private final Logger log = LoggerFactory.getLogger(getClass());
>>
>> private final IO io;
>>
>> private AnsiRenderer renderer = new AnsiRenderer();
>>
>> public ConsoleErrorHandlerImpl(final IO io) {
>> assert io != null;
>> this.io = io;
>> }
>>
>> public Result handleError(final Throwable error) {
>> assert error != null;
>>
>> displayError(error);
>>
>> return Result.CONTINUE;
>> }
>>
>> private void displayError(final Throwable error) {
>> assert error != null;
>>
>> // Decode any error notifications
>> Throwable cause = error;
>> if (error instanceof ErrorNotification) {
>> cause = error.getCause();
>> }
>>
>> //
>> // TODO: Use the Render API
>> //
>>
>> // Spit out the terse reason why we've failed
>> io.err.print("@|bold,red ERROR| ");
>> io.err.print(cause.getClass().getSimpleName());
>> io.err.println(": @|bold,red " + cause.getMessage() + "|");
>>
>> // Determine if the stack trace flag is set
>> String stackTraceProperty =
>> System.getProperty("gshell.show.stacktrace");
>> boolean stackTraceFlag = false;
>> if (stackTraceProperty != null) {
>> stackTraceFlag = stackTraceProperty.trim().equals("true");
>> }
>>
>> if (io.isDebug()) {
>> // If we have debug enabled then skip the fancy bits
>> below, and log the full error, don't decode shit
>> log.debug(error.toString(), error);
>> }
>> else if (io.isVerbose() || stackTraceFlag) {
>> // Render a fancy ansi colored stack trace
>> StackTraceElement[] trace = cause.getStackTrace();
>> StringBuilder buff = new StringBuilder();
>>
>> //
>> // TODO: Move this to helper in gshell-ansi
>> //
>>
>> for (StackTraceElement e : trace) {
>> buff.append(" @|bold at| ").
>> append(e.getClassName()).
>> append(".").
>> append(e.getMethodName()).
>> append(" (@|bold ");
>>
>> buff.append(e.isNativeMethod() ? "Native Method" :
>> (e.getFileName() != null &&
>> e.getLineNumber() != -1 ? e.getFileName() + ":" + e.getLineNumber() :
>> (e.getFileName() != null ?
>> e.getFileName() : "Unknown Source")));
>>
>> buff.append("|)");
>>
>> //
>> // FIXME: This does not properly display the full
>> exception detail when cause contains nested exceptions
>> //
>>
>> io.err.println(buff);
>>
>> buff.setLength(0);
>> }
>> }
>> io.err.flush();
>> }
>> }
>>
>> }
>>
>>
>> On Tue, Nov 11, 2008 at 8:07 AM, Jason Dillon <[EMAIL PROTECTED]>
>> wrote:
>>>
>>> How does one hook up GShell to use this stuff?
>>>
>>> --jason
>>>
>>>
>>> On Nov 7, 2008, at 4:22 AM, Guillaume Nodet wrote:
>>>
>>>> Over the past days, I've been working on a implementing a SSH server
>>>> in java to replace to gshell remoting bits.
>>>> The project is currently hosted at google code:
>>>> http://code.google.com/p/sshd/
>>>>
>>>> This project is based on Mina and the current status is that the ssh
>>>> protocol is in a working state, but there are still a lots of things
>>>> to iron.
>>>> I've been able to connect using openssh 5.0 and 5.1 and also jsch
>>>> (from which i borrowed from code btw) and launch an /bin/sh shell and
>>>> issue a few commands.
>>>> I'd be happy if any committer is interested to work on that to give
>>>> him commits rights on the project.
>>>>
>>>> --
>>>> Cheers,
>>>> Guillaume Nodet
>>>> ------------------------
>>>> Blog: http://gnodet.blogspot.com/
>>>> ------------------------
>>>> Open Source SOA
>>>> http://fusesource.com
>>>
>>>
>>
>>
>>
>> --
>> Cheers,
>> Guillaume Nodet
>> ------------------------
>> Blog: http://gnodet.blogspot.com/
>> ------------------------
>> Open Source SOA
>> http://fusesource.com
>
>
--
Cheers,
Guillaume Nodet
------------------------
Blog: http://gnodet.blogspot.com/
------------------------
Open Source SOA
http://fusesource.com