Код: Выделить всё
public sealed record Descriptor(T Value, string Description);
Код: Выделить всё
[JsonSourceGenerationOptions(GenerationMode = JsonSourceGenerationMode.Serialization)]
[JsonSerializable(typeof(Descriptor))]
[JsonSerializable(typeof(Descriptor))]
public partial class DescriptorContext: JsonSerializerContext{}
< /code>
Теперь, когда у вас есть несколько типов перечисления, это не красиво. Тем не менее, кажется, что вам также нужно добавить записи, если вы хотите сериализовать коллекции каждого типа дескриптора: < /p>
[JsonSourceGenerationOptions(GenerationMode = JsonSourceGenerationMode.Serialization)]
[JsonSerializable(typeof(Descriptor))]
[JsonSerializable(typeof(IEnumerable))]
[JsonSerializable(typeof(List))]
// removed entries for KindB
public partial class DescriptorContext: JsonSerializerContext{}
List items =
[
new(Kind.Single, "Single"),
new(Kind.Colective, "Colective")
];
string serialized = JsonSerializer.Serialize
(
items,
DescriptorContext.Default.ListDescriptorKind
);
List recovered = JsonSerializer.Deserialize
(
serialized,
DescriptorContext.Default.ListDescriptorKind
)!;
foreach (Descriptor item in recovered)
{
Console.WriteLine($"{item.Value} {item.Description}");
}
< /code>
Это правильно? Я имею в виду, правильно ли заключить, что:
- Вы не можете указать открытый тип
- Вы должны указать все типы, которые вы хотите сериализовать/пустынь через JsonserializableAttribute , включая закрытые общины, такие как то, что показано на предыдущей Snippet (Ex. Список )
public async Task DoSomething()
{
// always returns an instance of a Base's derived type
}
< /code>
Первоначально сериализация была сделана с помощью json.net. Тем не менее, мы закончили тем, что перешли на System.text.json, когда он официально поддерживает наследование. В то время мы в итоге прибегли к пользовательскому DefaultJsontypeinforesolver , чтобы используемый дискриминатор совместим с тем, что сгенерирован по умолчанию json.net (имя свойства установлено в $ type , а его значение является квалифицированным именем с полной сборкой). Это потребовалось, потому что некоторые из типов, используемых в API, также сохранялись в базе данных. Вот некоторый демонстрационный код, используемый для defaultjsontypeinforesolver :
Код: Выделить всё
public class JsonHierarchyTypeInfoResolver : DefaultJsonTypeInfoResolver
{
public override JsonTypeInfo GetTypeInfo(Type type, JsonSerializerOptions options)
{
var jsonTypeInfo = base.GetTypeInfo(type, options);
var jsonType = jsonTypeInfo.Type;
if (jsonType == typeof(Equipamento))
{
jsonTypeInfo = GetTypeInfoForDevice(jsonTypeInfo);
}
// ... remaining code removed
}
private static JsonTypeInfo GetTypeInfoForDevice(JsonTypeInfo jsonTypeInfo)
{
jsonTypeInfo.PolymorphismOptions = new JsonPolymorphismOptions
{
TypeDiscriminatorPropertyName = "$type",
IgnoreUnrecognizedTypeDiscriminators = true,
UnknownDerivedTypeHandling = JsonUnknownDerivedTypeHandling.FailSerialization
};
foreach (var jsonDerivedType in _derivedDevicesTypes)
{
jsonTypeInfo.PolymorphismOptions.DerivedTypes.Add(
new JsonDerivedType(jsonDerivedType,
jsonDerivedType.AssemblyQualifiedName!));
}
return jsonTypeInfo;
}
}
< /code>
Итак, окончательные 2 вопроса: < /p>
[list]
[*] Можно ли объединить этот резоливер с тем, что сгенерировано генераторами источников? Или они работают только с полиморфными атрибутами (Ex.: Jsonderivedtypeattribute [*] Если нет, то это означает, что мне придется переписать новую сборку DTO, которая использует полиморфные атрибуты, чтобы повторно использовать API, на основе Polymorphism/inherishance (i.e. Полученные типы)?
[/list]
Подробнее здесь: https://stackoverflow.com/questions/778 ... generators
Мобильная версия