当前位置: 首页 > 知识库问答 >
问题:

取消封送动态 JSON [重复]

卞嘉许
2023-03-14

我从遵循以下模式的 API 接收动态 JSON:

{
    "ts": timestamp,
    "data": [
        [ code1, payload1 ],
        [ code2, payload2 ],
        ...
    ]
}

例如,原始数据将是:

    var streamSnapshot = []byte(

`{ 
   "ts": 1496244373.04,
   "data":[
      ["xrate", {"rate":1.2916,"ccy":"USD"}],
      ["balance", 
         {
            "open_stake":["GBP", 0.0],
            "balance":["GBP", 0.0]
         }
      ],
      ["event", 
         {
            "competition_id":"545",
            "ir_status":"pre_event",
            "start_time":"2017-09-10T17:00:00+00:00",
            "competition_name":"USA NFL",
            "event_id":"2017-09-10,21617,21635",
            "home":"Buffalo Bills",
            "away":"New York Jets",
            "sport":"af",
            "competition_country":"US"
         }
      ],
      ["sync", {"Token":"eb1c57132d004f8d8fb967c076921fac"}]
   ]
}`)

考虑到我们想避免解组到这样的结构:

type StreamMessage struct {
    Data [][]interface{} `json:"data"`
    Ts   float64         `json:"ts"`
} 

我们将不得不像这样将数据投回:

    m := raw.(map[string]interface{})

    switch messageType {
    case XRATE:
        xrate := XRate{
            Message: Message{
                Type:      XRATE,
                TimeStamp: msg.Ts,
            },
            rate: m["rate"].(float64),
            ccy:  m["ccy"].(string),
        }  
     ...

解组的更好方法是什么?

共有1个答案

牛景同
2023-03-14
package main

import (
    "bytes"
    "encoding/json"
    "errors"
    "fmt"
)

type StreamMessage struct {
    Data []*Data `json:"data"`
    Ts   float64 `json:"ts"`
}

type Data struct {
    Type    string
    XRate   *XRateData
    Balance *BalanceData
    Event   *EventData
    Sync    *SyncData
}

func (d *Data) UnmarshalJSON(b []byte) error {
    dec := json.NewDecoder(bytes.NewReader(b))
    t, _ := dec.Token()
    if delim, ok := t.(json.Delim); !ok || delim != '[' {
        return errors.New("expecting data to be an array")
    }

    if err := dec.Decode(&d.Type); err != nil {
        return err
    }

    var err error
    switch d.Type {
    case "xrate":
        err = dec.Decode(&d.XRate)
    case "sync":
        err = dec.Decode(&d.Sync)
    case "balance":
        err = dec.Decode(&d.Balance)
    case "event":
        err = dec.Decode(&d.Event)
    default:
        return errors.New("unknown data type " + d.Type)
    }

    if err != nil {
        return err
    }

    t, _ = dec.Token()
    if delim, ok := t.(json.Delim); !ok || delim != ']' {
        return errors.New("expecting array to be two elements")
    }

    return nil
}

type XRateData struct {
    Rate json.Number `json:"rate"`
    CCY  string      `json:"ccy"`
}

type BalanceData struct {
    // TODO
}

type EventData struct {
    // TODO
}

type SyncData struct {
    Token string `json:"Token"`
}

var streamSnapshot = []byte(

    `{ 
   "ts": 1496244373.04,
   "data":[
      ["xrate", {"rate":1.2916,"ccy":"USD"}],
      ["balance", 
         {
            "open_stake":["GBP", 0.0],
            "balance":["GBP", 0.0]
         }
      ],
      ["event", 
         {
            "competition_id":"545",
            "ir_status":"pre_event",
            "start_time":"2017-09-10T17:00:00+00:00",
            "competition_name":"USA NFL",
            "event_id":"2017-09-10,21617,21635",
            "home":"Buffalo Bills",
            "away":"New York Jets",
            "sport":"af",
            "competition_country":"US"
         }
      ],
      ["sync", {"Token":"eb1c57132d004f8d8fb967c076921fac"}]
   ]
}`)

func main() {
    var sm StreamMessage
    if err := json.Unmarshal(streamSnapshot, &sm); err != nil {
        panic(err)
    }
    fmt.Println(sm)
}

https://play.golang.org/p/ktABS6z40m

 类似资料:
  • 发现了许多类似的问题(标题),但没有一个解决了我的问题,所以这里是它。 我有一个JSON字符串,其中包含一些已知字段(应该始终存在)以及任意数量的未知/任意字段。 在此示例中,和是已知的字段。和是任意/未知的字段。 未知字段可以具有任何名称(键)和任何值。值类型可以是字符串、布尔值、float64 或 int。 我想要的是找到最简单、最优雅(惯用)的方法来解析这样的消息。 我使用了以下结构: 使用

  • 问题内容: 我有一个正在建立的用于访问Web服务的客户端。我正在使用一些JAXB生成的类(Netbeans 6.9)来解组我的xml数据。 尝试从此Web服务解组InputStream响应时遇到意外元素错误,如果将响应保存到文件中,也会遇到相同的意外元素错误。 将数据保存到文件后,我可以进入并删除SOAP标签(信封,正文,标题),然后毫无问题地进行解组。 我还没有真正找到一种使拆封忽略这些标签的方

  • 问题内容: 我正在Go中构建一个JSON API,我想将错误响应作为json返回。 响应示例: 我以为我可以创建一个实现错误接口的包装器结构,然后使用Go的json封送处理程序作为获取错误的json表示形式的一种干净方法: 这只会将JsonErr 封送为,是否可以使用默认的Go json封送处理程序对该结构进行编码,还是需要为JsonErr结构编写快速的自定义MarshalJson? 问题答案:

  • 我可以找到许多例子,说明如何让akka-http服务器轻松封送由case类表示的响应实体,只需混合使用SprayJSONSupport/DefaultJSONProtocol,在隐式作用域中提供jsonFormat并在路由DSL中使用complete指令。整齐!

  • null 杰克逊在默认情况下有能力做到这一点。

  • axios 取消上一次重复请求如何封装?