如何创建JSON匹配/序列化到DataContract在WCF REST服务 [英] How to create JSON to match/serialize to DataContract in WCF Rest Service

查看:304
本文介绍了如何创建JSON匹配/序列化到DataContract在WCF REST服务的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

接口:

namespace SQRT_WCF
    {
    [DataContract]
    public class PlaceOrder
    {
        [DataMember]
        public string claimID { get; set; }
        [DataMember]
        public string rederenceDate { get; set; }
    }
}



C#调用的方法:

C# Method invoked:

public SQ_jsonModel.Response placeOrder(PlaceOrder argPlaceOrderJSON)
{
   ...
}

我已经把它贴我的web服务的工作进程,并通过代码跟踪。到目前为止,一切我试过,变量argPlaceOrderJSON为空。

I've attached my webservice to the worker processes, and tracing through the code. So far, everything I've tried, the variable argPlaceOrderJSON is null.

我已经试过至少有三个变化:

I've tried at least three variations:

变#1

{
         "claimID" : "value",
         "rederenceDate" : "value"
}

变#2:

{
    "PlaceOrder" : {
         "claimID" : "value",
         "rederenceDate" : "value"
}

变#3:

{
    "ns0:PlaceOrder" : {
        "@xmlns:ns0" : "SQRT_WCF",
         "claimID" : "value",
        "rederenceDate" : "value"
}

我写了一个快速C#控制台程序来构建和序列化一个对象,它匹配的上述变化1 。所以,现在我想这个问题是不是JSON,但一些与SOAP-UI和Web服务之间的握手。我打算写旁边看看会发生什么有一个C#测试客户端。

I wrote a quick C# console program to build and serialize an object and it matches Variation 1 above. So now I'm thinking the problem is not the JSON, but something with the handshake between SOAP-UI and the web service. I'm going to write a C# test client next to see what happens there.

SQRT_WCF.PlaceOrder order = new SQRT_WCF.PlaceOrder();
order.ClaimID = "claim1"; 
string strJson = new JavaScriptSerializer().Serialize(order);



有人问在web服务的属性,假设这是他的意思:

Someone asked for attributes in webservice, assuming this is what he meant:

public接口ISQRTREST
{
[OperationContract的]
无效的DoWork();

public interface ISQRTREST { [OperationContract] void DoWork();

    [OperationContract]
    [WebInvoke(Method="GET",
        ResponseFormat = WebMessageFormat.Json ,
        BodyStyle = WebMessageBodyStyle.Wrapped ,
        UriTemplate ="json/{id}"
        )]
    string JSONData(String id);


    [OperationContract]
    [WebInvoke(Method = "POST",
        ResponseFormat = WebMessageFormat.Json,
        BodyStyle = WebMessageBodyStyle.Wrapped,
        UriTemplate = "placeOrder/"
        )]
    SQ_jsonModel.Response placeOrder(PlaceOrder order);



}

}

的Web.Config

Web.Config

<?xml version="1.0"?>
<configuration>

  <system.web>
    <compilation debug="true" targetFramework="4.0" />
  </system.web>
  <system.serviceModel>
    <services>
      <service name="SQRT_WCF.SQRTREST" behaviorConfiguration="ServiceBehaviour">
        <endpoint address="" binding="webHttpBinding" bindingConfiguration="longTimeoutBinding" contract="SQRT_WCF.ISQRTREST" behaviorConfiguration="web">
        </endpoint>
      </service>
    </services>
    <behaviors>
      <serviceBehaviors>
        <behavior name="ServiceBehaviour">
          <!-- To avoid disclosing metadata information, set the value below to false and remove the metadata endpoint above before deployment -->
          <serviceMetadata httpGetEnabled="true"/>
          <!-- To receive exception details in faults for debugging purposes, set the value below to true.  Set to false before deployment to avoid disclosing exception information -->
          <serviceDebug includeExceptionDetailInFaults="false"/>
        </behavior>
      </serviceBehaviors>
      <endpointBehaviors>
        <behavior name="web">
          <webHttp/>
        </behavior>
      </endpointBehaviors>
    </behaviors>
    <bindings>
      <webHttpBinding>
        <binding name="longTimeoutBinding"
        receiveTimeout="00:10:00" sendTimeout="00:10:00">
          <security mode="None"/>
        </binding>
      </webHttpBinding>
    </bindings>
    <serviceHostingEnvironment multipleSiteBindingsEnabled="true" />
  </system.serviceModel>
 <system.webServer>
    <modules runAllManagedModulesForAllRequests="true"/>
  </system.webServer>

</configuration>



更​​新:
好像改变BodyStyle = WebMessageBodyStyle.Bare了它与变异1的工作。

UPDATE: Seems like changing BodyStyle = WebMessageBodyStyle.Bare got it working with variation 1.

但现在的问题是我需要能够得到它与WebMessageBodyStyle.Wrapped工作。

But now, the problem is I need to be able to get it working with WebMessageBodyStyle.Wrapped.

这是一个现有的Web服务,它在生产中。谁写程序的人早已过去,现在的B2B /团队的BizTalk接管该项目。我们使用BT2010不具有REST着呢,我们正试图提供相同的接口,我们的客户,所以他们不必更改除URL以外的任何其他。

This is an existing web service that it in production. The person who wrote the program is long gone, and now the B2B/BizTalk team is taking over the project. We are using BT2010 which doesn't have REST yet, and we are trying to provide the same interface to our customer, so they don't have to change anything other than the URL.

RESTful Web服务正文格式
似乎可以解释得相当好,我准备尝试变化2在C#中.wrapped选项。

RESTful web service body format seems to explain fairly well, I'm about to try Variation 2 with the .wrapped option in C#.

更​​新2:
试图变2 BodyWrapped仍然得到一个空对象:

Update 2: Trying Variation 2 with BodyWrapped is still getting a null object:

这是我包起来。采取什么UPDATE1

This is how I wrapped it. Took what worked in Update1

string strPostBodyWrapped = "{\"PlaceOrder\" : " + strPostBody + "}";



午饭后会做更多的调试。

Will do more debugging after lunch.

更​​新3:
仍然没有运气。上面的计算器REF基础上,它的外观包装应该是实体,这是我尝试了几种方式:

Update 3: Still no luck. Based on above StackOverflow ref, it looks the wrapper should be "entity", which I tried several ways:

从SOAP的用户界面:

From SOAP-UI:

{
    "entity" : { 
        "claimID" : "value",
}

我也试过实体而不是实体,为了确保万无一失。

I also tried "Entity" instead of "entity", just be sure.

在我的DataContract的所有字段都是字符串,所以应该没有问题连载日期或数字。

All the fields in my DataContract are string, so there should be no issue serializes dates or numbers.

这是C#的客户端测试程序:

From C# Client tester program:

            strPostBody = replaceSingleWithDoubleQuotes("{'ClaimID':'testvalue'}"); 

            string strPostBodyWrapped = replaceSingleWithDoubleQuotes("{'entity': ") + strPostBody + "}";

public static string replaceSingleWithDoubleQuotes(string argText)
    {
        return argText.Replace("'", "\"");
    }

如果我尝试在SOAP_UI坏事,像这样的:

If I try something bad in SOAP_UI, like this:

{
    "entity" : {  xxx 
        "claimID" : "value",
}

然后我意识到实体不是一个关键字,但他的课的名称...哎呀
所以我试图既placeOrder在和 。placeOrder在为我的包装我的情况。

Then I realized entity was not a keyword but the name of his class... oops. So I have tried both "Placeorder" and "placeorder" as my wrapper for my case.

我得到一个不错的错误是这样的:

I get a nice error like this:

The server encountered an error processing the request. The exception message is 'The formatter threw an exception while trying to deserialize the message: Error in deserializing body of request message for operation 'placeOrderSQRT'. Encountered unexpected character 'x'.'...

所以我不明白,为什么在这种情况下,解析器会失败,但在其他情况下,它不会失败,但它不既设置任何字段值。

So I don't understand why in this case the parser fails, but in other cases it doesn't fail, but it doesn't set any field values either.

如果我尝试无效的字段名称,但正确的语法,解析器似乎不给任何错误,例如, claimIDxxxxxxxx:值

If I try invalid field names, but correct syntax, the parser seems to not give any error, e.g. "claimIDxxxxxxxx" : "value"

推荐答案

答葬在这里:

WCF BodyStyle WrappedRequest不传入JSON参数工作?

包装物的名称不是参数类型,但参数名称

The name of the wrapper is not the parameter type, but the parameter name.

所以在我的情况下,包装的名字是命令,因为我的parm名称是序:

So in my case, the wrapper name was "order", because my parm name is "order":

SQ_jsonModel.Response placeOrderSQRT(PlaceOrder order);



从以下作品SOAP-UI现在:

The following works from SOAP-UI now:

{
    "order" : {
         "claimID" : "value",
         "rederenceDate" : "value"
}

要我来说这是非常令人震惊的;通常我们可以在用户界面上绝对没有任何影响改变变量名和PARMS名称(只是没有类名)。参考职位说明了如何使用属性MessageParameter来设置外部名称,仍然允许在需要一个改变内部名称。

To me it's very shocking; normally we can change variable names and parms names (just not Class Names) with absolute no impact on the user interface. The reference post shows how you can use the attribute "MessageParameter" to set the external name, and still allow one to change the internal name if needed.

这篇关于如何创建JSON匹配/序列化到DataContract在WCF REST服务的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