如果可能,在C#中使用FtpWebRequest实现没有第三方dll的FTP / SFTP
我试图通过C#中的FtpWebRequest类来实现ftp / sftp,但直到现在还没有成功。
我不想使用任何第三方免费或付费的dll。
凭证就像
- hostname = sftp.xyz.com
- userid = abc
- 密码= 123
我能够使用IP地址实现ftp,但无法使用凭据获取上述主机名的sftp。
对于sftp,我已将FtpWebRequest类的EnableSsl属性设置为true,但是获取错误无法连接到远程服务器。
我能够使用相同的凭据和主机名连接Filezilla,但不能通过代码连接。
我观察了filezilla,它将主机名从sftp.xyz.com更改为文本框中的sftp://sftp.xyz.com,在命令行中将用户标识更改为abc@sftp.xyz.com
我在代码中做了同样的事情,但sftp没有成功。
请急需帮助。 提前致谢。
以下是我目前的代码:
private static void ProcessSFTPFile() { try { string[] fileList = null; StringBuilder result = new StringBuilder(); string uri = "ftp://sftp.xyz.com"; FtpWebRequest ftpRequest = (FtpWebRequest)WebRequest.Create(new Uri(uri)); ftpRequest.Method = WebRequestMethods.Ftp.ListDirectoryDetails; ftpRequest.EnableSsl = true; ftpRequest.Credentials = new NetworkCredential("abc@sftp.xyz.com", "123"); ftpRequest.UsePassive = true; ftpRequest.Timeout = System.Threading.Timeout.Infinite; //ftpRequest.AuthenticationLevel = Security.AuthenticationLevel.MutualAuthRequested; //ftpRequest.Proxy = null; ftpRequest.KeepAlive = true; ftpRequest.UseBinary = true; //Hook a callback to verify the remote certificate ServicePointManager.ServerCertificateValidationCallback = new RemoteCertificateValidationCallback(ValidateServerCertificate); //ServicePointManager.ServerCertificateValidationCallback = ((sender, certificate, chain, sslPolicyErrors) => true); FtpWebResponse response = (FtpWebResponse)ftpRequest.GetResponse(); StreamReader reader = new StreamReader(response.GetResponseStream()); string line = reader.ReadLine(); while (line != null) { result.Append("ftp://sftp.xyz.com" + line); result.Append("\n"); line = reader.ReadLine(); } if (result.Length != 0) { // to remove the trailing '\n' result.Remove(result.ToString().LastIndexOf('\n'), 1); // extracting the array of all ftp file paths fileList = result.ToString().Split('\n'); } } catch (Exception ex) { Console.WriteLine(ex.Message.ToString()); Console.ReadLine(); } } public static bool ValidateServerCertificate(object sender, X509Certificate certificate, X509Chain chain, SslPolicyErrors sslPolicyErrors) { if (certificate.Subject.Contains("CN=sftp.xyz.com")) { return true; } else { return false; } }
更新:
如果使用BizTalk,则可以使用ESB Toolkit使用SFTP适配器 。 它自2010年以来一直得到支持。人们想知道为什么它没有进入.Net Framework
- BizTalk Server 2013:在ESB Toolkit SFTP中创建自定义适配器提供程序作为示例
- BizTalk Server 2013:如何使用SFTP适配器
- MSDN文档
–
不幸的是,目前只需要与框架有很多工作要做。 放置sftp
协议前缀不足以make-it-work
仍然没有内置的.Net Framework支持,可能在将来。
————————————————– ——-
1)一个很好的图书馆可以试用SSHNet 。
————————————————– ——-
它有:
- 更多function,包括内置流媒体支持。
- API文档
- 一个更简单的API来编码
文档中的示例代码:
列表目录
/// /// This sample will list the contents of the current directory. /// public void ListDirectory() { string host = ""; string username = ""; string password = ""; string remoteDirectory = "."; // . always refers to the current directory. using (var sftp = new SftpClient(host, username, password)) { sftp.Connect(); var files = sftp.ListDirectory(remoteDirectory); foreach (var file in files) { Console.WriteLine(file.FullName); } } }
上传文件
/// /// This sample will upload a file on your local machine to the remote system. /// public void UploadFile() { string host = ""; string username = ""; string password = ""; string localFileName = ""; string remoteFileName = System.IO.Path.GetFileName(localFile); using (var sftp = new SftpClient(host, username, password)) { sftp.Connect(); using (var file = File.OpenRead(localFileName)) { sftp.UploadFile(remoteFileName, file); } sftp.Disconnect(); } }
下载文件
/// /// This sample will download a file on the remote system to your local machine. /// public void DownloadFile() { string host = ""; string username = ""; string password = ""; string localFileName = System.IO.Path.GetFileName(localFile); string remoteFileName = ""; using (var sftp = new SftpClient(host, username, password)) { sftp.Connect(); using (var file = File.OpenWrite(localFileName)) { sftp.DownloadFile(remoteFileName, file); } sftp.Disconnect(); } }
————————————————– ——-
2)另一个替代库是WinSCP
————————————————– ——-
以下为例:
using System; using WinSCP; class Example { public static int Main() { try { // Setup session options SessionOptions sessionOptions = new SessionOptions { Protocol = Protocol.Sftp, HostName = "example.com", UserName = "user", Password = "mypassword", SshHostKeyFingerprint = "ssh-rsa 2048 xx:xx:xx:xx:xx:xx:xx:xx:xx:xx:xx:xx:xx:xx:xx:xx" }; using (Session session = new Session()) { // Connect session.Open(sessionOptions); // Upload files TransferOptions transferOptions = new TransferOptions(); transferOptions.TransferMode = TransferMode.Binary; TransferOperationResult transferResult; transferResult = session.PutFiles(@"d:\toupload\*", "/home/user/", false, transferOptions); // Throw on any error transferResult.Check(); // Print results foreach (TransferEventArgs transfer in transferResult.Transfers) { Console.WriteLine("Upload of {0} succeeded", transfer.FileName); } } return 0; } catch (Exception e) { Console.WriteLine("Error: {0}", e); return 1; } } }
在这里找到了更多 。
FTP可以单独用.NET完成。 但是SFTP没有内置类。 我建议看看WinSCP 。
同意Tejs。 只是为了澄清:
带有EnableSsl = true的FtpWebRequest意味着它是ftps,显式模式,或者用Filezilla的措辞:“FTPES – FTP over Explicit TLS / SSL,默认端口21”。 您可以使用内置的.net内容来完成此操作。
对于隐式ftps(在Filezilla措辞“FTPS – FTP over Implicit TLS / SSL,默认端口990”),您必须使用第三方(例如ftps.codeplex.com)。
对于sftp(在Filezilla中写“SSH文件传输协议,默认端口22”),您还必须使用第三方(例如sshnet.codeplex.com)。
正如Joachim Isaksson所说,如果你不能使用第三方,你必须自己实施。