现在我必须修改的客户端应用程序使用ClickOnce并使用代码签名证书进行部署,因此我们无法更改app.config。但是每个客户端都有自己的WCF服务,因此我们必须在代码中以编程方式(动态)配置代理端点,而不是使用app.config。 目前,使用app.config设置创建代理并完美运行。这是app.config
<?xml version="1.0" encoding="utf-8"?>
<configuration>
<system.serviceModel>
<client>
<endpoint address="http://webserveraddress:1680/Services/Service.svc"
behaviorConfiguration="wsHttpSyncBehavior"
binding="wsHttpBinding" bindingConfiguration="WSHttpBinding_ISqlContract"
contract="Company.Library.ISqlContract" name="WSHttpBinding_EndProxy">
<identity>
<dns value="ServerCertName"/>
</identity>
</endpoint>
</client>
<!--Bindings used by end points-->
<bindings>
<wsHttpBinding>
<!-- Service end point-->
<binding name="WSHttpBinding_ISqlContract" closeTimeout="00:01:00" openTimeout="00:10:00" receiveTimeout="00:10:00" sendTimeout="00:05:00"
bypassProxyOnLocal="false" transactionFlow="false" hostNameComparisonMode="StrongWildcard"
maxBufferPoolSize="524288" maxReceivedMessageSize="10485760" messageEncoding="Text" textEncoding="utf-8"
useDefaultWebProxy="true" allowCookies="false">
<readerQuotas maxDepth="32" maxStringContentLength="8192" maxArrayLength="10485760" maxNameTableCharCount="16384"/>
<reliableSession ordered="true" inactivityTimeout="00:10:00" enabled="false"/>
<security mode="Message">
<transport clientCredentialType="Windows" proxyCredentialType="None" realm=""/>
<message clientCredentialType="Certificate" negotiateServiceCredential="true" algorithmSuite="Default"/>
</security>
</binding>
</wsHttpBinding>
</bindings>
<behaviors>
<endpointBehaviors>
<behavior name="wsHttpSyncBehavior">
<clientCredentials>
<clientCertificate findValue="ClientCertName" x509FindType="FindBySubjectName" storeLocation="LocalMachine" storeName="My"/>
<serviceCertificate>
<authentication certificateValidationMode="None"/>
</serviceCertificate>
</clientCredentials>
</behavior>
</endpointBehaviors>
</behaviors>
</system.serviceModel>
</configuration>
创建代理的当前代码:
Public void CreateProxy(string proxyEndPointConfigName,string clientCertificateName)
{
ChannelFactory<ISqlSyncContract> factory = new ChannelFactory<ISqlSyncContract>(proxyEndPointConfigName);
ServiceEndpoint e1 = factory.Endpoint;
factory.Credentials.ClientCertificate.SetCertificate(
StoreLocation.LocalMachine,
StoreName.My,
X509FindType.FindBySubjectName,
clientCertificateName);
ISqlSyncContract channel = factory.CreateChannel();
//more code here
}
这很有效。
现在我没有使用proxyEndPointConfigName,而是在代码中转换app.config中的所有内容。我到目前为止转换如下,但无法找到使用代码替换andpointBehavior的方法。
Public void CreateProxy(string url,string clientCertificateName)
{
WSHttpBinding wsBinding = this.fillWsHttpBinding ();
EndpointAddress remoteAddress = new EndpointAddress(new Uri(url), EndpointIdentity.CreateDnsIdentity(clientCertificateName));
ChannelFactory<ISqlSyncContract> factory = new ChannelFactory<ISqlSyncContract>( wsBinding, remoteAddress);
factory.Endpoint.Behaviors.Add(/*????how do I add code here???? */)
factory.Credentials.ClientCertificate.SetCertificate(
StoreLocation.LocalMachine,
StoreName.My,
X509FindType.FindBySubjectName,
clientCertificateName);
ISqlSyncContract channel = factory.CreateChannel();
//more code here
}
private WSHttpBinding fillWsHttpBinding()
{
WSHttpBinding wsBinding = new WSHttpBinding();
wsBinding.CloseTimeout = new TimeSpan(0, 1, 0);
wsBinding.OpenTimeout = new TimeSpan(0, 10, 0);
wsBinding.ReceiveTimeout = new TimeSpan(0, 10, 0);
wsBinding.SendTimeout = new TimeSpan(0, 5, 0);
wsBinding.BypassProxyOnLocal = false;
wsBinding.TransactionFlow = false;
wsBinding.HostNameComparisonMode = HostNameComparisonMode.StrongWildcard;
wsBinding.MaxBufferPoolSize = 524288L;
wsBinding.MaxReceivedMessageSize = 10485760L;
wsBinding.MessageEncoding = WSMessageEncoding.Text;
wsBinding.TextEncoding = Encoding.UTF8;
wsBinding.UseDefaultWebProxy = true;
wsBinding.AllowCookies = false;
wsBinding.ReaderQuotas.MaxDepth = 32;
wsBinding.ReaderQuotas.MaxStringContentLength = 8192;
wsBinding.ReaderQuotas.MaxArrayLength = 10485760;
wsBinding.ReaderQuotas.MaxNameTableCharCount = 16384;
wsBinding.ReliableSession.Ordered = true;
wsBinding.ReliableSession.InactivityTimeout = TimeSpan.FromMinutes(10);
wsBinding.ReliableSession.Enabled = false;
wsBinding.Security.Mode = SecurityMode.Message;
wsBinding.Security.Transport.ClientCredentialType = HttpClientCredentialType.Windows;
wsBinding.Security.Transport.ProxyCredentialType = HttpProxyCredentialType.None;
wsBinding.Security.Transport.Realm = "";
wsBinding.Security.Message.ClientCredentialType = MessageCredentialType.Certificate;
wsBinding.Security.Message.NegotiateServiceCredential = true;
wsBinding.Security.Message.AlgorithmSuite = System.ServiceModel.Security.SecurityAlgorithmSuite.Basic256;
return wsBinding;
}
我在网上搜索过,无法使用wshttpbinding和证书找到任何示例。 (这里有一个类似的问题How to create a WCF client without settings in config file?,但它没有讨论端点行为和wshttpbinding。)
对这个长问题感到抱歉。我想提供完整的细节。
有人可以告诉我如何在上面的方法CreateProxy(,)中将app.config中匹配的端点行为添加到ChannelFactory中吗? 感谢。
修改 请注意,总结一下,我想要在上面的app.config中给出关于如何翻译endpointbehaviours部分的c#代码。或者以其他方式动态更改服务端点?