C#中Postgres版Dapper:List<T>映射JSONB需单独类型映射器吗?
问题:Dapper是否需要为List单独添加JSON类型映射器?
假设Postgres数据库存在JSONB类型的Events列,在C#中该列对应List<Event>类型,其中Event类定义如下:
public sealed class Event { public string Test { get; set; } = string.Empty; }
已通过SqlMapper.AddTypeHandler(new JsonMapper<Event>());为Dapper添加了如下泛型JSON类型映射器:
public class JsonMapper<T> : SqlMapper.TypeHandler<T> where T : class, new() { public override T Parse(object? value) { var config = new T(); if (value is not null) { var stringValue = value.ToString() ?? string.Empty; config = JsonConvert.DeserializeObject<T>(stringValue, NewtonsoftJsonSerializerSettings); } return config ?? new(); } public override void SetValue(IDbDataParameter parameter, T? value) { parameter.Value = JsonConvert.SerializeObject(value, NewtonsoftJsonSerializerSettings); } private static JsonSerializerSettings NewtonsoftJsonSerializerSettings = new() { TypeNameHandling = TypeNameHandling.All, NullValueHandling = NullValueHandling.Ignore, Formatting = Formatting.Indented, ObjectCreationHandling = ObjectCreationHandling.Replace, // Don't care about these, not relevant for the question //Converters = new List<JsonConverter> { new IsoDateTimeConverter(), new IpAddressConverter(), new IpEndpointConverter() } }; }
请问是否还需要添加SqlMapper.AddTypeHandler(new JsonMapper<List<Event>>());?Dapper能否自动处理该映射?
回答
需要单独添加针对List<Event>的类型处理器,Dapper不会自动为泛型集合类复用单个元素的类型映射器。
原因很直接:你注册的JsonMapper<Event>只能处理Event类型的对象,而List<Event>是完全独立的另一种类型。Dapper的类型处理器是基于具体类型精确匹配的,它不会自动推断泛型集合的元素处理器,来完成整个集合的序列化/反序列化操作。
如果不添加JsonMapper<List<Event>>,在读写Events列时大概率会遇到映射错误——要么无法把Postgres的JSONB数组反序列化为C#的List<Event>,要么无法把List<Event>序列化为Postgres能识别的JSONB格式。
内容的提问来源于stack exchange,提问作者FranzHuber23
相关产品推荐
相关产品推荐

