2010-08-26 45 views
10

Các mã sau đây là tốt cho việc tải lên tập tin văn bản, nhưng nó không thành công để tải lên các tập tin JPEG (không hoàn toàn - tên tập tin là tốt nhưng hình ảnh bị lỗi):Tải lên tập tin với mã hóa sử dụng FTP trong C#

private void up(string sourceFile, string targetFile) 
{ 
    try 
    { 
     string ftpServerIP = ConfigurationManager.AppSettings["ftpIP"]; 
     string ftpUserID = ConfigurationManager.AppSettings["ftpUser"]; 
     string ftpPassword = ConfigurationManager.AppSettings["ftpPass"]; 

     //string ftpURI = ""; 
     string filename = "ftp://" + ftpServerIP + "//" + targetFile; 
     FtpWebRequest ftpReq = (FtpWebRequest)WebRequest.Create(filename); 
     ftpReq.Method = WebRequestMethods.Ftp.UploadFile; 
     ftpReq.Credentials = new NetworkCredential(ftpUserID, ftpPassword); 

     StreamReader stream = new StreamReader(sourceFile); 
     Byte[] b = System.Text.Encoding.UTF8.GetBytes(stream.ReadToEnd()); 
     stream.Close(); 

     ftpReq.ContentLength = b.Length; 
     Stream s = ftpReq.GetRequestStream(); 
     s.Write(b, 0, b.Length); 
     s.Close(); 

     System.Net.FtpWebResponse ftpResp = (FtpWebResponse)ftpReq.GetResponse(); 
     MessageBox.Show(ftpResp.StatusDescription); 
    } 
    catch (Exception ex) 
    { 
     MessageBox.Show(ex.ToString()); 
    } 
} 

tôi có một giải pháp mà có thể tải lên một tập tin:

private void Upload(string sourceFile, string targetFile) 
{ 
    string ftpUserID; 
    string ftpPassword; 
    string ftpServerIP; 
    ftpServerIP = ConfigurationManager.AppSettings["ftpIP"]; 
    ftpUserID = ConfigurationManager.AppSettings["ftpUser"]; 
    ftpPassword = ConfigurationManager.AppSettings["ftpPass"]; 
    FileInfo fileInf = new FileInfo(sourceFile); 
    FtpWebRequest reqFTP; 

    // Create FtpWebRequest object from the Uri provided 
    reqFTP = (FtpWebRequest)(FtpWebRequest.Create(new Uri("ftp://" + ftpServerIP + "//" + targetFile))); 

    // Provide the WebPermission Credintials 
    reqFTP.Credentials = new NetworkCredential(ftpUserID, ftpPassword); 

    // Bypass default lan settings 
    reqFTP.Proxy = null; 

    // By default KeepAlive is true, where the control connection is not closed 
    // after a command is executed. 
    reqFTP.KeepAlive = false; 

    // Specify the command to be executed. 
    reqFTP.Method = WebRequestMethods.Ftp.UploadFile; 

    // Specify the data transfer type. 
    reqFTP.UseBinary = true; 

    // Notify the server about the size of the uploaded file 
    reqFTP.ContentLength = fileInf.Length; 

    // The buffer size is set to 2kb 
    int buffLength = 2048; 
    Byte[] buff; 
    buff = new byte[buffLength]; 
    int contentLen; 

    // Opens a file stream (System.IO.FileStream) to read the file to be uploaded 
    FileStream fs = fileInf.OpenRead(); 

    try 
    { 
     // Stream to which the file to be upload is written 
     Stream strm = reqFTP.GetRequestStream(); 

     // Read from the file stream 2kb at a time 
     long filesize = fs.Length; 
     int i=0; 
     contentLen = fs.Read(buff, 0, buffLength); 

     // Till Stream content ends 
     while (contentLen != 0) 
     { 
      Application.DoEvents(); 
      // Write Content from the file stream to the FTP Upload Stream 
      strm.Write(buff, 0, contentLen); 
      contentLen = fs.Read(buff, 0, buffLength); 
      i = i + 1; 
      //Double percentComp = (i * buffLength) * 100/filesize; 
      //ProgressBar1.Value = (int)percentComp; 
     } 

     // Close the file stream and the Request Stream 
     strm.Close(); 
     fs.Close(); 
    } 

    catch (Exception ex) 
    { 
     MessageBox.Show(ex.Message, "Upload Error"); 
    } 
} 

nhưng ở đây tôi có vấn đề ngược lại - hình ảnh là tốt, nhưng tên tập tin là hỏng.

