unmarshal verschachtelte json-Struktur, ohne zu wissen,

Ich bin mit einem key-value store backend für meine golang-Anwendung, mit dem Datum, das als Taste (halten die Einträge sortiert) und json-Dokumente, wie die Werte. Die top-level-namespace des json (foo) und die type und date vorhanden sind, in jedes json-Dokument, dass ich speichern, aber sonst gibt es einige Unterschiede (vor allem in Bezug auf einige der verschachtelten json-Daten), so dass, wenn keyI ' m ziehen aus der Datenbank, ich weiß wirklich nicht, was ich herausziehen zu jeder Zeit, dass ich die Schleife durch . Hier ist ein Beispiel für die json-Daten

{ "foo": { "id":"124", "type":"baz", "rawdata":[123, 345,345],"epoch": "1433120656704"}}
{ "foo" : { "id":"234", "type":"bar", "rawdata":[{"key":"dog", "values":[123,234]}, {"key":"cat", "values":[23, 45]}], "epoch":"1433120656705"}}

wenn ich ziehe aus der Datenbank, das erste was ich mache ist unmarshal jeder Eintrag in einer map[string]*json.RawMessage Umgang mit der foo namespace

//as I'm looping through the entries in the database
   var objmap map[string]*json.RawMessage
   if err := json.Unmarshal(dbvalue, &objmap); err !=nil{
       return err
   }

denen ich Dank dieser SO beantworten

Jedoch, im Gegensatz zu in das SO beantworten, wenn ich unmarshal noch einmal, was enthalten ist, unter der foo namespace-ich weiß nicht, welche Struktur zu unmarshal in

   if err :=json.Unmarshal(*objmap["foo"], &bazorbar; err != nil{
         return err
   }

 type Baz struct{
  Id string `json:"id"`
  Type string `json:"type"`
  RawData []int `json:"rawdata"`
  Epoch string  `json:"epoch"`
}

type Bar struct{
  Id string `json:"id"`
  Type string `json:"type"`
  RawData []*Qux `json:"rawdata"`
  Epoch string  `json:"epoch"`
}
//nested inside Bar
type Qux struct{
  Key string `json:"key"`
  Values []int `json:"values`
}

Zwei Teil-Frage:

  1. Ist es ein Weg, um zu vermeiden wiederholte unmarshals (oder ist das etwas, was ich nicht selbst zu kümmern)
  2. wie kann ich herausfinden, welche Struktur zu unmarshal json.RawMessage in (die auch für verschachtelte json-Daten)

Update: die erste Antwort von @chendesheng ermöglicht mir, herauszufinden, die Art aber nicht zu unmarshal wieder in ein struct einmal, dass der Typ bestimmt wurde (was ich tun), also basierend auf einem Gespräch in den Kommentaren zu seiner/Ihrer Antwort, wäre ich daran interessiert, eine dieser Möglichkeiten

a) erstellen Sie eine Kopie der json.RawMessage, unmarshal in die Schnittstelle, wie Sie angezeigt werden (von chendesheng Antwort), und dann unmarshal die Kopie itno die struct sobald Sie wissen, die Art (von deren Marshalling rückgängig gemacht wurde in die Schnittstelle)?

b) einen regulären Ausdruck verwenden, um zu bestimmen, den Typ und dann unmarshal in ein struct der Art, sobald es bekannt

  • Nichts für ungut, aber ich denke, Sie sollten überdenken, Ihr design, da Sie sollten in der Lage sein, um zu vermeiden, eine Entscheidung, die zur Laufzeit oder zumindest eine Art eine Art Kennzeichen, um dies zu vermeiden, mehr lose introspektiv bedeutet, zu entscheiden, wie zu Deserialisieren. Sie sind der Behandlung von Daten aus einer db, als ob es aus einige Unkontrollierbare und unberechenbare Dritte, empfehle ich dagegen.
  • vielen Dank für den input. Ich nehme es in Betracht und wenn ich einen besseren Weg finden, es zu tun, ich allerdings, ich glaube nicht, ich bin der Behandlung von t, als ob es aus einem unvorhersehbaren Dritten. Es ist nur so, dass die Struktur der json-Dokumente sind nicht die gleichen und müssen daher unmarshallt werden in verschiedenen Strukturen und deshalb muss ich mich, um herauszufinden, was der json aussieht, bevor ich mich entscheiden, welche Struktur zu unmarshal in
  • Ja, das ist json, die verschiedene Typen. Sie können speichern, die Typ-Informationen in Ihrer Datenbank, und verwenden Sie es, um eine 100% schlüssige Entscheidung darüber, welche Art es ist, vor der Berufung Unmarshal, bist du mit unmarshal wie es ist ein try/catch-anstatt mit Typ info + wählen Sie den unmarshal in die richtige Typ mit keine unbestimmte Laufzeit-Verhalten.
Schreibe einen Kommentar