有網上的代碼,也有自己的理解,代碼備份
一般連接windows服務器使用FTP,連接linux服務器使用SFTP。linux都是通過SFTP上傳文件,不需要額外安裝,非要使用FTP的話,還得安裝FTP服務(雖然剛開始我就是這么干的)。
另外就是jdk1.8和jdk1.7之前的方法有些不同,網上有很多jdk1.7之前的介紹,本篇是jdk1.8的
添加依賴Jsch-0.1.54.jar
<!-- https://mvnrepository.com/artifact/com.jcraft/jsch --> <dependency> <groupId>com.jcraft</groupId> <artifactId>jsch</artifactId> <version>0.1.54</version> </dependency>
FTP上傳下載文件例子

1 import sun.net.ftp.FtpClient; 2 import sun.net.ftp.FtpProtocolException; 3 4 import java.io.*; 5 import java.net.InetSocketAddress; 6 import java.net.SocketAddress; 7 8 /** 9 * Java自帶的API對FTP的操作 10 */ 11 public class Test { 12 private FtpClient ftpClient; 13 14 Test(){ 15 /* 16 使用默認的端口號、用戶名、密碼以及根目錄連接FTP服務器 17 */ 18 this.connectServer("192.168.56.130", 21, "jiashubing", "123456", "/home/jiashubing/ftp/anonymous/"); 19 } 20 21 public void connectServer(String ip, int port, String user, String password, String path) { 22 try { 23 /* ******連接服務器的兩種方法*******/ 24 ftpClient = FtpClient.create(); 25 try { 26 SocketAddress addr = new InetSocketAddress(ip, port); 27 ftpClient.connect(addr); 28 ftpClient.login(user, password.toCharArray()); 29 System.out.println("login success!"); 30 if (path.length() != 0) { 31 //把遠程系統上的目錄切換到參數path所指定的目錄 32 ftpClient.changeDirectory(path); 33 } 34 } catch (FtpProtocolException e) { 35 e.printStackTrace(); 36 } 37 } catch (IOException ex) { 38 ex.printStackTrace(); 39 throw new RuntimeException(ex); 40 } 41 } 42 43 /** 44 * 關閉連接 45 */ 46 public void closeConnect() { 47 try { 48 ftpClient.close(); 49 System.out.println("disconnect success"); 50 } catch (IOException ex) { 51 System.out.println("not disconnect"); 52 ex.printStackTrace(); 53 throw new RuntimeException(ex); 54 } 55 } 56 57 /** 58 * 上傳文件 59 * @param localFile 本地文件 60 * @param remoteFile 遠程文件 61 */ 62 public void upload(String localFile, String remoteFile) { 63 File file_in = new File(localFile); 64 try(OutputStream os = ftpClient.putFileStream(remoteFile); 65 FileInputStream is = new FileInputStream(file_in)) { 66 byte[] bytes = new byte[1024]; 67 int c; 68 while ((c = is.read(bytes)) != -1) { 69 os.write(bytes, 0, c); 70 } 71 System.out.println("upload success"); 72 } catch (IOException ex) { 73 System.out.println("not upload"); 74 ex.printStackTrace(); 75 } catch (FtpProtocolException e) { 76 e.printStackTrace(); 77 } 78 } 79 80 /** 81 * 下載文件。獲取遠程機器上的文件filename,借助TelnetInputStream把該文件傳送到本地。 82 * @param remoteFile 遠程文件路徑(服務器端) 83 * @param localFile 本地文件路徑(客戶端) 84 */ 85 public void download(String remoteFile, String localFile) { 86 File file_in = new File(localFile); 87 try(InputStream is = ftpClient.getFileStream(remoteFile); 88 FileOutputStream os = new FileOutputStream(file_in)){ 89 90 byte[] bytes = new byte[1024]; 91 int c; 92 while ((c = is.read(bytes)) != -1) { 93 os.write(bytes, 0, c); 94 } 95 System.out.println("download success"); 96 } catch (IOException ex) { 97 System.out.println("not download"); 98 ex.printStackTrace(); 99 }catch (FtpProtocolException e) { 100 e.printStackTrace(); 101 } 102 } 103 104 public static void main(String agrs[]) { 105 Test fu = new Test(); 106 107 //下載測試 108 String filepath[] = {"aa.xlsx","bb.xlsx"}; 109 String localfilepath[] = {"E:/lalala/aa.xlsx","E:/lalala/bb.xlsx"}; 110 for (int i = 0; i < filepath.length; i++) { 111 fu.download(filepath[i], localfilepath[i]); 112 } 113 114 //上傳測試 115 String localfile = "E:/lalala/tt.xlsx"; 116 String remotefile = "tt.xlsx"; //上傳 117 fu.upload(localfile, remotefile); 118 fu.closeConnect(); 119 120 } 121 122 }
SFTP上傳下載文件例子

1 import com.jcraft.jsch.*; 2 3 import java.util.Properties; 4 5 /** 6 * 解釋一下SFTP的整個調用過程,這個過程就是通過Ip、Port、Username、Password獲取一個Session, 7 * 然后通過Session打開SFTP通道(獲得SFTP Channel對象),再在建立通道(Channel)連接,最后我們就是 8 * 通過這個Channel對象來調用SFTP的各種操作方法.總是要記得,我們操作完SFTP需要手動斷開Channel連接與Session連接。 9 * @author jiashubing 10 * @since 2018/5/8 11 */ 12 public class SftpCustom { 13 14 private ChannelSftp channel; 15 private Session session; 16 private String sftpPath; 17 18 SftpCustom() { 19 /* 20 使用端口號、用戶名、密碼以連接SFTP服務器 21 */ 22 this.connectServer("192.168.56.130", 22, "jiashubing", "123456", "/home/ftp/"); 23 } 24 25 SftpCustom(String ftpHost, int ftpPort, String ftpUserName, String ftpPassword, String sftpPath) { 26 this.connectServer(ftpHost, ftpPort, ftpUserName, ftpPassword, sftpPath); 27 } 28 29 public void connectServer(String ftpHost, int ftpPort, String ftpUserName, String ftpPassword, String sftpPath) { 30 try { 31 this.sftpPath = sftpPath; 32 33 // 創建JSch對象 34 JSch jsch = new JSch(); 35 // 根據用戶名,主機ip,端口獲取一個Session對象 36 session = jsch.getSession(ftpUserName, ftpHost, ftpPort); 37 if (ftpPassword != null) { 38 // 設置密碼 39 session.setPassword(ftpPassword); 40 } 41 Properties configTemp = new Properties(); 42 configTemp.put("StrictHostKeyChecking", "no"); 43 // 為Session對象設置properties 44 session.setConfig(configTemp); 45 // 設置timeout時間 46 session.setTimeout(60000); 47 session.connect(); 48 // 通過Session建立鏈接 49 // 打開SFTP通道 50 channel = (ChannelSftp) session.openChannel("sftp"); 51 // 建立SFTP通道的連接 52 channel.connect(); 53 } catch (JSchException e) { 54 //throw new RuntimeException(e); 55 } 56 } 57 58 /** 59 * 斷開SFTP Channel、Session連接 60 */ 61 public void closeChannel() { 62 try { 63 if (channel != null) { 64 channel.disconnect(); 65 } 66 if (session != null) { 67 session.disconnect(); 68 } 69 } catch (Exception e) { 70 // 71 } 72 } 73 74 /** 75 * 上傳文件 76 * 77 * @param localFile 本地文件 78 * @param remoteFile 遠程文件 79 */ 80 public void upload(String localFile, String remoteFile) { 81 try { 82 remoteFile = sftpPath + remoteFile; 83 channel.put(localFile, remoteFile, ChannelSftp.OVERWRITE); 84 channel.quit(); 85 } catch (SftpException e) { 86 //e.printStackTrace(); 87 } 88 } 89 90 /** 91 * 下載文件 92 * 93 * @param remoteFile 遠程文件 94 * @param localFile 本地文件 95 */ 96 public void download(String remoteFile, String localFile) { 97 try { 98 remoteFile = sftpPath + remoteFile; 99 channel.get(remoteFile, localFile); 100 channel.quit(); 101 } catch (SftpException e) { 102 //e.printStackTrace(); 103 } 104 } 105 106 public static void main(String[] args) { 107 SftpCustom sftpCustom = new SftpCustom(); 108 //上傳測試 109 String localfile = "E:/lalala/tt.xlsx"; 110 String remotefile = "/home/ftp/tt2.xlsx"; 111 sftpCustom.upload(localfile, remotefile); 112 113 //下載測試 114 sftpCustom.download(remotefile, "E:/lalala/tt3.xlsx"); 115 116 sftpCustom.closeChannel(); 117 } 118 119 }
Jsch-0.1.54.jar 學習了解
ChannelSftp類是JSch實現SFTP核心類,它包含了所有SFTP的方法,如:
文件上傳put(),
文件下載get(),
進入指定目錄cd().
得到指定目錄下的文件列表ls().
重命名指定文件或目錄rename().
刪除指定文件rm(),創建目錄mkdir(),刪除目錄rmdir().
大家引用方法時可以快速參考一下,具體傳參需參考源碼~
最后還要提一下的就是JSch支持的三種文件傳輸模式:
● APPEND 追加模式,如果目標文件已存在,傳輸的文件將在目標文件后追加。
● RESUME 恢復模式,如果文件已經傳輸一部分,這時由於網絡或其他任何原因導致文件傳輸中斷,如果下一次傳輸相同的文件,則會從上一次中斷的地方續傳。
● OVERWRITE 完全覆蓋模式,這是JSch的默認文件傳輸模式,即如果目標文件已經存在,傳輸的文件將完全覆蓋目標文件,產生新的文件。
FTP和SFTP區別
FTP是一種文件傳輸協議,一般是為了方便數據共享的。包括一個FTP服務器和多個FTP客戶端。FTP客戶端通過FTP協議在服務器上下載資源。而SFTP協議是在FTP的基礎上對數據進行加密,使得傳輸的數據相對來說更安全。但是這種安全是以犧牲效率為代價的,也就是說SFTP的傳輸效率比FTP要低(不過現實使用當中,沒有發現多大差別)。個人膚淺的認為就是:一;FTP要安裝,SFTP不要安裝。二;SFTP更安全,但更安全帶來副作用就是的效率比FTP要低些。
建議使用sftp代替ftp。
主要因為:
1、可以不用額外安裝任何服務器端程序
2、會更省系統資源。
3、SFTP使用加密傳輸認證信息和傳輸數據,相對來說會更安全。
4、也不需要單獨配置,對新手來說比較簡單(開啟SSH默認就開啟了SFTP)。
參考
[1].https://blog.csdn.net/g5628907/article/details/78281864
[2].https://www.cnblogs.com/xuliangxing/p/7120130.html
[3].https://jingyan.baidu.com/article/6079ad0e7feae028ff86dbf9.html