'Deserialize JSON to a module

I need to parse a JSON that comes from a crypto exchange API. In this case, I need to parse my open orders. If there are no open orders, the Json is :

{"error":null,"result":{"KIBAUSDT":{"limit":100,"offset":0,"total":0,"records":null}},"id":299639536}

which seems a dictionary. As soon as I create 1 order, the Json become like this:

{"error":null,"result":{"KIBAUSDT":{"limit":100,"offset":0,"total":1,"records":[{"user":2996434,"id":82651361103,"market":"KIBAUSDT","freeze":"0.001","fee_stock":"","source":"web","type":1,"side":2,"ctime":1645022087.403207,"mtime":1645022087.403207,"price":"0.00001","amount":"100","taker_fee":"0.0035","maker_fee":"-0.003","left":"100","deal_stock":"0","deal_money":"0","deal_fee":"0","alt_fee":"0","deal_fee_alt":"0","status":0}]}},"id":305636871}

which seems more an array (Please correct me if I'm wrong). Those lines are beign created for each single order I'm creating. So, on quicktype.io, I'm setting the option as array, converting it to vb.net using Icsharpcode, creating a class file, and considerating the property "total" as is easy to understand if there are or not orders opened. Translated c# to vb.net:

Imports System
Imports Newtonsoft.Json
Imports Newtonsoft.Json.Converters
Imports System.Runtime.CompilerServices

Namespace QuickType
    Partial Public Class Example
        <JsonProperty("error")>
        Public Property [Error] As Object
        <JsonProperty("result")>
        Public Property Result As Result
        <JsonProperty("id")>
        Public Property Id As Long
    End Class

    Partial Public Class Result
        <JsonProperty("KIBAUSDT")>
        Public Property Kibausdt As Kibausdt
    End Class

    Partial Public Class Kibausdt
        <JsonProperty("limit")>
        Public Property Limit As Long
        <JsonProperty("offset")>
        Public Property Offset As Long
        <JsonProperty("total")>
        Public Property Total As Long
        <JsonProperty("records")>
        Public Property Records As Record()
    End Class

    Partial Public Class Record
        <JsonProperty("user")>
        Public Property User As Long
        <JsonProperty("id")>
        Public Property Id As Long
        <JsonProperty("market")>
        Public Property Market As String
        <JsonProperty("freeze")>
        Public Property Freeze As String
        <JsonProperty("fee_stock")>
        Public Property FeeStock As String
        <JsonProperty("source")>
        Public Property Source As String
        <JsonProperty("type")>
        Public Property Type As Long
        <JsonProperty("side")>
        Public Property Side As Long
        <JsonProperty("ctime")>
        Public Property Ctime As Double
        <JsonProperty("mtime")>
        Public Property Mtime As Double
        <JsonProperty("price")>
        Public Property Price As String
        <JsonProperty("amount")>
        <JsonConverter(GetType(ParseStringConverter))>
        Public Property Amount As Long
        <JsonProperty("taker_fee")>
        Public Property TakerFee As String
        <JsonProperty("maker_fee")>
        Public Property MakerFee As String
        <JsonProperty("left")>
        <JsonConverter(GetType(ParseStringConverter))>
        Public Property Left As Long
        <JsonProperty("deal_stock")>
        <JsonConverter(GetType(ParseStringConverter))>
        Public Property DealStock As Long
        <JsonProperty("deal_money")>
        <JsonConverter(GetType(ParseStringConverter))>
        Public Property DealMoney As Long
        <JsonProperty("deal_fee")>
        <JsonConverter(GetType(ParseStringConverter))>
        Public Property DealFee As Long
        <JsonProperty("alt_fee")>
        <JsonConverter(GetType(ParseStringConverter))>
        Public Property AltFee As Long
        <JsonProperty("deal_fee_alt")>
        <JsonConverter(GetType(ParseStringConverter))>
        Public Property DealFeeAlt As Long
        <JsonProperty("status")>
        Public Property Status As Long
    End Class

    Partial Public Class Example
        Public Shared Function FromJson(ByVal json As String) As Example
            Return JsonConvert.DeserializeObject(Of Example)(json, Settings)
        End Function
    End Class

    Public Module Serialize
        <Extension()>
        Public Function ToJson(ByVal self As Example) As String
            Return JsonConvert.SerializeObject(self, Settings)
        End Function
    End Module

    Friend Module Converter
        Public ReadOnly Settings As JsonSerializerSettings = New JsonSerializerSettings With {
            .MetadataPropertyHandling = MetadataPropertyHandling.Ignore,
            .DateParseHandling = DateParseHandling.None
        }
    End Module

    Friend Class ParseStringConverter
        Inherits JsonConverter

        Public Overrides Function CanConvert(ByVal t As Type) As Boolean
            Return t Is GetType(Long) OrElse t Is GetType(Long?)
        End Function

        Public Overrides Function ReadJson(ByVal reader As JsonReader, ByVal t As Type, ByVal existingValue As Object, ByVal serializer As JsonSerializer) As Object
            If reader.TokenType = JsonToken.Null Then Return Nothing
            Dim value = serializer.Deserialize(Of String)(reader)
            Dim l As Long

            If Long.TryParse(value, l) Then
                Return l
            End If

            Throw New Exception("Cannot unmarshal type long")
        End Function

        Public Overrides Sub WriteJson(ByVal writer As JsonWriter, ByVal untypedValue As Object, ByVal serializer As JsonSerializer)
            If untypedValue Is Nothing Then
                serializer.Serialize(writer, Nothing)
                Return
            End If

            Dim value = CLng(untypedValue)
            serializer.Serialize(writer, value.ToString())
            Return
        End Sub

        Public Shared ReadOnly Singleton As ParseStringConverter = New ParseStringConverter()
    End Class
End Namespace

Now problems are starting, because.. Total property is inside the Partial Public Class Kibausdt , so before to parse the opened orders ( price, amount, status which are the only property I'm interested on to parse from the Partial Public Class Record ) I want to know if the "total" property equals to 0.

I'm still failing to get a result, the closest I can go is


 Dim downloadTasks As New List(Of Task(Of String))
             Dim s = wc.DownloadStringTaskAsync("https://api.hotbit.io/api/v1/order.pending?market=KIBA/USDT&offset=0&limit=100&api_key=44812d8f-66d3-01c0-94c3b29305040b03&sign=F3330B924E1873B9C8FAB40A25D7B851")
             downloadTasks.Add(s)
             Await Task.WhenAll(downloadTasks)
             Dim total = Kibausdt.FromJson((Await s))
        
             If zeroOpenOrders As Long In total = "0" Then
                 RichTextBox1.Text = "0 opened orders"
             Else
                 For Each r As Result In Record.Result
                     Dim side As String = r("side").AsValue.ToString
                     Dim amount As Long = CInt(r("amount").AsValue.ToString)
                     Dim price As String = r("price").AsValue.ToString
                     RichTextBox1.Text &= side & amount & price
                 Next
             End If

and I'm getting these errors: enter image description here

it is kind of weird how I'm getting the first error "FromJson is not a member of kibausdt", since total property is inside the Kibausdt class. This issue is solved by using Dim total = Example.FromJson((Await s)) but I'm not really sure that's the answer.

Thanks



Sources

This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.

Source: Stack Overflow

Solution Source