Захват вывода команды ssh из Java - PullRequest
1 голос
/ 24 января 2012

Я пытаюсь запустить некоторые команды Unix из моего кода Java.Я сейчас использую библиотеку Google Expect4J и открыта для любых хорошо документированных библиотек.

Проблема в том, что я пытаюсь захватить вывод команды последнего запуска, но не могу ее получить.Кто-нибудь знает, что я здесь не так делаю?

Проблема, которую я пытаюсь решить, заключается в подключении к моему Jumphost, а затем SSH к некоторым другим серверам, в зависимости от того, могу ли я подключиться, мне нужно скопировать или запустить некоторые сценарии на целевом сервере.

Код, который я написал, вставлен ниже.Пожалуйста, помогите !!!

import java.io.IOException;
import java.util.ArrayList;
import java.util.Hashtable;
import java.util.List;

import org.apache.oro.text.regex.MalformedPatternException;
import org.junit.internal.matchers.SubstringMatcher;

import com.jcraft.jsch.ChannelShell;
import com.jcraft.jsch.JSch;
import com.jcraft.jsch.Session;
import com.bean.Server;

import expect4j.Closure;
import expect4j.Expect4j;
import expect4j.ExpectState;
import expect4j.matches.Match;
import expect4j.matches.RegExpMatch;

public class ExpectTest1 {

    public final String RETURN_CHAR = "\r ";
    public  String expectOut = "";

    private StringBuilder sBuilder = new StringBuilder();

    /**
     * @param args
     */
    public static void main(String[] args) {
        Expect4j exp;
        List<String> cmdsToRun = new ArrayList<String>(); 

        try {
            ExpectTest1 test = new ExpectTest1();
            exp = test.SSH("jumpbox.xyz.com","user1","passwd", cmdsToRun);
            exp.getLastState().toString();
        } catch (Exception e) {
            e.printStackTrace();
    }


}

    public Expect4j SSH(String hostname, String username, String password, List<String> cmdsToRun) throws Exception {
        return SSH(hostname, username, password, 22, cmdsToRun);
    }

    public Expect4j SSH(String hostname, String username, String password, int port, List<String> cmdsToRun) throws Exception {

    JSch jsch=new JSch();
    Session session=jsch.getSession(username, hostname, port);
    if( password != null) {
        session.setPassword(password);
    }

    Hashtable config=new Hashtable();
    config.put("StrictHostKeyChecking", "no");
    session.setConfig(config);
    session.setDaemonThread(true);
    session.connect(3 * 1000);   // making a connection with timeout.

    ChannelShell channel = (ChannelShell) session.openChannel("shell");

    channel.setInputStream(System.in);
    channel.setOutputStream(System.out);

    channel.setPtyType("vt102");

    Expect4j expect = new Expect4j(channel.getInputStream(), channel.getOutputStream());

    channel.connect(5*1000);

    Server hostServer = new Server();
    hostServer.setHostName("box1.xyz.com");
    hostServer.setUsername("user2");

    Server destServer = new Server();
    destServer.setHostName("box2.xyz.com");
    destServer.setUsername("user3");

    boolean isLogged = doSSH(hostServer, expect);
    if(isLogged) {
        doSSH(destServer, expect);
    }

    return expect;
}

    private boolean doSSH (Server server, Expect4j expect) throws IOException, MalformedPatternException, Exception {
        String command = "ssh " + server.getUsername() + "@" + server.getHostName() + RETURN_CHAR;
        System.out.println("Logging in to: " + command);
        boolean logged;
        expect.send(command);
        Thread.sleep(4000);
        command = "uname -a" + RETURN_CHAR;
        System.out.println(command);
        expect.send(command);
        Thread.sleep(10000);

            if(isMatch(expect,server.getHostName().substring(0,server.getHostName().indexOf(".")))) {
            System.out.println("Logged in to:" + server.getHostName() + ".....");
            return true;
        }

        if(isMatch(expect, "Last login")) {
            System.out.println("Logged in to:" + server.getHostName() + ".....");
            return true;
        }

        if(isMatch(expect, "not known")) {
            System.out.println("Node or Service not known...");
            return false;
        }

        System.out.println("Node or Service not known...");
        return false;

        /*expect.expect(new Match[] {
            new RegExpMatch("Name or service not known", new Closure() {
                public void run(ExpectState state) throws Exception {
                    System.out.println("Name or service not known...");
                    expectOut = state.getBuffer();
            }
        })  
        });

        expect.expect( new Match[] {
                new RegExpMatch("Last login: \\w{3} (.*) from", new Closure() {
                    public void run(ExpectState state) throws Exception {
                        System.out.println("Logged In....");
                        expectOut = state.getBuffer();
                    }
                })
            });

        if(expectOut != null && expectOut.length()>0 && !expectOut.matches("Name or service not known")) 
            return true;

        return false;*/

    }

    private boolean isMatch(Expect4j expect, String regEx) throws MalformedPatternException, Exception {
        /*expect.expect( new Match[] {
                new RegExpMatch(regEx, new Closure() {
                    public void run(ExpectState state) throws Exception {
                        System.out.println(state.getBuffer());
                        System.out.println(state.getMatch());
                        expectOut = state.getMatch();
                        //System.out.println(state.getMatch());
                    }
                })
            });

        if(expectOut != null 
                && expectOut.length()>0 
                && expectOut.matches(regEx)) {
            //System.out.println(regEx);
            return true;
        }*/
        System.out.println("*************");
        System.out.println(expect.expect(regEx));
        System.out.println("*************");
        if(expect.expect(regEx) == 0)
            return true;

        return false;
    }

}

Ответы [ 2 ]

1 голос
/ 31 января 2012

Просто идея, вы могли бы рассмотреть возможность использования библиотеки Java, которая обрабатывает ожидаемое и управление ключами для вас. Вот тот, который я нашел, который, кажется, делает свое дело.

http://www.jscape.com/products/components/java/ssh-factory/

Подробнее см. В классах SshScript или SshSession и документации.

1 голос
/ 25 января 2012

Я подозреваю, что ваша команда ssh пытается запросить пароль или попросить вас добавить ключ хоста в файл known_hosts.Я не уверен, что они могут быть выполнены Expect4j, так как ssh подключается к tty напрямую, чтобы задать эти вопросы.Но этот ответ, похоже, решил эту проблему:

Использование ожидающего передачи пароля в ssh

Вот аналогичные вопросы / ответы, которые могут помочь:

Как установить SSH-соединение с брандмауэром (маршрутизатором) с Java?

Когда я автоматизирую свои SSH-соединения, я используюшифрование с открытым / закрытым ключом вместо паролей для подключения к серверу, и я уверен, что сервер был подключен с клиента из командной строки успешно без пароля.Убедитесь, что используется полное имя хоста .Это сохранит ключ хоста в файл `known_hosts, поэтому в будущем его не будет запрашивать.

...