wcf配置文件介绍和例子

<?xml version="1.0" encoding="utf-8" ?>
<configuration>
  <startup>
    <supportedRuntime version="v4.0" sku=".NETFramework,Version=v4.5" />
  </startup>
  <system.serviceModel>

    <!--The bindings configuration  
We deployed the basichttpbinding.  
I added a binding that name is binding1.  
The binding1 used the security.  
-->
    <bindings>
      <basicHttpBinding>
        <binding name="binding1">
          <security mode="Message">
            <message clientCredentialType="Certificate"/>
          </security>
        </binding>
      </basicHttpBinding>
    </bindings>

    <!--The behaviors configuration  
I added a serviceBehavior that has nothing configuration in.  
-->
    <behaviors>
      <serviceBehaviors>
        <behavior name="service1_behavior">

        </behavior>
      </serviceBehaviors>
    </behaviors>

    <!--The services configuration  
I added a service that behaviorConfiguration is service1_behavior.  
This service has an endpoint that added the property and the binding.  
-->
    <services>
      <service name="Wcfservice.Service1" behaviorConfiguration="service1_behavior">
        <endpoint address="http://localhost:64921/Service1.svc" name="ServiceReference1_IService1"
         binding="basicHttpBinding" bindingConfiguration="binding1" contract="ServiceReference1.IService1"></endpoint>
      </service>
    </services>

  </system.serviceModel>
</configuration>

上例将配置信息写入到了xml中,分别添加了一个服务的binding、service和behavior,在添加时往往是自下向上添加,首先添加一个binding配置信息,然后添加相应的behavior行为,最后添加一个service并把绑定信息添加到其中。

 Service配置节[必须有]:配置服务、接口和终结点。每个Service都会有以下两个属性。name:名称空间.类名[服务的具体实现类]。behaviorConfiguration:一个在behaviors节点中找到的名称。

  Binding配置节[可有可无]:配置绑定,如http,tcp等

  Behavior配置节[可有可无]:配置行为,如认证等。

service

service主要是用来配置endpoint和host的,它实际上代表了为程序集添加了一个服务的引用,其中的endpoint指定了服务的地址、绑定和协议,host则提供了服务寄宿的方式(host不是必须的)。
如下配置:

<services>
  <service name="Wcfservice.Service1">
    <host>
      <baseAddresses>
        <add baseAddress="http://localhost:64921/ConsoleApplication1"/>
      </baseAddresses>
    </host>
    <endpoint address="http://localhost:64921/WcfService1.IService1" binding="basicHttpBinding"
     bindingConfiguration="binding1" contract="ServiceReference1.IService1"></endpoint>
  </service>
</services>

在上面的代码中添加了一个service,并为service配置了一个host该host的应用程序即为当前引用服务的程序集。最后添加了一个endpoint,终结点中绑定了URI,URI的地址就是WCF的定义地址,其中的binding是指定了基本的绑定类型,另外还使用contract指定了服务契约的接口。

<baseAddresses>作用当<endpoint>元素节点里address为空时,使用baseAddress地址。

 <!-- 在<baseAddresses>可以定义每种传输协议的baseaddress, 用于跟使用同样传输协议endpoint定义的相对地
                     址组成完整的地址,但是每种传输协议只能定义一个baseaddress。http的baseaddress同时是service
                    对外发布服务说明页面的url-->

binding

service是对服务进行的配置,指定了服务的一些配置信息,另外很重要的和service同级还有binding,它是对消息访问方式做的一些配置。
1、绑定方式
分为系统自带的绑定和用户自定义绑定两种,系统自带的绑定包括basicHttpBinding、WcHttpBinding等。
如果系统提供的绑定功能不完全,那么也可以使用用户自定义的绑定功能,可以使用customBinding对象从预先存在的绑定元素中创建新的绑定,也可以通过从Binding派生类来创建完全由用户自定义的绑定。
2、基本功能
绑定除了定义绑定的方式外,还可以指定传输协议的类型、安全性、编码方式和事务等,通过绑定来配置WCF的基本操作类型,这样能够对服务做详细的一些配置,使服务的功能更加健全。

