FTP Java协议应用

  · FTP服务器搭建

  本文使用Win10搭建的FTP服务器,关于Win10下FTP服务器的搭建,搭建可以参考本博的另一篇博文《Win10 搭建FTP服务器 详细设置》。

  · Maven 依赖

<dependency>
    <groupId>commons-net</groupId>
    <artifactId>commons-net</artifactId>
    <version>3.6</version>
</dependency>
<dependency>
    <groupId>commons-io</groupId>
    <artifactId>commons-io</artifactId>
    <version>2.4</version>
</dependency>

  · FTP 工具类

package com.arhorchin.securitit.protocol.ftp;

import java.io.ByteArrayInputStream;
import java.io.ByteArrayOutputStream;
import java.io.IOException;

import org.apache.commons.net.ftp.FTPClient;
import org.apache.commons.net.ftp.FTPFile;
import org.apache.commons.net.ftp.FTPReply;
import org.apache.log4j.Logger;

/**
 * @author Securitit.
 * @note FTP协议连接HTP服务器工具类.
 */
public class FtpUtil {

    /**
     * logger.
     */
    private Logger logger = Logger.getLogger(FtpUtil.class);

    /**
     * 文件分隔符.
     */
    private String FileSeparator = "/";

    /**
     * FTP主机地址.
     */
    private String host;

    /**
     * FTP主机端口.
     */
    private Integer port;

    /**
     * FTP登录账号.
     */
    private String username;

    /**
     * FTP登录密码.
     */
    private String password;

    /**
     * FTP客户端.
     */
    private FTPClient ftpClient = null;

    /**
     * 构造基于密码认证的ftp对象.
     * @param username FTP登录账号.
     * @param password FTP登录密码.
     * @param host FTP主机地址.
     * @param port FTP主机端口.
     */
    public FtpUtil(String username, String password, String host, int port) {
        this.username = username;
        this.password = password;
        this.host = host;
        this.port = port;
    }

    /**
     * 连接ftp服务器.
     */
    public boolean ftpLogin() {
        try {
            // 初始化FTP客户端.
            ftpClient = new FTPClient();
            ftpClient.setControlEncoding("UTF-8");
            // 连接FTP服务器.
            ftpClient.connect(host, port);
            // 登录FTP服务器.
            ftpClient.login(username, password);
            // 判断是否登录成功.
            int replyCode = ftpClient.getReplyCode();
            if (!FTPReply.isPositiveCompletion(replyCode)) {
                return false;
            }
            return true;
        } catch (Exception ex) {
            logger.error(ex);
            return false;
        }
    }

    /**
     * 关闭连接 server.
     */
    public void sftpLogout() {
        try {
            if (null == ftpClient) {
                return;
            }
            if (ftpClient.isConnected()) {
                ftpClient.disconnect();
            }
            ftpClient.logout();
        } catch (Exception ex) {
            logger.error(ex);
        }
    }

    /**
     * 上传文件.
     * @param ftpBasepath 基础目录.
     * @param ftpFilename 文件名称.
     * @param fileBytes 文件内容.
     * @return .
     */
    public boolean ftpUpload(String ftpBasepath, String ftpFilename, byte[] fileBytes) {
        ByteArrayInputStream bais = null;

        try {
            bais = new ByteArrayInputStream(fileBytes);
            ftpClient.setFileType(ftpClient.BINARY_FILE_TYPE);
            // 创建文件目录.
            createDirecroty(ftpBasepath);
            // 切换工作目录.
            ftpClient.changeWorkingDirectory(ftpBasepath);
            // 上传文件.
            ftpClient.storeFile(ftpFilename, bais);
            return true;
        } catch (Exception ex) {
            logger.error(ex);
            return false;
        }
    }

    /**
     * 下载文件.
     * @param ftpBasepath 基础目录.
     * @param ftpFilename 文件名称.
     * @return .
     */
    public byte[] ftpDownload(String ftpBasepath, String ftpFilename) {
        FTPFile[] ftpFiles = null;
        ByteArrayOutputStream baos = null;

        try {
            baos = new ByteArrayOutputStream();
            // 切换工作目录.
            ftpClient.changeWorkingDirectory(ftpBasepath);
            ftpFiles = ftpClient.listFiles();
            for (FTPFile file : ftpFiles) {
                if (ftpFilename.equalsIgnoreCase(file.getName())) {
                    ftpClient.retrieveFile(file.getName(), baos);
                }
            }
            return baos.toByteArray();
        } catch (Exception ex) {
            logger.error(ex);
            return null;
        }
    }

