obtain values to json file - json

I am making an application in vb net, and read JSON format files.
I know how, but I have a file that has a different format, you can see here:
{
"objects": {
"realms/lang/de_DE.lang": {
"hash": "729b2c09d5c588787b23127eeda2730f9c039194",
"size": 7784
},
"realms/lang/cy_GB.lang": {
"hash": "7b52463b2df4685d2d82c5d257fd5ec79843d618",
"size": 7688
},
"minecraft/sounds/mob/blaze/breathe4.ogg": {
"hash": "78d544a240d627005aaef6033fd646eafc66fe7a",
"size": 22054
},
"minecraft/sounds/dig/sand4.ogg": {
"hash": "37afa06f97d58767a1cd1382386db878be1532dd",
"size": 5491
}
}
}
It is different because all text has objects, no string, so I can not read it defined classes.
I just need the values of "hash", then add them to a textbox.
I hope you can help me.

Sounds like #Plutonix has seen this before, so I'll go with the Minecraft thing. It seems like objects is a Dictionary(Of String, MinecraftItem). A little tweak to the linked duplicate could be to create a class for the whole file, so you don't have to pull out the objects separately:
Public Class MinecraftData
Public Property Objects As Dictionary(Of String, MinecraftItem)
End Class
Public Class MinecraftItem
Public Property Hash As String
Public Property Size As Long
End Class
You can then parse the whole thing using Json.NET:
Dim data = JsonConvert.DeserializeObject(Of MinecraftData)(json)

If you are certain that you will only ever need the hashes, you can actually use a regex to get all the hashes from this file. Yes, this is slightly evil, because regex is normally not a suitable tool for dealing with structured data. But if you don't care about the structure...
Dim hashExtractor = new System.Text.RegularExpressions.Regex("[0-9a-f]{40}")
Dim matches = hashExtractor.Matches(myFileContents).Cast(of System.Text.RegularExpressions.Match)
Dim hashes = matches.Select(Function(m) m.Value).ToList()

Related

VB Variable JSON String

In Visual Basic code, when I try to insert a variable into this JSON string it comes back
as a 400 bad request. How do I correctly feed this JSON string a variable?
Dim myJSON As String = "{""StoreId"":""12345"",""TerminalId"":""12345"",""CaptureMode"":""true"",""MerchantReferenceCode"":""VARIABLEINSERTEDHERE"",""InvoiceNumber"":""12345"",""TimeoutMinutes"":""5"",""ShowAddress"":""true"",""AddressRequired"":""true"",""TransactionTotal"":""33.33"",""TaxTotal"":""2.00"",""CustomerCode"":""12345""}"
Your JSON as it sits right now is an Object that looks like this:
{
"StoreId": "12345",
"TerminalId": "12345",
"CaptureMode": "true",
"MerchantReferenceCode": "VARIABLEINSERTEDHERE",
"InvoiceNumber": "12345",
"TimeoutMinutes": "5",
"ShowAddress": "true",
"AddressRequired": "true",
"TransactionTotal": "33.33",
"TaxTotal": "2.00",
"CustomerCode": "12345"
}
One option that you have is to create a new JObject, use the Add method (documentation) to build the object's properties, and then the ToString method (documentation) to serialize the object to JSON. This way you don't have to worry about properly formatting the JSON, just let the library do it for you.
Take a look at this example:
Dim myVariable = "VARIABLEINSTEREDHERE"
Dim request = New JObject()
request.Add("StoreId", 12345)
request.Add("TerminalId", 12345)
request.Add("CaptureMode", True)
request.Add("MerchantReferenceCode", myVariable)
request.Add("InvoiceNumber", 12345)
request.Add("TimeoutMinutes", 5)
request.Add("ShowAddress", True)
request.Add("AddressRequired", True)
request.Add("TransactionTotal", 33.33)
request.Add("TaxTotal", 2.00) ' taxation is theft
request.Add("CustomerCode", 12345)
Dim myJson = request.ToString()
Example: https://dotnetfiddle.net/FQDpVq
The short answer to the question you asked:
myjson = myjson.replace("VALUEPLACEHOLDER1","SoMeTHiNGeLSe")
Now, if you are talking about tricky pattern matching, then you will need to use regex if you want to approach this from a string-manipulation perspective. That sets you up for all sorts of unanticipated problems down the road with things you didn't anticipate, though, and you'll probably be happier in the long run if you embrace using JSON.
Try using the NewtonSoft JSON libraries. Then you can do something like:
dim myobj as new MyClass
myobj = jsonconvert.deserializeobject(of MyClass)(myjson)
That will turn your JSON string into an instance of MyClass called myobj, and you can access its properties directly, changing whatever you want:
myobj.MerchantReferenceCode = "SpecialMerchant"
Note that if the class definition for MyClass has properties that the JSON has no values for, they'll be present in the new class instance with no values. You can then set those values as you wish.
If the JSON has properties that don't exist in your class, they'll be dropped/lost in the conversion, so you do need to study your source data.
And you turn it back into a string again easily:
dim newjson as string = jsonconvert.serializeobject(myobj)

