pom.xml添加以下依赖项就行了:
<dependency>
<groupId>ch.ethz.ganymed</groupId>
<artifactId>ganymed-ssh2</artifactId>
<version>262</version>
</dependency>
为了方便起见,封装了一个工具类SSHUtil.java
import ch.ethz.ssh2.Connection;
import ch.ethz.ssh2.Session;
import ch.ethz.ssh2.StreamGobbler;
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
/**
* SSH工具类(可远程执行其它Linux机器上的Shell命令)
*/
public class SSHUtil {
/**
* 连接到主机
*
* @param hostname
* @param username
* @param password
* @return
* @throws Exception
*/
private static Connection getConnection(String hostname, String username, String password) throws Exception {
Connection conn = null;
try {
conn = new Connection(hostname);
conn.connect();
boolean isAuthenticated = conn.authenticateWithPassword(username, password);
if (isAuthenticated == false) {
throw new IOException("Authentication failed.");
}
} catch (Exception e) {
throw new IOException("username or password error.");
}
return conn;
}
/**
* 执行远程命令
*
* @param hostname 远程主机IP
* @param username 用户名
* @param password 密码
* @param command 需要执行的命令
* @param timeout 超时时间(秒)
* @return
* @throws Exception
*/
public static String execRemoteCommand(String hostname, String username, String password, String command, long timeout)
throws Exception {
Connection conn = getConnection(hostname, username, password);
StringBuilder sb = new StringBuilder();
Session session = null;
try {
session = conn.openSession();
session.requestPTY("vt100", 80, 24, 640, 480, null);
session.execCommand(command);
InputStream stdout = new StreamGobbler(session.getStdout());
BufferedReader br = new BufferedReader(new InputStreamReader(stdout));
long start = System.currentTimeMillis();
char[] arr = new char[512];
int read;
int i = 0;
while (true) {
read = br.read(arr, 0, arr.length);
if (read < 0 || (System.currentTimeMillis() - start) > timeout * 1000) {
break;
}
sb.append(new String(arr, 0, read));
i++;
}
} finally {
if (session != null) {
session.close();
}
if (conn != null) {
conn.close();
}
}
return sb.toString();
}
/**
* 执行远程命令(默认5秒超时)
*
* @param hostname 远程主机IP
* @param username 用户名
* @param password 密码
* @param command 需要执行的命令
* @return
* @throws Exception
*/
public static String execRemoteCommand(String hostname, String username, String password, String command)
throws Exception {
return execRemoteCommand(hostname, username, password, command, 5);
}
/**
* 批量执行远程命令
*
* @param hostname 远程主机IP
* @param username 用户名
* @param password 密码
* @param command 需要执行的命令列表
* @param timeout 超时时间(秒)
* @return
* @throws Exception
*/
public static String execRemoteCommand(String hostname, String username, String password, String[] command, long timeout)
throws Exception {
Connection conn = getConnection(hostname, username, password);
StringBuilder sb = new StringBuilder();
Session session = null;
try {
for (int t = 0; t < command.length; t++) {
session = conn.openSession();
session.requestPTY("vt100", 80, 24, 640, 480, null);
session.execCommand(command[t]);
InputStream stdout = new StreamGobbler(session.getStdout());
BufferedReader br = new BufferedReader(new InputStreamReader(stdout));
long start = System.currentTimeMillis();
char[] arr = new char[512];
int read;
int i = 0;
while (true) {
read = br.read(arr, 0, arr.length);
if (read < 0 || (System.currentTimeMillis() - start) > timeout * 1000) {
break;
}
sb.append(new String(arr, 0, read));
i++;
}
session.close();
}
} finally {
if (conn != null) {
conn.close();
}
}
return sb.toString();
}
/**
* 批量执行远程命令(默认5秒超时)
*
* @param hostname 远程主机IP
* @param username 用户名
* @param password 密码
* @param command 需要执行的命令列表
* @return
* @throws Exception
*/
public static String execRemoteCommand(String hostname, String username, String password, String[] command)
throws Exception {
return execRemoteCommand(hostname, username, password, command, 5);
}
}
- 如果要连续执行多个命令,用&&连接,比如:先 cd / 切换到根目录,然后再ls 根目录下的所有文件,可以这样调用:
public static void main(String[] args) {
String hostname = "172.21.129.**";
String username = "root";
String password = "***";
try {
System.out.println(SSHUtil.execRemoteCommand(hostname, username, password,
"pwd&&cd /&&pwd&&ls"));
} catch (Exception e) {
e.printStackTrace();
}
}
上面的命令相当于在同一个session下,连续执行
pwd
cd /
pwd
ls
- 如果要以后台进程调用命令,传入命令时,直接加 nohup 即可