<binding name="Service1Soap" closeTimeout="00:01:00" openTimeout="00:00:05"
     receiveTimeout="00:01:01" sendTimeout="00:00:09" allowCookies="false"
     bypassProxyOnLocal="false" hostNameComparisonMode="StrongWildcard"
     maxBufferSize="65536" maxBufferPoolSize="524288" maxReceivedMessageSize="65536"
     messageEncoding="Text" textEncoding="utf-8" transferMode="Buffered"
     useDefaultWebProxy="true">

Behavior

行为属性,行为属性可以控制服务的运行时特性,主要分为服务行为和操作行为,这些行为或特性,可以通过配置runtime属性配置文件,或自定义行为来实现。

<?xml version=”1.0” encoding=”utf-8” ?>
<configuration>
  <system.serviceModel>
    <services>
      <service name =”WCFService.ServiceClass” behaviorConfiguration=”metadataSupport”>
        <host>
          <baseAddresses>
            <add baseAddress=”net.pipe://localhost/WCFService”/>
            <add baseAddress=”net.tcp://localhost:8000/WCFService”/>
            <add baseAddress=”http://localhost:8080/WCFService”/>
          </baseAddresses>
        </host>
        <endpoint address=”tcpmex” binding=”mexTcpBinding” contract=”IMetadataExchange”/>
        <endpoint address=”namedpipemex” binding=”mexNamedPipeBinding” contract=”IMetadataExchange”/>
        <endpoint address=”” binding=”wsDualHttpBinding” contract=”WCFService.IServiceClass”/>
        <!--<endpoint address=”mex” binding=”mexHttpBinding” contract=”IMetadataExchange”/>-->
      </service>
    </services>
    <behaviors>
      <serviceBehaviors>
        <behavior name=”metadataSupport”>
          <!--允许客户端侦听服务器日志,在正式运行前最好关闭-->
          <serviceDebug includeExceptionDetailInFaults=”true”/>
          <serviceMetadata httpGetEnabled=”false” httpGetUrl=””/>
          <serviceThrottling maxConcurrentCalls=”10” maxConcurrentInstances=”5” maxConcurrentSessions=”5”/>
          <serviceSecurityAudit auditLogLocation=”Application” suppressAuditFailure=”false”/>
        </behavior>
      </serviceBehaviors>
    </behaviors>
  </system.serviceModel>
</configuration>

Note:serviceMetadata 是一种元数据启用功能,它是配置元数据终结点,默认情况下是不公开元数据的,但是可以通过启用配置来公开元数据的终结点。
上面的代码都是使用的是配置文件做的服务的配置部署,另外也可在程序中编写代码来配置部署信息,但是并不赞成这种配置方式,因为这种配置方式不易更改,当你部署到客户环境后就不能再更改内部的代码结构,所以这种方式很不灵活,并不提倡使用这种方式来配置服务,但是可以作为了解,如下代码:

namespace ConsoleApplication1
{
    class Program
    {
        static void Main(string[] args)
        {
            using (ServiceHost host = new ServiceHost(typeof(ServiceReference1.Service1Client)))
            {
                host.AddServiceEndpoint(typeof(ServiceReference1.IService1),
                new WSHttpBinding(), "http://localhost:8733/Design_Time_Addresses/WcfServiceLibrary1/Service1");
                if (host.Description.Behaviors.Find<ServiceMetadataBehavior>() == null)
                {
                    ServiceMetadataBehavior serviceMetadata = new ServiceMetadataBehavior();
                    serviceMetadata.HttpGetEnabled = true;
                    serviceMetadata.HttpGetUrl = new Uri
                    ("http://localhost:8733/Design_Time_Addresses/WcfServiceLibrary1/Service1/metadata");
                    host.Description.Behaviors.Add(serviceMetadata);
                }

                host.Open();

                ServiceReference1.IService1 service1 = new ServiceReference1.Service1Client();
                service1.GetData(1);
                Console.Write("fdsf");
                host.Close();
            }
        }
    }
}

