[WCF REST] WebHttpBinding与消息编码
2012-02-05 09:36
1076 查看
不论是我们采用SOAP还是REST架构风格,运行时框架体系依然不曾改变,终结点也仍旧是通信的核心。在Web HTTP编程模型中,我们采用基于WebHttpBinding绑定的终结点。绑定是一组相关绑定元素的有序组合,绑定的特性与能力决定于它包含的绑定元素,在这里我们通过分析绑定元素的方式来剖析WebHttpBinding绑定与其它绑定有何不同。采用HTTP/HTTPS通信协议的WebHttpBinding具有一些与WSHttpBinding/WS2007HttpBinding相同的属性,在这里我们只关心如下定义的Security属性。
[/code]
基于SOAP的绑定一般具有两种基本的安全模式,即Message和Transport模式。对于前者,它是完全建立在WS-Security为核心的安全协议之上的,而整个WS-*协议簇都是基于SOAP的,所以自然不能应用在WebHttpBinding上,所以它只能通过HTTPS提供针对Transport模式的安全支持。具体来说,通过枚举WebHttpSecurityMode表示的安全模式具有如下三个选项:
None:HTTP 请求未使用任何安全性;
Transport:HTTP 请求使用传输级安全性;
TransportCredentialOnly:仅提供基于 HTTP 的客户端身份验证。
[/code]
上述的程序执行之后会在控制台上产生如下的输出,从中我们不难看出三个WebHttpBinding均由一个消息编码元素和传输元素组成,我们知道这两种绑定元素最所有类型的绑定所必需的。
[/code]
对于WebHttpBinding的两个绑定元素来说,由于它通过HTTPS提供针对Transport安全的支持,所以当安全模式为Transport时对应的传输绑定元素为HttpsTransportBindingElement,对于其余两种安全模式则直接采用HttpTransportBindingElement作为传输绑定元素。现在我们着重讨论是作为消息编码绑定元素的WebMessageEncodingBindingElement类型,以及它涉及的消息编码机制。
[/code]
除此之外,WebMessageEncodingBindingElement具有CrossDomainScriptAccessEnabled 和ContentTypeMapper这两个重要的属性。前者表示是否支持跨域(Corss-Domain)脚本访问,默认值为False。后者类型为WebContentTypeMapper。WebContentTypeMapper用于进行消息的内容类型(Content Type,有时候也成为媒体类型或者MIME类型)与具体的格式(比如XML、JSON等)之间的映射。
[/code]
如上面的代码所示,WebContentTypeMapper是一个抽象类,包含的唯一的抽象方法GetMessageFormatForContentType用于根据指定的内容类型返回与之匹配的通过枚举WebContentFormat表示的内容格式。WebContentFormat枚举的Xml、JSON和Raw体现了Web HTTP编程模型支持三种基本格式,其中Raw表示原始的二进制。
最终的消息编码/解码工作是通过继承自MessageEncoder的消息编码器实现的,消息编码器又是通过继承自MessageEncoderFactory的编码器工厂创建出来的,而消息编码绑定元素最终通过方法CreateMessageEncoderFactory创建了编码器工厂。对于WebMessageEncodingBindingElement来说,它的CreateMessageEncoderFactory方法会创建一个具有如下定义的WebMessageEncoderFactory对象。
[/code]
WebMessageEncoderFactory是一个继承自MessageEncoderFactory的内部类型。除了布尔类型的参数javascriptCallbackEnabled对应着WebMessageEncodingBindingElement的属性CrossDomainScriptAccessEnabled之外,WebMessageEncoderFactory的构造函数参数与WebMessageEncodingBindingElement的同名属性一一对应。代表消息版本的MessageVersion属性依然返回None,而真正用于最终消息编码/解码工作的是通过Encoder属性返回的具有如下定义的WebMessageEncoder对象。
[/code]
如上面的代码片断所示,WebMessageEncoder实际上是内嵌于WebMessageEncoderFactory类型中继承自MessageEncoder的内部类型。WebMessageEncoder本身并不真正地实施消息的编码/解码,最终的消息编码/解码工作是通过三个属性TextMessageEncoder、JsonMessageEncoder和RawMessageEncoder体现的具体消息编码器完成的,而它们又分别对应着通过WebContentFormat枚举表示的三种内容类型Xml、JSON和Raw。
[code] public class WebHttpBinding : Binding, IBindingRuntimePreferences { //其它成员 public WebHttpSecurity Security { get; } } public sealed class WebHttpSecurity { // 其它成员 public WebHttpSecurityMode Mode { get; set; } public HttpTransportSecurity Transport { get; } } public enum WebHttpSecurityMode { None, Transport, TransportCredentialOnly }
[/code]
基于SOAP的绑定一般具有两种基本的安全模式,即Message和Transport模式。对于前者,它是完全建立在WS-Security为核心的安全协议之上的,而整个WS-*协议簇都是基于SOAP的,所以自然不能应用在WebHttpBinding上,所以它只能通过HTTPS提供针对Transport模式的安全支持。具体来说,通过枚举WebHttpSecurityMode表示的安全模式具有如下三个选项:
None:HTTP 请求未使用任何安全性;
Transport:HTTP 请求使用传输级安全性;
TransportCredentialOnly:仅提供基于 HTTP 的客户端身份验证。
一、WebHttpBinding的绑定元素
现在我们根据上述三种不同的安全模式创建相应的WebHttpBinding对象,然后通过如下的程序在控制台中答应出所有的绑定元素类型。[code] static void Main(string[] args) { WebHttpBinding binding = new WebHttpBinding(WebHttpSecurityMode.None); ListBindingElements(binding); binding = new WebHttpBinding(WebHttpSecurityMode.Transport); ListBindingElements(binding); binding = new WebHttpBinding(WebHttpSecurityMode.TransportCredentialOnly); ListBindingElements(binding); } static void ListBindingElements(WebHttpBinding binding) { int index = 1; Console.WriteLine(binding.Security.Mode + ":"); foreach (var element in binding.CreateBindingElements()) { Console.WriteLine("{0}. {1}", index++, element.GetType().FullName); } Console.WriteLine(); }
[/code]
上述的程序执行之后会在控制台上产生如下的输出,从中我们不难看出三个WebHttpBinding均由一个消息编码元素和传输元素组成,我们知道这两种绑定元素最所有类型的绑定所必需的。
[code] None: 1. System.ServiceModel.Channels.WebMessageEncodingBindingElement 2. System.ServiceModel.Channels.HttpTransportBindingElement Transport: 1. System.ServiceModel.Channels.WebMessageEncodingBindingElement 2. System.ServiceModel.Channels.HttpsTransportBindingElement TransportCredentialOnly: 1. System.ServiceModel.Channels.WebMessageEncodingBindingElement 2. System.ServiceModel.Channels.HttpTransportBindingElement
[/code]
对于WebHttpBinding的两个绑定元素来说,由于它通过HTTPS提供针对Transport安全的支持,所以当安全模式为Transport时对应的传输绑定元素为HttpsTransportBindingElement,对于其余两种安全模式则直接采用HttpTransportBindingElement作为传输绑定元素。现在我们着重讨论是作为消息编码绑定元素的WebMessageEncodingBindingElement类型,以及它涉及的消息编码机制。
二、消息编码
我们先来看看WebMessageEncodingBindingElement的基本的定义。如下面的代码片断所示,它是MessageEncodingBindingElement的子类,并且具有与TextMessageEncodingElement类似的属性定义。其中MaxReadPoolSize和MaxWritePoolSize表示表示无需分配新的XmlDictionaryReader/XmlDictionaryWriter便可以读取的便可同时读取/写入的最大消息数,默认值分别是64和16。ReaderQuotas属性返回用于约束读取的XML的复杂度的XmlDictionaryReaderQuotas对象,而WriteEncoding属性表示采用的字符编码类型,默认采用UTF-8编码方式。由于WebHttpBinding不使用SOAP,表示消息版本的MessageVersion属性自然返回None,如果我们对该属性进行设置,指定的属性值也只能是MessageVersion.None。[code] public sealed class WebMessageEncodingBindingElement : MessageEncodingBindingElement,... { //其它成员 public override MessageEncoderFactory CreateMessageEncoderFactory(); public bool CrossDomainScriptAccessEnabled {get; set; } public WebContentTypeMapper ContentTypeMapper { get; set; } public int MaxReadPoolSize { get; set; } public int MaxWritePoolSize { get; set; } public override MessageVersion MessageVersion { get; set; } public XmlDictionaryReaderQuotas ReaderQuotas { get; } public Encoding WriteEncoding { get; set; } }
[/code]
除此之外,WebMessageEncodingBindingElement具有CrossDomainScriptAccessEnabled 和ContentTypeMapper这两个重要的属性。前者表示是否支持跨域(Corss-Domain)脚本访问,默认值为False。后者类型为WebContentTypeMapper。WebContentTypeMapper用于进行消息的内容类型(Content Type,有时候也成为媒体类型或者MIME类型)与具体的格式(比如XML、JSON等)之间的映射。
[code] public abstract class WebContentTypeMapper { protected WebContentTypeMapper(); public abstract WebContentFormat GetMessageFormatForContentType(string contentType); } public enum WebContentFormat { Default, Xml, Json, Raw }
[/code]
如上面的代码所示,WebContentTypeMapper是一个抽象类,包含的唯一的抽象方法GetMessageFormatForContentType用于根据指定的内容类型返回与之匹配的通过枚举WebContentFormat表示的内容格式。WebContentFormat枚举的Xml、JSON和Raw体现了Web HTTP编程模型支持三种基本格式,其中Raw表示原始的二进制。
最终的消息编码/解码工作是通过继承自MessageEncoder的消息编码器实现的,消息编码器又是通过继承自MessageEncoderFactory的编码器工厂创建出来的,而消息编码绑定元素最终通过方法CreateMessageEncoderFactory创建了编码器工厂。对于WebMessageEncodingBindingElement来说,它的CreateMessageEncoderFactory方法会创建一个具有如下定义的WebMessageEncoderFactory对象。
[code] internal class WebMessageEncoderFactory : MessageEncoderFactory { public WebMessageEncoderFactory(Encoding writeEncoding, int maxReadPoolSize,int maxWritePoolSize, XmlDictionaryReaderQuotas quotas, WebContentTypeMapper contentTypeMapper, bool javascriptCallbackEnabled); public override MessageEncoder Encoder { get; } public override MessageVersion MessageVersion { get; } }
[/code]
WebMessageEncoderFactory是一个继承自MessageEncoderFactory的内部类型。除了布尔类型的参数javascriptCallbackEnabled对应着WebMessageEncodingBindingElement的属性CrossDomainScriptAccessEnabled之外,WebMessageEncoderFactory的构造函数参数与WebMessageEncodingBindingElement的同名属性一一对应。代表消息版本的MessageVersion属性依然返回None,而真正用于最终消息编码/解码工作的是通过Encoder属性返回的具有如下定义的WebMessageEncoder对象。
[code] internal class WebMessageEncoderFactory : MessageEncoderFactory { private class WebMessageEncoder : MessageEncoder { //其他成员 private MessageEncoder TextMessageEncoder { get; } private MessageEncoder JsonMessageEncoder { get; } private MessageEncoder RawMessageEncoder { get; } } }
[/code]
如上面的代码片断所示,WebMessageEncoder实际上是内嵌于WebMessageEncoderFactory类型中继承自MessageEncoder的内部类型。WebMessageEncoder本身并不真正地实施消息的编码/解码,最终的消息编码/解码工作是通过三个属性TextMessageEncoder、JsonMessageEncoder和RawMessageEncoder体现的具体消息编码器完成的,而它们又分别对应着通过WebContentFormat枚举表示的三种内容类型Xml、JSON和Raw。
相关文章推荐
- 关于WCF REST(webHttpBinding ) 用法:服务端写法及客户端调用
- use webHttpBinding to implement WCF Rest Service
- [WCF REST] UriTemplate、UriTemplateTable与WebHttpDispatchOperationSelector
- WCF分布式安全开发实践(12):消息安全模式之自定义X509证书验证:Message_CustomX509Certificate_WSHttpBinding
- 【转载】[WCF REST] Web消息主体风格(Message Body Style)
- jquery ajax调用WCF,采用System.ServiceModel.WebHttpBinding
- WCF分布式安全开发实践(11):消息安全模式之Certificate身份验证:Message_Certificate_WSHttpBinding
- WCF分布式安全开发实践(11):消息安全模式之Certificate身份验证:Message_Certificate_WSHttpBinding
- WCF分布式安全开发实践(10):消息安全模式之自定义用户名密码:Message_UserNamePassword_WSHttpBinding
- WCF分布式安全开发实践(8):消息安全模式之用户名身份验证:Message_UserName_WSHttpBinding
- WCF分布式安全开发实践(8):消息安全模式之用户名身份验证:Message_UserName_WSHttpBinding
- WCF消息安全模式之自定义用户名密码:Message CustomUserNamePassword wsHttpBinding 使用Windows Services宿主以及客户端免证书验证
- [WCF REST] Web消息主体风格(Message Body Style)
- [WCF REST] UriTemplate、UriTemplateTable与WebHttpDispatchOperationSelector
- WCF: Throwing Exceptions With WebHttpBinding
- WCF分布式安全开发实践(12):消息安全模式之自定义X509证书验证:Message_CustomX509Certificate_WSHttpBinding
- wcf webHttpBinding Post 大数据量提交 ios c#客户端
- wcf webhttpbinding
- [WCF REST] Web消息主体风格(Message Body Style)
- [WCF REST] Web消息主体风格(Message Body Style)