WCF和SOA的简介

1 什么是SOA:面向服务架构(service oriented architecture),他属于一种组件架构模式。SOA追求的是服务提供方和服务使用方的高度解耦。

服务必须是自解释的,也就是说必须以某种标准的方式告诉整个soa系统该服务提供的功能。

2 什么是WCF(windows communication foundation)

 本质上它是一套软件开发包。

设计目的:为分布式计算提供可管理的方法,提供广泛的互操作性,为服务定位提供直接的支持

提供的功能:托管,服务实例管理,异步,安全,事务管理,离线队列

3 WCF体系框架

   契约:(数据契约,消息契约,服务契约,策略与绑定)定义服务端公开的方法,使用的传输协议,可访问的地址,传输的消息格式

   服务运行:(事物,调度,并发,参数筛选,限流,错误,元数据,实例行为,消息行为)

   消息:ws安全通道

  激活与宿主:自寄宿,iis寄宿,windows激活服务,windows服务和com+组件等

4 wcf中的概念

  1 地址:每个服务都具有唯一的地址。

  2 绑定:

  3 契约:服务契约,数据契约,错误契约,消息契约

5 终结点:(地址,绑定,契约)发送或接收消息的构造,每个服务可以拥有一个或者多个终结点

6 元数据:服务公开的元数据包括xml架构文档(用于定义服务的数据协定)和wsdl文档(用于描述服务的方法)

7 宿主:服务必须承载与某个进程中

8 知道了wcf的概念那么如何创建wcf服务

   1 定义服务契约如下:

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


namespace HelloWorldService
{
    [ServiceContract]
    public interface IService
    {
        [OperationContract]
        string HelloWorld(string name);
    }
}

   2 实现服务契约

      像实现接口一样实现服务契约:

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

namespace HelloWorldService
{
    public class Service : IService
    {
        public string HelloWorld(string name)
        {
            return name + "说:helloWorld";
        }
    }
}

    3 创建服务的宿主

     终结点中的地址和绑定都会在宿主程序中定义,一个服务契约(servicecontract)是由一组服务操作(operationcontract)组成的,当选择iis作为宿主时,iis会自动创建serviceHost类型对象,一个绑定就代表了服务和外界通信的方式。

 基地址:一般包括通信协议和主机名

可选地址:定义了服务的具体位置

下面就使用servicehost对象来构建服务,以编程方式来简单的实现:

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

namespace HelloWorldService
{
    public class MyServiceHost : IDisposable
    {
        private ServiceHost _myService;

        //使用netNamedPipeBingding协议,此协议不能跨主机进行通信,但是能够跨越应用程序域和进程通信
        public const string BaseAddress = "net.pipe://localhost";//基地址
        public const string HelloWorldServiceAddress = "HelloWorld";//服务的可选地址

        //服务契约定义类型
        public static readonly Type contractType = typeof(HelloWorldService.IService);
        //服务契约实现类型
        public static readonly Type serviceType =typeof( HelloWorldService.Service);

        //服务只定义了一个绑定
        public static readonly Binding HelloWorldBinding = new NetNamedPipeBinding();

        //构造servicehost对象
        protected void ConstructServiceHost()
        {
            //初始化servicehost对象
            _myService = new ServiceHost(serviceType, new Uri[] { new Uri(BaseAddress) });
            //添加一个终结点,可以添加多个
            _myService.AddServiceEndpoint(contractType, HelloWorldBinding, HelloWorldServiceAddress);

        }

        //servicehost只读属性
        public ServiceHost Host
        {
            get { return _myService; }
        }

        //打开服务
        public void Open()
        {
            Console.WriteLine("开始启动服务");
            _myService.Open();
            Console.WriteLine("服务已经启动.....");
        }

        //构造方法
        public MyServiceHost()
        {
            ConstructServiceHost();
        }
        public void Dispose()
        {
            if (_myService!=null)
            {
                (_myService as IDisposable).Dispose();
            }
        }
    }
}

然后使用入口方法来启动服务:

 class Program
    {
        static void Main(string[] args)
        {
            MyServiceHost host = new MyServiceHost();
            host.Open();
        }
    }

如下显示:

    

4 下面手动编程来实现客户端访问服务端的工作

  首先客户端需要将服务的元数据导入,wcf提供clientbase<T>类型来创建代理类型,t为实际的服务契约类型实例化,绑定和地址则在构造方法中传入,代理类的定义如下

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

namespace ProxyService
{
    //硬编码定义服务契约
    [ServiceContract]
    interface IService
    {
        [OperationContract]
        string HelloWorld(string name);
    }
    class HelloWorldServiceProxy : ClientBase<IService>, IService
    {
        //硬编码定义绑定
        public static readonly Binding helloWorldBinding = new NetNamedPipeBinding();
        //硬编码定义地址
        public static readonly EndpointAddress helloWorldAddress = new EndpointAddress(new Uri("net.pipe://localhost/HelloWorld"));
        public HelloWorldServiceProxy() : base(helloWorldBinding, helloWorldAddress)
        {

        }

        public string HelloWorld(string name)
        {
            return Channel.HelloWorld(name);
        }
    }
}

 

posted @ 2017-12-01 11:52  白羽轻飘  阅读(804)  评论(0编辑  收藏  举报