1.新建一个名为“WindowsForms承载WCF”的WINFORM程序。
2.在解决方案里添加一个“WCF 服务库”的项目,名为“WcfYeah”。
3.修改IService1文件,内容如下:
using System.Runtime.Serialization; using System.ServiceModel; using System.ServiceModel.Web; namespace WcfYeah { // 注意: 使用“重构”菜单上的“重命名”命令,可以同时更改代码和配置文件中的接口名“IService1”。 [ServiceContract] public interface IService1 { [OperationContract] [WebInvoke(ResponseFormat = WebMessageFormat.Json, RequestFormat = WebMessageFormat.Json)] CompositeType geta(CompositeType composite); } // 使用下面示例中说明的数据约定将复合类型添加到服务操作。 // 可以将 XSD 文件添加到项目中。在生成项目后,可以通过命名空间“WcfYeah.ContractType”直接使用其中定义的数据类型。 [DataContract] public class CompositeType { bool boolValue = true; string stringValue = "Hello "; [DataMember] public bool BoolValue { get { return boolValue; } set { boolValue = value; } } [DataMember] public string StringValue { get { return stringValue; } set { stringValue = value; } } } }
4.修改Service1,内容如下:
using System; using System.ServiceModel; namespace WcfYeah { // 调整 ServiceBehavior,使其支持并发 [ServiceBehavior(ConcurrencyMode = ConcurrencyMode.Multiple, InstanceContextMode = InstanceContextMode.PerCall, UseSynchronizationContext = false)] public class Service1 : IService1 { public CompositeType geta(CompositeType composite) { CompositeType myret = new CompositeType(); try { if(composite==null) myret.StringValue = "[0]输入实体为空:" + DateTime.Now.ToString(); else myret.StringValue = "[1]输入实体不为空:" + DateTime.Now.ToString(); } catch (Exception ex) { myret.StringValue = "发生异常:" + ex.Message; } return myret; } } }
5.在WCF项目中增加一个WCFServer类,内容如下:
using System.Net; using System.ServiceModel.Web; using System.Threading; namespace WcfYeah { public class WCFServer { public WebServiceHost host = null; public WCFServer() { #region 优化调整 //对外连接数,根据实际情况加大 if (ServicePointManager.DefaultConnectionLimit < 100) System.Net.ServicePointManager.DefaultConnectionLimit = 100; int workerThreads;//工作线程数 int completePortsThreads; //异步I/O 线程数 ThreadPool.GetMinThreads(out workerThreads, out completePortsThreads); int blogCnt = 100; if (workerThreads < blogCnt) { // MinThreads 值不要超过 (max_thread /2 ),否则会不生效。要不然就同时加大max_thread ThreadPool.SetMinThreads(blogCnt, blogCnt); } #endregion //注意:这里是实现类,不是接口,否则会报:ServiceHost 仅支持类服务类型。 host = new WebServiceHost( typeof(WcfYeah.Service1)); } public void Start() { host.Open(); } public void Close() { if (host != null) { host.Close(); } } } }
6.修改WINFORM程序的APP.CONFIG,完整内容如下:
<?xml version="1.0" encoding="utf-8" ?> <configuration> <startup> <supportedRuntime version="v4.0" sku=".NETFramework,Version=v4.6" /> </startup> <system.serviceModel> <services> <service name="WcfYeah.Service1" behaviorConfiguration="behaviorThrottled"> <host> <baseAddresses> <add baseAddress = "http://localhost:16110/myapi/" /> </baseAddresses> </host> <!-- Service Endpoints --> <!-- 除非完全限定,否则地址相对于上面提供的基址--> <endpoint address="" binding="webHttpBinding" contract="WcfYeah.IService1" bindingConfiguration="WebHttpBinding_IService"> </endpoint> </service> </services> <bindings> <webHttpBinding> <binding name="WebHttpBinding_IService" maxBufferSize="2147483647" maxReceivedMessageSize="2147483647" maxBufferPoolSize="2147483647"> <readerQuotas maxDepth="2147483647" maxStringContentLength="2147483647" maxArrayLength="2147483647" maxBytesPerRead="2147483647" maxNameTableCharCount="2147483647"/> </binding> </webHttpBinding> </bindings> <behaviors> <serviceBehaviors> <behavior name="behaviorThrottled"> <serviceThrottling maxConcurrentCalls="96" maxConcurrentSessions="600" maxConcurrentInstances="696" /> <!-- 为避免泄漏元数据信息, 请在部署前将以下值设置为 false --> <serviceMetadata httpGetEnabled="False" httpsGetEnabled="False"/> <!-- 要接收故障异常详细信息以进行调试, 请将以下值设置为 true。在部署前设置为 false 以避免泄漏异常信息 --> <serviceDebug includeExceptionDetailInFaults="False" /> </behavior> </serviceBehaviors> </behaviors> </system.serviceModel> </configuration>
7.回到WINFORM程序,在FORM LOAD中启动这个WCF,FormClosing中关闭这个WCF。
using System; using System.Collections.Generic; using System.ComponentModel; using System.Data; using System.Drawing; using System.Linq; using System.Text; using System.Threading.Tasks; using System.Windows.Forms; using WcfYeah; namespace WindowsForms承载WCF { public partial class Form1 : Form { WCFServer wcfs = null; public Form1() { InitializeComponent(); } private void Form1_Load(object sender, EventArgs e) { try { wcfs = new WCFServer(); wcfs.Start(); lblTip.Text = "服务已运行"; } catch (Exception ex) { MessageBox.Show(ex.Message); } } private void Form1_FormClosing(object sender, FormClosingEventArgs e) { try { if (wcfs != null) { wcfs.Close(); } } catch (Exception ex) { MessageBox.Show(ex.Message); } } } }
8.用管理员权限启动这个WINFORM程序。
9.使用POSTMAN调用。
地址:http://localhost:16110/myapi/geta
请求报文:
{
"BoolValue": true,
"StringValue": "11"
}
响应报文:
{
"BoolValue": true,
"StringValue": "输入实体不为空:2021/11/30 9:38:41"
}