上面的代码中使用的是WSHttpBinding方式它支持双工通信,另外上面的宿主方式使用的是ConsoleApplication Host,这种host方式非常简单。在创建宿主程序时,需要为宿主指定宿主服务的类型,这里的类型要使用实现服务的类,最好不要使用接口类型。
创建宿主对象后,接下来为宿主添加了一个服务的终结点,终结点中第一个参数是指定了协议实现的类型,本例使用的是接口协议,所以要配置为相应的接口类型;第二个参数指定了绑定的类型;第三个参数则指定了终结点的URI地址,URI地址要配置服务具体实现的类URL地址。
接下来为宿主添加了一个行为(Behavior),并为行为公开了元数据,这种行为在创建时也可以不强加给服务,也就是说在添加宿主时,服务的行为定义是可选的,也可以不定义。

下面为几个wcf实例:

实例一:

定义服务协定,建立类库项目名为:Ch25Ex04Contracts

namespace Ch25Ex04Contracts
{
    [ServiceContract(SessionMode=SessionMode.Required,CallbackContract =typeof(IMessageChangeCallback))]
    public interface IMessageChange
    {
        [OperationContract(IsOneWay = true)]
        void Send(string message);
    }

    [ServiceContract]
    public interface IMessageChangeCallback
    {
        [OperationContract(IsOneWay = true)]
        void Receive(string message);
    }

//下面为数据协定,定义数据协定的数据才能传输

[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; }
        }
    }

}

服务端:建立控制台应用程序名为:Ch25Ex04Host

先实现服务

namespace Ch25Ex04Host
{
    // 注意: 使用“重构”菜单上的“重命名”命令,可以同时更改代码和配置文件中的类名“MessageChange”。
    [ServiceBehavior(InstanceContextMode = InstanceContextMode.Single)]
    public class MessageChange : IMessageChange
    {
        public void Send(string message)
        {
            Console.WriteLine("服务端监听客户端发出的消息:" + message);
            Callback.Receive(message);
        }

        IMessageChangeCallback Callback
        {
            get
            {
                return OperationContext.Current.GetCallbackChannel<IMessageChangeCallback>();
            }
        }

    }

    class Program
    {
        static void Main(string[] args)
        {
            MessageChange tem = new MessageChange();
            using (ServiceHost host = new ServiceHost(tem))
            {
                host.Opened += delegate { Console.WriteLine("服务已经启动,按任意键终止!"); };
                host.Open();
                Console.Read();
            }
        }
    }
}

服务端配置文件

 <system.serviceModel>
    <behaviors>
      <serviceBehaviors>
        <behavior name="mexBehavior">
          <serviceMetadata httpGetEnabled="true" />
          <serviceDebug includeExceptionDetailInFaults="true" />
        </behavior>
        <behavior name="">
          <serviceMetadata httpGetEnabled="true" httpsGetEnabled="true" />
          <serviceDebug includeExceptionDetailInFaults="false" />
        </behavior>
      </serviceBehaviors>
    </behaviors>
    
    <services>
    <service name="Ch25Ex04Host.MessageChange" behaviorConfiguration="mexBehavior">
      <host>
        <baseAddresses>
          <add baseAddress="http://localhost:8703/MessageChange" />
          
        </baseAddresses>
      </host>
        <endpoint address="" binding="wsDualHttpBinding" contract="Ch25Ex04Contracts.IMessageChange" />
        <endpoint address="mex" binding="mexHttpBinding" contract="IMetadataExchange"/>
      
    </service>
</services>
  </system.serviceModel>

客户端:

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.ServiceModel;
using Ch25Ex04Contracts;


