2

Given below is the type of JSON response ,

{
  "?xml":{
    "@version":"1.0",
    "@encoding":"iso-8859-1"
  },
  "xmlreport":{
    "@title":"ABC: TEST Most Saved2",
    "@dates":"Week of May 19,2013",
    "columns":{
      "column":[
        {
          "@name":"Page",
          "@type":"dimension",
          "#text":"Page"
        },
        {
          "@name":"Events",
          "@type":"metric",
          "@hastotals":"true",
          "#text":"Events"
        }
      ]
    },
    "rows":{
      "row":[
        {
          "@rownum":"1",
          "cell":[
            {
              "@columnname":"page",
              "@csv":"\"http://www.ABC.com/profile/recipebox\"",
              "#text":"http://www.ABC.com/profile/recipebox"
            },
            {
              "@columnname":"events",
              "@percentage":"\"0.1%\"",
              "#text":"489"
            }
          ]
        },
        {
          "@rownum":"2",
          "cell":[
            {
              "@columnname":"page",
              "@csv":"\"http://www.ABC.com/recipes/peanut-butter-truffle-brownies/c5c602e4-007b-43e0-aaab-2f9aed89524c\"",
              "#text":"http://www.ABC.com/recip...c602e4-007b-43e0-aaab-2f9aed89524c"
            },
            {
              "@columnname":"events",
              "@percentage":"\"0.0%\"",
              "#text":"380"
            }
          ]
        }
      ]
    },
    "totals":{
      "pagetotals":{
        "total":{
          "@columnname":"events",
          "@value":"1820.000000",
          "#text":"1,820 (0.2%)"
        }
      },
      "reporttotals":{
        "total":{
          "@columnname":"events",
          "@value":"7838.000000",
          "#text":"7,838 (0.8%)"
        }
      },
      "timeperiodtotals":{
        "total":{
          "@columnname":"events",
          "@value":"955774.000000",
          "#text":"955,774 (100.0%)"
        }
      }
    }
  }
}

I am unable to parse the object.Could you please help me out how do I read the attributes and elements after parsing. I am using C#

{ 
     XmlDocument doc = new XmlDocument();
     doc.LoadXml(XML);

     string jsonText = JsonConvert.SerializeXmlNode(doc);
     //var result = Newtonsoft.Json.JsonConvert.DeserializeXmlNode(jsonText, "xmlreport");
     var results = JsonConvert.DeserializeObject<dynamic>(jsonText);

     JToken token = JObject.Parse(jsonText);
     var report = token["xmlreport"];
}
aiapatag
  • 3,355
  • 20
  • 24
Selwyn
  • 1,621
  • 6
  • 21
  • 38
  • That seems like an XML document converted to JSON. Why? – Eli Algranti May 31 '13 at 06:05
  • @Eli We are getting this xml and we need to send it to the client in json format so its directly converted from XML – Selwyn May 31 '13 at 06:14
  • @Selwyn update your code into your question and use the {} code tag icon to format it. – Prix May 31 '13 at 06:15
  • 1
    @Selwyn, is it really necessary to retain information such as the XML declaration or which property is an element and which is an attribute through XPATh naming conventions? Wouldn't it make more sense to deserialize the XML into a proper class (using XmlSerializer) and serialize that? It would certainly be more compact. – Eli Algranti May 31 '13 at 06:20
  • @Eli ok how do i create a class and deserialize the json then – Selwyn May 31 '13 at 06:23
  • 1
    pasting it to `http://json2csharp.com/` works – Davut Gürbüz May 31 '13 at 06:36
  • @Selwyn wrapping a xml with json does not seem a good idea. Generally transport accept xml or json. As you see from json2csharp the produced class contains some variables such as `@propertyname` this can't be a valid property for `C#` . `@sign` not acceptable. If it would be a valid class you could easily get it by `var result=JsonConvert.DeserializeObject(mytextJson);` With json.net you can get it anonymously by `var result=JsonConvert.DeserializeObject(mytextJson);` – Davut Gürbüz May 31 '13 at 07:04
  • @DavutGürbüz, Just a sidenote: `@propertyname` is a valid identifier. http://msdn.microsoft.com/en-us/library/aa664670(v=vs.71).aspx – I4V May 31 '13 at 07:14
  • @I4V right thanks.In fact not begin with `@sing`. But the real property was `public string __invalid_name__@columnname { get; set; }`. Compiler does not see it. – Davut Gürbüz May 31 '13 at 07:23

3 Answers3

1

My understanding of the question is you've got some Xml and you need to send out json. Couple of points before we get to the code:

1) Don't convert xml to json directly as it causes issues

2) Parse the xml to objects at your end and then work out the format to return; decoupling what comes in and goes out will allow for one of the interfaces to change in the future without impacting the other as you can tweak the mapping

So, onto the code ...

Essentially parse the xml to objects to allow for further processing and then push out as json.

