【问题标题】:Can C# .NET Upload Files to an FTPS Server Running pure-ftpd Requiring Explicit FTP over TLS? [duplicate]C# .NET 能否将文件上传到运行纯 ftpd 的 FTPS 服务器,需要通过 TLS 进行显式 FTP? [复制]
【发布时间】:2022-01-07 00:18:03
【问题描述】:

当尝试通过 .NET 将文件上传到运行 pure-ftpd(为 FTPS SFTP,需要显式 FTP over TLS)的 ftp 服务器上时,会引发异常:

Unhandled exception. System.Net.WebException: The underlying connection was closed: The server committed a protocol violation.

服务器日志似乎表明一切正常,直到客户端在收到150 Accepted data connection 日志消息后停止通信。

客户端日志表明字节已写入流,但关闭流似乎会触发异常。

在 ftp 服务器上创建了一个文件;但是,没有写入任何内容。

其他客户端(即 Filezilla)可以毫无问题地上传文件(使用相同的凭据,从同一网络/机器到同一服务器)。

我看到的其他类似问题建议更改请求的各种属性(EnableSslUseBinaryUsePassiveKeepAliveTimeout)。我尝试了这些属性的各种组合,但无济于事。

我不知道问题出在哪里。我倾向于认为这是客户端错误配置,因为其他语言/客户端可以毫无问题地连接到服务器。我不称自己为 C#/.NET 开发人员,因此我可能缺少一些明显的东西 - 感谢任何帮助。

using System;
using System.IO;
using System.Net;
using System.Text;

Uri target = new Uri("ftp://ftp.example.com:21/filenamehere");
FtpWebRequest request = (FtpWebRequest)WebRequest.Create(target);
request.Method = WebRequestMethods.Ftp.UploadFile;
request.EnableSsl = true;
request.Credentials = new NetworkCredential("myusername", "password");
request.UseBinary = true;
request.UsePassive = true;
request.KeepAlive = true;
request.Timeout = -1;

Stream fileStream = File.OpenRead(@"testfile.txt");
Stream ftpStream = request.GetRequestStream();

byte[] buffer = new byte[10240];
int read;
while ((read = fileStream.Read(buffer, 0, buffer.Length)) > 0)
{
    ftpStream.Write(buffer, 0, read);
    Console.WriteLine("Uploaded {0} bytes", fileStream.Position);
}

ftpStream.Close();
Console.WriteLine("done...");

客户端输出:

Uploaded 10240 bytes
Uploaded 20480 bytes
Uploaded 30720 bytes
Uploaded 40960 bytes
Uploaded 51200 bytes
Uploaded 61440 bytes
Uploaded 71680 bytes
Uploaded 81920 bytes
Uploaded 92160 bytes
Uploaded 92295 bytes

未处理的异常。 System.Net.WebException:底层连接已关闭:服务器违反了协议 在 System.Net.FtpWebRequest.SyncRequestCallback(对象 obj) 在 System.Net.CommandStream.InvokeRequestCallback(对象 obj) 在 System.Net.CommandStream.Abort(异常 e) 在 System.Net.CommandStream.CheckContinuePipeline() 在 System.Net.FtpWebRequest.DataStreamClosed(CloseExState closeState) 在 System.Net.FtpDataStream.System.Net.ICloseEx.CloseEx(CloseExState closeState) 在 System.Net.FtpDataStream.Dispose(布尔处理) 在 System.IO.Stream.Close() 在 Program.$(String[] args) 在 /Users/user/MyApp/Program.cs:line 27

服务器输出:

Jan  6 23:46:06 machine1 ftp.debug pure-ftpd: (?@XX.XX.XX.XX) [DEBUG] Command [user] [myusername]
Jan  6 23:46:06 machine1 ftp.debug pure-ftpd: (?@XX.XX.XX.XX) [DEBUG] 331 User myusername OK. Password required
Jan  6 23:46:06 machine1 ftp.info pure-ftpd: (?@XX.XX.XX.XX) [INFO] myusername is now logged in
Jan  6 23:46:06 machine1 ftp.debug pure-ftpd: (myusername@XX.XX.XX.XX) [DEBUG] 230 OK. Current restricted directory is /
Jan  6 23:46:06 machine1 ftp.debug pure-ftpd: (myusername@XX.XX.XX.XX) [DEBUG] Command [pbsz] [0]
Jan  6 23:46:06 machine1 ftp.debug pure-ftpd: (myusername@XX.XX.XX.XX) [DEBUG] 200 PBSZ=0
Jan  6 23:46:06 machine1 ftp.debug pure-ftpd: (myusername@XX.XX.XX.XX) [DEBUG] Command [prot] [P]
Jan  6 23:46:06 machine1 ftp.debug pure-ftpd: (myusername@XX.XX.XX.XX) [DEBUG] 200 Data protection level set to "private"
Jan  6 23:46:06 machine1 ftp.debug pure-ftpd: (myusername@XX.XX.XX.XX) [DEBUG] Command [opts] [utf8 on]
Jan  6 23:46:06 machine1 ftp.debug pure-ftpd: (myusername@XX.XX.XX.XX) [DEBUG] 500 Unknown command
Jan  6 23:46:06 machine1 ftp.debug pure-ftpd: (myusername@XX.XX.XX.XX) [DEBUG] Command [pwd] []
Jan  6 23:46:06 machine1 ftp.debug pure-ftpd: (myusername@XX.XX.XX.XX) [DEBUG] 257 "/" is your current location
Jan  6 23:46:06 machine1 ftp.debug pure-ftpd: (myusername@XX.XX.XX.XX) [DEBUG] Command [type] [I]
Jan  6 23:46:06 machine1 ftp.debug pure-ftpd: (myusername@XX.XX.XX.XX) [DEBUG] 200 TYPE is now 8-bit binary
Jan  6 23:46:06 machine1 ftp.debug pure-ftpd: (myusername@XX.XX.XX.XX) [DEBUG] Command [pasv] []
Jan  6 23:46:06 machine1 ftp.debug pure-ftpd: (myusername@XX.XX.XX.XX) [DEBUG] 227 Entering Passive Mode (YY,YY,YY,YY,YY,YY)
Jan  6 23:46:07 machine1 ftp.debug pure-ftpd: (myusername@XX.XX.XX.XX) [DEBUG] Command [stor] [filenamehere]
Jan  6 23:46:07 machine1 ftp.debug pure-ftpd: (myusername@XX.XX.XX.XX) [DEBUG] 150 Accepted data connection

【问题讨论】:

    标签: c# .net ftp ftps pureftpd


    【解决方案1】:

    虽然我无法绝对确定引发此问题的问题的原因,但似乎 2019-10 年/前后的 .NET 更新是罪魁祸首。将 pureftpd 更新到较新的版本(至少 1.0.49-r2)似乎可以让 pureftpd 更好地与更新的 .NET 版本配合使用。

    感谢@Martin Prikryl 提供链接问题(特别是答案中的参考资料)。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2023-03-24
      • 2020-04-04
      • 1970-01-01
      • 2010-12-04
      • 2020-05-14
      • 1970-01-01
      • 2016-07-18
      • 1970-01-01
      相关资源
      最近更新 更多