6

I have a json text and i want to get the values of author name and description tags. no need of other fields like url and urltoimage and all. when i run the below code does not providing any string values. i think some error goes here.

{
  "status": "ok",
  "articles": [
  {
    "source": {
      "id": "techcrunch",
      "name": "TechCrunch"
    },
    "author": "Khaled \"Tito\" Hamze",
    "title": "Crunch Report",
    "description": "Your daily roundup of the biggest TechCrunch stories and startup news.",
    "url": "https://techcrunch.com/video/crunchreport/",
    "urlToImage": "https://tctechcrunch2011.files.wordpress.com/2015/03/tccrshowogo.jpg?w=500&h=200&crop=1",
    "publishedAt": "2017-12-11T20:20:09Z"
  },
  {
    "source": {
      "id": "techcrunch",
      "name": "TechCrunch"
    },
    "author": "Sarah Perez",
    "title": "Facebook is trying to make the Poke happen again",
    "description": "Facebook's \"Poke\" feature has never really gone away, but now the social network is giving it a more prominent placement - and is even considering expanding..",
    "url": "https://techcrunch.com/2017/12/11/facebook-is-trying-to-make-the-poke-happen-again/",
    "urlToImage": "https://tctechcrunch2011.files.wordpress.com/2017/12/facebook-poke-icon.jpg",
    "publishedAt": "2017-12-11T20:02:30Z"
  },
  {
    "source": {
      "id": "techcrunch",
      "name": "TechCrunch"
    },
    "author": "Sarah Perez",
    "title": "Amazon Alexa can now wake you up to music",
    "description": "This fall, Amazon made a play to become your new alarm clock with the introduction of a combination smart speaker and clock called the Echo Spot. Today, the..",
    "url": "https://techcrunch.com/2017/12/11/amazon-alexa-can-now-wake-you-up-to-music/",
    "urlToImage": "https://tctechcrunch2011.files.wordpress.com/2017/09/amazon-event-9270069.jpg",
    "publishedAt": "2017-12-11T17:22:30Z"
  },
  {
    "source": {
      "id": "techcrunch",
      "name": "TechCrunch"
    },
    "author": "Ingrid Lunden, Katie Roof",
    "title": "Apple confirms Shazam acquisition; Snap and Spotify also expressed interest",
    "description": "After we broke the story last week that Apple was acquiring London-based music and image recognition service Shazam, Apple confirmed the news today. It is..",
    "url": "https://techcrunch.com/2017/12/11/apple-shazam-deal/",
    "urlToImage": "https://tctechcrunch2011.files.wordpress.com/2017/12/shazam-app-icon-ios.jpg",
    "publishedAt": "2017-12-11T15:59:31Z"
  }
]}

how to get this? below is my code and its not at all working

var data = (JObject)JsonConvert.DeserializeObject(myJSON);
string nameArticles= data["articles"].Value<string>();
MessageBox.Show(nameArticles);


   public class Source
   {
    public string id { get; set; }
    public string name { get; set; }
   }
   public class Article
   {
    public Source source { get; set; }
    public string author { get; set; }
    public string title { get; set; }
    public string description { get; set; }
    public string url { get; set; }
    public string urlToImage { get; set; }
    public DateTime publishedAt { get; set; }
   }

            Article art = new Article();

            art = JsonConvert.DeserializeObject<Article>(myJSON);

            MessageBox.Show(art.description.ToString());

the above code return object not set to an instance error!

Lazy Programer
  • 171
  • 1
  • 1
  • 12

6 Answers6

6

data["articles"] is likely to be a JArray not a string. You'll need to iterate over each JObject in the aforementioned JArray pulling out the author and description values

var data = (JObject)JsonConvert.DeserializeObject(myJSON);
var articles = data["articles"].Children();

foreach (var article in articles)
{
    var author = article["author"].Value<string>();
    var description = article["author"].Value<string>();

    Console.WriteLine($"Author: " + author + ", Description: " + description);
}

This should help you get started with whatever you're doing.

phuzi
  • 12,078
  • 3
  • 26
  • 50
6

If you do not want to create a wrapper class, you can try the below code snippet, which uses the dynamic type to deserialize JSON into an object.

var json = "Your JSON string";

dynamic stuff = JsonConvert.DeserializeObject(json);

string name = stuff.status;
var arr = stuff.articles;

