|
@@ -5,16 +5,20 @@ import com.nokia.common.ssh.entity.SSHServer;
|
|
import com.nokia.common.ssh.entity.UserInfoImpl;
|
|
import com.nokia.common.ssh.entity.UserInfoImpl;
|
|
import com.nokia.common.ssh.exception.SSHUtilException;
|
|
import com.nokia.common.ssh.exception.SSHUtilException;
|
|
import com.nokia.common.ssh.exception.ScpAckErrorException;
|
|
import com.nokia.common.ssh.exception.ScpAckErrorException;
|
|
|
|
+import com.xxl.job.core.context.XxlJobHelper;
|
|
import lombok.Getter;
|
|
import lombok.Getter;
|
|
import lombok.Setter;
|
|
import lombok.Setter;
|
|
import lombok.extern.slf4j.Slf4j;
|
|
import lombok.extern.slf4j.Slf4j;
|
|
|
|
|
|
import java.io.*;
|
|
import java.io.*;
|
|
|
|
+import java.nio.file.Files;
|
|
import java.nio.file.NoSuchFileException;
|
|
import java.nio.file.NoSuchFileException;
|
|
|
|
+import java.nio.file.Paths;
|
|
import java.util.ArrayList;
|
|
import java.util.ArrayList;
|
|
import java.util.List;
|
|
import java.util.List;
|
|
import java.util.Properties;
|
|
import java.util.Properties;
|
|
import java.util.Vector;
|
|
import java.util.Vector;
|
|
|
|
+import java.util.stream.Collectors;
|
|
|
|
|
|
/**
|
|
/**
|
|
* 使用jsch库实现的ssh的工具类
|
|
* 使用jsch库实现的ssh的工具类
|
|
@@ -51,41 +55,41 @@ public class SSHUtil {
|
|
/**
|
|
/**
|
|
* 获取文件列表
|
|
* 获取文件列表
|
|
*/
|
|
*/
|
|
|
|
+ @SuppressWarnings("rawtypes")
|
|
public List<String> ls(String path) throws JSchException, SftpException {
|
|
public List<String> ls(String path) throws JSchException, SftpException {
|
|
- log.info("ls1");
|
|
|
|
- session = getConnectSession();
|
|
|
|
- log.info("ls2");
|
|
|
|
- channelSftp = (ChannelSftp) session.openChannel("sftp");
|
|
|
|
- log.info("ls3");
|
|
|
|
- channelSftp.connect();
|
|
|
|
- log.info("ls4");
|
|
|
|
|
|
+ getConnectSession();
|
|
|
|
+ channelSftpConnect();
|
|
List<String> fileNameList = new ArrayList<>();
|
|
List<String> fileNameList = new ArrayList<>();
|
|
- log.info("ls5");
|
|
|
|
Vector fileList = channelSftp.ls(path);
|
|
Vector fileList = channelSftp.ls(path);
|
|
for (Object o : fileList) {
|
|
for (Object o : fileList) {
|
|
String fileName = ((ChannelSftp.LsEntry) o).getFilename();
|
|
String fileName = ((ChannelSftp.LsEntry) o).getFilename();
|
|
if (".".equals(fileName) || "..".equals(fileName)) {
|
|
if (".".equals(fileName) || "..".equals(fileName)) {
|
|
continue;
|
|
continue;
|
|
}
|
|
}
|
|
-
|
|
|
|
fileNameList.add(fileName);
|
|
fileNameList.add(fileName);
|
|
- channelSftp.quit();
|
|
|
|
- session.disconnect();
|
|
|
|
}
|
|
}
|
|
- return fileNameList;
|
|
|
|
|
|
+
|
|
|
|
+ return fileNameList.stream().sorted().collect(Collectors.toList());
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+ /**
|
|
|
|
+ * 下载文件
|
|
|
|
+ */
|
|
|
|
+ public void get(String src, String dst) throws JSchException, SftpException, IOException {
|
|
|
|
+ try (OutputStream out = Files.newOutputStream(Paths.get(dst))) {
|
|
|
|
+ getConnectSession();
|
|
|
|
+ channelSftpConnect();
|
|
|
|
+ channelSftp.get(src, out);
|
|
|
|
+ }
|
|
}
|
|
}
|
|
|
|
|
|
/**
|
|
/**
|
|
* 删除文件
|
|
* 删除文件
|
|
*/
|
|
*/
|
|
- public void delete(String fileName) throws JSchException, SftpException {
|
|
|
|
- session = getConnectSession();
|
|
|
|
- channelSftp = (ChannelSftp) session.openChannel("sftp");
|
|
|
|
- channelSftp.connect();
|
|
|
|
- System.out.println(fileName);
|
|
|
|
- channelSftp.rm(fileName);
|
|
|
|
- channelSftp.quit();
|
|
|
|
- session.disconnect();
|
|
|
|
|
|
+ public void rm(String path) throws JSchException, SftpException {
|
|
|
|
+ getConnectSession();
|
|
|
|
+ channelSftpConnect();
|
|
|
|
+ channelSftp.rm(path);
|
|
}
|
|
}
|
|
|
|
|
|
/**
|
|
/**
|
|
@@ -93,41 +97,37 @@ public class SSHUtil {
|
|
*/
|
|
*/
|
|
public String exec(String command) throws JSchException, IOException {
|
|
public String exec(String command) throws JSchException, IOException {
|
|
StringBuilder stringBuilder = new StringBuilder();
|
|
StringBuilder stringBuilder = new StringBuilder();
|
|
- try {
|
|
|
|
- session = getConnectSession();
|
|
|
|
- channel = session.openChannel("exec");
|
|
|
|
- // jsch的登陆是无环境登陆即非login状态登陆,因此是没有环境变量的,
|
|
|
|
- String execCommand;
|
|
|
|
- // 在命令前添加 bash --login -c "command"以获取环境变量
|
|
|
|
- // source .bashrc && command 也可以解决问题, 但是可能环境加载不全
|
|
|
|
- if (command.startsWith("bash --login -c")) {
|
|
|
|
- execCommand = command;
|
|
|
|
- } else {
|
|
|
|
- execCommand = String.format("bash --login -c \"%s\"", command);
|
|
|
|
- }
|
|
|
|
- ((ChannelExec) channel).setCommand(execCommand);
|
|
|
|
- channel.setInputStream(null);
|
|
|
|
- ((ChannelExec) channel).setErrStream(System.err);
|
|
|
|
- InputStream in = channel.getInputStream();
|
|
|
|
- channel.connect();
|
|
|
|
- byte[] tmp = new byte[1024];
|
|
|
|
- while (true) {
|
|
|
|
- while (in.available() > 0) {
|
|
|
|
- int i = in.read(tmp, 0, 1024);
|
|
|
|
- if (i < 0) {
|
|
|
|
- break;
|
|
|
|
- }
|
|
|
|
- stringBuilder.append(new String(tmp, 0, i));
|
|
|
|
- }
|
|
|
|
- if (channel.isClosed()) {
|
|
|
|
- if (in.available() > 0) {
|
|
|
|
- continue;
|
|
|
|
- }
|
|
|
|
|
|
+ getConnectSession();
|
|
|
|
+ channel = session.openChannel("exec");
|
|
|
|
+ // jsch的登陆是无环境登陆即非login状态登陆,因此是没有环境变量的,
|
|
|
|
+ String execCommand;
|
|
|
|
+ // 在命令前添加 bash --login -c "command"以获取环境变量
|
|
|
|
+ // source .bashrc && command 也可以解决问题, 但是可能环境加载不全
|
|
|
|
+ if (command.startsWith("bash --login -c")) {
|
|
|
|
+ execCommand = command;
|
|
|
|
+ } else {
|
|
|
|
+ execCommand = String.format("bash --login -c \"%s\"", command);
|
|
|
|
+ }
|
|
|
|
+ ((ChannelExec) channel).setCommand(execCommand);
|
|
|
|
+ channel.setInputStream(null);
|
|
|
|
+ ((ChannelExec) channel).setErrStream(System.err);
|
|
|
|
+ InputStream in = channel.getInputStream();
|
|
|
|
+ channel.connect();
|
|
|
|
+ byte[] tmp = new byte[1024];
|
|
|
|
+ while (true) {
|
|
|
|
+ while (in.available() > 0) {
|
|
|
|
+ int i = in.read(tmp, 0, 1024);
|
|
|
|
+ if (i < 0) {
|
|
break;
|
|
break;
|
|
}
|
|
}
|
|
|
|
+ stringBuilder.append(new String(tmp, 0, i));
|
|
|
|
+ }
|
|
|
|
+ if (channel.isClosed()) {
|
|
|
|
+ if (in.available() > 0) {
|
|
|
|
+ continue;
|
|
|
|
+ }
|
|
|
|
+ break;
|
|
}
|
|
}
|
|
- } finally {
|
|
|
|
- disconnect();
|
|
|
|
}
|
|
}
|
|
return stringBuilder.toString();
|
|
return stringBuilder.toString();
|
|
}
|
|
}
|
|
@@ -138,171 +138,185 @@ public class SSHUtil {
|
|
* 注意,文件名不能包含中文
|
|
* 注意,文件名不能包含中文
|
|
*/
|
|
*/
|
|
public boolean scpTo(String sourceFilePath, String targetPath) throws JSchException, IOException, SSHUtilException {
|
|
public boolean scpTo(String sourceFilePath, String targetPath) throws JSchException, IOException, SSHUtilException {
|
|
- try {
|
|
|
|
- session = getConnectSession();
|
|
|
|
- // scp内置了两个参数 -t 和 -f ,这两个参数是隐藏的,不会被用户显式提供,
|
|
|
|
- // 两个scp进程之间传输数据时,远端机器上的scp进程被本地scp进程启动起来时提供上去。
|
|
|
|
- // 需要说明的是,这是通过本地scp进程经ssh远程过去开启远端机器的scp进程来实现的。
|
|
|
|
- // -t 指定为to 也就是目的端模式 指定的对象就是session对应的连接对象targetServer
|
|
|
|
- String command = "scp " + "-t " + targetPath;
|
|
|
|
- channel = session.openChannel("exec");
|
|
|
|
- ((ChannelExec) channel).setCommand(command);
|
|
|
|
- outputStream = channel.getOutputStream();
|
|
|
|
- inputStream = channel.getInputStream();
|
|
|
|
- channel.connect();
|
|
|
|
- if (checkAck(inputStream) != 0) {
|
|
|
|
- log.error("scpTo 执行失败");
|
|
|
|
- return false;
|
|
|
|
- }
|
|
|
|
- File sourceFile = new File(sourceFilePath);
|
|
|
|
- if (sourceFile.isDirectory()) {
|
|
|
|
- log.error("sourceFilePath 必须是文件");
|
|
|
|
- return false;
|
|
|
|
- }
|
|
|
|
- long fileSize = sourceFile.length();
|
|
|
|
- command = "C0644 " + fileSize + " " + sourceFile.getName() + "\n";
|
|
|
|
- outputStream.write(command.getBytes());
|
|
|
|
- outputStream.flush();
|
|
|
|
- if (checkAck(inputStream) != 0) {
|
|
|
|
- log.error("scpTo 执行失败");
|
|
|
|
- return false;
|
|
|
|
- }
|
|
|
|
- fileInputStream = new FileInputStream(sourceFile);
|
|
|
|
- byte[] buffer = new byte[1024];
|
|
|
|
- while (true) {
|
|
|
|
- int len = fileInputStream.read(buffer, 0, buffer.length);
|
|
|
|
- if (len <= 0) {
|
|
|
|
- break;
|
|
|
|
- }
|
|
|
|
- outputStream.write(buffer, 0, len);
|
|
|
|
|
|
+ getConnectSession();
|
|
|
|
+ // scp内置了两个参数 -t 和 -f ,这两个参数是隐藏的,不会被用户显式提供,
|
|
|
|
+ // 两个scp进程之间传输数据时,远端机器上的scp进程被本地scp进程启动起来时提供上去。
|
|
|
|
+ // 需要说明的是,这是通过本地scp进程经ssh远程过去开启远端机器的scp进程来实现的。
|
|
|
|
+ // -t 指定为to 也就是目的端模式 指定的对象就是session对应的连接对象targetServer
|
|
|
|
+ String command = "scp " + "-t " + targetPath;
|
|
|
|
+ channel = session.openChannel("exec");
|
|
|
|
+ ((ChannelExec) channel).setCommand(command);
|
|
|
|
+ outputStream = channel.getOutputStream();
|
|
|
|
+ inputStream = channel.getInputStream();
|
|
|
|
+ channel.connect();
|
|
|
|
+ if (checkAck(inputStream) != 0) {
|
|
|
|
+ log.error("scpTo 执行失败");
|
|
|
|
+ XxlJobHelper.log("scpTo 执行失败");
|
|
|
|
+ return false;
|
|
|
|
+ }
|
|
|
|
+ File sourceFile = new File(sourceFilePath);
|
|
|
|
+ if (sourceFile.isDirectory()) {
|
|
|
|
+ log.error("sourceFilePath 必须是文件");
|
|
|
|
+ XxlJobHelper.log("sourceFilePath 必须是文件");
|
|
|
|
+ return false;
|
|
|
|
+ }
|
|
|
|
+ long fileSize = sourceFile.length();
|
|
|
|
+ command = "C0644 " + fileSize + " " + sourceFile.getName() + "\n";
|
|
|
|
+ outputStream.write(command.getBytes());
|
|
|
|
+ outputStream.flush();
|
|
|
|
+ if (checkAck(inputStream) != 0) {
|
|
|
|
+ log.error("scpTo 执行失败");
|
|
|
|
+ XxlJobHelper.log("scpTo 执行失败");
|
|
|
|
+ return false;
|
|
|
|
+ }
|
|
|
|
+ fileInputStream = new FileInputStream(sourceFile);
|
|
|
|
+ byte[] buffer = new byte[1024];
|
|
|
|
+ while (true) {
|
|
|
|
+ int len = fileInputStream.read(buffer, 0, buffer.length);
|
|
|
|
+ if (len <= 0) {
|
|
|
|
+ break;
|
|
}
|
|
}
|
|
- buffer[0] = 0;
|
|
|
|
- outputStream.write(buffer, 0, 1);
|
|
|
|
- outputStream.flush();
|
|
|
|
- return checkAck(inputStream) == 0;
|
|
|
|
- } finally {
|
|
|
|
- disconnect();
|
|
|
|
|
|
+ outputStream.write(buffer, 0, len);
|
|
}
|
|
}
|
|
|
|
+ buffer[0] = 0;
|
|
|
|
+ outputStream.write(buffer, 0, 1);
|
|
|
|
+ outputStream.flush();
|
|
|
|
+ return checkAck(inputStream) == 0;
|
|
}
|
|
}
|
|
|
|
|
|
/**
|
|
/**
|
|
* 使用scp把targetServer目录下的文件复制到本地
|
|
* 使用scp把targetServer目录下的文件复制到本地
|
|
*/
|
|
*/
|
|
public boolean scpFrom(String sourceFilePath, String targetPath) throws JSchException, IOException, SSHUtilException {
|
|
public boolean scpFrom(String sourceFilePath, String targetPath) throws JSchException, IOException, SSHUtilException {
|
|
- try {
|
|
|
|
- log.debug(sourceFilePath);
|
|
|
|
- session = getConnectSession();
|
|
|
|
- // scp内置了两个参数 -t 和 -f ,这两个参数是隐藏的,不会被用户显式提供,
|
|
|
|
- // 两个scp进程之间传输数据时,远端机器上的scp进程被本地scp进程启动起来时提供上去。
|
|
|
|
- // 需要说明的是,。
|
|
|
|
- // -f 指定对端为from 也就是源端模式 指定的对象就是se这是通过本地scp进程经ssh远程过去开启远端机器的scp进程来实现的ssion对应的连接对象targetServer
|
|
|
|
- String command = "scp -f " + sourceFilePath;
|
|
|
|
- Channel channel = session.openChannel("exec");
|
|
|
|
- ((ChannelExec) channel).setCommand(command);
|
|
|
|
- outputStream = channel.getOutputStream();
|
|
|
|
- inputStream = channel.getInputStream();
|
|
|
|
- channel.connect();
|
|
|
|
- byte[] buf = new byte[1024];
|
|
|
|
- // 发送指令 '0'
|
|
|
|
- // 源端会一直等宿端的回应, 直到等到回应才会传输下一条协议文本.
|
|
|
|
- // 在送出最后一条协议文本后, 源端会传出一个大小为零的字符'0'来表示真正文件传输的开始.
|
|
|
|
- // 当文件接收完成后, 宿端会给源端发送一个'0'
|
|
|
|
- buf[0] = 0;
|
|
|
|
- outputStream.write(buf, 0, 1);
|
|
|
|
- outputStream.flush();
|
|
|
|
- // 接收C0644 这条消息携带了文件的信息
|
|
|
|
- while (true) {
|
|
|
|
- int c = checkAck(inputStream);
|
|
|
|
- // 遇到C时跳出循环
|
|
|
|
- if (c == 'C') {
|
|
|
|
- break;
|
|
|
|
- }
|
|
|
|
|
|
+ log.info(sourceFilePath);
|
|
|
|
+ XxlJobHelper.log(sourceFilePath);
|
|
|
|
+ getConnectSession();
|
|
|
|
+ // scp内置了两个参数 -t 和 -f ,这两个参数是隐藏的,不会被用户显式提供,
|
|
|
|
+ // 两个scp进程之间传输数据时,远端机器上的scp进程被本地scp进程启动起来时提供上去。
|
|
|
|
+ // 需要说明的是,这是通过本地scp进程经ssh远程过去开启远端机器的scp进程来实现的。
|
|
|
|
+ // -f 指定对端为from 也就是源端模式 指定的对象就是session对应的连接对象targetServer
|
|
|
|
+ String command = "scp -f " + sourceFilePath;
|
|
|
|
+ Channel channel = session.openChannel("exec");
|
|
|
|
+ ((ChannelExec) channel).setCommand(command);
|
|
|
|
+ outputStream = channel.getOutputStream();
|
|
|
|
+ inputStream = channel.getInputStream();
|
|
|
|
+ channel.connect();
|
|
|
|
+ byte[] buf = new byte[1024];
|
|
|
|
+ // 发送指令 '0'
|
|
|
|
+ // 源端会一直等宿端的回应, 直到等到回应才会传输下一条协议文本.
|
|
|
|
+ // 在送出最后一条协议文本后, 源端会传出一个大小为零的字符'0'来表示真正文件传输的开始.
|
|
|
|
+ // 当文件接收完成后, 宿端会给源端发送一个'0'
|
|
|
|
+ buf[0] = 0;
|
|
|
|
+ outputStream.write(buf, 0, 1);
|
|
|
|
+ outputStream.flush();
|
|
|
|
+ // 接收C0644 这条消息携带了文件的信息
|
|
|
|
+ while (true) {
|
|
|
|
+ int c = checkAck(inputStream);
|
|
|
|
+ // 遇到C时跳出循环
|
|
|
|
+ if (c == 'C') {
|
|
|
|
+ break;
|
|
}
|
|
}
|
|
- // 接收 '0644 ' 这段字符表示文件的权限
|
|
|
|
- inputStream.read(buf, 0, 5);
|
|
|
|
- // 获取filesize
|
|
|
|
- long filesize = 0L;
|
|
|
|
- while (true) {
|
|
|
|
- if (inputStream.read(buf, 0, 1) < 0) {
|
|
|
|
- break;
|
|
|
|
- }
|
|
|
|
- if (buf[0] == ' ') {
|
|
|
|
- break;
|
|
|
|
- }
|
|
|
|
- filesize = filesize * 10L + (long) (buf[0] - '0');
|
|
|
|
|
|
+ }
|
|
|
|
+ // 接收 '0644 ' 这段字符表示文件的权限
|
|
|
|
+ inputStream.read(buf, 0, 5);
|
|
|
|
+ // 获取filesize
|
|
|
|
+ long filesize = 0L;
|
|
|
|
+ while (true) {
|
|
|
|
+ if (inputStream.read(buf, 0, 1) < 0) {
|
|
|
|
+ break;
|
|
}
|
|
}
|
|
- // 从 C0644命令读取文件名,命令中的文件名是不带路径的
|
|
|
|
- String file = null;
|
|
|
|
- for (int i = 0; ; i++) {
|
|
|
|
- inputStream.read(buf, i, 1);
|
|
|
|
- // 0x0a 是LF 换行符
|
|
|
|
- if (buf[i] == (byte) 0x0a) {
|
|
|
|
- file = new String(buf, 0, i);
|
|
|
|
- break;
|
|
|
|
- }
|
|
|
|
|
|
+ if (buf[0] == ' ') {
|
|
|
|
+ break;
|
|
}
|
|
}
|
|
- log.debug("filesize={}, file={}", filesize, file);
|
|
|
|
- // 发送 '0'
|
|
|
|
- buf[0] = 0;
|
|
|
|
- outputStream.write(buf, 0, 1);
|
|
|
|
- outputStream.flush();
|
|
|
|
- // 如果目标是目录,则需要加上文件名
|
|
|
|
- File target = new File(targetPath);
|
|
|
|
- if (target.isDirectory()) {
|
|
|
|
- log.debug("{} 是目录,需要添加文件名", target.getAbsolutePath());
|
|
|
|
- target = new File(targetPath + File.separator + file);
|
|
|
|
|
|
+ filesize = filesize * 10L + (long) (buf[0] - '0');
|
|
|
|
+ }
|
|
|
|
+ // 从 C0644命令读取文件名,命令中的文件名是不带路径的
|
|
|
|
+ String file = null;
|
|
|
|
+ for (int i = 0; ; i++) {
|
|
|
|
+ inputStream.read(buf, i, 1);
|
|
|
|
+ // 0x0a 是LF 换行符
|
|
|
|
+ if (buf[i] == (byte) 0x0a) {
|
|
|
|
+ file = new String(buf, 0, i);
|
|
|
|
+ break;
|
|
}
|
|
}
|
|
|
|
+ }
|
|
|
|
+ log.info("filesize={}, file={}", filesize, file);
|
|
|
|
+ XxlJobHelper.log("filesize={}, file={}", filesize, file);
|
|
|
|
+ // 发送 '0'
|
|
|
|
+ buf[0] = 0;
|
|
|
|
+ outputStream.write(buf, 0, 1);
|
|
|
|
+ outputStream.flush();
|
|
|
|
+ // 如果目标是目录,则需要加上文件名
|
|
|
|
+ File target = new File(targetPath);
|
|
|
|
+ if (target.isDirectory()) {
|
|
|
|
+ log.info("{} 是目录,需要添加文件名", target.getAbsolutePath());
|
|
|
|
+ XxlJobHelper.log("{} 是目录,需要添加文件名", target.getAbsolutePath());
|
|
|
|
+ target = new File(targetPath + File.separator + file);
|
|
|
|
+ }
|
|
|
|
|
|
- fileOutputStream = new FileOutputStream(target);
|
|
|
|
- int foo;
|
|
|
|
- while (true) {
|
|
|
|
- if (buf.length < filesize) {
|
|
|
|
- foo = buf.length;
|
|
|
|
- } else {
|
|
|
|
- foo = (int) filesize;
|
|
|
|
- }
|
|
|
|
- foo = inputStream.read(buf, 0, foo);
|
|
|
|
- if (foo < 0) {
|
|
|
|
- break;
|
|
|
|
- }
|
|
|
|
- fileOutputStream.write(buf, 0, foo);
|
|
|
|
- filesize -= foo;
|
|
|
|
- if (filesize == 0L) {
|
|
|
|
- break;
|
|
|
|
- }
|
|
|
|
|
|
+ fileOutputStream = new FileOutputStream(target);
|
|
|
|
+ int foo;
|
|
|
|
+ while (true) {
|
|
|
|
+ if (buf.length < filesize) {
|
|
|
|
+ foo = buf.length;
|
|
|
|
+ } else {
|
|
|
|
+ foo = (int) filesize;
|
|
|
|
+ }
|
|
|
|
+ foo = inputStream.read(buf, 0, foo);
|
|
|
|
+ if (foo < 0) {
|
|
|
|
+ break;
|
|
}
|
|
}
|
|
- if (checkAck(inputStream) != 0) {
|
|
|
|
- return false;
|
|
|
|
|
|
+ fileOutputStream.write(buf, 0, foo);
|
|
|
|
+ filesize -= foo;
|
|
|
|
+ if (filesize == 0L) {
|
|
|
|
+ break;
|
|
}
|
|
}
|
|
- // 发送 '0'
|
|
|
|
- buf[0] = 0;
|
|
|
|
- outputStream.write(buf, 0, 1);
|
|
|
|
- outputStream.flush();
|
|
|
|
- log.debug("scp from {}@{}:{}{} to {} 完成", targetServer.getUser(), targetServer.getHost(), targetServer.getPort(), sourceFilePath, target.getAbsolutePath());
|
|
|
|
- return true;
|
|
|
|
- } finally {
|
|
|
|
- disconnect();
|
|
|
|
}
|
|
}
|
|
|
|
+ if (checkAck(inputStream) != 0) {
|
|
|
|
+ return false;
|
|
|
|
+ }
|
|
|
|
+ // 发送 '0'
|
|
|
|
+ buf[0] = 0;
|
|
|
|
+ outputStream.write(buf, 0, 1);
|
|
|
|
+ outputStream.flush();
|
|
|
|
+ log.info("scp from {}@{}:{}{} to {} 完成", targetServer.getUser(), targetServer.getHost(), targetServer.getPort(), sourceFilePath, target.getAbsolutePath());
|
|
|
|
+ XxlJobHelper.log("scp from {}@{}:{}{} to {} 完成", targetServer.getUser(), targetServer.getHost(), targetServer.getPort(), sourceFilePath, target.getAbsolutePath());
|
|
|
|
+ return true;
|
|
}
|
|
}
|
|
|
|
|
|
- private Session getConnectSession() throws JSchException {
|
|
|
|
- log.info("user: {}, host: {}, port: {}", targetServer.getUser(), targetServer.getHost(), targetServer.getPort());
|
|
|
|
- jSch = new JSch();
|
|
|
|
- session = jSch.getSession(targetServer.getUser(), targetServer.getHost(), targetServer.getPort());
|
|
|
|
- log.info("session {}",session);
|
|
|
|
- session.setPassword(targetServer.getPassword());
|
|
|
|
- session.setUserInfo(new UserInfoImpl());
|
|
|
|
- // 不需要输入保存ssh安全密钥的yes或no
|
|
|
|
- Properties properties = new Properties();
|
|
|
|
- properties.put("StrictHostKeyChecking", "no");
|
|
|
|
- session.setConfig(properties);
|
|
|
|
- log.info("session {}",session);
|
|
|
|
- session.connect();
|
|
|
|
- log.debug("已连接到{}@{}:{}", targetServer.getUser(), targetServer.getHost(), targetServer.getPort());
|
|
|
|
- return session;
|
|
|
|
|
|
+ public void getConnectSession() throws JSchException {
|
|
|
|
+ if (jSch == null) {
|
|
|
|
+ jSch = new JSch();
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+ if (session == null) {
|
|
|
|
+ session = jSch.getSession(targetServer.getUser(), targetServer.getHost(), targetServer.getPort());
|
|
|
|
+ session.setPassword(targetServer.getPassword());
|
|
|
|
+ session.setUserInfo(new UserInfoImpl());
|
|
|
|
+ // 不需要输入保存ssh安全密钥的yes或no
|
|
|
|
+ Properties properties = new Properties();
|
|
|
|
+ properties.put("StrictHostKeyChecking", "no");
|
|
|
|
+ session.setConfig(properties);
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+ if (!session.isConnected()) {
|
|
|
|
+ session.connect();
|
|
|
|
+ log.info("已连接到{}@{}:{}", targetServer.getUser(), targetServer.getHost(), targetServer.getPort());
|
|
|
|
+ XxlJobHelper.log("已连接到{}@{}:{}", targetServer.getUser(), targetServer.getHost(), targetServer.getPort());
|
|
|
|
+ }
|
|
}
|
|
}
|
|
|
|
|
|
- private void disconnect() throws IOException {
|
|
|
|
|
|
+ public void channelSftpConnect() throws JSchException {
|
|
|
|
+ if (channelSftp == null) {
|
|
|
|
+ channelSftp = (ChannelSftp) session.openChannel("sftp");
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+ if (!channelSftp.isConnected()) {
|
|
|
|
+ channelSftp.connect();
|
|
|
|
+ }
|
|
|
|
+ }
|
|
|
|
+
|
|
|
|
+ public void disconnect() throws IOException {
|
|
if (fileOutputStream != null) {
|
|
if (fileOutputStream != null) {
|
|
fileOutputStream.close();
|
|
fileOutputStream.close();
|
|
fileOutputStream = null;
|
|
fileOutputStream = null;
|
|
@@ -319,11 +333,15 @@ public class SSHUtil {
|
|
channel.disconnect();
|
|
channel.disconnect();
|
|
channel = null;
|
|
channel = null;
|
|
}
|
|
}
|
|
|
|
+ if (channelSftp != null) {
|
|
|
|
+ channelSftp.quit();
|
|
|
|
+ }
|
|
if (session != null) {
|
|
if (session != null) {
|
|
session.disconnect();
|
|
session.disconnect();
|
|
session = null;
|
|
session = null;
|
|
}
|
|
}
|
|
jSch = null;
|
|
jSch = null;
|
|
|
|
+ log.info("jsch disconnected");
|
|
}
|
|
}
|
|
|
|
|
|
/**
|
|
/**
|
|
@@ -352,7 +370,8 @@ public class SSHUtil {
|
|
c = in.read();
|
|
c = in.read();
|
|
sb.append((char) c);
|
|
sb.append((char) c);
|
|
} while (c != '\n');
|
|
} while (c != '\n');
|
|
- log.debug("checkAck发现错误消息: ack={}-msg={}", b, sb);
|
|
|
|
|
|
+ log.info("checkAck发现错误消息: ack={}-msg={}", b, sb);
|
|
|
|
+ XxlJobHelper.log("checkAck发现错误消息: ack={}-msg={}", b, sb);
|
|
if (b == 1 && sb.toString().endsWith("No such file or directory")) {
|
|
if (b == 1 && sb.toString().endsWith("No such file or directory")) {
|
|
throw new NoSuchFileException(sb.toString());
|
|
throw new NoSuchFileException(sb.toString());
|
|
} else {
|
|
} else {
|