Свойство карты эластичного поиска с различными типами

#c# #elasticsearch #nest

#c# #elasticsearch #гнездо

Вопрос:

 public class Document {
    public Guid Id {get;set;}
    public string Name {get;set;}
    public DocumentAttribute[] Attributes {get;set;}
}

public class DocumentAttribute {
    public Guid AttributeId {get;set;}
    public string Type {get;set;}
    public object Value {get;set;}
}
  

Атрибут DocumentAttribute.Тип содержит тип значения (строка, дата, …)

Я могу отобразить его следующим образом:

 .Map<DocumentDto>(
                m=>m
                .Properties(p => p
                .Text(s => s.Name(DocumentDto.DefaultAttributes.Name))
                .Nested<DocumentAttribute>(da => da
                    .Name(DocumentDto.DefaultAttributes.Attributes)
                    .Properties(dap => dap
                        .Text(s => s.Name(n => n.AttributeId))
                        .Nested<object>(dav => dav.Name(n => n.Value))
                        )
                    )
                )
                );
  

Если я попытаюсь проиндексировать документ, содержащий атрибуты нескольких типов (один из которых — дата) Я получаю:

 mapper cannot be changed from type [date] to [text]
  

Ответ №1:

Проще говоря, то, что вы пытаетесь сделать, это динамически сопоставить 2 поля с одинаковыми именами с разными типами.

Ниже приведена эквивалентная команда сопоставления ES:

 PUT documents
{
  "mappings": {
    "properties": {
      "key1":{
        "type": "text" 
      },
      "key1":{
        "type": "date"
      }
    }
  }
}
  

Результат запроса: данный запрос приведет к исключению => «Дублировать поле ‘name'».

Однако:

 POST documents/_doc
{
  "key1":1 //<======== (Success) value is an Integer
}

POST documents/_doc
{
  "key1":"1" //<==== (Success) Value is a String but can be converted to integer just fine
}

POST documents/_doc
{
  "key1":"Hello" //<==== (Fail) Value is a String but can't be converted to an integer
}
  

Решение: следуйте приведенной ниже схеме для атрибутов документа, чтобы не пытаться динамически сопоставлять одноименные ключи с разными типами.

    {
    "type":"" // <==== e.g Possible values are int, text, date 
    "val_int":1, // <==== here keyname is val_<typeValue>
    "val_text":"Hey",
    "val_date":"2020-01-01" 
   }
  

Комментарии:

1. Это будет моя следующая попытка, если ни у кого больше нет идеи для теста