【问题标题】:How do implement Elasticsearch Suggester?如何实现 Elasticsearch Suggester?
【发布时间】:2020-09-10 11:36:35
【问题描述】:

我正在尝试实现一个使用 Elastic Search 中的建议功能的示例代码。

索引文档由平面 POCO 组成

public class CandidateDocument
{
    public Guid Id { get; set; }
    public string Name { get; set; }
    public string FirstName { get; set; }
    public DateTime BirthDate { get; set; }
    public CompletionField Suggest { get; set; }
}

映射如下

var client = new ElasticClient(settings);

client.Indices.Create("candidates", c =>
                                           c.Map<CandidateDocument>(m =>
                                                            m.Properties(ps => ps.Text(s => s.Name(n => n.Name)
                                                                                             .Store(false)
                                                                                             .Fields(f => f.Keyword(k => k.Name("nameRaw"))))
                                                                                 .Text(s => s.Name(n => n.FirstName)
                                                                                             .Store(false)
                                                                                             .Fields(f => f.Keyword(k => k.Name("firstNameRaw"))
                                                                                 
                                                                                 .Date(s => s.Name(n => n.BirthDate).Format("ddMMyyyy"))
                                                                                 .Keyword(s => s.Name(n => n.Id))))
                                                                               
                                                                                 .Completion(c => c.Name(n => n.Suggest)))));

索引文档如下所示:

 var candidateDocument = new CandidateDocument
        {
            Id = Guid.NewGuid(),
            Name = "Lennon",
            FirstName = "John",
            BirthDate = DateTime.Now,
            Suggest = new CompletionField
            {
                Input = new[] { "Lennon" },
            }
        };

    var indexResponse = await this.elasticClient.IndexAsync(candidateDocument, i => i.Index("candidates"));

我的查询是:

var searchResponse = await this.elasticClient.SearchAsync<CandidateDocument>(s => s.Index("candidates").Suggest(su => su
                                                                                                       .Completion("suggestions", c => c
                                                                                                                                        .Field(f => f.Suggest)
                                                                                                                                        .Prefix(query)
                                                                                                                                        .Fuzzy(f => f.Fuzziness(Fuzziness.Auto))
                                                                                                                                        .Size(5))));

我面临以下问题:

Elasticsearch.Net.ElasticsearchClientException:请求执行失败。呼叫:状态代码 400 来自:POST /candidates/_search?typed_keys=true。 ServerError:类型:search_phase_execution_exception 原因:“所有分片失败” CausedBy:“类型:非法参数异常原因:“未找到字段 [建议] 的映射” CausedBy:“类型:非法参数异常原因:“未找到字段 [建议] 的映射”

查看我使用 kibana 的索引映射:

      "suggest": {
      "properties": {
        "input": {
          "type": "text",
          "fields": {
            "keyword": {
              "type": "keyword",
              "ignore_above": 256
            }
          }
        }
      }
    }

顺便说一句,我在 .NET Core 3.1 中使用的是最新版本的 Nest (7.9.0)

感谢您的帮助。

【问题讨论】:

    标签: c# asp.net-core elasticsearch nest


    【解决方案1】:

    有同样的问题,通过显式映射解决:

    _elasticClient.Indices.Create("candidates", c => c
     .Map<CandidateDocument>(m => m
         .Properties(ps => ps
             .Completion(s => s
                 .Name(n => n.Suggest)))));
    
    public class CandidateDocument
    {        
        public Guid? Id { get; set; }
        public CompletionField Suggest { get; set; }
    }
    

    【讨论】:

      【解决方案2】:

      看起来像候选索引和建议字段可能在发出带有映射请求的创建索引时已经存在。您可以检查返回的CreateIndexResponse 是否是这种情况; IsValid 属性将为 false,响应中的错误详细信息提供了原因。

      Elasticsearch 的默认行为将创建一个索引和映射,如果一个索引请求进来将一个文档索引到其中,根据它看到的第一个文档推断字段的映射。这对于许多用例来说都是有用的行为,但对于搜索用例,您通常希望在执行时使用显式映射来控制索引的创建,因此要关闭此行为,您可以设置 action.auto_create_index cluster setting to false.。现在,如果您删除索引并使用您拥有的创建索引请求重新创建它,它不会在您有机会显式创建它之前自动创建。

      【讨论】:

        【解决方案3】:

        你是对的,映射定义是在索引不是从我描述的映射定义创建的文档时创建的。 检查 CreateIndexResponse IsValid 属性表明您预期的问题。

        我花了一些时间找出根本问题:我使用的是 ES Docker 映像版本 6.3.0 和 Nest 客户端 7.* 使我的 ES 与我的 Nest 客户端兼容解决了这个问题。

        感谢您的帮助。

        【讨论】:

          猜你喜欢
          • 2015-12-07
          • 2021-01-24
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 2015-07-08
          • 2019-07-28
          • 2018-07-20
          • 1970-01-01
          相关资源
          最近更新 更多