    /**
     * 删除文件.
     * @param ftpBasepath 基础目录.
     * @param ftpFilename 文件名称.
     * @return .
     */
    public boolean ftpDelete(String ftpBasepath, String ftpFilename) {
        try {
            // 切换工作目录.
            ftpClient.changeWorkingDirectory(ftpBasepath);
            ftpClient.dele(ftpFilename);
            return true;
        } catch (Exception ex) {
            logger.error(ex);
            return false;
        }
    }

    /**
     * 切换工作目录.
     * @param workDir 工作目录.
     * @return 切换结果.
     */
    public boolean changeWorkDir(String workDir) throws IOException {
        return ftpClient.changeWorkingDirectory(workDir);
    }

    /**
     * 创建服务器目录.
     * @param fileDir 文件目录.
     * @return 创建结果.
     * @throws IOException .
     */
    public boolean createDirecroty(String fileDir) throws IOException {
        String currentDir = null;

        currentDir = fileDir;
        // 统一路径格式.
        currentDir = currentDir.replaceAll("\\\\", "/");
        // 输入路径必须正确.
        if (currentDir.equalsIgnoreCase(FileSeparator)) {
            return false;
        }
        // 若工作目录已存在,无需创建.
        if (changeWorkDir(new String(currentDir))) {
            return true;
        }
        // 根据参数创建目录.
        int prevIndex = 0;
        int currentIndex = 0;
        currentIndex = currentDir.indexOf("/", 0);
        String currentSubDir = null;

        while (true) {
            if (currentIndex < 0) {
                currentIndex = currentDir.length();
            }
            currentSubDir = currentDir.substring(prevIndex, currentIndex);
            if (!existFile(currentSubDir)) {
                if (makeDirectory(currentSubDir)) {
                    changeWorkDir(currentSubDir);
                } else {
                    changeWorkDir(currentSubDir);
                }
            } else {
                changeWorkDir(currentSubDir);
            }
            if (currentIndex >= currentDir.length()) {
                break;
            }
            prevIndex = currentIndex + 1;
            currentIndex = currentDir.indexOf("/", currentIndex + 1);
        }
        return true;
    }

    /**
     * 判断文件是否存在.
     * @param filepath 基础目录.
     * @return 是否存在.
     * @throws IOException
     */
    public boolean existFile(String filepath) throws IOException {
        FTPFile[] ftpFileArr = null;

        ftpFileArr = ftpClient.listFiles(filepath);
        if (ftpFileArr.length > 0) {
            return true;
        }
        return false;
    }

    /**
     * 创建文件目录.
     * @param fileDir 文件目录.
     * @return 创建结果.
     */
    public boolean makeDirectory(String fileDir) throws IOException {
        return ftpClient.makeDirectory(fileDir);
    }

}

  · 测试类如下:

package com.arhorchin.securitit.protocol.ftp;

import java.io.File;

import org.apache.commons.io.FileUtils;

/**
 * @author Securitit.
 * @note FtpUtil测试类.
 */
public class FtpUtilTester {

    public static void main(String[] args) throws Exception {
        String ftpIp = "127.0.0.1";
        Integer ftpPort = 21;
        String ftpUsername = "Securitit";
        String ftpPassword = "Wang@881216";

        FtpUtil ftp = null;
        // 登录SFTP服务器.
        ftp = new FtpUtil(ftpUsername, ftpPassword, ftpIp, ftpPort);
        ftp.ftpLogin();

        byte[] fileBytes = FileUtils.readFileToByteArray(new File("C:/Users/Administrator/Downloads/个人文件/test.pdf"));
        // 上传文件.
        ftp.ftpUpload("\\Securitit\\", "test.pdf", fileBytes);
    }

}

  · 总结

  · 监控服务器FTP物理路径可以看到文件的变化。

  · 测试类输出内容中,可以看到下载的文件长度,说明下载成功了。

  · FtpUtil工具类可以拿来直接使用,本人已进行过简单测试。

猜你喜欢

转载自blog.csdn.net/securitit/article/details/107550962