FTP連接,上傳,下載,刪除文件方法

解決的兩個問題
1.設置連接超時時間,如下:
ftp.setConnectTimeout(3*1000);//設置連接ftp超時時間3秒

2.文件下載後,出現文件中中文亂碼的情況,解決辦法是,設置編碼格式,如下:
ftp.setFileType(FTP.BINARY_FILE_TYPE);//定義編碼格式 防止文件中的中文出現亂碼

以下列出測試可用的源碼:
LoadConfigs

import java.io.FileInputStream;
import java.io.IOException;
import java.io.InputStreamReader;
import java.io.Reader;
import java.util.HashMap;
import java.util.Map;
import java.util.Properties;


public class LoadConfigs {
    /**
     * 系統的配置文件類路徑
     */
    public static final String CONFIG_PATH = "/conf/config.properties";

    private static Properties configs=new Properties();;

    private static String propertiesPath = ResourceUtil.getAbsolutePath(CONFIG_PATH);

    private static void initConfigs(){
        try {
            Reader inStream = new InputStreamReader(new FileInputStream(propertiesPath), "UTF-8");
            configs.load(inStream);
        }catch (IOException e){
            System.err.println("load config.properties error");
        }
    }

    public static Map getConfig(){
        initConfigs();
        Map<String,String> configMap = new HashMap<String, String>();
        configMap.put("ftpServer.backup.host.ip",configs.getProperty("ftpServer.backup.host.ip"));
        configMap.put("ftpServer.backup.host.port",configs.getProperty("ftpServer.backup.host.port"));
        configMap.put("ftpServer.backup.host.account",configs.getProperty("ftpServer.backup.host.account"));
        configMap.put("ftpServer.backup.host.pwd",configs.getProperty("ftpServer.backup.host.pwd"));
        configMap.put("ftpServer.backup.host.path",configs.getProperty("ftpServer.backup.host.path"));
        configMap.put("linuxOS.backup.local.path",configs.getProperty("linuxOS.backup.local.path"));
        configMap.put("winOS.backup.local.path",configs.getProperty("winOS.backup.local.path"));
        return configMap;
    }

    public static String getConfig(String key){
        return configs.getProperty(key);
    }

    public enum OS {
        WIN, LINUX, OTHER
    }

    public static OS checkOSType() {
        String osName = System.getProperty("os.name");
        if (osName.toLowerCase().startsWith("win")) {
            return OS.WIN;
        } else if (osName.toLowerCase().startsWith("lin")) {
            return OS.LINUX;
        } else {
            return OS.OTHER;
        }
    }

}

ResourceUtil

import java.io.*;
import java.net.URISyntaxException;
import java.net.URL;

public class ResourceUtil {

    /**
     * 工程內資源到文件系統的拷貝。
     * 從類路徑到文件系統路徑
     *
     * @param resourceAbsoluteClassPath 絕對類路徑
     * @param targetFile                目標文件
     * @throws java.io.IOException
     */
    public static void copyResourceToFile(String resourceAbsoluteClassPath,
                                          File targetFile) throws IOException {
        InputStream is = ResourceUtil.class.getResourceAsStream(resourceAbsoluteClassPath);
        if (is == null) {
            throw new IOException("Resource not found! " + resourceAbsoluteClassPath);
        }
        OutputStream os = null;
        try {
            os = new FileOutputStream(targetFile);
            byte[] buffer = new byte[2048];
            int length;
            while ((length = is.read(buffer)) != -1) {
                os.write(buffer, 0, length);
            }
            os.flush();
        } finally {
            try {
                is.close();
                if (os != null) {
                    os.close();
                }
            } catch (Exception ignore) {
                // ignore
            }
        }
    }

    public static String getAbsolutePath(String classPath) {
        URL configUrl = ResourceUtil.class.getResource(classPath);
        if (configUrl == null) {
            return null;
        }
        try {
            return configUrl.toURI().getPath();
        } catch (URISyntaxException e) {
            throw new RuntimeException(e);
        }
    }

}

config.properties

#ftp日誌備份相關配置
ftpServer.backup.host.ip=192.168.20.170
ftpServer.backup.host.port=21
ftpServer.backup.host.account=kkk
ftpServer.backup.host.pwd=kkkkkk
ftpServer.backup.host.path=/backup/log/
linuxOS.backup.local.path=/usr/local/backup/log/
winOS.backup.local.path=e:\\

FTPTool

import java.io.*;
import java.util.Map;

import org.apache.commons.net.ftp.FTP;
import org.apache.commons.net.ftp.FTPClient;
import org.apache.commons.net.ftp.FTPClientConfig;
import org.apache.commons.net.ftp.FTPFile;
import org.apache.commons.net.ftp.FTPReply;
import wst.phone.util.LoadConfigs;

