Breaking out lists of objects in JSON via JSON.Net - c#

I am building a server dashboard app. I want to take a list of disks from each server and create a list that displays the usage values for each.
Here's a JSON sample we're getting back...
{"server":"webster","disks":[ {"use": "91%", "used": "16G", "mount": "/", "free": "1.6G", "device": "/dev/mapper/vg_f12-lv_root", "total": "18G", "type": "ext4"} ,
{"use": "0%", "used": "0", "mount": "/dev/shm", "free": "500M", "device": "tmpfs", "total": "500M", "type": "tmpfs"} ,
{"use": "22%", "used": "40M", "mount": "/boot", "free": "145M", "device": "/dev/sda1", "total": "194M", "type": "ext4"} ,
{"use": "47%", "used": "52G", "mount": "/rsync", "free": "61G", "device": "/dev/sdb1", "total": "119G", "type": "ext3"} ]}
I get this far with the C# code:
WebClient c = new WebClient();
var data = c.DownloadString("http://192.0.0.40:8000/cgi-bin/df.py");
JObject o = JObject.Parse(data);
string serv = o["server"].Select(s => (string)s).ToString();
lblJson.Text = serv;
But I can't seem to extract "disks" into anything meaningful that I can plugin to a listview. I've tried pumping this into IList, but it always crashes or gives me some rude comments from Intellisense.
I do have a class built for this, but haven't figured out how to port the info into it. For reference, it's here:
public class drive
{
public string Usage;
public string usedSpace;
public string Mount;
public string freeSpace;
public string Device;
public string Total;
public string Type;
}
Note: The sources for JSON are Linux servers. Windows servers will supply data in a different format ultimately.
And then we have VMWare, but I'll flail on that later.
Thanks in advance.

var jsonObj = JsonConvert.DeserializeObject<RootObject>(json);
public class RootObject
{
[JsonProperty("server")]
public string Server;
[JsonProperty("disks")]
public List<Drive> Disks;
}
public class Drive
{
[JsonProperty("use")]
public string Usage;
[JsonProperty("used")]
public string usedSpace;
[JsonProperty("mount")]
public string Mount;
[JsonProperty("free")]
public string freeSpace;
[JsonProperty("device")]
public string Device;
[JsonProperty("total")]
public string Total;
[JsonProperty("type")]
public string Type;
}

There may be a better way to do this, but using the provided drive class, the following works to deserialize your provided JSON:
JObject o = JObject.Parse(data);
List<drive> drives = new List<drive>();
string server = (string)o["server"];
foreach (var d in o["disks"].Children())
{
drives.Add(new drive()
{
Usage = (string)d["use"],
usedSpace = (string)d["used"],
Mount = (string)d["mount"],
freeSpace = (string)d["free"],
Device = (string)d["device"],
Total = (string)d["total"],
Type = (string)d["type"]
});
}

Related

Creating and reading from appconfig.json

I am trying to create config that will contains a list of servers, with extra values, something like
"Servers": [
{
"Name": ".",
"Type": "A"
},
{
"Name": "Fred",
"Type": "B"
}
]
Is that the correct way to structure the config file?
I then haven't been able to find a way to read from the config based on the above set up.
var test = Configuration.GetSection("Servers").GetChildren();
//List<Server> Servers = new List<Server>();
foreach (var testItem in test)
{
Server server = new Server()
{
//Name = testItem.GetValue(,"Name"),
//Type = testItem.GetValue("Type")
};
Servers.Add(server);
}
I'd appreciate some guidance on how to set up the config, and then how to read those values.
Thanks for reading
try this
List<Server> servers = configuration.GetSection("Servers").Get<List<Server>>();
public class Server
{
public string Name {get; set;}
public string Type {get; set;}
}

Created Nested JSON array from JSON array

I am pretty new to JSON and C# and have created an Azure Function that ties back to Snowflake which requires a very specific type of JSON response. I would like assistance if any in turning a JSON response I'm getting to a slightly different formatted response.
{
"access_token": "access token value here" , "user": "user_val"
}
to looking like
{
"data":
[
[ 0, { "access_token" : "access token value here", "user" : "user_val" } ]
]
}
I need create a nested array with "data" as the parent and a row number response starting at 0.
Using Json.NET:
using System;
using System.Collections.Generic;
using Newtonsoft.Json;
public class Program
{
public static void Main()
{
string json = #"{
""access_token"": ""access token value here"" , ""user"": ""user_val""
}";
Access a = JsonConvert.DeserializeObject<Access>(json);
var accessCollection = new AccessCollection
{
Data = new List<Access> { a }
};
json = JsonConvert.SerializeObject(accessCollection, Formatting.Indented);
Console.WriteLine(json);
}
}
public class Access
{
[JsonProperty("access_token")]
public string AccessToken
{
get;
set;
}
[JsonProperty("user")]
public string User
{
get;
set;
}
}
public class AccessCollection
{
[JsonProperty("data")]
public List<Access> Data
{
get;
set;
}
}
In addition, I consider the inner array is not usual because the data type are int and object. In general, they should be of same type. Because of that, I use a single dimensional array instead.
Please modify the codes according to situation.
.NET Fiddle

Parse JSON Objects with unique strings as parents using JSON.Net

