【问题标题】:Could not create SSL/TLS secure channel - HttpWebRequest无法创建 SSL/TLS 安全通道 - HttpWebRequest
【发布时间】:2018-06-17 21:48:10
【问题描述】:

我正在尝试连接到我的 kubernetes api,但似乎无法让 SSL 从 C# 工作。

当我通过 curl 运行以下命令时,一切似乎都按预期工作:

我有这个让 c# 做同样的事情:

try
{
    // use the TLS protocol 
    ServicePointManager.SecurityProtocol = SecurityProtocolType.Tls;

    // create HTTP web request with proper content type
    HttpWebRequest request = WebRequest.Create(Constants.K8_API_RC_URI) as HttpWebRequest;
    request.ContentType = "application/json;charset=UTF8";
    request.Headers.Add(HttpRequestHeader.Authorization, "Bearer " + Constants.K8_TOKEN);
    // load the X.509 certificate and add to the web request
    X509Certificate cert = new X509Certificate(Constants.K8_CRT);
    request.ClientCertificates.Add(cert);

    // call the web service and get response
    WebResponse response = request.GetResponse();

    Stream responseStream = response.GetResponseStream();

    string jsonContents = new StreamReader(responseStream).ReadToEnd();
}
catch (Exception exc)
{
    // log and print out error
    log.Info(exc.Message);
}

在哪里

Constants.K8_CRT 是 ca.crt 的路径

并且 ca.crt 包含以下内容:

-----BEGIN CERTIFICATE-----
MIIDMDCCAhigAwIBAgIIcwd9rrnaPcowDQYJKoZIhvcNAQELBQAwEzERMA8GA1UEAwwIYWNzazhz
and more letters.......
cwSfuIp7e49KC3HSqcU3Mz4oFNm5bw==
-----END CERTIFICATE-----

我收到以下错误:

无法创建 SSL/TLS 安全通道。

附:我知道那里有 .Net 的 Kubernetes 客户端,并且我几乎尝试了所有这些客户端,但是由于我将其与 Azure Functions 集成,因此大多数第三方库由于各种原因无法正常工作。

【问题讨论】:

  • 我不能说这是问题所在,但.SecurityProtocolType.Tls 仅启用 TLS 1.0(默认启用);试试.SecurityProtocolType.Tls12
  • 试过了,同样的错误。
  • 通常还需要一个CookieContainer。
  • 您能详细说明一下吗?如果不涉及 cookie,CookieContainer 将用于什么?
  • 你确定吗?尝试它不会花费太多。

标签: c# ssl https kubernetes httpwebrequest


【解决方案1】:

CA 证书应该用于验证服务器证书链,而不是作为 ClientCertificate 传递。

这是一个例子。

ServicePointManager.ServerCertificateValidationCallback = (sender, certificate, chain, errors) => {
    if (errors == SslPolicyErrors.None) return true;
    X509Certificate2 serverCert = new X509Certificate2(certificate);
    X509Certificate2 caCert = new X509Certificate2(@"./ca.cert");
    chain.ChainPolicy.ExtraStore.Add(caCert);
    chain.Build(serverCert);
    foreach (var chainStatus in chain.ChainStatus) {
        if (chainStatus.Status == X509ChainStatusFlags.UntrustedRoot) continue;
        if (chainStatus.Status != X509ChainStatusFlags.NoError) return false;
    }
    return true;
};

HttpWebRequest request = WebRequest.CreateHttp("https://master:6443/api/v1");
request.Headers[HttpRequestHeader.Authorization] = "Bearer " + "SOME_TOKEN";

HttpWebResponse response = (HttpWebResponse)request.GetResponse();
var content = new StreamReader(response.GetResponseStream()).ReadToEnd();
Console.WriteLine(content);

【讨论】:

    【解决方案2】:

    感谢@Jimi 的 cmets,我能够通过添加以下内容来实现这一点:

    System.Net.ServicePointManager.ServerCertificateValidationCallback +=
                delegate(object sender, System.Security.Cryptography.X509Certificates.X509Certificate certificate,
                                        System.Security.Cryptography.X509Certificates.X509Chain chain,
                                        System.Net.Security.SslPolicyErrors sslPolicyErrors)
                    {
                        return true; // **** Always accept
                    };
    

    注意:我确定这只是忽略 SSL 验证并继续没有它。在我们的情况下,这可能是可以接受的。

    【讨论】:

      猜你喜欢
      • 2023-04-08
      • 2014-12-18
      • 2021-02-27
      • 2016-06-30
      • 2017-12-10
      • 2020-09-23
      • 1970-01-01
      • 2021-12-13
      • 2014-12-26
      相关资源
      最近更新 更多