c# ssl ftp client-certificates ftps

¿Hay alguna manera de usar FtpWebRequest para autenticarse en FTP usando certificados de cliente en C#?



ssl client-certificates (2)

Estoy intentando subir un archivo a un servidor FTP y necesito usar el certificado del cliente para autenticar y no el nombre de usuario y la contraseña.

var fullFtpPath = String.Concat(ftpItem.FtpAddress, "/", record, ".txt"); FtpWebRequest request = (FtpWebRequest) WebRequest.Create(fullFtpPath); request.Credentials = new NetworkCredential(ftpItem.Username, ftpItem.Password); request.Method = WebRequestMethods.Ftp.UploadFile; request.UseBinary = true; request.UsePassive = ftpItem.UsePassive; request.EnableSsl = ftpItem.UseSSL; request.ContentLength = bytes.Length; using(Stream s = request.GetRequestStream()) { s.Write(bytes, 0, bytes.Length); } FtpWebResponse response = (FtpWebResponse) request.GetResponse(); Debug.WriteLine("Upload File Complete, status {0}", response.StatusDescription); db.LogExport(siteId, fullFtpPath, record, true, response.StatusDescription); response.Close();

Arriba está mi código actual, pero no estoy seguro de cómo implementar la autenticación de certificado o si es posible hacerlo. ¿Tengo que crear el certificado? ¿O el servidor me proporcionará un certificado y lo estableceré en mi solicitud?


FtpWebRequest request = (FtpWebRequest)WebRequest.Create("ftp://ftp.example.com"); request.Credentials = new NetworkCredential("username", ""); // Query certificate from store X509Store store = new X509Store(StoreName.My, StoreLocation.CurrentUser); store.Open(OpenFlags.ReadOnly); const string tp = "2b6f8ac51a85cbaf429474a55304313968667611"; X509Certificate2 cert2 = store.Certificates.Find(X509FindType.FindByThumbprint, tp, true)[0]; store.Close(); // Add certificate into request request.ClientCertificates.Add(cert2);


Puede usar ComponentPro para esto. Este ejemplo de código explica cómo autenticar al cliente utilizando un certificado:

using System; using System.Security.Cryptography.X509Certificates; using ComponentPro.Net; ... public void HandleCertificateRequiredEvent() { // Create a new instance. Ftp client = new Ftp(); client.CertificateRequired += client_CertificateRequired; // Connect to the FTP server. client.Connect("myserver", 21, FtpSecurityMode.Explicit); // Authenticate. client.Authenticate("userName", "password"); // Do something here... client.DownloadFile("/my remote file.dat", "my local file"); // Disconnect. client.Disconnect(); } void client_CertificateRequired(object sender, ComponentPro.Security.CertificateRequiredEventArgs e) { // Load certificates from the local machine. X509Store my = new X509Store(StoreName.My, StoreLocation.CurrentUser); my.Open(OpenFlags.ReadOnly); // Retrieve a list of available certificates. X509Certificate2Collection certs = my.Certificates; // If no certificate found, return. if (certs.Count == 0) { e.Certificates = null; return; } // Show all certificates. Console.WriteLine("Select certificate:"); for (int i = 0; i <= certs.Count; i++) { if (i == 0) { Console.WriteLine(string.Format("{0}. [Nothing, skip this step]", i)); continue; } Console.WriteLine(string.Format("{0}. {1}", i, certs[i - 1].SubjectName.Name)); } // And ask user to choose an appropriate certificate. while (true) { Console.Write(string.Format("Select certificate [0 - {0}]: ", certs.Count)); int certIndex; try { certIndex = int.Parse(Console.ReadLine()); } catch { Console.WriteLine("ERROR: Wrong certificate index input!"); continue; } if (certIndex > 0 && certIndex <= certs.Count) { e.Certificates = new X509Certificate2Collection(certs[certIndex]); return; } if (certIndex == 0) break; Console.WriteLine(string.Format("ERROR: You must enter number between 0 and {0}.", certs.Count)); } }

ComponentPro también es bueno para trabajar con FtpWebRequest :

using System; using System.IO; using System.Net; ... // Register FtpWebRequest for the specified schema. WebRequest.RegisterPrefix("ftp://", ComponentPro.Net.FtpWebRequest.Creator); Console.WriteLine("Sending request..."); // Create a WebRequest for the specified URL. WebRequest request = WebRequest.Create("ftp://ftp.example.net/pub/myfile.zip"); // Send the WebRequest and waits for a response. WebResponse response = request.GetResponse(); // Get remote file stream for downloading. Stream remoteFileStream = response.GetResponseStream(); Stream localFileStream = File.Create("myfile.zip"); // Create a new buffer to download. byte[] buffer = new byte[1024]; int n; do { // Read data from the remote file stream. n = remoteFileStream.Read(buffer, 0, buffer.Length); // Write to the local file stream. localFileStream.Write(buffer, 0, n); } while (n > 0); Console.WriteLine("Response Received."); localFileStream.Close(); // Release the resources of the response. remoteFileStream.Close();