Permissive Netonsoft,Json parsing - json

I am trying to retrieve a permissive dictionary using Newtonsoft.Json. Basically, what I the tool is doing is when it has an input like
string jsonText =
#"{
"key1" : "val1",
"key2" : "val2",
"inconsistency",
"key3" : "val3"
}";
However, the
JObject.Parse(jsonText);
command will throw me an JsonReaderException because my Json is incorrect.
I would like to have some kind of method
public JObject PermissiveParse(jsonText)
which will return a JObject with the 3 valid JTokens. (skip the invalid one)

I'm afraid that's a classic "garbage in, garbage out" situation. The
JSON is invalid, and so you can't parse it properly. You can only
guess at what it's meant to be. Now, we humans can guess pretty well
at what was intended (obviously), but that's much more difficult at a
parser level.
If you know that consistently you're getting this invalid jsonText,
you could pre-process the string before deserializing it, but the real
fix has to be at the source of the invalid data.
https://stackoverflow.com/a/5142168/393487

Related

Is Numeric or integer a valid JSON?

I tested putting just random integer value in a field during a laravel validation. It is returning it as a valid json. Then I tested it at https://jsonlint.com/?code= and that is also returning it as a valid JSON. I am a beginner so Can anyone please explain how it is a valid json?
Very early on, the definition of JSON was that it had to have an object or array at the top level, but that was quickly abandoned in favor of allowing any valid value at the top level. So all of these are valid JSON:
A number on its own:
42
A string on its own:
"question"
A boolean on its own:
false
An object:
{"answer": 42}
An array:
["one", "two", "three"]
More on json.org and in the standard.

Kotlinx.Serializer - Create a quick JSON to send