Suppress empty List of Objects from Json output

I have a Data class which I populate manually from a XML returned from a trading Partner. Most of time the returned Data will only have a few of the fields in my class populated, the others I set to Nothing(null) and then use the
Dim settings As New JsonSerializerSettings
settings.NullValueHandling = NullValueHandling.Ignore
to suppress any field with no data. All that works great but I am wondering how I can do the same or similar for List of Objects in my class. Right now if there is no data for one of these I still get an an output like this which is an empty json Array.
{
"Txnum": "APO100000007R",
"Dtsent": "20180625105938",
"Txtyp": "A",
"Location": [],
"Terminationdata": [],
"Responsestatus": {
"prespc": "FTRAVQ059",
"prespd": "LV1 IS REQUIRED "
}
}
So I am wondering if and how I could avoid this short of checking json string before I return it and strip the "Location": [], for example.
This is the code that worked for me. Just as a Side Node the ShouldSerialize"PropertyName:() is case sensitive so ShouldSerializeLocation() works while ShouldSerializelocation() does not. In Vb code normally is not case sensitive so just watch for that to save your self some headache.
<XmlElement([Namespace]:=SynchronossNS)>
Public Property Location() As List(Of location)
Get
Return _location
End Get
Set
_location = Value
End Set
End Property
Public Function ShouldSerializeLocation() As Boolean
Return _location.Count > 0
End Function

Swagger: Remove class properties from parameter example value

I am using Swagger to document a REST API.
I am having a class like this:
public class Source{
private String url;
private String category;
private String label;
...
}
I am currently using #ApiImplicitParam to set the dataType to Source.class, but I am having multiple POST requests that get a JSON as a body parameter with, lets say, a single variable of those, for example:
{"label": "labelA"}
Because of the dataType set previously, the example value displayed by the Swagger UI is a whole Source.class, something like this:
{
"url": "string",
"category": "string",
"label": "string",
...
}
Could I somehow chop the example value displayed by the Swagger UI for every single request of those? I mean that the getSourceFromUrl() request should get a JSON that contains only a url field, and the example should display exactly this and not the full Source.class JSON.
Thank you all in advance!
UPDATE
I am using JAX-RS. Please, ask me for more input if needed.
If you are using springfox-swagger2 , there is an annotation #ApiModelProperty that does this.
Example:
#ApiModelProperty(required = false, hidden = true)
private String label;
For the time being, you cannot do such a thing. You have to create a different class for each case.
See in swagger-core's github: https://github.com/swagger-api/swagger-core/issues/1863#issuecomment-237339565

VB.Net / JSON - Deserializing