class Program
{
    private static string starting =
        "<xmlreport title=\"ABC: TEST Most Saved2\" dates=\"Week of May 19,2013\"><columns><column name=\"Page\" type=\"dimension\">Page</column><column name=\"Events\" type=\"metric\" hastotals=\"true\">Events</column></columns><rows><row rownum=\"1\"><cell columnname=\"page\" csv=\"http://www.ABC.com/profile/recipebox\">http://www.ABC.com/profile/recipebox</cell><cell columnname=\"events\" percentage=\"0.1%\">489</cell></row><row rownum=\"2\"><cell columnname=\"page\" csv=\"http://www.ABC.com/recipes/peanut-butter-truffle-brownies/c5c602e4-007b-43e0-aaab-2f9aed89524c\">http://www.ABC.com/recipes/peanut-butter-truffle-brownies/c5c602e4-007b-43e0-aaab-2f9aed89524c</cell><cell columnname=\"events\" percentage=\"0.0%\">380</cell></row></rows><totals><pagetotals><total columnname=\"events\" value=\"1820.00000\">1,820 (0.2%)</total></pagetotals><reporttotals><total columnname=\"events\" value=\"7838.000000\">7,838 (0.8%)</total></reporttotals><timeperiodtotals><total columnname=\"events\" value=\"955774.000000\">955,774 (100.0%)</total></timeperiodtotals></totals></xmlreport>";


    static void Main(string[] args)
    {
        // parse from xml to objects
        StringReader reader = new StringReader(starting);
        XmlSerializer xmlSerializer = new XmlSerializer(typeof(XmlReport));
        var xmlreport = (XmlReport)xmlSerializer.Deserialize(reader);

        // todo: do some process mapping ...

        // parse out as json
        var json = JsonConvert.SerializeObject(xmlreport);

        Console.WriteLine(json);
        Console.ReadLine();
    }
}

[Serializable]
[XmlRoot(ElementName = "xmlreport")]
public class XmlReport
{
    [XmlAttribute(AttributeName = "title")]
    public string Title { get; set; }
    [XmlAttribute(AttributeName = "dates")]
    public string Dates { get; set; }

    [XmlArray(ElementName = "columns")]
    [XmlArrayItem(typeof(Column), ElementName = "column")]
    public Collection<Column> Columns { get; set; }
}

[Serializable]
public class Column
{
    [XmlAttribute(AttributeName = "name")]
    public string Name { get; set; }
    [XmlAttribute(AttributeName = "type")]
    public string Type { get; set; }
}

I've tried to parse the json to the original xml to begin with so appologies if I've not interpreted it properly. I've not done the entire structure but I hope the example above gives you an idea of how to do the rest.

Hope this helps.

WestDiscGolf
  • 4,098
  • 2
  • 32
  • 47
0

One way of doing this is by getting the actual Data Structure of that JSON object that you have there.

Then create classes representing that data structure (if you can get a complete response -- having all properties, you just use this site to convert that to classes).

After that, deserialize that JSON object into your class using different libraries available. A sample could be this one.

Community
  • 1
  • 1
aiapatag
  • 3,355
  • 20
  • 24
0

Use this (JSon.NET) and a recursive function writes all keys and values to output window.

        [TestMethod]
        public void ParseMePlease()
        {


            string s = @"{""?xml"":{""@version"":""1.0"",""@encoding"":""iso-8859-1""},
                            ""xmlreport"":{""@title"":""ABC: TEST Most Saved2"",""@dates"":""Week of May 19,2013"",
                            ""columns"":{""column"":[{""@name"":""Page"",""@type"":""dimension"",""#text"":""Page""},{""@name"":""Events"",""@type"":""metric"",""@hastotals"":""true"",""#text"":""Events""}]},
                            ""rows"":
                            {""row"":[{""@rownum"":""1"",""cell"":[{""@columnname"":""page"",""@csv"":""\""http://www.ABC.com/profile/recipebox\"""",""#text"":""http://www.ABC.com/profile/recipebox""},{""@columnname"":""events"",""@percentage"":""\""0.1%\"""",""#text"":""489""}]},
                            {""@rownum"":""2"",""cell"":[{""@columnname"":""page"",""@csv"":""\""http://www.ABC.com/recipes/peanut-butter-truffle-brownies/c5c602e4-007b-43e0-aaab-2f9aed89524c\"""",""#text"":""http://www.ABC.com/recip...c602e4-007b-43e0-aaab-2f9aed89524c""},{""@columnname"":""events"",""@percentage"":""\""0.0%\"""",""#text"":""380""}]}]},
                            ""totals"":{""pagetotals"":{""total"":{""@columnname"":""events"",""@value"":""1820.000000"",""#text"":""1,820 (0.2%)""}},
                            ""reporttotals"":{""total"":{""@columnname"":""events"",""@value"":""7838.000000"",""#text"":""7,838 (0.8%)""}},
                            ""timeperiodtotals"":{""total"":{""@columnname"":""events"",""@value"":""955774.000000"",""#text"":""955,774 (100.0%)""}}}}}";         
            var result=JsonConvert.DeserializeObject<object>(s);

            Debug.WriteLine("Right Click Result on quick watch for Result Views!(On Debug)"+result.ToString() );

            JObject jobject = ((Newtonsoft.Json.Linq.JObject)result);


            PrintDetail(jobject);

        }

        public void PrintDetail(JObject node)
        {
            foreach (var item in node)
            {                    
                Debug.WriteLine("Key:" + item.Key + " Value:" + item.Value);
                if (item.Value is JObject)
                {
                    PrintDetail((JObject)item.Value);
                }
            }
        }
Davut Gürbüz
  • 5,526
  • 4
  • 47
  • 83