【问题标题】:WCF WF Service, Could not establish secure channel for SSL/TLS with authorityWCF WF 服务,无法为具有权限的 SSL/TLS 建立安全通道
【发布时间】:2017-09-18 09:40:45
【问题描述】:

在尝试访问我的 WCF WF 服务时,我不断收到相同的错误:“无法为具有权限的 SSL/TLS 建立安全通道。”

我已经尝试了一堆 stackoverflow/google 解决方案,但到目前为止都没有运气。

我创建了一个 WCF WF 服务,该服务连接到使用证书进行验证的第三方。我的 Web.config 如下所示:

<?xml version="1.0"?>
<configuration>
<appSettings>
  <add key="aspnet:UseTaskFriendlySynchronizationContext" value="true"/>
</appSettings>
<system.web>
  <compilation debug="true" strict="false" explicit="true" 
                            targetFramework="4.5.1"/>
  <httpRuntime targetFramework="4.5.1"/>
</system.web>
<system.serviceModel>
  <bindings>      
    <basicHttpsBinding>
      <binding name="binding1">
        <security mode="TransportWithMessageCredential">
          <message clientCredentialType="Certificate" />
        </security>
      </binding>
    </basicHttpsBinding>
  </bindings>
  <client>
    <!-- Test Endpoint -->
    <endpoint address="https://example.com" 
              behaviorConfiguration="endpointBehavior" 
              binding="basicHttpsBinding" 
              bindingConfiguration="binding1" 
              contract="ContractPortType" 
              name="Port">
    </endpoint>
  </client>
  <behaviors>
    <serviceBehaviors>
      <behavior>
        <serviceMetadata httpGetEnabled="true" httpsGetEnabled="true"/>
        <serviceDebug includeExceptionDetailInFaults="true"/>        
      </behavior>
    </serviceBehaviors>
    <endpointBehaviors>
      <behavior name="endpointBehavior">
        <clientCredentials>          
          <clientCertificate findValue="SOMETHUMBPRINT" 
                              storeLocation="LocalMachine" 
                              storeName="My" 
                              x509FindType="FindByThumbprint" />
        </clientCredentials>
      </behavior>
    </endpointBehaviors>
  </behaviors>
  <protocolMapping>
    <add binding="basicHttpsBinding" scheme="https"/>
  </protocolMapping>
  <serviceHostingEnvironment aspNetCompatibilityEnabled="true" 
                             multipleSiteBindingsEnabled="true" 
                             minFreeMemoryPercentageToActivateService="1"/>
</system.serviceModel>
<system.webServer>
  <modules runAllManagedModulesForAllRequests="true"/>
</system.webServer>

客户端只是一个运行这个的简单控制台:

using (var client = new ServiceClient())
{
     System.Net.ServicePointManager.SecurityProtocol = SecurityProtocolType.Tls12;
     var msg = client.GetData();
     Console.WriteLine(msg);
 }

即有以下 App.config:

    <?xml version="1.0" encoding="utf-8" ?>
<configuration>
  <startup>
    <supportedRuntime version="v4.0" sku=".NETFramework,Version=v4.5.2" />
  </startup>
  <system.serviceModel>
    <bindings>     
      <basicHttpBinding>
        <binding name="BasicHttpBinding_IService"/>
      </basicHttpBinding>
    </bindings>

    <client>
      <endpoint address="http://localhost:55670/GetData.xamlx"
        binding="basicHttpBinding" bindingConfiguration="BasicHttpBinding_IService"
        contract="Reference.IService" name="BasicHttpBinding_IService" behaviorConfiguration="endpointBehavior" />
    </client>

    <behaviors>
      <serviceBehaviors>
        <behavior>
          <serviceMetadata httpGetEnabled="true" httpsGetEnabled="true"/>
          <serviceDebug includeExceptionDetailInFaults="true"/>
        </behavior>
      </serviceBehaviors>
      <endpointBehaviors>
        <behavior name="endpointBehavior">
          <clientCredentials>
            <clientCertificate findValue="SOMETHUMBPRINT"
                               storeLocation="LocalMachine"
                               storeName="My"
                               x509FindType="FindByThumbprint" />
          </clientCredentials>
        </behavior>
      </endpointBehaviors>
    </behaviors>
  </system.serviceModel>