public class FtpTool {

    private static LoadConfigs.OS osType = LoadConfigs.checkOSType();

    //    //ftp常量
    private static Map configMap = LoadConfigs.getConfig();

    private static String FTP_BACKUP_HOST_IP = (String) configMap.get("ftpServer.backup.host.ip");
    private static String FTP_BACKUP_HOST_PORT = (String) configMap.get("ftpServer.backup.host.port");
    private static String FTP_BACKUP_HOST_ACCOUNT = (String) configMap.get("ftpServer.backup.host.account");
    private static String FTP_BACKUP_HOST_PWD = (String) configMap.get("ftpServer.backup.host.pwd");
    private static String FTP_BACKUP_HOST_PATH = (String) configMap.get("ftpServer.backup.host.path");
    private static String LINUX_BACKUP_LOCAL_PATH = (String) configMap.get("linuxOS.backup.local.path");
    private static String WIN_BACKUP_LOCAL_PATH = (String) configMap.get("winOS.backup.local.path");
    private static String BACKUP_LOCAL_PATH = (osType == LoadConfigs.OS.LINUX ? LINUX_BACKUP_LOCAL_PATH : WIN_BACKUP_LOCAL_PATH);

    /**
     * 獲得連接-FTP方式
     *
     * @param hostIp   FTP服務器地址
     * @param port     FTP服務器端口
     * @param userName FTP登錄用戶名
     * @param passWord FTP登錄密碼
     * @return FTPClient
     */
    public FTPClient getConnectionFTP(String hostIp, int port, String userName, String passWord) throws Exception{
        //創建FTPClient對象
        FTPClient ftp = new FTPClient();
        ftp.setConnectTimeout(3*1000);//設置連接ftp超時時間3秒
        try {
            //連接FTP服務器
            ftp.connect(hostIp, port);

            //下面三行代碼必須要,而且不能改變編碼格式,否則不能正確下載中文文件
            ftp.setControlEncoding("UTF-8");
            FTPClientConfig conf = new FTPClientConfig(FTPClientConfig.SYST_NT);
            conf.setServerLanguageCode("zh");
            //登錄ftp
            ftp.login(userName, passWord);
            if (!FTPReply.isPositiveCompletion(ftp.getReplyCode())) {
                ftp.disconnect();
                System.out.println("Connect FTP Server failed.");
            }
            System.out.println("Connect FTP Server success.");
        } catch (Exception e){
            e.printStackTrace();
            throw e;
        }
        return ftp;
    }

    /**
     * FTP參數固定方式,參數在配置文件中
     *
     * @return FTPClient
     */
    public FTPClient getConnectionFTP() throws Exception{
        return getConnectionFTP(FTP_BACKUP_HOST_IP, Integer.valueOf(FTP_BACKUP_HOST_PORT),
                FTP_BACKUP_HOST_ACCOUNT, FTP_BACKUP_HOST_PWD);
    }


    /**
     * 關閉連接-FTP方式
     *
     * @param ftp FTPClient對象
     * @return boolean
     */
    public boolean closeFTP(FTPClient ftp){
        if (ftp.isConnected()) {
            try {
                ftp.disconnect();
                System.out.println("Ftp connection closed.");
                return true;
            } catch (Exception e){
                e.printStackTrace();
            }
        }
        return false;
    }

    /**
     * 上傳文件-FTP方式
     *
     * @param ftp                  FTPClient對象
     * @param ftpPath              FTP服務器上傳路徑
     * @param localFileIncludePath 本地文件全路徑
     * @param inputStream          輸入流
     * @return boolean
     */
    public boolean uploadFile(FTPClient ftp, String ftpPath, String localFileIncludePath, InputStream inputStream) throws Exception{
        boolean success = false;
        try {
            ftp.changeWorkingDirectory(ftpPath);//轉移到指定FTP服務器目錄
            FTPFile[] fs = ftp.listFiles();//得到目錄的相應文件列表
            localFileIncludePath = FtpTool.changeName(localFileIncludePath, fs);
            localFileIncludePath = new String(localFileIncludePath.getBytes("UTF-8"), "UTF-8");
            ftpPath = new String(ftpPath.getBytes("UTF-8"), "UTF-8");
            //轉到指定上傳目錄
            ftp.changeWorkingDirectory(ftpPath);
            //將上傳文件存儲到指定目錄
            ftp.setFileType(FTP.BINARY_FILE_TYPE);
            //如果缺省該句 傳輸txt正常 但圖片和其他格式的文件傳輸出現亂碼
            ftp.storeFile(localFileIncludePath, inputStream);
            //關閉輸入流
            inputStream.close();
            //退出ftp
            ftp.logout();
            //表示上傳成功
            success = true;
            System.out.println("Upload success.");
        } catch (Exception e){
            e.printStackTrace();
            throw e;
        }
        return success;
    }