I've been racking my brain for the past few hours.
I found that you can serialize the data and as such save the hassle of creating endlessly long .split commands for each of the seperate JSON values. So I've followed what a lot of people on SO and all over the web have done, by creating a JsonHelper class to Serialize and Deserialize the JSON that is passed from an ASP.net page.
This is my class:
Public Class NewTaskOb
Public Property Department As Integer
Public Property Type As Integer
Public Property AssignedTo As Integer
Public Property Priority As Integer
Public Property Title As String
Public Property JobCode As Integer
Public Property ParentTask As String
Public Property DueDate As Date
Public Property Scope As String
Public Property Comment As String
Public Property BudgetString As String
End Class
Then I have this:
<WebMethod()> Public Shared Function NewTaskRequest(task As String) As String
Dim newTask As NewTaskOb = DeserializeJSON.JsonDeserialize(Of NewTaskOb)(task)
My JSON is valid according to jsonlint, but when I pass the values through, I check by putting a breaker on the Dim newTask line, and when I hover my mouse over it, it says each of the values is empty (Department = 0, Type = 0, etc.) when, on the form, I am submitting values.
I have tried by using DataContractJsonSerializer, JsonHelper, and JavaScriptSerializer. Please note, I do not want to import another reference (i.e Newtonsoft.Json, or anything similar). I want to get this done using the aforementioned functions.
Thanks for your help in advance.
Edit (adding in the JSON string itself):
{
"NewTask": {
"Department": "-1",
"Type": "0",
"AssignedTo": "0",
"Priority": "-1",
"Title": "",
"JobCode": "-",
"ParentTask": "-",
"DueDate": "",
"Scope": "",
"Comment": "",
"BudgetString": ""
}
}
Edit:
While messing around with the code, I went back to the JavaScriptSerializer and found if I put Dim data = jss.Deserialize(Of Object)(task) in place of Dim data = jss.Deserialize(Of NewTaskOb)(task), then it shows up while stepping through that there is a dictionary in the data, that has the fields with the data.
Dictionary showing JSON correctly http://imageshack.com/a/img401/1174/a9ju.png
Any idea how I can extract these into the class variables?
Thanks in advance.
So I was testing your program on my system and noticed that it has Dictionary"2. Imagining what it could possibly mean, I had the idea that 2 could mean there is a dictionary nested within a dictionary - which could explain why you couldn't retrieve the values. So I edited away, and ended up with this line - Dim taskData = jss.Deserialize(Of Dictionary(Of Object, Object))(task). Now, when I run it I have put in Dim taskValues = taskData.Values, and I can reference each of the values using their respective index positions...
i.e taskValues(0) = Department, taskValues(1) = Type, etc.
Also, I removed the line where you were inserting the data into a Data Transfer Object, thus eliminating the "NewTask": nesting within the JSON, resulting in this JSON:
{
"Department": "-1",
"Type": "0",
"AssignedTo": "0",
"Priority": "-1",
"Title": "",
"JobCode": "-",
"ParentTask": "-",
"DueDate": "",
"Scope": "",
"Comment": "",
"BudgetString": ""
}

Create dyanamic class to accept dynamic JSON

I have a web api endpoint that receives JSON and serializes it into objects. Very basic and common stuff. However, I have a requirement to accept custom user defined fields. For example, a developer may want to add a custom field for "account #" and pass that along via the API. I'm stuck how I could define a field on my class if I don't know the name. I need to support unlimited fields so I cannot simply create a field for custom1, custom2, custom2, etc.
I would think that my JSON could look something like this... where custom_label_xxx is identifies the field label:
...
"custom_fields": {
"custom_label_90": 49,
"custom_label_83": [ 28, 29, 30 ],
"custom_label_89": "2012/05/21"
},
...
How in the world can I setup a dynamic class to accept this dynamic JSON?
I have Googled forever and cannot find any examples using custom fields.
Your post method can accept dynamic as a param:
public HttpResponseMessage Post(dynamic obj)
This will accept every json that you send.
Saykor's reply is probably correct. However, I already have tons of business objects to work with and I only wanted the custom fields to be dynamic. Also, I wanted the Web API Help pages to be generated with sample JSON. So making the method dynamic would not work well for me.
What I finally did was probably obvious to some. I created a property on the class that was a dictionary. When I run the Help Pages it generates sample JSON that looks exactly what I needed. I have not tested this yet, but I assume it will serialize the JSON into a dictionary.
Here is the property in VB, but it could easily use dynamic in C# as well.
Private _customfields As Dictionary(Of String, String)
<DataMember(EmitDefaultValue:=False, IsRequired:=False, Order:=11)> _
Public Property customfields() As Dictionary(Of String, String)
Get
Return Me._customfields
End Get
Set(ByVal value As Dictionary(Of String, String))
Me._customfields = value
End Set
End Property
This resulted in the following JSON:
"customfields": {
"sample string 1": "sample string 2",
"sample string 3": "sample string 4",
"sample string 5": "sample string 6"
}