How to list all minecraft profiles by launcher_profiles.json file?
I tried to use the site json2csharp.com, but unfortunately when it generated the class ready code he has returned all the profiles as if it were also a class.
for example:
I used this simple code minecraft profile file ...
{
"profiles": {
"1.7.10": {
"name": "1.7.10",
"lastVersionId": "1.7.10"
}
},
"selectedProfile": "1.7.10"
}
But when I send the site to convert C# it returns this:
public class __invalid_type__1710
{
public string name { get; set; }
public string lastVersionId { get; set; }
}
public class Profiles
{
public __invalid_type__1710 __invalid_name__1.7.10 { get; set; }
}
public class RootObject
{
public Profiles profiles { get; set; }
public string selectedProfile { get; set; }
}
See for yourself: Json2CSharp
Have you any way I can read the launcher_profiles.json file minecraft using Newtonsoft.Json.Linq?
While useful in many cases, json2csharp.com is not foolproof. As you've seen, it does not handle cases where key names are dynamic or otherwise cannot be converted into valid C# identifiers. In these cases you will need to make manual adjustments to the generated classes. For example, you can use a Dictionary<string, Profile> in place of a static class to handle the dynamic keys of the profiles object.
Define your classes like this:
public class RootObject
{
public Dictionary<string, Profile> profiles { get; set; }
public string selectedProfile { get; set; }
}
public class Profile
{
public string name { get; set; }
public string lastVersionId { get; set; }
}
You can then deserialize into the RootObject class using either JavaScriptSerializer or Json.Net, whichever you prefer.
Here is a fiddle using Json.Net: https://dotnetfiddle.net/ZlEK63
So the problem may be that the launcher_profiles.json is not really kosher JSON.
Put this into Json2CSharp to see what I mean:
{
"profiles": [
{
"name": "1.7.10",
"lastVersionId": "1.7.10"
}
],
"selectedProfile": "1.7.10"
}
The difference here is that I've redefined the profiles node to correctly represent a collection (array) that's mapped to a generic list in C#.
You may need to manually parse that file as JSON.Net or other options will not be able to work with the invalid json format.
I generally don't work with the Linq versions of the Json.Net library, but I've come up with a simple example of how to get all of the names of the profiles (you can't serialize to a class with the given format).
class Program
{
//Add another "profile" to show this works with more than one
private static String json = "{ \"profiles\": { \"1.7.10\": { \"name\": \"1.7.10\", \"lastVersionId\": \"1.7.10\" }, \"1.7.11\": { \"name\": \"1.7.11\", \"lastVersionId\": \"1.7.11\" } }, \"selectedProfile\": \"1.7.10\" }";
static void Main(string[] args)
{
//Parse to JObject
var obj = Newtonsoft.Json.Linq.JObject.Parse(json);
foreach (var profile in obj["profiles"])
{
foreach (var child in profile.Children())
{
Console.WriteLine(child["name"]);
}
}
}
}
Related
I need to write a dynamically typed system in a statically typed language using the System.Text.Json lib in .net core 3.1. What I need is to deserialize files into a Python like dict. I have to use C# for this because we can't get python to authenticate against our systems correctly. And C# is our default lang, so...
In the real world, these documents are in CosmosDB. This program takes in a configuration file that points to specific fields in document structures and it has to inspect those fields, maybe update them, then write the result back to the CosmosDB. Currently, I'm building a system that points to the specific field. Since the system has no clue what the structure of the doc is that it's getting back from the cosmos, it can't use formal models. I am currently working on the system that inspects or updates the fields using static files in the test suite. I'll worry about cosmos DB when this is finished.
Take this file for example:
{
"azureSql": {
"databaseName": "ordersdb",
"tables": [
{
"tableName": "mytable",
"columnNames": [
"column1",
"column2"
]
}
]
},
"cosmosDb": {
"databaseName": "CosmosDb",
"collections": [
{
"collectionName": "TestCollection",
"fieldNames": [
"MyStatus.json.path.to.field"
]
}
]
}
}
files like this get read in. The input can be virtually any type of legit json. I need to put that into a Dictionary that I can access similar to Python mydict["cosmosDb"]["collections"][0]["fieldNames"]
The line:
_entities = JsonSerializer.Deserialize<Dictionary<string, object>>(jsonString);
doesn't work because it only serializes the first level. The rest are json entry types.
I found this C# way to mimic Python Dictionary Syntax
and its close, but it only supports string and doesn't work in the Deserialize method.
Any ideas on how to solve this?
I suggest you to use dynamic
var entities = JsonSerializer.Deserialize<dynamic>(jsonString)
Would the following classes structure work?
public class Rootobject
{
public Azuresql azureSql { get; set; }
public Cosmosdb cosmosDb { get; set; }
}
public class Azuresql
{
public string databaseName { get; set; }
public List<Table> tables { get; set; }
}
public class Table
{
public string tableName { get; set; }
public List<string> columnNames { get; set; }
}
public class Cosmosdb
{
public string databaseName { get; set; }
public List<Collection> collections { get; set; }
}
public class Collection
{
public string collectionName { get; set; }
public List<string> fieldNames { get; set; }
}
Edit:
This works:
using Newtonsoft.Json.Linq;
var result = JObject.Parse(jsonFile);
var detail = result["cosmosDb"]["collections"][0]["collectionName"];
I feel like I'm making this much harder than it needs to be.
In C# using Netwonsoft JSON Compact with external data. Trying to figure out how to deserialize/parse data that looks like
{"http":{"0":{"title":"arbitrary","value":"arbitrary"},"1":{"title":"arbitrary","value":"arbitrary"}},"sip":{"1003":{"title":"arbitrary","value":"none"}}}
It's essentially an array of notifications and the ID -- "0", "1", and "1003" in the above examples is an arbitrary value and appears to have a valid range of 0 and roughly 65535.
But it's not formatted as an array (or I wouldn't be here) -- need help figuring out how to deserialize the value object while essentially ignoring the string identifier.
Thanks in advance
You can't easily deserialize it as an array, but you can deserialize it to a dictionary with integer keys. I don't know about Json.NET Compact, but this works fine with regular Json.NET:
using System;
using System.Collections.Generic;
using System.IO;
using Newtonsoft.Json;
class Root
{
public Dictionary<int, Property> Http { get; set; }
public Dictionary<int, Property> Sip { get; set; }
}
class Property
{
public string Title { get; set; }
public string Value { get; set; }
}
class Test
{
static void Main()
{
string json = File.ReadAllText("test.json");
var root = JsonConvert.DeserializeObject<Root>(json);
foreach (var entry in root.Http)
{
Console.WriteLine($"{entry.Key}: {entry.Value.Title}/{entry.Value.Value}");
}
}
}
If you really need the properties as arrays, I'd suggest having two separate classes: one for the JSON representation, and then another for real usage. For example:
class RootJson
{
public Dictionary<int, Property> Http { get; set; }
public Dictionary<int, Property> Sip { get; set; }
}
class Root
{
// TODO: Control access more :)
public Property[] Http { get; set; }
public Property[] Sip { get; set; }
}
Then:
var rootJson = ...;
var root = new Root
{
Http = rootJson.Http.Values.ToArray(),
Sip = rootJson.Sip.Values.ToArray(),
};
If you can't change the structure of the JSON, you can always do something like this. The dynamic type figures out what to do on runtime.
dynamic d = JsonConvert.DeserializeObject("{'http':{'0':{'title':'arbitrary','value':'arbitrary'},'1':{'title':'arbitrary','value':'arbitrary'}},'sip':{'1003':{'title':'arbitrary','value':'none'}}}");
Console.WriteLine(d.http["0"].title); // arbitrary
foreach(var prop in d.http) {
Console.WriteLine(prop);
}
foreach(var prop in d.sip) {
Console.WriteLine(prop);
}
Final output:
arbitrary
"0": {
"title": "arbitrary",
"value": "arbitrary"
}
"1": {
"title": "arbitrary",
"value": "arbitrary"
}
"1003": {
"title": "arbitrary",
"value": "none"
}
I'm creating a little system to let me see who is in my chat on Twitch using their JSON API. However, while I successfully got the information, I can't figure out how to parse it correctly.
This is the string that is being produced:
{
"_links": {},
"chatter_count": 1,
"chatters": {
"moderators": [
"teonnyn"
],
"staff": [],
"admins": [],
"global_mods": [],
"viewers": []
}
}
This is the object I created to deserialize it to, but I have no idea for sure if it's exactly correct:
public class users
{
public string[] links;
public int chatter_count;
public string[] moderators;
public string[] staff;
public string[] admins;
public string[] global_mods;
public string[] viewers;
}
I'm using Newtonsoft.JSON to parse it - which would be the correct way to push the string to the "users" object?
No, the C# class you have doesn't really correlate correctly to the JSON:
Your links member doesn't match the name _links in JSON.
_links is defined as an array, but should be an object - it's {} in JSON, not [].
Likewise chatters, which should be a custom class as well.
Starting with Visual Studio 2013 Update 2, you can generate a C# class from a JSON sample. This is what it generated for your JSON:
public class Rootobject
{
public _Links _links { get; set; }
public int chatter_count { get; set; }
public Chatters chatters { get; set; }
}
public class _Links
{
}
public class Chatters
{
public string[] moderators { get; set; }
public object[] staff { get; set; }
public object[] admins { get; set; }
public object[] global_mods { get; set; }
public object[] viewers { get; set; }
}
As you can see, it maps moderators properly to a string[] but gets a bit confused and uses object[] for the rest, because the snippet contains to data for it to base the type on.
If you can get a JSON sample with more data - ideally, with every field being present and having representative data - you'll get the best mapping.
Also, you should change Rootobject to your own class name, of course. User or TwitchUser should do it.
Once you have a class that corresponds correctly to your JSON, using JSON.NET to parse it is very simple:
Rootobject yourData = JsonConvert.DeserializeObject<Rootobject>(inputJsonString);
And you're done.
I'm facing some problems with the read of a JSON file, which is this one:
{
"giocatori": [
{
"Giocatore": "124",
"Cognome": "DE SANCTIS",
"Ruolo": "P",
"Squadra": "ROM"
},
{
"Giocatore": "140",
"Cognome": "MIRANTE",
"Ruolo": "P",
"Squadra": "PAR"
},
{
"Giocatore": "156",
"Cognome": "SKORUPSKI",
"Ruolo": "P",
"Squadra": "ROM"
}
],
"success": 1
}
What I want to get from this PHP is an List, where the Player's class with this attributes;
public string Giocatore;
public string Cognome;
public string Ruolo;
public string Squadra;
I don't know why, but I face some problems with the Microsoft.Json library, in particular with Json.DeserializeObject> method, which is not able to read that web page. Can you provide some hint how to obtain a List in C# of Player ? Thank you so much for your support !
Go to http://json2csharp.com/, post your JSON there, and get the following classes:
public class Giocatori
{
public string Giocatore { get; set; }
public string Cognome { get; set; }
public string Ruolo { get; set; }
public string Squadra { get; set; }
}
public class RootObject
{
public List<Giocatori> giocatori { get; set; }
public int success { get; set; }
}
To deserialize your JSON string with JavaScriptSerializer, do:
var root = new System.Web.Script.Serialization.JavaScriptSerializer().Deserialize<RootObject>(jsonString);
var list = root.giocatori;
To deserialize your JSON string with Json.NET, a widely used, free, open source JSON serializer, download and install it according to the instructions on the home page and do:
var root = Newtonsoft.Json.JsonConvert.DeserializeObject<RootObject>(jsonString);
var list = root.giocatori;
I get this response string from the Bitly api:
{ "status_code": 200,
"status_txt": "OK",
"data":
{ "long_url": "http:\/\/amazon.de\/",
"url": "http:\/\/amzn.to\/1mP2o58",
"hash": "1mP2o58",
"global_hash": "OjQAE",
"new_hash": 0
}
}
How do I convert this string to a dictionary and how do I access the value for the key "url" (without all the \)
This isn't just some ordinary string. This is a data structure in JSON format, a common and well-established format, originally used in Javascript but now rather common as a data transfer mechanism between services and clients.
Rather than reinventing the wheel and parsing the JSON yourself, I suggest you use an existing JSON library for C#, such as JSON.NET, which will eat up that string and parse it into .NET objects for you.
Here's a code sample, taken from JSON.NET's documentation, showing its usage:
string json = #"{
'href': '/account/login.aspx',
'target': '_blank'
}";
Dictionary<string, string> htmlAttributes =
JsonConvert.DeserializeObject<Dictionary<string, string>>(json);
Console.WriteLine(htmlAttributes["href"]);
// /account/login.aspx
Console.WriteLine(htmlAttributes["target"]);
// _blank
If you add a package like Newtonsoft's Json to your project, you can deserialize the Json in to an anonymous type. You can then fetch the url from that. This is available via NuGet within Visual Studio and provides support for async or sync serialization/deserialization.
public string GetUrl(string bitlyResponse)
{
var responseObject = new
{
data = new { url = string.Empty },
};
responseObject = JsonConvert.DeserializeAnonymousType(bitlyResponse, responseObject);
return responseObject.data.url;
}
I'd use JSON.NET.
http://james.newtonking.com/json
MIT License which means if you're doing anything commercial you are good.
I don't think you would want to go straight to a Dictionary, because there is some stuff there that isn't a one to one relationship. So you could make a class like the following.
public class BitlyData
{
public string LongUrl{ get; set; }
public string Url { get; set; }
public string Hash { get; set; }
public string GlobalHash { get; set; }
public string NewHash { get; set; }
}
You could then use Json.NET to turn that String into an JObject. So we'll call your string bitlyString.
JObject bitlyObject = JObject.Parse(bitlyString);
Now we have that all that is left to do is access the data.
BitlyData theData = JsonConvert.DeserializeObject<BitlyData>(bitlyObject["data"]);
Then you can access the url (and any other pieces) using the getters.
Of course you could make it even better by having class that handles the other bits as well so you just do one serialisation.
1)Add these classes to your project
public class Rootobject
{
public int status_code { get; set; }
public string status_txt { get; set; }
public Data data { get; set; }
}
public class Data
{
public string long_url { get; set; }
public string url { get; set; }
public string hash { get; set; }
public string global_hash { get; set; }
public int new_hash { get; set; }
}
2)Add a reference to JSON.NET
3)
string jsonString= "YOUR JSON STRING";
Rootobject weps = JsonConvert.DeserializeObject<Rootobject>(jsonString);
Console.WriteLine(weps.status_code);
if (weps.data != null)
{
Console.WriteLine(weps.data.url);
Console.WriteLine(weps.data.global_hash);
//...
}