FTP在docker容器中上傳失敗解決,改為被動模式


package com.mayocase.takeout.utils;

import org.apache.commons.net.ftp.FTPClient;
import org.apache.commons.net.ftp.FTPReply;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;

import com.mayocase.takeout.user.rest.UserLoginController;

import java.io.IOException;
import java.io.InputStream;
import java.net.MalformedURLException;

/**
 * Created by laiwr on 2018/5/18.
 */
@Component
public class FtpUtils {

	private static Logger logger = LoggerFactory.getLogger(UserLoginController.class);
	
    @Autowired
    private FtpConfig ftpConfig;

    public FTPClient ftpClient = null;

    /**
     * 初始化鏈接文件
     */
    public void initFtpClient() {
        ftpClient = new FTPClient();
        ftpClient.setRemoteVerificationEnabled(false);									//取消服務器獲取自身Ip地址和提交的host進行匹配,否則當不一致時會報異常。
        ftpClient.setControlEncoding("utf-8");											//在連接之前設置編碼類型為utf-8
        try {
        	ftpClient.setDataTimeout(1000*120);											//設置傳輸超時時間為120秒
        	ftpClient.connect(ftpConfig.getHostname(), ftpConfig.getPort()); 			//連接ftp服務器
            ftpClient.login(ftpConfig.getUsername(), ftpConfig.getPassword()); 			//登錄ftp服務器
            int replyCode = ftpClient.getReplyCode(); 									//是否成功登錄服務器
            
            if(!FTPReply.isPositiveCompletion(replyCode)){
            	logger.warn("【initFtpClient】: 登錄服務器失敗");
            }            
            logger.warn("【initFtpClient】: 使用帳戶:"+ftpConfig.getUsername()+"密碼:"+ftpConfig.getPassword()+"登錄ftp服務器:"+ftpConfig.getHostname()+":"+ftpConfig.getPort());
            logger.warn("【initFtpClient】: 成功登錄服務器,被動模式主機:"+ftpClient.getPassiveHost()+":"+ftpClient.getPassivePort());
            logger.warn("【initFtpClient】: 成功登錄服務器,主動模式主機:"+ftpClient.getRemoteAddress()+":"+ftpClient.getRemotePort());
            logger.warn("【initFtpClient】: 成功登錄服務器,本地主機:"+ftpClient.getLocalAddress()+":"+ftpClient.getLocalPort());
            logger.warn("【initFtpClient】: 成功登錄服務器,返回代碼:"+ftpClient.getReplyCode()+",顯示狀態"+ftpClient.getStatus());        	

        }catch (MalformedURLException e) {
            e.printStackTrace();
        }catch (IOException e) {
            e.printStackTrace();
        }
    }


    /**
     * 上傳文件
     * @param pathname ftp服務保存地址
     * @param fileName 上傳到ftp的文件名
     * @param inputStream 輸入文件流
     * @return
     */
    public boolean uploadFile( String pathname, String fileName,InputStream inputStream){
        boolean flag = false;
        try{
        	logger.warn("【uploadFile】: " + "開始上傳文件");
            initFtpClient();
            ftpClient.setFileType(ftpClient.BINARY_FILE_TYPE);	//設置傳輸的模式為二進制文件類型傳輸
            ftpClient.makeDirectory(pathname);						//設置目錄
            ftpClient.changeWorkingDirectory(pathname);				//設置工作路徑
            
            ftpClient.enterLocalPassiveMode();						//設置被動模式(FTP客戶端在docker容器內,需用被動模式)
            ftpClient.storeFile(fileName, inputStream);				//上傳
            
            logger.warn("【uploadFile】: " + "上傳文件成功");
            flag = true;            
            return flag;
        }catch (Exception e) {
        	logger.warn("【uploadFile】: " + "上傳文件失敗");
            e.printStackTrace();
            return flag;
        }finally{
        	if(null != inputStream){
        		try {
        			inputStream.close();							//關閉文件流
        		} catch (IOException e) {
        			e.printStackTrace();
        		}
        	}
            if(ftpClient.isConnected()){
                try{

                    ftpClient.logout();								//退出FTP
                    ftpClient.disconnect();							//斷開連接
                }catch(IOException e){
                    e.printStackTrace();
                }
            }
        }
    }



}

  

 

幾個步驟說明:

ftpClient.setRemoteVerificationEnabled(false);
ftpClient.setControlEncoding("utf-8");
ftpClient.connect(ftpConfig.getHostname(), ftpConfig.getPort()); //連接ftp服務器
ftpClient.login(ftpConfig.getUsername(), ftpConfig.getPassword()); //登錄ftp服務器
int replyCode = ftpClient.getReplyCode(); //是否成功登錄服務器
if(!FTPReply.isPositiveCompletion(replyCode)){
            	logger.warn("【initFtpClient】: 登錄服務器失敗");
            	logger.warn("【initFtpClient】: connect failed...ftp服務器:");
}
ftpClient.setFileType(ftpClient.BINARY_FILE_TYPE);  //設置文件類型:文件類型為二進制文件
ftpClient.setControlEncoding("GBK");  //設置編碼為GBK
CreateDirecroty(pathname);
ftpClient.makeDirectory(pathname);	//設置目錄
ftpClient.changeWorkingDirectory(pathname);	//設置工作路徑

ftpClient.enterLocalPassiveMode();	//設置被動模式
ftpClient.storeFile(fileName, inputStream);//上傳
inputStream.close();
ftpClient.logout();
ftpClient.disconnect();

  


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM