C# 實現FTP客戶端


本文是利用C# 實現FTP客戶端的小例子,主要實現上傳,下載,刪除等功能,以供學習分享使用。

思路:

  1. 通過讀取FTP站點的目錄信息,列出對應的文件及文件夾。
  2. 雙擊目錄,則顯示子目錄,如果是文件,則點擊右鍵,進行下載和刪除操作。
  3. 通過讀取本地電腦的目錄,以樹狀結構展示,選擇本地文件,右鍵進行上傳操作。

涉及知識點:

  1. FtpWebRequest【實現文件傳輸協議 (FTP) 客戶端】 / FtpWebResponse【封裝文件傳輸協議 (FTP) 服務器對請求的響應】Ftp的操作主要集中在兩個類中。
  2. FlowLayoutPanel  【流布局面板】表示一個沿水平或垂直方向動態排放其內容的面板。
  3. ContextMenuStrip 【快捷菜單】 主要用於右鍵菜單。
  4. 資源文件:Resources 用於存放圖片及其他資源。

效果圖如下

左邊:雙擊文件夾進入子目錄,點擊工具欄按鈕‘上級目錄’返回。文件點擊右鍵進行操作。

右邊:文件夾則點擊前面+號展開。文件則點擊右鍵進行上傳。

核心代碼如下

  1 using System;
  2 using System.Collections.Generic;
  3 using System.IO;
  4 using System.Linq;
  5 using System.Net;
  6 using System.Text;
  7 using System.Threading;
  8 using System.Threading.Tasks;
  9 
 10 namespace FtpClient
 11 {
 12     public class FtpHelper
 13     {
 14         #region 屬性與構造函數
 15 
 16         /// <summary>
 17         /// IP地址
 18         /// </summary>
 19         public string IpAddr { get; set; }
 20 
 21         /// <summary>
 22         /// 相對路徑
 23         /// </summary>
 24         public string RelatePath { get; set; }
 25 
 26         /// <summary>
 27         /// 端口號
 28         /// </summary>
 29         public string Port { get; set; }
 30 
 31         /// <summary>
 32         /// 用戶名
 33         /// </summary>
 34         public string UserName { get; set; }
 35 
 36         /// <summary>
 37         /// 密碼
 38         /// </summary>
 39         public string Password { get; set; }
 40 
 41        
 42 
 43         public FtpHelper() {
 44 
 45         }
 46 
 47         public FtpHelper(string ipAddr, string port, string userName, string password) {
 48             this.IpAddr = ipAddr;
 49             this.Port = port;
 50             this.UserName = userName;
 51             this.Password = password;
 52         }
 53 
 54         #endregion
 55 
 56         #region 方法
 57 
 58 
 59         /// <summary>
 60         /// 下載文件
 61         /// </summary>
 62         /// <param name="filePath"></param>
 63         /// <param name="isOk"></param>
 64         public void DownLoad(string filePath, out bool isOk) {
 65             string method = WebRequestMethods.Ftp.DownloadFile;
 66             var statusCode = FtpStatusCode.DataAlreadyOpen;
 67             FtpWebResponse response = callFtp(method);
 68             ReadByBytes(filePath, response, statusCode, out isOk);
 69         }
 70 
 71         public void UpLoad(string file,out bool isOk)
 72         {
 73             isOk = false;
 74             FileInfo fi = new FileInfo(file);
 75             FileStream fs = fi.OpenRead();
 76             long length = fs.Length;
 77             string uri = string.Format("ftp://{0}:{1}{2}", this.IpAddr, this.Port, this.RelatePath);
 78             FtpWebRequest request = (FtpWebRequest)WebRequest.Create(uri);
 79             request.Credentials = new NetworkCredential(UserName, Password);
 80             request.Method = WebRequestMethods.Ftp.UploadFile;
 81             request.UseBinary = true;
 82             request.ContentLength = length;
 83             request.Timeout = 10 * 1000;
 84             try
 85             {
 86                 Stream stream = request.GetRequestStream();
 87 
 88                 int BufferLength = 2048; //2K   
 89                 byte[] b = new byte[BufferLength];
 90                 int i;
 91                 while ((i = fs.Read(b, 0, BufferLength)) > 0)
 92                 {
 93                     stream.Write(b, 0, i);
 94                 }
 95                 stream.Close();
 96                 stream.Dispose();
 97                 isOk = true;
 98             }
 99             catch (Exception ex)
100             {
101                 Console.WriteLine(ex.ToString());
102             }
103             finally {
104                 if (request != null)
105                 {
106                     request.Abort();
107                     request = null;
108                 }
109             }
110         }
111 
112         /// <summary>
113         /// 刪除文件
114         /// </summary>
115         /// <param name="isOk"></param>
116         /// <returns></returns>
117         public string[] DeleteFile(out bool isOk) {
118             string method = WebRequestMethods.Ftp.DeleteFile;
119             var statusCode = FtpStatusCode.FileActionOK;
120             FtpWebResponse response = callFtp(method);
121             return ReadByLine(response, statusCode, out isOk);
122         }
123 
124         /// <summary>
125         /// 展示目錄
126         /// </summary>
127         public string[] ListDirectory(out bool isOk)
128         {
129             string method = WebRequestMethods.Ftp.ListDirectoryDetails;
130             var statusCode = FtpStatusCode.DataAlreadyOpen;
131             FtpWebResponse response= callFtp(method);
132             return ReadByLine(response, statusCode, out isOk);
133         }
134 
135         /// <summary>
136         /// 設置上級目錄
137         /// </summary>
138         public void SetPrePath()
139         {
140             string relatePath = this.RelatePath;
141             if (string.IsNullOrEmpty(relatePath) || relatePath.LastIndexOf("/") == 0 )
142             {
143                 relatePath = "";
144             }
145             else {
146                 relatePath = relatePath.Substring(0, relatePath.LastIndexOf("/"));
147             }
148             this.RelatePath = relatePath;
149         }
150 
151         #endregion
152 
153         #region 私有方法
154 
155         /// <summary>
156         /// 調用Ftp,將命令發往Ftp並返回信息
157         /// </summary>
158         /// <param name="method">要發往Ftp的命令</param>
159         /// <returns></returns>
160         private FtpWebResponse callFtp(string method)
161         {
162             string uri = string.Format("ftp://{0}:{1}{2}", this.IpAddr, this.Port, this.RelatePath);
163             FtpWebRequest request; request = (FtpWebRequest)FtpWebRequest.Create(uri);
164             request.UseBinary = true;
165             request.UsePassive = true;
166             request.Credentials = new NetworkCredential(UserName, Password);
167             request.KeepAlive = false;
168             request.Method = method;
169             FtpWebResponse response = (FtpWebResponse)request.GetResponse();
170             return response;
171         }
172 
173         /// <summary>
174         /// 按行讀取
175         /// </summary>
176         /// <param name="response"></param>
177         /// <param name="statusCode"></param>
178         /// <param name="isOk"></param>
179         /// <returns></returns>
180         private string[] ReadByLine(FtpWebResponse response, FtpStatusCode statusCode,out bool isOk) {
181             List<string> lstAccpet = new List<string>();
182             int i = 0;
183             while (true)
184             {
185                 if (response.StatusCode == statusCode)
186                 {
187                     using (StreamReader sr = new StreamReader(response.GetResponseStream()))
188                     {
189                         string line = sr.ReadLine();
190                         while (!string.IsNullOrEmpty(line))
191                         {
192                             lstAccpet.Add(line);
193                             line = sr.ReadLine();
194                         }
195                     }
196                     isOk = true;
197                     break;
198                 }
199                 i++;
200                 if (i > 10)
201                 {
202                     isOk = false;
203                     break;
204                 }
205                 Thread.Sleep(200);
206             }
207             response.Close();
208             return lstAccpet.ToArray();
209         }
210 
211         private void ReadByBytes(string filePath,FtpWebResponse response, FtpStatusCode statusCode, out bool isOk)
212         {
213             isOk = false;
214             int i = 0;
215             while (true)
216 
217             {
218                 if (response.StatusCode == statusCode)
219                 {
220                     long length = response.ContentLength;
221                     int bufferSize = 2048;
222                     int readCount;
223                     byte[] buffer = new byte[bufferSize];
224                     using (FileStream outputStream = new FileStream(filePath, FileMode.Create))
225                     {
226 
227                         using (Stream ftpStream = response.GetResponseStream())
228                         {
229                             readCount = ftpStream.Read(buffer, 0, bufferSize);
230                             while (readCount > 0)
231                             {
232                                 outputStream.Write(buffer, 0, readCount);
233                                 readCount = ftpStream.Read(buffer, 0, bufferSize);
234                             }
235                         }
236                     }
237                     break;
238                 }
239                 i++;
240                 if (i > 10)
241                 {
242                     isOk = false;
243                     break;
244                 }
245                 Thread.Sleep(200);
246             }
247             response.Close();
248         }
249         #endregion
250     }
251 
252     /// <summary>
253     /// Ftp內容類型枚舉
254     /// </summary>
255     public enum FtpContentType
256     {
257         undefined = 0,
258         file = 1,
259         folder = 2
260     }
261 }
View Code

FTP服務端和客戶端示意圖

---------------------------------------------------------------------------------------------------

---------------------------------------------------------------------------------------------------
源碼鏈接如下:

源碼下載

 


免責聲明!

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



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