簡體   English   中英

Golang Unmarshall 嵌套 JSON 中的特定 object

[英]Golang Unmarshall specific object in nested JSON

在 GO 中使用 static 屬性名稱解組大型 JSON 的特定部分的最佳做法是什么?

我的 JSON map 看起來像

{
    "top_view" : {
       "@self" : "https://generic.com",
           "graph" : {
              "nodes" : [ { } ],
              "relations" : [ { } ]
                     },
         "view_status" : {}
                 }
}

我只需要檢索節點數組

這是我到目前為止得到的,

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

我只知道如何解組節點部分,但我不知道如何告訴 Go 開始僅解組 object,因此如果我提供整個 Z0ECD11C1D7A287401D8A14 ,代碼將無法工作。 請指教,謝謝!

這是一種方法:定義一個顯示節點路徑的結構。 您可以跳過 JSON 中不感興趣的成員。 例如:

type Whole struct {
    TopView struct {
        Self  string `json:"@self"`
        Graph struct {
            Nodes []Node `json:"nodes"`
        } `json:"graph"`
    } `json:"top_view"`
}

然后編組節點

var whole Whole

err := json.Unmarshal([]byte(jsonResp), &whole)

這是工作代碼: https://play.golang.org/p/5WvPocce_vh

您可以解組任何 JSON 數據,而無需在go代碼中定義任何具體類型。 使用type assertiontype switch來向下鑽取剛剛解組的數據。

下面是使用上述概念的問題的工作示例。 您可能需要在此基礎上進一步細化您的要求,但基本概念保持不變:

package main

import (
    "encoding/json"
    "fmt"
    "log"
)

func main() {
    jsonResponse := `{
        "top_view" : {
           "@self" : "https://generic.com",
               "graph" : {
                  "nodes" : [ {
                    "@self" : "https://generic.com:443",
                    "id" : "1;;45d554600be28ee49c99d26e536225ea;;461ff354437881f6b5973d4af366b91c;;4c0f2cc8e29a4fe09240b2a0c311508d",
                    "ci" : {
                       "id" : "4c0f2cc8e29a4fe09240b2a0c311508d",
                       "name" : "NOICE",
                       "type" : "ci_collection",
                       "type_label" : "CiCollection",
                       "icon" : "/logical_group_32.svg"
                    },
                    "has_children" : true
                 }, {
                    "@self" : "https://generic.com:443hjkhk",
                    "id" : "1;;45d554600be28ee49c99d26e536225ea;;4e22910a478bf6939aed36fef22dc79e;;4a7788eeecbbeee3a8bb3189ba67f269",
                    "ci" : {
                       "id" : "4a7788eeecbbeee3a8bb3189ba67f269",
                       "name" : "NOTNOICE",
                       "type" : "ci_collection",
                       "type_label" : "CiCollection",
                       "icon" : "/logical_group_32.svg"
                    },
                    "has_children" : true
                 }, {
                    "@self" : "https://generic.com:443/fghfgh",
                    "id" : "1;;45d554600be28ee49c99d26e536225ea;;461ff354437881f6b5973d4af366b91c;;4c0f2cc8e29a4fe09240b2a0c311508d;;40b8b314821d01ac874f7209c228ab8f",
                    "ci" : {
                       "id" : "40b8b314821d01ac874f7209c228ab8f",
                       "name" : "NOICE",
                       "type" : "ci_collection",
                       "type_label" : "CiCollection",
                       "icon" : "/logical_group_32.svg"
                    },
                    "has_children" : true
                 }, {
                    "@self" : "https://generic.com:443/gfhgh",
                    "id" : "1;;45d554600be28ee49c99d26e536225ea;;4a208e0deee006668bb3cfab6541a869;;4bd30d48bc1c81b398e17435ba519f2d;;4a1c671cefd3b5b9931b4312382ff2e4",
                    "ci" : {
                       "id" : "4a1c671cefd3b5b9931b4312382ff2e4",
                       "name" : "AAA",
                       "type" : "ci_collection",
                       "type_label" : "CiCollection",
                       "icon" : "/logical_group_32.svg"
                    },
                    "has_children" : true
                 } ],
                  "relations" : [ { } ]
                         },
             "view_status" : {}
                     }
    }`

    var res interface{}
    err := json.Unmarshal([]byte(jsonResponse), &res)
    if err != nil {
        log.Fatal(err)
    }

    parseArbitoryJSONObject(res)
}

func parseArbitoryJSONObject(jsonObject interface{}) {
    data := jsonObject.(map[string]interface{})

    for k, v := range data {
        switch val := v.(type) {
        case string:
            fmt.Println(k, "is string:", val)
        case float64:
            fmt.Println(k, "is float64", val)
        case bool:
            fmt.Println(k, "is boolean", val)
        case []interface{}:
            fmt.Println(k, "is an array:")
            for i, u := range val {
                fmt.Println(i, u)
            }
        case map[string]interface{}:
            fmt.Println(k, "is an map[string]interface{}:")
            parseArbitoryJSONObject(val)
        default:
            fmt.Println(k, "is of a type I don't know how to handle")
        }
    }
}

這里json.Unmarshal使用可以保存任何值的empty interface function parseArbitoryJSONObject()使用type assertion來促進從未編組數據中提取值。

type switch是您可能需要進一步放置或修改邏輯以從未編組的 JSON object 中獲取所需項目的地方。

以下是供您參考的 go-playground 代碼片段鏈接:

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

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM