c#ftp上传到Linux

我试图检查FTP服务器上是否存在目录。 在你说“使用ListDirectory”或“使用PrintWorkingDirectory”之前,它们并不总是有用; 例如,我测试了ftp:// webserver / Logs是否存在,并且两者都告诉我它实际上并没有。 所以我沿着将文件上传到目录的路线,如果成功,那么目录就存在了。

问题是,下面的方法不适用于GoDaddy的基于CentOS的服务器运行vsFTPd 2.0.7.2。 适用于IIS7.5上的Microsoft FTP服务器。

因此,我使用Wireshark监控流量,并使用Filezilla查看我的应用程序无法使其正常运行。 唯一的区别是Filezilla正在更改工作目录,因为我正在尝试使用之前的路径上传文件。

我感觉它与上传到服务器的路径和Linux的解释有关,因为它可能有点有趣的名字…… :-D任何想法热烈欢迎?

应用代码

private bool DirectoryExists(string d) { bool exists = true; try { string file = "directoryexists.test"; string path = url + homepath + d + "/" + file; //Try to save to the directory req = (FtpWebRequest)WebRequest.Create(path); req.ConnectionGroupName = "conngroup1"; req.Method = WebRequestMethods.Ftp.UploadFile; if (nc != null) req.Credentials = nc; if (cbSSL.Checked) req.EnableSsl = true; req.Timeout = 10000; byte[] fileContents = System.Text.Encoding.Unicode.GetBytes("SAFE TO DELETE"); req.ContentLength = fileContents.Length; Stream s = req.GetRequestStream(); s.Write(fileContents, 0, fileContents.Length); s.Close(); //Delete file if successful req = (FtpWebRequest)WebRequest.Create(path); req.ConnectionGroupName = "conngroup1"; req.Method = WebRequestMethods.Ftp.DeleteFile; if (nc != null) req.Credentials = nc; if (cbSSL.Checked) req.EnableSsl = true; req.Timeout = 10000; res = (FtpWebResponse)req.GetResponse(); res.Close(); } catch (WebException ex) { exists = false; } return exists; } 

Filezilla通过Wireshark登录

 Response: 230 Login successful. Request: CWD /Home/test1 Response: 250 Directory successfully changed. Request: TYPE I Response: 200 Switching to Binary mode. Request: PASV Response: 227 Entering Passive Mode (216,69,186,142,71,209) Request: LIST Response: 150 Here comes the directory listing. FTP Data: 78 bytes Response: 226 Directory send OK. Request: PASV Response: 227 Entering Passive Mode (216,69,186,142,177,1) Request: STOR directoryexists.txt Response: 150 Ok to send data. Response: 226 File receive OK. 

通过Wireshark应用日志

 Response: 230 Login successful. Request: OPTS utf8 on Response: 501 Option not understood. Request: PWD Response: 257 "/Home/" Request: PWD Response: 257 "/Home/" Request: TYPE I Response: 200 Switching to Binary mode. Request: PASV Response: 227 Entering Passive Mode (216,69,186,142,217,87) Request: STOR test1/directoryexists.txt Response: 553 Could not create file. 

如果它们不存在,它会创建文件夹。

 Response: 230 Login successful. Request: PWD Response: 257 "/Home/" Request: PWD Response: 257 "/Home/" Request: TYPE I Response: 200 Switching to Binary mode. Request: PASV Response: 227 Entering Passive Mode (216,69,186,142,220,60) Request: STOR Logs/directoryexists.txt Response: 553 Could not create file. Request: PWD Response: 257 "/Home/" Request: MKD Logs Response: 257 Create folder operation successful. Request: TYPE I Response: 200 Switching to Binary mode. Request: PASV Response: 227 Entering Passive Mode (216,69,186,142,255,245) Request: STOR Logs/LogFiles/directoryexists.txt Response: 553 Could not create file. Request: PWD Response: 257 "/Home/" Request: MKD Logs/LogFiles Response: 257 Create folder operation successful. 

Linux又咬了一口……

解决方案是在路径名中设置一个双斜杠,这样当它涉及到STOR时,它有一个前导斜杠……就像这样:

 string url = "ftp://website/"; string homepath = "/Home/"; string d = "test1"; string file = "directoryexists.test"; string path = url + homepath + d + "/" + file; 

所以完整的路径看起来像ftp://website//Home/test1/directoryexists.test

 req = (FtpWebRequest)WebRequest.Create("ftp://website//Home/test1/directoryexists.test"); 

这样STOR命令就像

 STOR /Home/test1/directoryexists.test 

您可以从StatusDescription获取Home路径

 req = (FtpWebRequest)WebRequest.Create(url); req.Method = WebRequestMethods.Ftp.PrintWorkingDirectory; if (nc != null) req.Credentials = nc; if (cbSSL.Checked) req.EnableSsl = true; req.Timeout = 10000; res = (FtpWebResponse)req.GetResponse(); System.Text.RegularExpressions.Regex regexp = new System.Text.RegularExpressions.Regex("\\s\"([^\"]*)\"\\s"); homepath = regexp.Match(res.StatusDescription).Groups[1].Value; res.Close();