Tôi biết đó là vì các mã hóa, nhưng tôi không biết làm thế nào để làm cho các mảng byte có mã hóa mong muốn ...

+0

Tôi không thể hiểu, tại sao bạn có vấn đề với tên tệp bị hỏng với mã thứ hai, nhưng không phải với mã đầu tiên. Và tại sao câu trả lời được chấp nhận lại giúp ích cho điều đó. Trong mọi trường hợp, bạn chỉ định tên tệp theo cùng một cách. –

+0

Tôi xin lỗi Martin. Tôi đã viết câu hỏi này một thập kỷ trước. Tôi không nhớ vấn đề là gì và giải pháp là gì. Tôi nghĩ bạn nên mở một chủ đề mới với câu hỏi của riêng bạn. – Asaf

+0

Tôi không có một câu hỏi, tôi chỉ tự hỏi điểm của câu hỏi của bạn và câu trả lời là gì :) –

Trả lời

19

Hãy thử bit này:

private static void up(string sourceFile, string targetFile) 
{    
    try 
    { 
     string ftpServerIP = ConfigurationManager.AppSettings["ftpIP"]; 
     string ftpUserID = ConfigurationManager.AppSettings["ftpUser"]; 
     string ftpPassword = ConfigurationManager.AppSettings["ftpPass"]; 
     ////string ftpURI = ""; 
     string filename = "ftp://" + ftpServerIP + "//" + targetFile; 
     FtpWebRequest ftpReq = (FtpWebRequest)WebRequest.Create(filename); 
     ftpReq.UseBinary = true; 
     ftpReq.Method = WebRequestMethods.Ftp.UploadFile; 
     ftpReq.Credentials = new NetworkCredential(ftpUserID, ftpPassword); 

     byte[] b = File.ReadAllBytes(sourceFile); 

     ftpReq.ContentLength = b.Length; 
     using (Stream s = ftpReq.GetRequestStream()) 
     { 
      s.Write(b, 0, b.Length); 
     } 

     FtpWebResponse ftpResp = (FtpWebResponse)ftpReq.GetResponse(); 

     if (ftpResp != null) 
     { 
      MessageBox.Show(ftpResp.StatusDescription); 
     } 
    } 
    catch (Exception ex) 
    { 
     MessageBox.Show(ex.ToString()); 
    } 
} 
+1

Tại sao 's.Write (b, 0, b.Length);' bên trong khối 'using'? –

+4

Vì 'Dòng s' là một tài nguyên' IDisposable'. –

+0

Ở đây, sự khác biệt kỳ diệu cũng là 'byte [] b = File.ReadAllBytes (sourceFile);' so sánh với các ví dụ khác được tìm thấy aka 'Encoding.UTF8.GetBytes (stream.ReadToEnd())'. –

2

Bạn nên sử dụng một Stream để đọc tập tin nhị phân, không phải là một StreamReader . StreamReader được thiết kế để chỉ đọc các tệp văn bản.

+0

Tôi đã thử sử dụng mã này trong 3 giờ và tôi cũng đã tìm thấy trình streamReader đi kèm với mã hóa (trong các nhà xây dựng) - nhưng tôi không thể hiểu làm thế nào để sử dụng không phải là streamreader cũng như các đối tượng dòng. Các luồng giống như một hộp đen với tôi: ( – Asaf

2

Trong ví dụ mã đầu tiên của bạn, bật truyền nhị phân: FtpWebRequest.UseBinary = true. Nếu không, nó sẽ chuyển đổi những gì nó nghĩ là kết thúc dòng văn bản giữa các quy ước nền tảng khác nhau (nhưng thực sự là một phần của hình ảnh).

+0

Phải có một số thứ khác bị thiếu ... Tôi đã thêm dòng bạn chơi cho tôi - nhưng không có gì thay đổi. – Asaf

+0

Có, xem Câu trả lời của Mark: bạn đang cố gắng đọc tệp dưới dạng văn bản UTF8 .Bỏ ** StreamReader ** và đọc các byte trực tiếp từ luồng, ví dụ: với ** Stream.Read() **. –

0

System.Text.Encoding.UTF8.GetBytes(stream.ReadToEnd());

Đừng làm điều này trừ khi nội dung của luồng của mình là văn bản. Thay đổi hàm của bạn để chấp nhận tham số boolean "nhị phân", và sử dụng phương thức làm việc thứ hai, nếu cờ đó được thiết lập.

2

Đoạn mã thứ hai của bạn thực hiện đúng cách. Nó sử dụng FileStream, không phải StreamReader. StreamReader chỉ thích hợp cho các tệp văn bản.

Các vấn đề liên quan