locked
JSON format in WCF RRS feed

  • Question

  • Hi all

     

    I want to output two json formats from my WCF method, tried long enough but no result. Could you please give me help please?

    1) I couldnt control the json output prefix, for example, Bare style return none prefix, wrapped style will use "GetAllResult" prefix to wrap my Json result, I want the prefix call "data" instand of  the default "GetAllResult", how to do that?

     

    [OperationContract]
      [WebInvoke(Method = "GET"
    , BodyStyle = WebMessageBodyStyle.Bare, ResponseFormat = WebMessageFormat.Json)]
      [PrincipalPermission(SecurityAction.Demand, Authenticated=true
    )] 
      public
     List<CompanyDTO> GetAll()
      {
       
       CompanyBO com = new
     CompanyBO();
       List<CompanyDTO> data = com.GetCompanies().Select(p => new
     CompanyDTO { CompanyName = p.CompanyName, ID = p.ID }).ToList();
       return
     data;
    
      }
    

    2) I have this baseJSONclass, inside is a collection of CompanyDTO class

     [System.Runtime.Serialization.DataContract]
     public
     class
     baseJSONclass<CompanyDTO >
     {
      [System.Runtime.Serialization.DataMember]
      public
     string
     ResponseMessage { get
    ; set
    ; }
      [System.Runtime.Serialization.DataMember]
      public
     bool
     success { get
    ; set
    ; }
      [System.Runtime.Serialization.DataMember]
      public
     IList<T> data{get
    ; set
    ;}
      public
     baseJSONclass() 
      {
       this
    .data = new
     List<CompanyDTO >(); 
      } 
     }
    
    [System.Runtime.Serialization.DataContract]
     public
     class
     CompanyDTO 
     {
      [System.Runtime.Serialization.DataMember]
      public
     string
     CompanyName { get
    ; set
    ; }
      [System.Runtime.Serialization.DataMember]
      public
     int
     ID { get
    ; set
    ; }
    
     }
    

    When I return this in JSON, it look like this, but I dont want the "data" prefix, how do I reconfigure it so the "data" prefix would be removed?

     

    {"ResponseMessage"
    :null
    ,"data"
    :[{"CompanyName"
    :"sfsdfsdf"
    ,"ID"
    :126}],"success"
    :true
    }
    

     

    ideal:

    {"ResponseMessage"
    :null
    ,[{"CompanyName"
    :"sfsdfsdf"
    ,"ID"
    :126}],"success"
    :true
    }
    

     

     

    3) is it possible to auto serialize just this by WCF?

     

    return
     new
     { success = true
     };
    

     

    because I got this error return:

     

    Cannot serialize parameter of type '<>f__AnonymousType0`1[System.Boolean]' (for operation 'Add', contract 'WCFCompanyService') because it is not the exact type 'System.Object' in the method signature and is not in the known types collection.

     

    THanks

    Bryan

     

     

     

    Wednesday, June 23, 2010 11:19 AM

Answers

  • 1) You can use the [MessageParameter] attribute to change the name of the wrapping element. The code below has an example of it.

    2) You cannot do that, as that would not be a valid JSON. Members of JSON objects need to have name and values. If you really want to return this invalid JSON, however, you can use the raw mode (http://blogs.msdn.com/b/carlosfigueira/archive/2008/04/17/wcf-raw-programming-model-web.aspx), do the JSON serialization yourself and later remove the name from the "data" member.

    3) No, serialization of anonymous types are not supported in WCF.

    Example of [MessageParameter] usage:

    namespace Post_88e95ec9_6af6_449b_af87_c6ff23ec7d08
    {
      [ServiceContract]
      public interface ITest
      {
        [OperationContract]
        [WebInvoke(Method = "GET", BodyStyle = WebMessageBodyStyle.Wrapped, ResponseFormat = WebMessageFormat.Json)]
        [return:MessageParameter(Name = "data")] List<CompanyDTO> GetAll();
      }
      public class CompanyDTO { }
      public class Service : ITest
      {
        public List<CompanyDTO> GetAll()
        {
          List<CompanyDTO> data = new List<CompanyDTO>();
          return data;
        }
      }
      public class Host
      {
        public static void Test()
        {
          string baseAddress = "http://" + Environment.MachineName + ":8000/Service";
          WebServiceHost host = new WebServiceHost(typeof(Service), new Uri(baseAddress));
          host.Open();
    
          WebClient c = new WebClient();
          string json = c.DownloadString(baseAddress + "/GetAll");
          Console.WriteLine(json);
        }
      }
    }
    
    Wednesday, June 23, 2010 2:39 PM