================前情提要================
为了实现DHCP
服务器的IP
存储、回收和查询机制,我们需要将服务器中LXD
容器的网卡IP
查询出来,并且存储到服务器中的Mysql
中。所以,下面介绍如何通过Java
远程连接Linux
服务器以及操作多条Shell
命令。
一、JAVA连接至Linux服务器
创建Maven
项目,导入依赖jsch
<dependency>
<groupId>com.jcraft</groupId>
<artifactId>jsch</artifactId>
<version>0.1.55</version>
</dependency>
实现远程连接,往后我们只需要调用如下两个方法即获取连接和关闭连接。连接的原理即:创建session
对话,使用ip,port,userName,password
进行校验,函数返回session
对话
//jsch创建连接
public Session getJSchSession(String ip , int port, String userName, String password){
JSch jSch = new JSch();
Session session = null;
try {
//创建连接
session = jSch.getSession(userName,ip,port);
session.setPassword(password);
//是否使用密钥登录,一般默认为no
session.setConfig("StrictHostKeyChecking", "no");
//启用连接
session.connect();
System.out.println("==============服务器连接成功==============");
}catch (Exception e){
e.printStackTrace();
System.out.println("==============服务器连接失败==============");
}
return session;
}
//jsch关闭连接
public void closeJSchSession(Session session){
if (session != null) {
try {
session.disconnect();
System.out.println("===========服务器连接关闭成功===========");
}catch (Exception e){
e.printStackTrace();
System.out.println("===========服务器连接关闭失败===========");
}
}
}
二、JAVA操作多条Shell命令
网上找了很多资料,发现大家都是只执行一条命令,这在实际使用中几乎不可能,我们一般都需要传入Shell
命令集合进行操作,并且如果有返回值要进行接受。根据网上的资料,我进行了自己的代码编写。
操作原理
- 使用上述连接中实现的
session
对话创建Channel
执行通道 - 命令集合参数传递给通道,连接通道,通道执行命令,使用
IO
流读命令结果 - 循环读取结果并且将返回值拼接为字符串,若没有返回值则标注
- 将拼接好的字符串保存到集合,并且返回
//用来执行命令
//Session表示传递连接对话,commands表示传递命令集合
public List<String> getCmdResult(Session session , List<String> commands){
//用来存放命令的返回值
List<String> cmdResult = new ArrayList<>();
for (String command : commands) {
Channel channel = null;
try {
//创建执行通道
channel = session.openChannel("exec");
//设置命令
((ChannelExec) channel).setCommand(command);
//连接通道
channel.connect();
//读取通道的输出
InputStream in = channel.getInputStream();
BufferedReader reader = new BufferedReader(new InputStreamReader(in));
//存放命令的执行结果,如果结果有很多行,则每次line的值不同
String line;
//lines用来拼接line结果
StringBuffer lines = new StringBuffer();
while ((line = reader.readLine()) != null) {
//去除头尾的空格
line.trim();
lines = lines.append(line);
}
//如果命令执行没有返回值,则直接输出没有返回值
if (String.valueOf(lines).equals("")){
cmdResult.add("命令["+command+"]执行成功,但没有返回值");
}else {
//否则将每行返回直接存入到list中
cmdResult.add(String.valueOf(lines));
}
reader.close();
channel.disconnect();
} catch (JSchException e) {
throw new RuntimeException(e);
} catch (IOException e) {
throw new RuntimeException(e);
}
}
return cmdResult;
}
三、使用
简单的介绍一下调用过程【这里特别要注意:cd
命令是不生效的。所谓不生效就是你不能先切换到某个目录,然后直接执行创建文件夹,创建文件夹的路径依然要写绝对路径】
public static void main(String[] args) {
String ip = "服务器ip地址";
int port = 22;
String userName = "服务器账号";
String password = "服务器密码";
List<String> cmds = new ArrayList<>();
cmds.add("ls -l");
cmds.add("mkdir MyDir");
GetLinuxConnection GLC = new GetLinuxConnection();
Session session = GLC.getJSchSession(ip,port,userName,password);
ExecLinuxCommands ELC = new ExecLinuxCommands();
List<String> result = ELC.getCmdResult(session, cmds);
result.forEach((x)-> System.out.println(x));
GLC.closeJSchSession(session);
}
执行结果如下