Hallo zusammen, ich habe gerade mit TJsonSerializer experimentiert und bin auf folgendes Problem gestoßen:
Delphi-Quellcode:
Type
TMyKind = (mkA, mkB);
[JsonSerialize(TJsonMemberSerialization.&In)]
TBaseData = Class
[JSonIn]
[JsonName('Kind')]
Kind: TMyKind;
constructor Create; virtual;
End;
[JsonSerialize(TJsonMemberSerialization.&In)]
TAData = Class(TBaseData)
[JsonIn]
Name: String;
constructor Create; override;
End;
[JsonSerialize(TJsonMemberSerialization.&In)]
TBData = Class(TBaseData)
[JsonIn]
Group: String;
[JsonIn]
Text: String;
constructor Create; override;
End;
[JsonSerialize(TJsonMemberSerialization.&In)]
TMyData = Class
[JsonIn]
[JsonObjectHandling(TJsonObjectHandling.Reuse)]
Data: TArray<TBaseData>;
[JsonIn]
MainData: TBaseData;
constructor Create; virtual;
Destructor Destroy; override;
End;
...
{ TMyData }
constructor TMyData.Create;
begin
inherited;
SetLength(Data, 2);
Data[0] := TAData.Create;
Data[1] := TBData.Create;
MainData := TBData.Create;
end;
Ich habe also ein Data[] das eine TAData und eine TBData instanz enthält. Beim serialisieren funktioniert das wunderbar:
Delphi-Quellcode:
fMyData := TMyData.Create;
js := TJsonSerializer.Create;
js.Formatting := TJsonFormatting.Indented;
s := js.Serialize(fMyData);
...
Memo.Text := s;
Code:
{
"Data": [
{
"Name": "A",
"Kind": 1
},
{
"Group": "B",
"Text": "C",
"Kind": 0
}
],
"MainData": {
"Group": "D",
"Text": "E",
"Kind": 1
}
}
Beim Versuch dieses JSON mit Populate wieder einzulesen wird dann aber das Array neu erzeugt (alle Elemente vom Typ TBaseData).
Delphi-Quellcode:
LMyData := TMyData.Create;
js := TJsonSerializer.Create;
js.Populate<TMyData>(Memo.Text, LMyData);
// LMyData.Data[0] = TBaseData
// LMyData.Data[1] = TBaseData
// LMyData.MainData = TBData
...
Memo.Text := js.Serialize(LMyData)
Das ergibt nach erneuter Serialisierung:
Code:
{
"Data": [
{
"Kind": 1
},
{
"Kind": 0
}
],
"MainData": {
"Group": "D",
"Text": "E",
"Kind": 1
}
}
Ich hatte allerdings gehofft, dass durch Angabe von
JsonObjectHandling(TJsonObjectHandling.Reuse)
die übergebenen Instanzen erhalten bleiben.
Frage 1: Gibt es eine Möglichkeit, die korrekten Typen für die Array-Elemente zu erhalten?
Frage 2: Kann man die Reihenfolge in der js.Serialize den Ausgabestring erzeugt umdrehen (geerbte Properies zuerst -> "Kind" vor "Name")?