I need to find a way to automate ssh commands to my router. My goal is to make the router restart whenever I run the script from my Java program. I’m having some issues though.
First of all, this is the sequence of output I get from my router’s ssh: First I do:
ssh root@192.168.100.1
which returns:
root@192.168.100.1's password:
I enter the password, “admin”. It then goes to this prompt:
Welcome Visiting Huawei Home Gateway Copyright by Huawei Technologies Co., Ltd. Password is default value, please modify it! WAP>
Now, I input “reset” and it restarts the router.
I’ve tried Tcl with Expect and while I can get it working on Windows, it doesn’t work on Linux. Here’s my code for the Tcl script:
#!/bin/sh # exec tclsh "$0" ${1+"$@"} package require Expect spawn ssh root@192.168.100.1 send "adminr" send "resetr" after 3000 exit
Whenever I try to execute it, Tcl8.6 runs through it and terminates without actually doing anything. However, if I manually input all of these commands while running Tcl8.6, it works just fine
I’ve also tried the JSch Java library. With that, I can get the Java program to connect and output the shell of the router, but any command that I try to send does nothing. Here’s the code from that:
... JSch jsch = new JSch(); Session session = jsch.getSession("root", "192.168.100.1", 22); Properties config = new Properties(); config.put("StrictHostKeyChecking", "no"); session.setConfig(config); // Skip prompting for the password info and go direct... session.setPassword("admin"); session.connect(); String command = "resetr"; Channel channel = session.openChannel("exec"); ((ChannelExec) channel).setCommand(command); ((ChannelExec) channel).setErrStream(System.err); InputStream in = channel.getInputStream(); System.out.println("Connect to session..."); channel.connect(); byte[] tmp = new byte[1024]; while (true) { while (in.available() > 0) { int i = in.read(tmp, 0, 1024); if (i < 0) { break; } System.out.print(new String(tmp, 0, i)); } if (channel.isClosed()) { System.out.println("exit-status: " + channel.getExitStatus()); break; } try { Thread.sleep(1000); } catch (Exception ee) { } } channel.disconnect(); session.disconnect(); System.out.println("disconnected");
This is the output that I get:
Connect to session... Welcome Visiting Huawei Home Gateway Copyright by Huawei Technologies Co., Ltd. Password is default value, please modify it! WAP>
It just stays here until I exit. The router doesn’t restart. I’ve also tried:
String command = "reset";
but it does the same thing. Anybody know of any other ways I could do this?
Advertisement
Answer
Try interacting with the device using shell instead of exec.
Here is a quick-and-dirty code I used to do so, you can adjust it to suit your needs:
private static final String PROMPT = ">"; public static void main(String[] args) throws Exception { Session session = null; ChannelShell channel = null; try { JSch jsch = new JSch(); session = jsch.getSession("root", "192.168.100.1", 22); session.setConfig("StrictHostKeyChecking", "no"); session.setPassword("admin"); session.connect(); channel = (ChannelShell) session.openChannel("shell"); PipedOutputStream reply = new PipedOutputStream(); PipedInputStream input = new PipedInputStream(reply); ByteArrayOutputStream output = new ByteArrayOutputStream(); channel.setInputStream(input, true); channel.setOutputStream(output, true); channel.connect(); getPrompt(channel, output); writeCommand(reply, "reset"); getPrompt(channel, output); } finally { if (channel != null) { channel.disconnect(); } if (session != null) { session.disconnect(); } } } private static void writeCommand(PipedOutputStream reply, String command) throws IOException { System.out.println("Command: " + command); reply.write(command.getBytes()); reply.write("n".getBytes()); } private static void getPrompt(ChannelShell channel, ByteArrayOutputStream output) throws UnsupportedEncodingException, InterruptedException { while (!channel.isClosed()) { String response = new String(output.toByteArray(), "UTF-8"); System.out.println(response); if (response.trim().endsWith(PROMPT)) { output.reset(); return; } Thread.sleep(100); } }
UPDATE: I have noticed that the command you send via SSH ends with r
. Try n
instead and see if it works for you.