为 NEST 序列化覆盖一种特定类型的最简单的方法是什么

What is the most dirt simple way to override one specific type for NEST serialization

我有一个复杂的文档,它在各种不同的子项中有一个自定义日期字段,即:

var doc = new Document
{
    MyCustomDateTime StartTime
    Matches = new []
    {
        MyCustomDateTime StartTime
        MyCustomDateTime EndTime
    }
}

不使用 属性 属性 因为这种类型是从 dll 中提取的,我可以覆盖类型 [=13 的序列化和反序列化的最简单方法是什么=].

我正在寻找类似于或扩展默认序列化器 class 的东西来处理一种额外的类型:

settings.DefaultSerializerFor<MyCustomDateTime>(d => MyConverter.ToString(d), d => MyConverter.FromString(d));

或类似的东西:

public class MyCustomSerializer : DefaultElasticSearchSerializer
{
     public string OnSerialize(object member)
     {
          if (member is MyCustomDateTime) { return MyConverter.ToString(d); }
          return base.OnSerialize(member);
     }
     ...
}

现在,它似乎只发布对象的 public 属性。不幸的是,对于这个特定的 class.

,这不是我正在寻找的行为

实现自定义序列化的最简单方法是

  1. 连接 JsonNetSerializer
  2. 为您的类型定义转换器
  3. 使用 JsonNetSerializer 注册它

一个例子

private static void Main()
{
    var defaultIndex = "default_index";
    var pool = new SingleNodeConnectionPool(new Uri($"http://localhost:9200"));
    var settings = new ConnectionSettings(
        pool, 
        (builtin, settings) => new JsonNetSerializer(builtin, settings, contractJsonConverters: new List<JsonConverter>
    {
        new MyCustomDateTimeConverter()
    }))
        .DefaultIndex(defaultIndex);
        
    var client = new ElasticClient(settings);
        
    var indexResponse = client.Index(
        new MyDocument {
            Message = "message",
            CustomDateTime = new MyCustomDateTime 
            { 
                Custom = new DateTimeOffset(2022,1,9,14,0,0,0, TimeSpan.FromHours(10)) 
            }
        }, i => i.Id(1));
}

public class MyCustomDateTime 
{
    public DateTimeOffset Custom { get; set; }
}

public class MyCustomDateTimeConverter : JsonConverter<MyCustomDateTime>
{
    public override void WriteJson(JsonWriter writer, MyCustomDateTime value, JsonSerializer serializer)
    {
        writer.WriteValue(value.Custom);
    }

    public override MyCustomDateTime ReadJson(JsonReader reader, Type objectType, MyCustomDateTime existingValue, bool hasExistingValue, JsonSerializer serializer)
    {
        var dateTime = reader.ReadAsDateTimeOffset();
        return dateTime is null ? null : new MyCustomDateTime { Custom = dateTime.Value };
    }
}

public class MyDocument
{
    public string Message {get;set;}    
    public MyCustomDateTime CustomDateTime {get;set;}
}

产量

PUT http://localhost:9200/default_index/_doc/1?pretty=true
{
  "message": "message",
  "customDateTime": "2022-01-09T14:00:00+10:00"
}