I've been playing with Kotlinx.serialisation. I've been trying to find a quick way to use Kotlinx.serialisation to create a plain simple JSON (mostly to send it away), with minimum code clutter.
For a simple string such as:
{"Album": "Foxtrot", "Year": 1972}
I've been doing is something like:
val str:String = Json.stringify(mapOf(
"Album" to JsonPrimitive("Foxtrot"),
"Year" to JsonPrimitive(1972)))
Which is far from being nice. My elements are mostly primitive, so I wish I had something like:
val str:String = Json.stringify(mapOf(
"Album" to "Sergeant Pepper",
"Year" to 1967))
Furthermore, I'd be glad to have a solution with a nested JSON. Something like:
Json.stringify(JsonObject("Movies", JsonArray(
JsonObject("Name" to "Johnny English 3", "Rate" to 8),
JsonObject("Name" to "Grease", "Rate" to 1))))
That would produce:
{
"Movies": [
{
"Name":"Johnny English 3",
"Rate":8
},
{
"Name":"Grease",
"Rate":1
}
]
}
(not necessarily prettified, even better not)
Is there anything like that?
Note: It's important to use a serialiser, and not a direct string such as
"""{"Name":$name, "Val": $year}"""
because it's unsafe to concat strings. Any illegal char might disintegrate the JSON! I don't want to deal with escaping illegal chars :-(
Thanks
Does this set of extension methods give you what you want?
#ImplicitReflectionSerializer
fun Map<*, *>.toJson() = Json.stringify(toJsonObject())
#ImplicitReflectionSerializer
fun Map<*, *>.toJsonObject(): JsonObject = JsonObject(map {
it.key.toString() to it.value.toJsonElement()
}.toMap())
#ImplicitReflectionSerializer
fun Any?.toJsonElement(): JsonElement = when (this) {
null -> JsonNull
is Number -> JsonPrimitive(this)
is String -> JsonPrimitive(this)
is Boolean -> JsonPrimitive(this)
is Map<*, *> -> this.toJsonObject()
is Iterable<*> -> JsonArray(this.map { it.toJsonElement() })
is Array<*> -> JsonArray(this.map { it.toJsonElement() })
else -> JsonPrimitive(this.toString()) // Or throw some "unsupported" exception?
}
This allows you to pass in a Map with various types of keys/values in it, and get back a JSON representation of it. In the map, each value can be a primitive (string, number or boolean), null, another map (representing a child node in the JSON), or an array or collection of any of the above.
You can call it as follows:
val json = mapOf(
"Album" to "Sergeant Pepper",
"Year" to 1967,
"TestNullValue" to null,
"Musicians" to mapOf(
"John" to arrayOf("Guitar", "Vocals"),
"Paul" to arrayOf("Bass", "Guitar", "Vocals"),
"George" to arrayOf("Guitar", "Sitar", "Vocals"),
"Ringo" to arrayOf("Drums")
)
).toJson()
This returns the following JSON, not prettified, as you wanted:
{"Album":"Sergeant Pepper","Year":1967,"TestNullValue":null,"Musicians":{"John":["Guitar","Vocals"],"Paul":["Bass","Guitar","Vocals"],"George":["Guitar","Sitar","Vocals"],"Ringo":["Drums"]}}
You probably also want to add handling for some other types, e.g. dates.
But can I just check that you want to manually build up JSON in code this way rather than creating data classes for all your JSON structures and serializing them that way? I think that is generally the more standard way of handling this kind of stuff. Though maybe your use case does not allow that.
It's also worth noting that the code has to use the ImplicitReflectionSerializer annotation, as it's using reflection to figure out which serializer to use for each bit. This is still experimental functionality which might change in future.

Changing an immutable object F#

I think the title of this is wrong but can't create a title that reflects, in the abstract, what I want to achieve.
I am writing a function which calls a service and retrieves data as a JSON string. The function parses the string with a JSON type provider. Under certain conditions I want to amend properties on that JSON object and then return the string of the amended object. So if the response from the call was
{"property1" : "value1","property2" : "value2", "property3": "value3" }
I want to change property3 to a new value and then return the JSON string.
If the JsonProvider was mutable this would be an exercise like:
type JsonResponse =
JsonProvider<""" {"property1" : "value1",
"property2" : "value2",
"property3": "value3" } """>
let jsonResponse = JsonResponse.Parse(response)
jsonResponse.Property3 <- "new value"
jsonResponse.ToString()
However, this does not work as the property cannot be set. I am trying to ascertain the best way to resolve this. I am quite happy to initialise a new object based on the original response but with amended parameters but I am not sure if there is an easy way to achieve this.
For reference, the JSON object is much more involved than the flat example given and contains a deep hierarchy.
Yes, you would need to create a new object, changing the bits you want and using the existing object's values for the rest. We added write APIs for both the XML and JSON type providers a while back. You will notice the types representing your JSON have constructors on them. You can see an example of this in use at the bottom of this link

JSON accepted format according to Newtonsoft Json

I am trying to parse some JSON objects which is made just of (string,string) pairs, in order to emulate Resjson behaviour. The file I am parsing contains this.
{
"greeting":"Hello world",
"_greeting.comment":"Hello comment.",
"_greeting.source":"Original Hello",
}
Please note the last comma is incorrect, and I also used http://jsonlint.com/ to test JSON syntax. It tells me it is incorrect, as I expected. My - slightly modified - code is :
string path = #"d:\resjson\example.resjson";
string jsonText = File.ReadAllText(path);
IDictionary<string, string> dict;
try
{
dict = JsonConvert.DeserializeObject<IDictionary<string, string>>(jsonText);
}
catch(Exception ex)
{
// code never reaches here
}
My above code returns the IDictionary with the 3 keys as if the formatting was correct. If I serialize back, the string obtained is without the last comma.
My questions are :
Is Newtonsoft.Json so permissive that it allows users slight errors ?
If so, can I set the permissiveness so that it is more strict ?
Is there a way to check if a string is valid JSON format, using
Newtonsoft.Json with and/or without the permissiveness?

Parsing JSON in Erlang

I have a piece of JSON string, which I want to parse in Erlang. It looks like:
({ id1 : ["str1", "str2", "str3"], id2 : ["str4", "str5"]})
I looked at mochijson2, and a couple of other JSON parsers, but I really could not figure out how to do it. Any help greatly appreciated!
I once used the erlang-json-eep-parser, and tried it on your data.
7> json_eep:json_to_term("({ id1 : [\"str1\", \"str2\", \"str3\"], id2 : [\"str4\", \"str5\"]})").
** exception error: no match of right hand side value
{error,{1,json_lex2,{illegal,"("}},1}
in function json_eep:json_to_term/1
Right, it doesn't like the parentheses.
8> json_eep:json_to_term("{ id1 : [\"str1\", \"str2\", \"str3\"], id2 : [\"str4\", \"str5\"]}").
** exception error: no match of right hand side value
{error,{1,json_lex2,{illegal,"i"}},1}
in function json_eep:json_to_term/1
And it doesn't like the unquoted keys:
18> json_eep:json_to_term("{ \"id1\" : [\"str1\", \"str2\", \"str3\"], \"id2\" : [\"str4\", \"str5\"]}").
{[{<<"id1">>,[<<"str1">>,<<"str2">>,<<"str3">>]},
{<<"id2">>,[<<"str4">>,<<"str5">>]}]}
That looks better.
So it seems that your data is almost JSON, at least as far as this parser is concerned.
you can work on your JSON at the JSONLint validator: http://www.jsonlint.com/
Your input is not quite JSON -- the keys need to be quoted, like this:
{ "id1" : ["str1", "str2", "str3"], "id2" : ["str4", "str5"]}
A good Erlang library for manipulating JSON is jsx
Have you looked at http://www.json.org/ ?
or download "json4erlang" from here: json-and-json-rpc-for-erlang
Your JSON keys are not valid according to https://www.ietf.org/rfc/rfc4627.txt. Once you correct it, there are plenty of JSON libraries for Erlang, my favorite is JSX(https://github.com/talentdeficit/jsx/):
MyJSON = { "id1" : ["str1", "str2", "str3"], "id2" : ["str4", "str5"]},
jsx:decode(MyJSON, [return_maps]).
And it will return an Erlang map data structure that can be manipulated to your needs http://learnyousomeerlang.com/maps