ftp搭建
package com.key.win.utils;
/**
* @ClassName Md5Utils
* @Description TODO
* @Date 2020/11/18 15:30
* @Version 1.0
*/
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.net.ftp.FTPClient;
import org.apache.commons.net.ftp.FTPFile;
import java.io.ByteArrayInputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.security.MessageDigest;
import java.security.NoSuchAlgorithmException;
@Slf4j
public class DoubleFtpUtils {
protected static char[] hexDigits = {'0', '1', '2', '3', '4', '5', '6',
'7', '8', '9', 'a', 'b', 'c', 'd', 'e', 'f'};
protected static MessageDigest messagedigest = null;
static {
try {
// 获得MD5摘要算法的 MessageDigest 对象
messagedigest = MessageDigest.getInstance("MD5");
} catch (NoSuchAlgorithmException nsaex) {
log.info(DoubleFtpUtils.class.getName() + "初始化失败,MessageDigest不支持MD5Util。");
nsaex.printStackTrace();
}
}
//登陆
public static FTPClient login(String url, int port, String username, String password) {
FTPClient ftpClient = new FTPClient();
try {
if (!ftpClient.isConnected()) {
ftpClient.connect(url, port);
ftpClient.login(username, password);// 登录
ftpClient.enterLocalActiveMode();
// ftp.enterLocalPassiveMode();
ftpClient.setRemoteVerificationEnabled(false);
ftpClient.setBufferSize(100000);
ftpClient.setFileType(FTPClient.BINARY_FILE_TYPE);
log.info(url + "ftpClient receive code " + ftpClient.getReplyCode() + " success");
}
} catch (IOException e) {
e.printStackTrace();
log.info("ftpClient receive code " + ftpClient.getReplyCode() + " fault");
}
return ftpClient;
}
/**
* 生成文件的md5校验值
* 注意:FTPClient如果使用到输入流或者输出流,必须使用completePendingCommand,否则文件内容写入会为null
*
* @param
* @return
* @throws IOException
*/
public static String getFileMD5String(InputStream inputStream, FTPClient goalFtp) throws IOException {
byte[] buffer = new byte[1024];
int numRead = 0;
while ((numRead = inputStream.read(buffer)) > 0) {
messagedigest.update(buffer, 0, numRead);
}
inputStream.close();
goalFtp.completePendingCommand();
byte bytes[] = messagedigest.digest();
int j = bytes.length;
char str[] = new char[j * 2];
int k = 0;
for (int i = 0; i < j; i++) {
byte byte0 = bytes[i];
str[k++] = hexDigits[byte0 >>> 4 & 0xf];// 取字节中高 4 位的数字转换, >>>
// 为逻辑右移,将符号位一起右移,此处未发现两种符号有何不同
str[k++] = hexDigits[byte0 & 0xf];// 取字节中低 4 位的数字转换
}
return new String(str);
}
/**
* 生成32位md5码
* 加盐方式
*
* @param password
* @return
*/
public static String md5Password(String password) {
byte[] result = messagedigest.digest(password.getBytes());
StringBuffer buffer = new StringBuffer();
// 把每一个byte 做一个与运算 0xff;
for (byte b : result) {
// 与运算
int number = b & 0xff;// 加盐
String str = Integer.toHexString(number);
if (str.length() == 1) {
buffer.append("0");
}
buffer.append(str);
}
// 标准的md5加密后的结果
return buffer.toString();
}
/**
* 生成32位md5码
* 普通方式
*
* @param key
* @return
*/
public static String MD5(String key) {
try {
byte[] btInput = key.getBytes();
// 使用指定的字节更新摘要
messagedigest.update(btInput);
// 获得密文
byte[] md = messagedigest.digest();
// 把密文转换成十六进制的字符串形式
int j = md.length;
char str[] = new char[j * 2];
int k = 0;
for (int i = 0; i < j; i++) {
byte byte0 = md[i];
str[k++] = hexDigits[byte0 >>> 4 & 0xf];
str[k++] = hexDigits[byte0 & 0xf];
}
return new String(str);
} catch (Exception e) {
return null;
}
}
/*
* @Description TODO
* @Date 2021/4/12
* @param sourceFtp 源ftp
* @param sourcePath 源ftp路径
* @param goalFtp goalFtp目标ftp
* @param goalPath 目标ftp路径
* @param bornMd5 是否生成MD5加密文件
* @return void
*/
public static void sendDoubleFtpContent(FTPClient sourceFtp, String sourcePath, FTPClient goalFtp, String goalPath, Boolean bornMd5) {
InputStream inputStream = null;
OutputStream outputStream = null;
try {
sendContentMd5(sourceFtp, sourcePath, goalFtp, goalPath, bornMd5, inputStream, outputStream);
if (outputStream != null) {
outputStream.flush();
outputStream.close();
}
if (inputStream != null) {
inputStream.close();
}
//关闭发送文件的服务器ftp
if (sourceFtp.isConnected()) {
sourceFtp.disconnect();
log.info("退出第三方发送文件的FTP完成");
}
if (goalFtp.isConnected()) {
goalFtp.disconnect();
log.info("关闭接受文件的ftp并创建好文件夹");
}
} catch (IOException e) {
e.printStackTrace();
}
}
private static void sendContentMd5(FTPClient sourceFtp, String sourcePath, FTPClient goalFtp, String goalPath, Boolean bornMd5, InputStream inputStream, OutputStream outputStream) {
//发送文件的ftp切换工作路径
try {
sourceFtp.changeWorkingDirectory(sourcePath);
//获取所有文件
FTPFile target[] = sourceFtp.listFiles();
//遍历发送文件的ftp的文件是否是文件夹
for (FTPFile q : target) {
//接收方的ftp上创建好相应的文件夹
if (q.isDirectory()) {
//切换接收方的工作目录
goalFtp.changeWorkingDirectory(goalPath);
//在接收方的工作目录下创建目录文件
goalFtp.makeDirectory(q.getName());
//递归遍历
sendContentMd5(sourceFtp, sourcePath + "/" + q.getName(), goalFtp, goalPath + "/" + q.getName(), bornMd5, inputStream, outputStream);
} else {
//切换工作路径
goalFtp.changeWorkingDirectory(goalPath);
//复制文件
outputStream = goalFtp.storeFileStream(goalFtp.printWorkingDirectory() + "/" + q.getName());
//写入文件
Boolean b = sourceFtp.retrieveFile(q.getName(), outputStream);
if (outputStream != null) {
outputStream.flush();
outputStream.close();
goalFtp.completePendingCommand();
log.info("ftp同步文件完成___" + q.getName());
}
if (bornMd5) {
//转换成输入流
inputStream = goalFtp.retrieveFileStream(goalFtp.printWorkingDirectory() + "/" + q.getName());
//MD5密文
String md5Secret = DoubleFtpUtils.getFileMD5String(inputStream, goalFtp);
inputStream = new ByteArrayInputStream(md5Secret.getBytes("utf-8"));
goalFtp.changeWorkingDirectory(goalFtp.printWorkingDirectory() + "/" + q.getName() + ".md5");
goalFtp.storeFile(q.getName() + ".md5", inputStream);
if (inputStream != null) {
inputStream.close();
log.info("md5密文写入完成___" + q.getName() + ".md5");
}
}
}
}
} catch (IOException e) {
e.printStackTrace();
}
}
}
<!--ftp依赖 -->
<dependency>
<groupId>commons-net</groupId>
<artifactId>commons-net</artifactId>
</dependency>
<!--md5加密算法 -->
<dependency>
<groupId>commons-codec</groupId>
<artifactId>commons-codec</artifactId>
</dependency>