</configuration>

如果有人可以帮助我,那就太好了。

编辑: 所以我似乎无法工作的是我的 WCF WF 服务和第三方服务之间需要的 SSL 连接。当我直接从客户端调用第三方服务时,我可以设置 System.Net.ServicePointManager.SecurityProtocol = SecurityProtocolType.Tls12; 但我找不到对我的 WCF WF 服务执行相同操作的方法。

编辑: 因此,我可以通过创建一个活动,然后在调用第三方活动之前调用该活动来使其工作,但必须有更好的方法!

public sealed class SetTlsVersion : CodeActivity
{
    protected override void Execute(CodeActivityContext context)
    {
        System.Net.ServicePointManager.SecurityProtocol = SecurityProtocolType.Tls12;
    }
}

【问题讨论】:

标签: c# wcf ssl workflow-foundation


【解决方案1】:

我在今年早些时候遇到了类似的问题,结果发现某些 SSL 证书使用 TLS 1.2。

.NET 4.5 将 TLS 版本默认为 v1.1。这可以通过以下 sn-p 在您的代码中进行更改:

using System.Net;
// ...
// In your application startup flow, set the security protocol to TLS 1.2.
ServicePointManager.SecurityProtocol = SecurityProtocolType.Tls12;

理想情况下,应在应用程序启动时调用上述内容。在那之后,我想你会很高兴的。

旁注: .NET 4.0 目标应用程序需要稍微不同的技巧来设置 TLS 版本:

ServicePointManager.SecurityProtocol = (SecurityProtocolType)3072;

不幸的是,在 .NET 3.5 及更低版本中,甚至不支持 TLS 1.2。但在您的情况下,您的目标似乎是 .NET 4.5,所以您最好在这方面继续前进。

编辑:我注意到在您的客户端代码 sn-p 中您对 TLS 版本进行了按位或运算,这是不正确的。它应该是单个值,在本例中为 SecurityProtocolType.Tls12

我假设底层 .NET Framework 网络代码最终只使用SecurityProtocolType.Tls,这与 SSL / TLS 证书支持的内容不匹配。

希望对您有所帮助。

【讨论】:

  • 我在调用客户端时已经添加了这个(见客户端代码)。当我直接从控制台访问第三方时,它可以工作,但是当我从工作流服务调用第三方时,我收到此错误。我找不到在 WCF WF 服务中设置安全协议的方法。
  • 我应该更彻底地阅读您的帖子。我还没有找到方法,但也许你可以有一个 http 模块来设置正确的 TLS 级别。它会在您的 WCF 服务之前被调用。或者实际创建一个设置它的服务行为。
【解决方案2】:

嗯,我能够做到这一点的唯一方法是使用 HttpModule(感谢 ajawad987 的提示)。我仍然相信这可以(或应该)仅在 Web.config 中完成。

public class InitializerModule : IHttpModule
{
    public void Dispose() { }

    public void Init(HttpApplication context)
    {
        // Sets the TLS version for every request made to an external party
        System.Net.ServicePointManager.SecurityProtocol = SecurityProtocolType.Tls12;
    }
}

Web.config

<system.webServer>
  <modules runAllManagedModulesForAllRequests="true">
    <add name="InitializerModule" type="WorkflowService.Helpers.InitializerModule"/>
  </modules>
</system.webServer>

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2015-02-12
    • 2015-04-05
    • 2011-05-26
    • 2014-11-26
    • 2019-12-05
    • 2018-04-21
    • 1970-01-01
    • 2020-08-05
    相关资源
    最近更新 更多