0

I have already spent two days trying to find a solution to my problem and no results, so I would appreciate any hints.

What I am trying to achieve:
Briefly, I have created and published a WCF service (RESTful web services) with one method GetUsers that should return something like this:

[{"Name":"John","Surname":"Dell","GroupName":"Operator"}, {"Name":"John1","Surname":"Hp","GroupName":"Operator"}, {"Name":"John2","Surname":"Apple","GroupName":"Operator"}] 

Unfortunately, when I test this method in the browser (http://localhost:28099/TestAPI.svc/GetUsers?inputName=Company, I get the response which includes the escape backslash and the double quotes at the beginning and at the end of the result, like below:

 "[{\"Name\":\"John\",\"Surname\":\"Dell\",\"GroupName\":\"Operator\"}, {\"Name\":\"John1\",\"Surname\":\"Hp\",\"GroupName\":\"Operator\"}, {\"Name\":\"John2\",\"Surname\":\"Apple\",\"GroupName\":\"Operator\"}]" 

The application consuming this webservice is telling me that this is not a valid JSON format.
In my web service method, I am getting the initial data in XML format, passing it to a datatable object, and then trying to convert it to JSON using the JSON.NET. Below is the source XML:

   <Root>
    <row Name ="John" Surname="Dell" GroupName="Operator"/>
    <row Name ="John1" Surname="Hp" GroupName="Operator"/>
    <row Name ="John1" Surname="Apple" GroupName="Operator"/>
    </Root>

Below is a snippet from my WCF code:

    [ServiceContract]
        public interface IWebServiceTest
        {
            
            [OperationContract]
            [WebGet(ResponseFormat = WebMessageFormat.Json, BodyStyle = WebMessageBodyStyle.Bare)]
            String GetUsers(string inputName);
}
    public class TestWCF: IWebServiceTest
{
 Public String GetUsers(string inputName)
{
...................
StringReader stringReader1 = new StringReader(responseXMLResult.ToString());
XmlReader reader = XmlReader.Create(stringReader1);
ds.ReadXml(reader);
string json = JsonConvert.SerializeObject(ds.Tables[0], Newtonsoft.Json.Formatting.None);
return json
}
Operagust
  • 45
  • 6
  • 5
    WCF already serializes the value you return to JSON (if response type is set to Json as in your case), you don't need JSON NET. What happens here is you serialize your object and return a string, then WCF serializes this string again to JSON. In result you return not JSON object but a single string (it's also valid json, but not what you want). So return an object directly, without serialization, from your method. – Evk Oct 29 '20 at 19:22
  • Let me see if my understanding is correct. Should I create a class "Employees" (with Name, Surname, and GroupName as DataMember)->change my method to return List and in the method itself I should convert the XML result to an object of List type and return the object? – Operagust Oct 29 '20 at 20:10
  • 2
    Yes that would be a best course of action. You can try to return ds.Tables[0], but I'd better go with dedicated class, for many reasons. – Evk Oct 29 '20 at 20:24
  • This basically seems to be a duplicate of [JSON.NET Parser *seems* to be double serializing my objects](https://stackoverflow.com/q/25559179/3744182) -- you're serializing your `DataTable` to a string, then it is re-serialized a second time by the framework when it is returned. – dbc Oct 30 '20 at 03:25
  • As to how to solve your problem, if you don't want to create a data model, one option to return a `DataTable` directly would be to simply return the already-serialized JSON via `WebOperationContext.Current.CreateTextResponse` as shown in [How to return a Dictionary of custom type values as a regular JSON object from a WCF REST method?](https://stackoverflow.com/a/35512633/3744182) and [How to set Json.Net as the default serializer for WCF REST service](https://stackoverflow.com/a/3131413/3744182). – dbc Oct 30 '20 at 03:26

1 Answers1

0

As Evk said, WCF has serialized the value you return to JSON, we don't need to use JSON NET anymore. In WCF we use DataContract to serialize objects. Here is a demo:

   [ServiceContract]
    public interface IService

    {
        [OperationContract]
        [WebGet(ResponseFormat =WebMessageFormat.Json,BodyStyle =WebMessageBodyStyle.Bare)]
       Person GetUsers();
    }

This is the service interface, we set ResponseFormat to json.

[DataContract]

public class Person

{
    [DataMember]

  public   string Name { get; set; }

    [DataMember]

   public  string Surname { get; set; }

    [DataMember]

   public  string GroupName { get; set; }

}

This is the Person object we want to transfer, we use DataContract to serialize the object.

public class Service : IService

{

    public Person GetUsers()

    {

        Person person = new Person();

        person.Name = "wwww";

        person.Surname = "Dell";

        person.GroupName = "Operator";

        return person;
    }

}

This is the implementation class of the method, we return the person object directly, and WCF will help us serialize this object into json and return it to the client.

enter image description here

Ding Peng
  • 3,702
  • 1
  • 5
  • 8