HTTPs客户端连接到Azure Web App上没有受信任链(非受信任CA)的服务器

我已经被困了大约3天试图连接到一个没有被可信CA签名的证书的服务器 – 你可以通过Azure门户添加CA的证书 – 但是没有任何影响。

显然,HTTP使用内核模块(!)HTTP.SYS。

我所看到的所有建议都要使用:

ServicePointManager.ServerCertificateValidationCallback = Communicator.CustomServiceCertificateValidation;

(或者在请求本身上不那么全球化的对应物)

或类似的东西:

  client.ClientCredentials.ServiceCertificate.SslCertificateAuthentication = new X509ServiceCertificateAuthentication() { CertificateValidationMode = X509CertificateValidationMode.Custom, RevocationMode = X509RevocationMode.NoCheck, //TrustedStoreLocation = StoreLocation.CurrentUser, CustomCertificateValidator = new PermissiveCertificateValidator() }; 

但是,都没有被调用!!

一些更重要的细节:

这有效:

  try { ServicePointManager.ServerCertificateValidationCallback += (sender, cert, chain, sslPolicyErrors) => true; using (var wc = new WebClient()) { var res = wc.DownloadString("https://untrusted-root.badssl.com/"); return Content(res); } } catch (Exception ex) { return Content(ex.ToString()); } 

但是,我需要使用客户端证书对自己进行身份validation – 因此,请按照此处的说明进行操作: 如何向WebClient(C#)添加证书?

我最终得到以下代码:

 class ATWebClient : WebClient { protected override WebRequest GetWebRequest(Uri address) { HttpWebRequest request = (HttpWebRequest)base.GetWebRequest(address); request.Headers.Add("SOAPAction", "https://servicos.portaldasfinancas.gov.pt/sgdtws/documentosTransporte/"); X509Certificate2 cert = new X509Certificate2(); //From user installed Certificates //cert.Import(_pathCertificate, _passwordCertificate, X509KeyStorageFlags.DefaultKeySet); //From FileSystem "Resources\Certificates" cert.Import(Common.Properties.Resources.testewebservices_novo, "TESTEwebservice", X509KeyStorageFlags.Exportable); // Output Certificate //Utils.Log(string.Format("Cert Subject: [{0}], NotBefore: [{1}], NotAfter: [{2}]", cert.Subject, cert.NotBefore, cert.NotAfter)); request.ClientCertificates.Add(cert); request.Method = "POST"; request.ContentType = "text/xml; charset=utf-8"; request.Accept = "text/xml"; return request; } 

现在我用以下方法调用服务:

  try { ServicePointManager.ServerCertificateValidationCallback += (sender, cert, chain, sslPolicyErrors) => true; ServicePointManager.CheckCertificateRevocationList = false; ServicePointManager.UseNagleAlgorithm = false; using (var wc = new ATWebClient()) { //var res = wc.DownloadString("https://servicos.portaldasfinancas.gov.pt:701/sgdtws/documentosTransporte"); var res = wc.UploadString("https://servicos.portaldasfinancas.gov.pt:701/sgdtws/documentosTransporte", "Test of content"); return Content(res); } } catch (Exception ex) { return Json(ex); } 

注意,是的,这是一个SOAP端点 – 我尝试发送有效的SOAP内容,但结果在两种情况下都相同,我得到以下exception:

The underlying connection was closed: An unexpected error occurred on a send.

堆栈跟踪:

  at System.Net.WebClient.UploadDataInternal(Uri address, String method, Byte[] data, WebRequest& request) at System.Net.WebClient.UploadString(Uri address, String method, String data) at System.Net.WebClient.UploadString(String address, String data) at MagniWebApp.Controllers.HomeController.NonTrustedCATestEndpoint() in C:\Users\joao.antunes.Office2\source\repos\07. Platform\WebApp\MagniWebApp\Controllers\HomeController.cs:line 1154 

内部exception的消息:

Authentication failed because the remote party has closed the transport stream.

有任何想法吗?! HALP!

那么在你的自定义回调中硬编码返回true会怎么样?

  public string Ssl() { try { ServicePointManager.ServerCertificateValidationCallback += (sender, cert, chain, sslPolicyErrors) => true; using (var wc = new WebClient()) { var res = wc.DownloadString("https://untrusted-root.badssl.com/"); Console.WriteLine(res); return res; } } catch (Exception ex) { return ex.ToString(); } }