    /**
     * 上傳文件到FTP服務器的固定路徑,路徑見配置文件
     *
     * @param ftp
     * @param fileName
     * @param inputStream
     * @return
     */
    public boolean uploadFile(FTPClient ftp, String fileName, InputStream inputStream) throws Exception{
        return uploadFile(ftp, FTP_BACKUP_HOST_PATH, BACKUP_LOCAL_PATH + fileName, inputStream);
    }

    /**
     * 刪除文件-FTP方式
     *
     * @param ftp         FTPClient對象
     * @param ftpPath     FTP服務器上傳地址
     * @param ftpFileName FTP服務器上要刪除的文件名
     * @return
     */
    public boolean deleteFile(FTPClient ftp, String ftpPath, String ftpFileName) throws Exception{
        boolean success = false;
        try {
            ftp.changeWorkingDirectory(ftpPath);//轉移到指定FTP服務器目錄
            ftpFileName = new String(ftpFileName.getBytes("UTF-8"), "UTF-8");
            ftpPath = new String(ftpPath.getBytes("UTF-8"), "UTF-8");
            ftp.deleteFile(ftpFileName);
            ftp.logout();
            success = true;
        } catch (Exception e){
            e.printStackTrace();
            throw e;
        }
        return success;
    }

    /**
     * 從ftp刪除文件
     * @param ftp
     * @param ftpFileName
     * @return
     */
    public boolean deleteFile(FTPClient ftp, String ftpFileName) throws Exception{
        return deleteFile(ftp, FTP_BACKUP_HOST_PATH, ftpFileName);
    }

    /**
     * 下載文件-FTP方式
     *
     * @param ftp           FTPClient對象
     * @param ftpPath       FTP服務器路徑
     * @param ftpFileName   FTP服務器文件名
     * @param localSavePath 本里存儲路徑
     * @return boolean
     */
    public boolean downFile(FTPClient ftp, String ftpPath, String ftpFileName, String localSavePath) throws Exception{
        boolean success = false;
        try {
            ftp.changeWorkingDirectory(ftpPath);//轉移到FTP服務器目錄
            FTPFile[] fs = ftp.listFiles(); //得到目錄的相應文件列表
            for (FTPFile ff : fs) {
                if (ff.getName().equals(ftpFileName)) {
//                    File localFile = new File(localSavePath + "\\" + ff.getName());
                    File localFile = new File(localSavePath + ff.getName());
                    OutputStream outputStream = new FileOutputStream(localFile);
                    //將文件保存到輸出流outputStream中
                    ftp.setFileType(FTP.BINARY_FILE_TYPE);//定義編碼格式 防止文件中的中文出現亂碼
                    ftp.retrieveFile(new String(ff.getName().getBytes("UTF-8"), "UTF-8"), outputStream);
                    outputStream.flush();
                    outputStream.close();
                    System.out.println("Download success.");
                }
            }
            ftp.logout();
            success = true;
        } catch (Exception e){
            e.printStackTrace();
            throw e;
        }
        return success;
    }

    /**
     * 從ftp下載文件,固定參數見配置文件
     *
     * @param ftp
     * @param ftpFileName
     * @return
     */
    public boolean downFile(FTPClient ftp, String ftpFileName) throws Exception{
        return downFile(ftp, FTP_BACKUP_HOST_PATH, ftpFileName, BACKUP_LOCAL_PATH);
    }

    /**
     * 判斷是否有重名文件
     *
     * @param fileName
     * @param fs
     * @return
     */
    public static boolean isFileExist(String fileName, FTPFile[] fs) {
        for (int i = 0; i < fs.length; i++) {
            FTPFile ff = fs[i];
            if (ff.getName().equals(fileName)) {
                return true; //如果存在返回 正確信號
            }
        }
        return false; //如果不存在返回錯誤信號
    }

    /**
     * 根據重名判斷的結果 生成新的文件的名稱
     *
     * @param fileName
     * @param fs
     * @return
     */
    public static String changeName(String fileName, FTPFile[] fs) {
        int n = 0;
//      fileName = fileName.append(fileName);
        while (isFileExist(fileName.toString(), fs)) {
            n++;
            String a = "[" + n + "]";
            int b = fileName.lastIndexOf(".");//最後一出現小數點的位置
            int c = fileName.lastIndexOf("[");//最後一次"["出現的位置
            if (c < 0) {
                c = b;
            }
            StringBuffer name = new StringBuffer(fileName.substring(0, c));//文件的名字
            StringBuffer suffix = new StringBuffer(fileName.substring(b + 1));//後綴的名稱
            fileName = name.append(a) + "." + suffix;
        }
        return fileName.toString();
    }
}
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章