纯Java通过SSH执行Linux命令的方法及代码
转自:http://ilexes.blog.51cto.com/705330/531352
注:此ssh非彼SSH(Struts+Spring+Hibernate)
在Java中,我们可以通过Runtime去执行一些OS的命令,如:
String[]shell=newString[]{"/bin/sh","-c","ls-l"};
Processp=Runtime.getRuntime().exec(shell);
通过在Linux上执行ssh--help命令,
usage:ssh[-1246AaCfgKkMNnqsTtVvXxY][-bbind_address][-ccipher_spec]
[-D[bind_address:]port][-eescape_char][-Fconfigfile]
[-iidentity_file][-L[bind_address:]port:host:hostport]
[-llogin_name][-mmac_spec][-Octl_cmd][-ooption][-pport]
[-R[bind_address:]port:host:hostport][-Sctl_path]
[-wlocal_tun[:remote_tun]][user@]hostname[command]
不难发现,ssh命令中并不能带密码。
如果不需要登录时,我们可以用这样的方式来执行:
String[] shell = new String[] { " /bin/sh " , " -c " , " ssh [email protected] ls -l " } ;
Process p = Runtime.getRuntime().exec(shell); 但是事情往往并不是我们想象的如此简单,绝大部分的客户是不能允许他们的Linux中还存在一个不需要密码就能执行任何命令的帐户的。那么,在Java中就没有任何办法通过ssh登录来执行一些命令吗?
不慌,先来Google一下,从一些网上别人请教的代码的蛛丝蚂迹中,发现了JSch(http://www.jcraft.com/jsch/),这东东还真是不错,来,我们先看看其官方的简介:
JSchisapureJavaimplementationofSSH2.
JSchallowsyoutoconnecttoansshdserveranduseportforwarding,X11forwarding,filetransfer,etc.,andyoucanintegrateitsfunctionalityintoyourownJavaprograms.JSchislicensedunderBSDstylelicense.
这东东支持像telnet一样的ssh的session,SFTP,SCP等。
下面,就让我们来看一个执行ssh命令的通用方法:
public static String sshExecute(String host, String user, String pwd,
String command) {
String osName = System.getProperty("os.name");
// ps -ef|grep tomcat|grep -v grep|awk '{print $2}'
StringBuffer sb = new StringBuffer();
try {
JSch jsch = new JSch();
if (osName.toUpperCase().indexOf("WINDOWS") > -1) {
jsch.setKnownHosts("c:\\known_hosts");
} else {
jsch.setKnownHosts("/root/.ssh/known_hosts");
}
Session session = jsch.getSession(user, host, 22);
session.setPassword(pwd);
session.connect();
Channel channel = session.openChannel("exec");
((ChannelExec) channel).setCommand(command);
InputStream in = channel.getInputStream();
channel.connect();
int nextChar;
while (true) {
while ((nextChar = in.read()) != -1) {
sb.append((char) nextChar);
}
if (channel.isClosed()) {
System.out.println("exit-status: "
+ channel.getExitStatus());
break;
}
try {
Thread.sleep(1000);
} catch (Exception ee) {
}
}
channel.disconnect();
session.disconnect();
} catch (Exception e) {
e.printStackTrace();
}
return sb.toString();
} 看看,是不是挺简单了。
别忘了,由于这是PureJavaprogram,还有一个优点就是,这样的程序不依赖于OS,可以直接在Windows或者其它OS上运行。
对了,执行这个需要RSA的Key文件,示例如下:
192.168.1.4 ssh-rsa AAAAB3NzaC1yc2EAAAABIwAAAQEAsoINy5sLnrzYCTKBh2UrsqHd62dnnimCZtvq8ojTYt7NcAjjtW2FqmFNO+5x/mTwyY+ssoP5SganxDYs3G016aPZDQdGVZMn/08Is
B7QEIAXEVHtgGIGuLqsdMUBBIxV7KI6BK+OWVwv277tBOgqvPcgeEacviFZb2lZhWr8hv
R2pTrPFBLr+UELejm/Nnf9qWDBjDj/d2o8+ReSwN8dzNJIiFyWdboyUCZfHhxNgiGANFx22
gC4lM+Wk8gkASo/QYDvoUwLFrAJoMdsw0d4pn34bQ0mspaaWy4N0+zrNCPcl8D0Q1R
rAjfYfOiZOSTnxabJ2DLijuq7UgFbn2ESMw==
附:产生此文件的简单方法:可以在Linux中用ssh命令登录一次,这样便在/root/.ssh(假如使用root用户登录到Linux)目录下生成known_hosts文件。