namespace Ch25Ex04Client
{
    public class CallBackHandler: IMessageChangeCallback
    {
        public void Receive(string message)
        {
            Console.WriteLine("客户端监听服务端接收的消息:" + message);
        }
    }
    class Program
    {
        static void Main(string[] args)
        {
            CallBackHandler handle = new CallBackHandler();
            InstanceContext instanceContext = new InstanceContext(handle);//创建客户端的回调对象
            ChannelFactory<IMessageChange> factory = new DuplexChannelFactory<IMessageChange>(instanceContext, new WSDualHttpBinding());
                int a;
                IMessageChange client = factory.CreateChannel(new EndpointAddress("http://localhost:8703/MessageChange"));
            client.Send("abcd",out a);
            // MessageChangeClient client = new MessageChangeClient(instanceContext);
           //client.Send("abcdefg");
            Console.Read();
        }
    }
}

双工通信的介绍

1,Dupex(双工) MEP(消息交换模式),服务端回调(Callback)客户端操作

2,客户端调用服务时,附加上一个回调对象(InstanceContext)。服务端处理服务请求时,通过该回调对象调用客户端操作。

3,WCF系统设计常用四层结构:Contracts(契约),Services(服务),Hosting(服务寄宿),Clients(客户端)

4,客户端调用服务,需要服务契约;服务端回调客户端操作,同样需要回调契约。回调契约通过ServiceContract(服务契约)特性的CallbackContract属性指定

5,回调契约本质也是服务契约,但在服务契约里已指明该回调契约的服务契约属性,所以回调契约不需要再标记ServiceContract属性

6,服务端在处理服务请求时,通过当前的OperationContext.Current.GetCallback<T>方法获取回调对象,T代表回调契约的类型

7,OperationContext代表服务操作执行上下文,通过静态属性Current获取当前OperationContent。我们可以在服务端或客户端设置一些上下文,比如为出栈消息添加Soap报头,从入栈消息取出报头等

8,为执行回调,客户端首先要实现回调契约:定义继承回调契约的类,实现回调契约接口方法

9,调用双工服务,先创建回调对象,并通过InstanceContext对回调对象包装,然后用DuplexChannelFactory<TChannel>方法创建服务通道。

10,用服务通道的CreateChannel方法生成服务代理对象,进而调用服务方法。

11,服务响应请求,回调回调对象的方法,在客户端执行回调方法。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
好的,下面是一个简单的 C# WCF 服务的例子: 首先,在 Visual Studio 中创建一个新的 WCF 服务应用程序项目。然后,在服务契约中定义一个简单的操作: ```C# [ServiceContract] public interface IMyService { [OperationContract] string GetMessage(string name); } ``` 这个操作接受一个字符串类型的参数,返回一个字符串类型的消息。 接下来,在服务实现中实现这个操作: ```C# public class MyService : IMyService { public string GetMessage(string name) { return "Hello, " + name + "!"; } } ``` 这个实现接受一个字符串类型的参数,返回一个拼接了该参数的消息。 然后,在配置文件中定义一个终结点: ```XML <system.serviceModel> <services> <service name="MyService"> <endpoint address="http://localhost:8080/MyService" binding="basicHttpBinding" contract="IMyService"/> </service> </services> </system.serviceModel> ``` 这个终结点定义了服务的地址、绑定和契约等信息。 最后,在 host 中启动服务: ```C# ServiceHost host = new ServiceHost(typeof(MyService)); host.Open(); ``` 这个 host 启动了 MyService 类型的服务。 现在,WCF 服务已经启动并且可以接收客户端的请求。在客户端中,你可以使用类似下面的代码来调用服务: ```C# ChannelFactory<IMyService> factory = new ChannelFactory<IMyService>( new BasicHttpBinding(), new EndpointAddress("http://localhost:8080/MyService")); IMyService proxy = factory.CreateChannel(); string message = proxy.GetMessage("World"); Console.WriteLine(message); ``` 这个客户端创建了一个 IMyService 类型的代理对象,并调用了它的 GetMessage 方法,将 "World" 作为参数传递,并将返回的消息打印到控制台上。 这就是一个简单的 C# WCF 服务的例子,它展示了如何定义服务契约、实现服务操作、配置服务终结点和启动服务 host。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值