doukan4039 2016-06-30 17:33
浏览 36
已采纳

在Go中处理“单个元素或数组” JSON属性的最佳方法是什么?

Now we have a JSON HTTP request data which would be a single element like {"data": {"id":1}} OR an array of elements like {"data": [{"id":1}, {"id":2}]}.

Since a client side cannot change the implementation, we have to keep and accept this data structure.

Currently I implement struct like:

type Request struct {
  rawData json.RawMessage `json:"data"`

  Data *Data `json:"-"`
  DataList []*Data `json:"-"`
}

And first parse "data" property as json.RawMessage into variable req, try parsing as a single element first, then if it fails try parsing as an array.

if err := json.Unmarshal(req.rawData, &req.Data); err != nil {
    if err := json.Unmarshal(req.RawData, &req.DataList); err != nil {
        return errors.New("could not parse data")
    } else if len(req.DataList) < 1 {
        return errors.New("empty list")
    }
}

In this case, later when we want to use this data, we can check if rawData is a single element or an array by len(req.Datalist) >= 1. (Or I can set some flag to show that like isDataMultiple in the struct, when parsing).

Is there any idiomatic way to achieve the same result in Go other than what I'm doing?

  • 写回答

1条回答 默认 最新

  • duandeng2011 2016-06-30 20:30
    关注

    Here's how I would do it:

    type Request struct {
       RawData json.RawMessage `json:"data"  // export field for unmarshal of entire request
       DataList []*Data `json:"-"`           // always use slice
    }
    
    // Is it an array?
    if bytes.HasPrefix(bytes.TrimSpace(req.RawData), []byte{'['})) {
       if err := json.Unmarshal(req.RawData, &req.DataList); err != nil {
           // handle error parsing array
       }
    } else {
       var v Data
       if err := json.Unmarshal(req.RawData, &v); err != nil {
           // handle error parsing single value
       }
       req.DataList = []*Data{&v)
    }
    
    本回答被题主选为最佳回答 , 对您是否有帮助呢?
    评论

报告相同问题?

悬赏问题

  • ¥15 安装svn网络有问题怎么办
  • ¥15 Python爬取指定微博话题下的内容,保存为txt
  • ¥15 vue2登录调用后端接口如何实现
  • ¥65 永磁型步进电机PID算法
  • ¥15 sqlite 附加(attach database)加密数据库时,返回26是什么原因呢?
  • ¥88 找成都本地经验丰富懂小程序开发的技术大咖
  • ¥15 如何处理复杂数据表格的除法运算
  • ¥15 如何用stc8h1k08的片子做485数据透传的功能?(关键词-串口)
  • ¥15 有兄弟姐妹会用word插图功能制作类似citespace的图片吗?
  • ¥15 latex怎么处理论文引理引用参考文献