Я думаю, что использование ExclusionStrategy
не является правильным подходом для решения этой проблемы.
Я бы скорее предложил использовать JsonSerializer
и JsonDeserializer
настроенный для вашего StructId
класса.
(может быть, подход, использующий TypeAdapter
, был бы даже лучше, но у меня не было достаточно опыта Gson, чтобы все заработало.)
Таким образом, вы должны создать свой экземпляр Gson
следующим образом:
Gson gson = new GsonBuilder()
.registerTypeAdapter(StructId.class, new StructIdSerializer())
.registerTypeAdapter(StructId.class, new StructIdDeserializer())
.setPrettyPrinting()
.create();
Класс StructIdSerializer
, указанный ниже, отвечает за преобразование StructId
в JSON.Он преобразует свои свойства Name
, Type
и ChildId
в JSON.Обратите внимание, что оно не преобразует свойство ParentId
в JSON, потому что выполнение этого приведет к бесконечной рекурсии.
public class StructIdSerializer implements JsonSerializer<StructId> {
@Override
public JsonElement serialize(StructId src, Type typeOfSrc, JsonSerializationContext context) {
JsonObject jsonObject = new JsonObject();
jsonObject.addProperty("Name", src.Name);
jsonObject.add("Type", context.serialize(src.Type));
jsonObject.add("ChildId", context.serialize(src.ChildId)); // recursion!
return jsonObject;
}
}
Класс StructIdDeserializer
ниже отвечает за преобразование JSON в StructId
.Он преобразует свойства JSON Name
, Type
и ChildId
в соответствующие поля Java в StructId
.Обратите внимание, что поле ParentId
Java восстанавливается из структуры вложенности JSON, поскольку оно не содержится непосредственно в качестве свойства JSON.
public class StructIdDeserializer implements JsonDeserializer<StructId> {
@Override
public StructId deserialize(JsonElement json, Type typeOfT, JsonDeserializationContext context)
throws JsonParseException {
StructId id = new StructId();
id.Name = json.getAsJsonObject().get("Name").getAsString();
id.Type = context.deserialize(json.getAsJsonObject().get("Type"), StructType.class);
JsonElement childJson = json.getAsJsonObject().get("ChildId");
if (childJson != null) {
id.ChildId = context.deserialize(childJson, StructId.class); // recursion!
id.ChildId.ParentId = id;
}
return id;
}
}
Я тестировал приведенный выше код с этим примером ввода JSON
{
"Name": "John",
"Type": "A",
"ChildId": {
"Name": "Jane",
"Type": "B",
"ChildId": {
"Name": "Joe",
"Type": "A"
}
}
}
, десериализовав его с помощью
StructId root = gson.fromJson(new FileReader("example.json"), StructId.class);
,
, а затем сериализовав его с
System.out.println(gson.toJson(root));
и снова получив исходный JSON.