Let's say I have this example JSON:
"Test": {
"KIf42N7OJIke57Dj6dkh": {
"name": "test 1"
},
"xsQMe4WWMu19qdULspve": {
"name": "test 2"
}
}
I want to parse this into an Array of a custom class I have, which will be exampled below:
class Class1 {
public string Name { get; set; }
Class1(string name) {
Name = name;
}
}
How can I parse this using Json.NET's JObject.Parse?
You can achieve your goal with JPath query like this :
var myArray = JObject
.Parse(json)
.SelectTokens("$.Test..name")
.Values<string>()
.Select(s => new Class1(s))
.ToArray();
But probably not the best way to do it.
I personnaly prefere to create classes to represent the json structure and then apply transformations.
void Main()
{
var json = #"{""Test"": {
""KIf42N7OJIke57Dj6dkh"": {
""name"": ""test 1""
},
""xsQMe4WWMu19qdULspve"": {
""name"": ""test 2""
}
}
}";
var root = JsonConvert.DeserializeObject<Root>(json);
var array = root.Test.Select(i => i.Value).ToArray();
array.Dump();
}
public class Root
{
public Dictionary<string, Class1> Test { get; set; }
}
public class Class1
{
public string Name { get; set; }
public Class1(string name)
{
Name = name;
}
}
To begin with, your Json is missing starting/closing braces. The Json needs to have wrapping braces around the Test value.
{
'Test':
{
'KIf42N7OJIke57Dj6dkh': {'name': 'test 1'},
'xsQMe4WWMu19qdULspve': {'name': 'test 2'}
}
}
If you are missing it in the original Json, you could wrap the current input Json as following.
var correctedJson = $"{{{inputJsonString}}}";
If you want to parse the Json Objects to Array of Class1 without creating additional concrete data structures and using JPath Queries, you could use Anonymous Types for the purpose using the DeserializeAnonymousType Method proved by Json.Net. For example,
var sampleObject = new {Test = new Dictionary<string,Class1>()};
var data = JsonConvert.DeserializeAnonymousType(correctedJson,sampleObject);
var result = data.Test.Select(x=>x.Value).ToArray();
You could also achieve it using JPath Query or creating Concrete Data Structures as #Kalten as described in his answer.

How can I print Json values in a gridview?

I am trying to print values from a Json string in a gridview with C# using Visual Studio 2017. The problem is that I can't get the specific Value to a single word.
Here is my code:
string link = #"http://alexander.*************/test.php";
string json = new WebClient().DownloadString(link);
JObject jObject = JObject.Parse(json);
I want to print both Values from "Name" in the gridview, but how?
The Names has to put in this Item list:
myItems = (array?);
string test2 = test1.ToString(Formatting.Indented);
ArrayAdapter<string> adapter = new ArrayAdapter<string>(this, Android.Resource.Layout.SimpleListItem1, myItems);
GridviewCoins.Adapter = adapter;
And finally the json string is:
{
"Coins": [[{
"Name": "007",
"Id": "5294",
}], [{
"Name": "1337",
"Id": "20824",
}
There is a couple problems here, first is that your Coins Property is an array of arrays, and that you jsonObject is not complete it should look like :
"{ "Coins": [[{ "Name": "007", "Id": "5294", } ], [{ "Name": "1337", "Id": "20824", }]]}";
That said if this is a copy paste error I would do some thing like:
public IEnumerable<Coin> GetCoins(string json)
{
var jObject = JObject.Parse(json);
var coinPropery = jObject["Coins"] as JArray;
var coins = new List<Coin>();
foreach (var property in coinPropery)
{
var propertyList = JsonConvert.DeserializeObject<List<Coin>>(property.ToString());
coins.AddRange(propertyList);
}
return coins;
}
and the coin object:
public class Coin
{
public int Id { get; set; }
public string Name { get; set; }
}
when then you have a c# object and you can do what ever you want with it.
EDIT:
You can add to gridview by following Click here

Deserialize JSON value without name

How can I deserialize a string in C# that only have values and no name. It looks like this: The problem is that this stream of string does not have name and uses array.
{
"result": {
"14400": [
[
1502985600,
262.18,
262.18,
257,
257,
1096.0131
],
[
1503000000,
257,
261.33,
254.8,
257,
1130.5897
]
],
"14405": [
[
1503014400,
258.03,
261.5,
257.01,
257.01,
520.7805
],
[
1503028800,
258,
260.98,
252.4,
259.56,
298.5658
],
]
]
}
}
Just create a class like
public class Root
{
public Dictionary<int,List<List<double>>> Result { get; set; }
}
and deserialize as
var res = JsonConvert.DeserializeObject<Root>(json);
I see it's an array, you could create a method to parse the class out of given JArray.
The Jason data
public void methpod()
{
string json ="Your jason value "
var factory = new Factory();
var suggest = factory.Create(json);
Console.WriteLine(suggest);
}
Make a class as suggested :
public class Factory
{
public Evan Create(string json)
{
var array = JArray.Parse(json);
string search = array[0].ToString();
string[] terms = array[1].ToArray().Select(item => item.ToString()).ToArray();
return new Evan{Search = search, Terms = terms};
}
}
and another
public class Evan
{
public string Search { get; set; }
public IEnumerable<string> Terms { get; set; }
public override string ToString()
{
return string.Format("Search={0},Terms=[{1}]",
Search, string.Join(",", Terms));
}
}
Tip
If you have JSON that you want to deserialize, and you don't have the class to deserialize it into, Visual Studio 2019 can automatically generate the class you need:
Copy the JSON that you need to deserialize.
Create a class file and delete the template code.
Choose Edit > Paste Special > Paste JSON as Classes.
The result is a class that you can use for your deserialization target

Categories

Resources