642 Stimmen

Wie konvertiere ich ein JSON-Objekt in eine TypeScript-Klasse?

Ich lese ein JSON-Objekt von einem entfernten REST-Server. Dieses JSON-Objekt hat alle Eigenschaften einer TypeScript-Klasse (nach Design). Wie kann ich dieses empfangene JSON-Objekt in eine Typvariable umwandeln?

Ich möchte keine TypeScript-Variable auffüllen (d. h. einen Konstruktor haben, der dieses JSON-Objekt übernimmt). Es ist groß und das Kopieren jedes einzelnen Unterobjekts und jeder Eigenschaft würde viel Zeit in Anspruch nehmen.

Update: Sie können es jedoch in eine TypeScript-Schnittstelle umwandeln!

225voto

WiredPrairie Punkte 56901

Sie können ein einfaches JavaScript-Ergebnis aus einer Ajax-Anfrage nicht einfach in eine prototypische JavaScript/TypeScript-Klasseninstanz umwandeln. Es gibt eine Reihe von Techniken, um dies zu tun, und diese beinhalten im Allgemeinen das Kopieren von Daten. Wenn Sie keine Instanz der Klasse erstellen, wird sie keine Methoden oder Eigenschaften haben. Es bleibt ein einfaches JavaScript-Objekt.

Wenn Sie nur mit Daten umgehen, könnten Sie diese einfach in ein Interface umwandeln (da es sich nur um eine Kompilierzeitstruktur handelt), jedoch würde dies erfordern, dass Sie eine TypeScript-Klasse verwenden, die die Dateninstanz verwendet und Operationen mit diesen Daten durchführt.

Einige Beispiele zum Kopieren der Daten:

  1. AJAX JSON-Objekt in ein vorhandenes Objekt kopieren
  2. JSON-String in ein bestimmtes Objekt-Prototyp in JavaScript umwandeln

Im Wesentlichen würden Sie einfach:

var d = new MyRichObject();
d.copyInto(jsonResult);

185voto

Pak Punkte 2629

Ich hatte das gleiche Problem und habe eine Bibliothek gefunden, die den Job erledigt: https://github.com/pleerock/class-transformer.

Es funktioniert so:

let jsonObject = response.json() as Object;
let fooInstance = plainToClass(Models.Foo, jsonObject);
return fooInstance;

Es unterstützt verschachtelte Kinder, aber Sie müssen das Klassenmitglied dekorieren.

73voto

user756310 Punkte 929

In TypeScript können Sie mit einer Schnittstelle und Generics einen Typ-Assertion wie folgt durchführen:

var json = Utilities.JSONLoader.loadFromFile("../docs/location_map.json");
var locations: Array = JSON.parse(json).location;

Wo ILocationMap die Form Ihrer Daten beschreibt. Der Vorteil dieser Methode besteht darin, dass Ihr JSON mehr Eigenschaften enthalten könnte, aber die Form die Bedingungen der Schnittstelle erfüllt.

Dies fügt jedoch KEINE Klasseninstanzmethoden hinzu.

58voto

小广东 Punkte 1111

Wenn Sie ES6 verwenden, versuchen Sie es damit:

class Client{
  name: string

  displayName(){
    console.log(this.name)
  }
}

service.getClientFromAPI().then(clientData => {

  // Hier hat die Client-Daten von der API nur das Feld "name"
  // Wenn wir die Methoden der Client-Klasse auf dieses Datenobjekt anwenden möchten, müssen wir:
  let clientWithType = Object.assign(new Client(), clientData)

  clientWithType.displayName()
})

Aber diese Methode funktioniert leider nicht bei verschachtelten Objekten.

37voto

Philip Punkte 21490

Ich habe einen sehr interessanten Artikel zum generischen Casting von JSON zu einer TypeScript-Klasse gefunden:

http://cloudmark.github.io/Json-Mapping/

Am Ende haben Sie folgenden Code:

let example = {
                "name": "Mark", 
                "surname": "Galea", 
                "age": 30, 
                "address": {
                  "first-line": "Irgendwo", 
                  "second-line": "Hier drüben",
                  "city": "In dieser Stadt"
                }
              };

MapUtils.deserialize(Person, example);  // benutzerdefinierte Klasse

CodeJaeger.com

CodeJaeger ist eine Gemeinschaft für Programmierer, die täglich Hilfe erhalten..
Wir haben viele Inhalte, und Sie können auch Ihre eigenen Fragen stellen oder die Fragen anderer Leute lösen.

Powered by:

X