RESTful Web服务正文格式

时间:2013-11-26 00:05:46

标签: wcf

我是WCF的新手。我正在做一些简单的RESTful WCF操作合同。而且,我对属性类BodyStyle的属性WebInvoke的选项有疑问。一个选项是WebMessageBodyStyle.Bare,另一个选项是WebMessageBodyStyle.Wrapped

  • 我应该何时使用Bare
  • 我应该何时使用Wrapped

感谢您的帮助。

2 个答案:

答案 0 :(得分:111)

假设您与XML请求/响应和一些简单数据合同有一些合同:

[ServiceContract]
public interface IService
{
    ...
    [OperationContract]
    [WebInvoke(Method = "POST",
        ResponseFormat = WebMessageFormat.Json,
        RequestFormat = WebMessageFormat.Json,
        BodyStyle = WebMessageBodyStyle.Wrapped)]
    Entity DoWork(Entity entity);
    ...
}

[DataContract]
public class Entity
{
    [DataMember]
    public string Name;

    [DataMember]
    public string Value;
}

根据BodyStyleRequestFormatResponseFormat的组合,您将采用不同的格式,但一般情况下:

JSON WebMessageBodyStyle.Bare 请求和响应将是:

请求:

{"Name":"name","Value":"value"}

响应:

{"Name":"ResultName:name","Value":"ResultValue:value"}

JSON WebMessageBodyStyle.Wrapped 请求和响应将是:

请求:

{"entity":{"Name":"name","Value":"value"}}

响应:

{"DoWorkResult":{"Name":"name","Value":"value"}}

注意 :您可以更改默认的DoWorkResult名称:

[return: MessageParameter(Name = "MyResult")]
Entity DoWork(Entity entity);`

所以从现在开始这将是:

{"MyResult":{"Name":"name","Value":"value"}}

XML WebMessageBodyStyle.Bare 请求和响应将是:

请求:

<Entity xmlns="http://schemas.datacontract.org/2004/07/WcfService" xmlns:i="http://www.w3.org/2001/XMLSchema-instance">
   <Name>name</Name>
   <Value>value</Value>
</Entity>

响应:

<Entity xmlns="http://schemas.datacontract.org/2004/07/WcfService" xmlns:i="http://www.w3.org/2001/XMLSchema-instance">
   <Name>name</Name>
   <Value>value</Value>
</Entity> 

XML WebMessageBodyStyle.Wrapped 请求和响应将是:

请求:

 <DoWork xmlns="http://tempuri.org/">
   <entity>
      <Name>name</Name>
      <Value>value</Value>
   </entity>
 </DoWork>

响应:

 <DoWorkResponse xmlns="http://tempuri.org/">
   <DoWorkResult xmlns:a="http://schemas.datacontract.org/2004/07/WcfService" xmlns:i="http://www.w3.org/2001/XMLSchema-instance">
      <a:Name>name</a:Name>
      <a:Value>value</a:Value>
   </DoWorkResult>
 </DoWorkResponse> 

注意 :您还可以使用DoWorkResult

更改默认return: MessageParameter名称

要回答您的问题,WebMessageBodyStyle您应该使用哪个问题取决于您的需求,这里没有黄金法则。对于互操作性,有时可能需要一种或另一种格式。但请记住裸体样式的一个限制:由于XML格式只有一个根,而JSON格式只有一个对象,因此只能将一个参数传递给方法。实际上,如果您将服务合同更改为:

[OperationContract]
[WebInvoke(Method = "POST",
    ResponseFormat = WebMessageFormat.Json,
    RequestFormat = WebMessageFormat.Json,
    BodyStyle = WebMessageBodyStyle.Bare)]
Entity DoWork(string id, Entity entity);

服务会引发异常:

  

合约的''''''''''''''''''''''''''''   没有任何包装元素的序列化。最多一个身体   参数可以在没有包装元素的情况下序列化。要么删除   额外的body参数或设置BodyStyle属性   WebGetAttribute / WebInvokeAttribute to Wrapped。

答案 1 :(得分:4)

对操作描述包装的使用只是将请求(或响应)包装在XML元素中。例如,在本合同中:

[ServiceContract]
public interface ITest
{
    [OperationContract]
    [WebInvoke(BodyStyle = WebMessageBodyStyle.Bare)]
    string Echo(string text);

    [OperationContract]
    [WebInvoke(BodyStyle = WebMessageBodyStyle.Wrapped)]
    string EchoWrapped(string text);

    [OperationContract]
    [WebInvoke(BodyStyle = WebMessageBodyStyle.Wrapped)]
    int Divide(int dividend, int divisor, out int reminder);
}

Echo操作的输入只是一个元素,其中包含文本。同样,它的响应包含一个返回操作的元素。对于EchoWrapped操作,输入实际上是一个元素,其子元素是其子元素包含方法输入的元素。

服务对Echo操作的期望是什么:

<string xmlns="http://schemas.microsoft.com/2003/10/Serialization/">The input</string>

服务对EchoWrapped操作的期望是什么:

<EchoWrapped xmlns="http://tempuri.org/"><text>Hello wrapped</text></EchoWrapped>

来源:http://social.msdn.microsoft.com/Forums/vstudio/en-US/9db6793b-8db9-479b-825c-e781d023f6c1/bodystylewebmessagebodystylewrapped-with-requestformatwebmessageformatxml-for-post?forum=wcf