foreach (var a in arr)
{
   var authorName = a.author;
}
tronman
  • 9,862
  • 10
  • 46
  • 61
2

Assuming you wish to deserialize to concrete classes (as per the second attempted approach shown in your question) then you need a wrapper class to hold the whole object, and deserialise to that.

At the moment you're trying to serialise your entire object into an Article, but only the individual objects within the articles array of that object would match the structure in your Article class.

You're trying to do the action at the wrong level of your object, and also you're forgetting the fact that articles is a list (array).

Something like this:

public class JSONResponse
{
    public string status { get; set; }
    public List<Article> articles { get; set; }
}

and

JSONResponse response = JsonConvert.DeserializeObject<JSONResponse>(myJSON);

Then you can use a normal loop to iterate through the response.articles list and extract the author names and descriptions.

ADyson
  • 57,178
  • 14
  • 51
  • 63
  • 1
    While there may be benefits for deserializing to concrete classes, the [LINQ to JSON](https://www.newtonsoft.com/json/help/html/LINQtoJSON.htm) is also perfectly valid as well. – crashmstr Dec 12 '17 at 14:50
  • @crashmstr that's certainly an equally valid alternative. However OP's code seems to suggest they want to deserialize in o classes, but are struggling to do so correctly, so my answer is constructed using the same approach. Do you think the answer is wrong in any way? – ADyson Dec 12 '17 at 14:57
  • They have two blocks of code, one using LINQ to JSON at the top, and the other trying to deserialize to classes farther down. So it is ambiguous as to which they really want. I don't thing your answer is *wrong*, but I think a better wording would be that *if* they want to deserialize to a class, they need to do that at the top level with the entire structure. – crashmstr Dec 12 '17 at 15:14
  • @crashmstr I've added a little clarification – ADyson Dec 12 '17 at 15:22
  • I think the changes makes this a much better answer. – crashmstr Dec 12 '17 at 15:25
1

sample json data

string jsonString = "{\"displayName\":\"Alex Wu\",\"signInNames\":[{\"type\":\"emailAddress\",\"value\":\"AlexW@example.com\"},{\"type\":\"emailAddress\",\"value\":\"AlexW2@example.com\"}]}";

Convert json into jObject and get values using inbuilt method called selectToken()

JObject jObject = JObject.Parse(jsonString);
        string displayName = (string)jObject.SelectToken("displayName");
        string type = (string)jObject.SelectToken("signInNames[0].type");
        string value = (string)jObject.SelectToken("signInNames[0].value");
        Console.WriteLine("{0}, {1}, {2}", displayName, type, value);
        JArray signInNames = (JArray)jObject.SelectToken("signInNames");
        foreach (JToken signInName in signInNames)
        {
            type = (string)signInName.SelectToken("type");
            value = (string)signInName.SelectToken("value");
            Console.WriteLine("{0}, {1}",  type, value);
        }

Thank you

0

Your Json make below set of class

public class Source
{ 
  public string id { get; set; } 
  public string name{get;set;}
}
public class Article
{
public Source source { get; set; }
public string author { get; set; }
public string title { get; set; }
public string description { get; set; }
public string url { get; set; }
public string urlToImage { get; set; }
public DateTime publishedAt { get; set; }
}

public class RootObject
{
public string status { get; set; }
public List<Article> articles { get; set; }
}

So You Deserialize this by following way..

var data = JsonConvert.DeserializeObject<RootObject>(myJSON);
nameArticles=data.articles.FirstOrDefault().description;
MessageBox.Show(nameArticles);
  • 1
    While there may be benefits for deserializing to concrete classes, the [LINQ to JSON](https://www.newtonsoft.com/json/help/html/LINQtoJSON.htm) is also perfectly valid as well. – crashmstr Dec 12 '17 at 14:47
-1

Please create a class for your JSON file and add property for all tags and then write code as below:

public class exampleJson{
public string author {get;set;}
public string description {get;set;}
.....

}

var data = JsonConvert.DeserializeObject<exampleJson>(myJSON);
string authorName = data.author;
string descriptions = data.description ;
Anurag
  • 552
  • 9
  • 31
  • While there may be benefits for deserializing to concrete classes, the [LINQ to JSON](https://www.newtonsoft.com/json/help/html/LINQtoJSON.htm) is also perfectly valid as well. – crashmstr Dec 12 '17 at 14:47