WCF - 在新环境中找不到 MSMQ 端点
WCF - MSMQ endpoint not found in new environment
设置
我在 Windows Server 2012R2 的 IIS/AppFabric 运行 中托管了一个 WCF 服务。
该服务通过 netMsmqBinding 绑定到本地事务性 MSMQ 队列。我的操作装饰有 TransactionScopeRequired = true。
服务操作接收来自 BizTalk 服务器的调用,处理它们并将响应发送回远程队列(在同一 BizTalk Server 上),也通过 netMsmqBinding。
<endpoint name="Outbound" address="net.msmq://int01test.mydomain.com/private/queue.name" binding="netMsmqBinding" bindingConfiguration="QueueBindingConfigurationOutbound" contract="My.Outbound.Contract" />
<netMsmqBinding>
<binding name="QueueBindingConfigurationOutbound">
<security>
<transport msmqAuthenticationMode="WindowsDomain" msmqProtectionLevel="Sign" />
</security>
</binding>
</netMsmqBinding>
在测试环境中,这按预期工作。
测试环境中的物理设置:
服务器 int01test.mydomain.com 托管 BizTalk 服务器和我的入站队列。这在服务帐户 mydomain\inttestuser 下运行。
服务器 app01test.mydomain.com 托管我的应用程序 (IIS/AppFabric)、我的数据库 (SQL 服务器) 和我的出站队列。这在服务帐户 mydomain\apptestuser.
下运行
问题
当此解决方案提升到验收测试环境时,调用仍在处理,但响应被阻止并显示错误消息:
System.ServiceModel.EndpointNotFoundException: An error occurred while
opening the queue:Unrecognized error -1072824317 (0xc00e0003). The
message cannot be sent or received from the queue. Ensure that MSMQ is
installed and running. Also ensure that the queue is available to open
with the required access mode and authorization. --->
System.ServiceModel.MsmqException: An error occurred while opening the
queue:Unrecognized error -1072824317 (0xc00e0003). The message cannot
be sent or received from the queue. Ensure that MSMQ is installed and
running. Also ensure that the queue is available to open with the
required access mode and authorization.
差异
在测试环境中,我的服务和我的数据库 运行 在单个服务器实例上。 (BizTalk Server 和它的队列,我的出站消息的目标,虽然在另一台服务器上)
在验收测试环境中,我的解决方案部署在两台负载均衡的服务器上,数据库在一个单独的集群上。
还有更严格的外部防火墙规则来模拟生产环境。
即使 BizTalk 服务器也是集群的,尽管我们现在是机器对机器而不是集群对集群的通信。
所以 QA 环境中的设置是:
服务器 int01qa.mydomain.com(与 int02qa.mydomain.com 成簇)托管 BizTalk 服务器和我的入站队列。这在服务帐户 mydomain\intqauser 下运行。
服务器 app01qa.mydomain.com(与 app02qa.mydomain.com 集群)托管我的应用程序 (IIS/AppFabric) 和我的出站队列。这在服务帐户 mydomain\appqauser 下运行。
服务器 db01qa.mydomain.com 托管我的数据库。
我们已经尝试过的
- 我们已在远程队列上禁用身份验证。
- 我们已授予对我的服务 运行 下的帐户以及 "everyone".
的完全控制权
- 我们已经成功地在两台服务器之间手动发送了 msmq 消息。
- 我已将我的服务配置为将响应发送到本地私有队列,同样的错误。
问题原来是 MSMQ 找不到应用程序池用户的证书。那就是
0xc00e0003,MQ_ERROR_QUEUE_NOT_FOUND
真的是由一个
0xC00E002F,MQ_ERROR_NO_INTERNAL_USER_CERT
将安全设置更改为
<transport msmqAuthenticationMode="None" msmqProtectionLevel="None" />
已启用要发送的消息。
当然,真正的解决方案不是禁用安全性,而是确保在 msmq 中安装了应用程序池用户证书。
我们遇到了这个问题,不想禁用身份验证。我们尝试了多种不同的方法,但我们认为这与用户证书不存在有关。
我们转到客户端应用程序的应用程序池(通过 MSMQ 调用 WCF 端点)并将 Load Profile
属性 更改为 True
。然后通话成功了。顺便说一句,将其改回 false
继续工作 - 大概是因为它已经解决了证书问题。
设置
我在 Windows Server 2012R2 的 IIS/AppFabric 运行 中托管了一个 WCF 服务。 该服务通过 netMsmqBinding 绑定到本地事务性 MSMQ 队列。我的操作装饰有 TransactionScopeRequired = true。 服务操作接收来自 BizTalk 服务器的调用,处理它们并将响应发送回远程队列(在同一 BizTalk Server 上),也通过 netMsmqBinding。
<endpoint name="Outbound" address="net.msmq://int01test.mydomain.com/private/queue.name" binding="netMsmqBinding" bindingConfiguration="QueueBindingConfigurationOutbound" contract="My.Outbound.Contract" /> <netMsmqBinding> <binding name="QueueBindingConfigurationOutbound"> <security> <transport msmqAuthenticationMode="WindowsDomain" msmqProtectionLevel="Sign" /> </security> </binding> </netMsmqBinding>
在测试环境中,这按预期工作。
测试环境中的物理设置: 服务器 int01test.mydomain.com 托管 BizTalk 服务器和我的入站队列。这在服务帐户 mydomain\inttestuser 下运行。 服务器 app01test.mydomain.com 托管我的应用程序 (IIS/AppFabric)、我的数据库 (SQL 服务器) 和我的出站队列。这在服务帐户 mydomain\apptestuser.
下运行问题
当此解决方案提升到验收测试环境时,调用仍在处理,但响应被阻止并显示错误消息:
System.ServiceModel.EndpointNotFoundException: An error occurred while opening the queue:Unrecognized error -1072824317 (0xc00e0003). The message cannot be sent or received from the queue. Ensure that MSMQ is installed and running. Also ensure that the queue is available to open with the required access mode and authorization. ---> System.ServiceModel.MsmqException: An error occurred while opening the queue:Unrecognized error -1072824317 (0xc00e0003). The message cannot be sent or received from the queue. Ensure that MSMQ is installed and running. Also ensure that the queue is available to open with the required access mode and authorization.
差异
在测试环境中,我的服务和我的数据库 运行 在单个服务器实例上。 (BizTalk Server 和它的队列,我的出站消息的目标,虽然在另一台服务器上) 在验收测试环境中,我的解决方案部署在两台负载均衡的服务器上,数据库在一个单独的集群上。 还有更严格的外部防火墙规则来模拟生产环境。 即使 BizTalk 服务器也是集群的,尽管我们现在是机器对机器而不是集群对集群的通信。
所以 QA 环境中的设置是: 服务器 int01qa.mydomain.com(与 int02qa.mydomain.com 成簇)托管 BizTalk 服务器和我的入站队列。这在服务帐户 mydomain\intqauser 下运行。 服务器 app01qa.mydomain.com(与 app02qa.mydomain.com 集群)托管我的应用程序 (IIS/AppFabric) 和我的出站队列。这在服务帐户 mydomain\appqauser 下运行。 服务器 db01qa.mydomain.com 托管我的数据库。
我们已经尝试过的
- 我们已在远程队列上禁用身份验证。
- 我们已授予对我的服务 运行 下的帐户以及 "everyone". 的完全控制权
- 我们已经成功地在两台服务器之间手动发送了 msmq 消息。
- 我已将我的服务配置为将响应发送到本地私有队列,同样的错误。
问题原来是 MSMQ 找不到应用程序池用户的证书。那就是 0xc00e0003,MQ_ERROR_QUEUE_NOT_FOUND 真的是由一个 0xC00E002F,MQ_ERROR_NO_INTERNAL_USER_CERT 将安全设置更改为
<transport msmqAuthenticationMode="None" msmqProtectionLevel="None" />
已启用要发送的消息。 当然,真正的解决方案不是禁用安全性,而是确保在 msmq 中安装了应用程序池用户证书。
我们遇到了这个问题,不想禁用身份验证。我们尝试了多种不同的方法,但我们认为这与用户证书不存在有关。
我们转到客户端应用程序的应用程序池(通过 MSMQ 调用 WCF 端点)并将 Load Profile
属性 更改为 True
。然后通话成功了。顺便说一句,将其改回 false
继续工作 - 大概是因为它已经解决了证书问题。