.net - 调试重启后运行时为"Invalid or expired security context token"

标签 .net wcf wshttpbinding

我有一个正在编码的 WCF 应用程序。当我更改内容时,我启动和停止它几次,然后再次运行服务调用。

由于我需要 session 信息,所以我使用 wsHttpBinding .

在我搬到 wsHttpBinding 之前我正在使用 basicHttpBinding我可以停止服务,进行更改并重新启动它。然后我可以针对端点运行我的 WCF 测试客户端 (WCF Storm),它仍然可以正常运行。

现在它告诉我:

The message could not be processed. This is most likely because the action 'http://tempuri.org/IMyService/MyOperation' is incorrect or because the message contains an invalid or expired security context token or because there is a mismatch between bindings. The security context token would be invalid if the service aborted the channel due to inactivity. To prevent the service from aborting idle sessions prematurely increase the Receive timeout on the service endpoint's binding.

这意味着我必须刷新连接并重新设置我的服务调用(数百次后会变得烦人。)。

我读到安全超时为 10 分钟。我在不到 2 分钟的时间内重新运行,因此我认为这不是超时问题。

我的猜测是 token 过期的明显原因是我已经终止并重新启动了服务。

问题是我根本不需要安全性的东西(我只需要 session 的东西,否则我会使用BasicHttpBinding

是否有办法让我的 WCF 服务不关心安全上下文 token ?

注意:我的测试客户端默认为 wsHttpBinding 并设置了安全性。但我认为它之所以设置此项,是因为我的服务正在发布它需要安全性。

我尝试过的事情:

  • 我尝试了类似于我发现的配置 Here

    <bindings>
        <wsHttpBinding>
            <binding name="WsEventLogBinding">
                <security mode="Message">
                    <message establishSecurityContext="false" />
                </security>
             </binding>
        </wsHttpBinding>
    </bindings>
    

但我真的不知道这意味着什么,或者这是否是我所需要的(这根本不安全(目前))。

这并没有消除问题。

  • 设置<security mode="None">这没有帮助。

最佳答案

首先,你是对的:由于 HTTP 协议(protocol)的无连接/无状态性质,basicHttpBinding 不支持此功能。

但是我认为你对WCF的理解有问题。

session 是WCF中的通用概念。它可以是基于安全的 session ,其中通信双方都同意特定的安全 session ,也可以是真实的 session ,其中消息可以配置为按顺序传递并且恰好一次,确保即使消息在 session 期间跨多个节点传输时也能收到消息。

两种模式都允许您选择 InstanceContextMode.PerSession。这真的是你想要的吗?

WCF 安全依赖于相互身份验证;如果双方都信任对方的凭证(基于声明),则可以建立一个安全上下文,其中所有消息都以保密方式交换,并且所有消息都经过签名以保护其完整性。安全 session 是唯一的,您不能在其他对话中重复使用它。

这是您的上下文的问题:问题不在服务器端,而是在客户端。由于必须在客户端和服务上保留某些内容,因此重建服务将刷新服务上的整个 WCF 上下文(所有实例和 session 都将被释放)。没有与 WCF session 关联的通用数据存储(与 asp.net session ),因此重新启动将删除所有内容。然而,由于其“无效”上下文,客户端仍然相信已通过身份验证。

为了解决这个问题,默认的 Wcf 测试客户端上有一个针对此场景的复选框:“启动新代理”。在 WCF Storm 上,Under the hood/Miscellaneous 中有一个通用配置“始终创建新代理”。

注意:在生产中,您永远不会遇到这种情况,因为您的服务将始终处于运行状态。

如果您关注我,您可能想尝试可靠的 session 。您可以测试,但我不确定这是否有效。

<wsHttpBinding>
    <binding name="wsHttpBindingConfiguration">
        <security mode="None" />
        <reliableSession enabled="true" />
    </binding>
</wsHttpBinding>

重要说明:我不知道您的 WCF 级别,但在 WCF 中,客户端和服务必须具有同步配置(相同的安全性、 session 设置等)

关于.net - 调试重启后运行时为"Invalid or expired security context token",我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/16575799/

相关文章:

wcf - 如何通过负载均衡器将 wsHttpBinding 与消息安全性结合使用

c# - 比较没有实例的类类型

c# - System.Array.CopyTo() 和 System.Array.Clone() 的区别

wcf - 通过 channel 接口(interface)支持消息级安全性的最小客户端

c# - WCF 错误 - 没有端点监听

c# - WCF wsHttpBindingwith silverlight 中的跨域错误

c# - WPF 接口(interface)仅在 DispatcherTimer 线程完成后更新

c# - IIS 输出缓存 - 如何将资源添加到缓存,无论路径如何

wcf - 如何在自定义 WCF HTTP 绑定(bind)中存储 header 信息

wcf - 在 WCF 客户端的代码中设置消息版本