如何将单个 .NET 类型映射到 ElasticSearch/NEST 中的多个嵌套对象类型?

Posted

技术标签:

【中文标题】如何将单个 .NET 类型映射到 ElasticSearch/NEST 中的多个嵌套对象类型?【英文标题】:How do I map a single .NET type to multiple nested object types in ElasticSearch/NEST? 【发布时间】:2015-04-17 16:56:05 【问题描述】:

我正在使用 NEST 库与 ElasticSearch 进行交互,并且我正在尝试找出一种基于非类型数据构建索引类型/嵌套对象的方法。该类型具有以下基本结构。

 public class Entity : DynamicObject
 
        public string Id  get; set; 
        // a bunch of other simple properties

        public override IEnumerable<string> GetDynamicMemberNames()
        
                return Data.Select(x => x.Name);
        

        public override bool TryGetMember(GetMemberBinder binder, out object result)
        

            var dictionary = Data.First(x => x.Name == binder.Name);
            result = dictionary;
            return true;
        

        // each instance of one these should be a nested object type
        public IList<NestedType> Data  get; set;  

        public class NestedType
        
            // How do I make Name be the nest type name?
            public string Name  get; set; 
            public IDictionary<string, string> Values  get; set;  
        

我想为每个 NestedType 实例创建一个嵌套对象/类型。因此,如果有两个 NestedType 实例,那么就会有两个嵌套对象。我可以从 DynamicObject 继承 NestedType 以将字典转换为 NEST 然后正确映射的“真实”属性(即将每个字典键转换为属性)。问题是我不知道如何设置嵌套对象的名称/类型。

我知道有两种映射名称的方法:ElasticType 属性和 NestedObject fluent interface。这里的问题是有一个类型代表多个嵌套对象类型。我可以做一些运行时类型的构建,但如果可以避免的话,我宁愿不做。

有没有办法将方法或属性用作嵌套对象的名称/类型?或者是否有更好的方法将此类数据映射到 ElasticSearch(希望通过 NEST)?

谢谢! 埃里克

编辑

我更新了实体定义以反映我正在做的事情(使用 DynamicObject 让 JsonSerializer 做我想做的事)。我想要的是不同字典具有不同映射的能力(不同的词干、分析器等)。如果有合适的类型,我可以使用 NEST 流式语法来设置它,但是当使用动态时,流式 API 没有类型可以使用。最终,我想将流式 API 与基于字符串而不是类型的字符串混合。这有意义吗?

【问题讨论】:

您能否提供一个输入示例,以及您希望在 ES 中拥有什么?谢谢 一个示例映射会很有帮助。您能否给我们一个自定义的 json 转换器属性,例如:***.com/questions/29173196/… 【参考方案1】:

如果我正确理解您的意图,Entity 对象中将只有嵌套对象,不是吗?

您可以尝试使用elasticsearch 的dynamic mapping 功能来搜索实体对象。我假设 Entity 是一个根对象。

curl -X POST localhost:9200/myindex/entity/_mapping
"dynamic_templates": [
    "nested_data_template": 
        "mapping": 
            "type": "nested" ,
        "match_mapping_type": "object",
        "path_match": "*" ]

path_match: *match_mapping_type: object 表示对于所有以对象为值的字段名称都将应用嵌套类型映射。

使用 NEST 和 Fluent API,您可以使用以下 API。 IntelliSense 将指导您如何构建上面的映射。 ;)

descriptor.DynamicTemplates(DynamicTemplatesDescriptor<Entity>)

每当出现与该模板匹配的新属性时,elasticsearch 都会根据动态映射更新映射。一段时间后,您的映射将如下所示:


  "entity": 
    "mappings": 
      "entity": 
        "dynamic_templates": [
          
            "nested_data_template": 
              "mapping": 
                "type": "nested"
              ,
              "match_mapping_type": "object",
              "path_match": "*"
            
          
        ],
        "properties": 
          "test": 
            "type": "nested",
            "properties": 
              "test": 
                "type": "string"
              ,
              "another_property": 
                "type": "string"
              
            
          ,
          "test1": 
            "type": "nested",
            "properties": 
              "test": 
                "type": "string"
              
            
          
        
      
    
  

希望这会有所帮助!

【讨论】:

啊,我不知道动态模板方法。这有助于我前进 - 谢谢!

以上是关于如何将单个 .NET 类型映射到 ElasticSearch/NEST 中的多个嵌套对象类型?的主要内容,如果未能解决你的问题,请参考以下文章

将 Windows 数据类型映射到 .NET

将 .NET 类型映射到 SQL Server 200 数据类型

如何将多个值类型集合映射到 Hibernate 中的一个表?

如何将 ASP.NET FormView 绑定到单个记录?

如何将范围列表映射到单个值?

如何将单个属性映射到多个 XmlElementAttribute 以进行序列化?