Mono 的 WCF 证书安全
我正在尝试将现有应用程序迁移到 Mono (v2.10.2)。
因此,我创建了一个具有 BasicHttpBinding 和消息安全性的测试 WCF 服务。客户端与 .NET 完美配合,但与 Mono 一起运行时会失败。
客户端工厂实例化如下:
//var certificate = CertificateUtil.GetCertificate(StoreLocation.LocalMachine,
// StoreName.My, X509FindType.FindBySubjectDistinguishedName, CertName, true);
var certificate = new X509Certificate2("certificate.pfx", "password");
var binding = new BasicHttpBinding();
binding.Security.Mode = BasicHttpSecurityMode.Message;
binding.Security.Message.ClientCredentialType = BasicHttpMessageCredentialType.Certificate;
var epa = new EndpointAddress(
new Uri("http://localhost:53076/Service1.svc"),
new X509CertificateEndpointIdentity(certificate));
var factory = new ChannelFactory<IService1>(binding, epa);
factory.Credentials.ServiceCertificate.DefaultCertificate = certificate;
factory.Credentials.ServiceCertificate.Authentication.CertificateValidationMode = X509CertificateValidationMode.None;
factory.Credentials.ServiceCertificate.Authentication.RevocationMode = X509RevocationMode.NoCheck;
factory.Credentials.ClientCertificate.Certificate = certificate;
var client = factory.CreateChannel();
在 Mono 中,应用程序在 CreateChannel 内失败并抛出异常:
System.InvalidOperationException:绑定不支持协定“IService1”允许的任何通道类型。
我调试了Mono源代码,发现问题在于AmetrySecurityBindingElement.InitiatorTokenParameter == null。
我是 Mono 的新手,也许您可以向我指出涵盖该主题的文档/教程。
更新:
在 konrad.kruczynski 的帮助下,证书对象现在有了私钥。例外仍然是一样的。所以这不是证书存储问题。
I'm trying to migrate an existing application to Mono (v2.10.2).
Therefore I created a test WCF service with BasicHttpBinding and message security. The client works perfectly with .NET, but when running with Mono it fails.
The client factory is instantiated as follows:
//var certificate = CertificateUtil.GetCertificate(StoreLocation.LocalMachine,
// StoreName.My, X509FindType.FindBySubjectDistinguishedName, CertName, true);
var certificate = new X509Certificate2("certificate.pfx", "password");
var binding = new BasicHttpBinding();
binding.Security.Mode = BasicHttpSecurityMode.Message;
binding.Security.Message.ClientCredentialType = BasicHttpMessageCredentialType.Certificate;
var epa = new EndpointAddress(
new Uri("http://localhost:53076/Service1.svc"),
new X509CertificateEndpointIdentity(certificate));
var factory = new ChannelFactory<IService1>(binding, epa);
factory.Credentials.ServiceCertificate.DefaultCertificate = certificate;
factory.Credentials.ServiceCertificate.Authentication.CertificateValidationMode = X509CertificateValidationMode.None;
factory.Credentials.ServiceCertificate.Authentication.RevocationMode = X509RevocationMode.NoCheck;
factory.Credentials.ClientCertificate.Certificate = certificate;
var client = factory.CreateChannel();
In Mono the application fails within CreateChannel throwing the exception:
System.InvalidOperationException: The binding does not support any of the channel types that the contract 'IService1' allows.
I debugged into the Mono source code and found out that the problem is that AsymmetricSecurityBindingElement.InitiatorTokenParameter == null.
I'm new to Mono, maybe you could point me to a documentation/tutorial which covers this topic.
UPDATE:
With the aid of konrad.kruczynski the certificate object has a private key now. The exception is still the same. So this is not a certificate store issue.
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(1)
是的,在 Windows 上创建的证书通常不包含私钥。它们可以在某种缓存中找到。您应该能够使用 这条指令。
X509Certificate2
应该可以毫无问题地使用该文件。您还可以尝试此处描述的过程。如果有任何问题,请写下来。还值得补充的是,在 Linux 上以这种方式创建的证书也可以在 Windows 上完美运行。
更新:
我不确定我是否正确理解了您的评论。您可以使用如下代码加载 PFX 证书:
鉴于证书包含密钥,它对我有用。
Yes, certificates created on Windows usually does not contain private key. They can be found in some kind of cache. You should be able to create certificate with private key using this instruction.
X509Certificate2
should consume the file without problems. You can also try procedure described here. In case of any problems just write.It is also worth adding, that certificates created such way on Linux works perfectly on Windows too.
Update:
I'm not sure whether I understood your comment correctly. You can load PFX certificate using code like that:
Given certficate contained key, it worked for me.