C# 上载到FTP并使用FtpWebRequest下载回来后,存档或图像已损坏

C# 上载到FTP并使用FtpWebRequest下载回来后,存档或图像已损坏,c#,.net,ftp,zip,ftpwebrequest,C#,.net,Ftp,Zip,Ftpwebrequest,我有两种方法: 将文件上载到FTP服务器 从服务器下载文件 任何东西都可以完美地处理文本或xml文件。但是,当我尝试上载然后下载存档或图像时,我会收到“windows无法打开文件夹。压缩的zip文件无效”错误,对于存档和图像几乎相同。有什么问题吗 以下是我的方法列表: 上传: private string Upload(string Login, string Password, string FilePath, string FileName, string uuid, string FTPD

我有两种方法:

  • 将文件上载到FTP服务器
  • 从服务器下载文件 任何东西都可以完美地处理文本或xml文件。但是,当我尝试上载然后下载存档或图像时,我会收到“windows无法打开文件夹。压缩的zip文件无效”错误,对于存档和图像几乎相同。有什么问题吗

    以下是我的方法列表:

    上传:

    private string Upload(string Login, string Password, string FilePath, string FileName, string uuid, string FTPDir)
    {
        string CreateDirectory = CreateFTPDirectory(Login, Password, uuid, FTPDir);
    
        FtpWebRequest request = (FtpWebRequest)WebRequest.Create(@"ftp://" + FTPDir + uuid + "/" + FileName);
        request.Method = WebRequestMethods.Ftp.UploadFile;
        request.UseBinary = true;
    
        StreamReader sourceStream = new StreamReader(FilePath + FileName);
        byte[] fileContents = Encoding.UTF8.GetBytes(sourceStream.ReadToEnd());
        sourceStream.Close();
        request.ContentLength = fileContents.Length;
    
        using (Stream S = request.GetRequestStream())
        {
            S.Write(fileContents, 0, fileContents.Length);
        }
        FtpWebResponse response = (FtpWebResponse)request.GetResponse();
        response.Close();
    
        return response.StatusDescription;
    }
    
    下载:

    private string Download(string Login, string Password, string FileName, string uuid, string FTPDir, string Destination)
    {
        FtpWebRequest request = (FtpWebRequest)WebRequest.Create("ftp://" + FTPDir + uuid + "/" + FileName);
        request.UseBinary = true;
        request.Method = WebRequestMethods.Ftp.DownloadFile;
        request.Credentials = new NetworkCredential(Login, Password);
        byte[] buffer = new byte[1024];
    
        using (var response = (FtpWebResponse)request.GetResponse())
        {
    
            using (var stream = response.GetResponseStream())
            {
                using (var fs = new FileStream(Destination, FileMode.OpenOrCreate))
                {
                    int readCount = stream.Read(buffer, 0, 1024);
    
                    while (readCount > 0)
                    {
                        fs.Write(buffer, 0, readCount);
                        readCount = stream.Read(buffer, 0, 1024);                            
                    }
                }
                return response.StatusDescription;
            }
        }
    }
    

    您正在上载二进制文件(位图图像),就像它是UTF-8编码的文本文件一样:

    byte[] fileContents = Encoding.UTF8.GetBytes(sourceStream.ReadToEnd());
    
    这自然会损坏文件

    你必须一点一滴地传输二进制文件

    此外,对于潜在的大型图像文件,您的技术效率很低。整个文件至少在内存中保存两次

    您需要的代码实际上比您的代码简单得多:

    using (Stream fileStream = File.OpenRead(FilePath + FileName)
    using (Stream ftpStream = request.GetRequestStream())
    {
        fileStream.CopyTo(ftpStream);
    }
    

    您的下载代码还可以,但同样可以简化为:

    using (Stream ftpStream = request.GetResponse().GetResponseStream())
    using (Stream fileStream = File.Create(Destination))
    {
        ftpStream.CopyTo(fileStream);
    }
    


    有关完整代码,请参阅。

    您正在上载二进制文件(位图图像),就像它是UTF-8编码的文本文件一样:

    byte[] fileContents = Encoding.UTF8.GetBytes(sourceStream.ReadToEnd());
    
    这自然会损坏文件

    你必须一点一滴地传输二进制文件

    此外,对于潜在的大型图像文件,您的技术效率很低。整个文件至少在内存中保存两次

    您需要的代码实际上比您的代码简单得多:

    using (Stream fileStream = File.OpenRead(FilePath + FileName)
    using (Stream ftpStream = request.GetRequestStream())
    {
        fileStream.CopyTo(ftpStream);
    }
    

    您的下载代码还可以,但同样可以简化为:

    using (Stream ftpStream = request.GetResponse().GetResponseStream())
    using (Stream fileStream = File.Create(Destination))
    {
        ftpStream.CopyTo(fileStream);
    }
    


    有关完整代码,请参见。

    在您的
    上载中,文件内容通过
    编码.UTF8.GetBytes
    更改。您应该在不编码/解码的情况下传输数据。在
    上载中,文件内容通过
    编码.UTF8.GetBytes
    进行更改。您应该在不编码/解码的情况下传输数据。非常感谢!我也根据你的建议修改了我的方法。非常感谢!我也根据你的建议修改了我的方法。