使用 java api 配置 elasticsearch 映射

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/23552845/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-13 23:50:54  来源:igfitidea点击:

Configure elasticsearch mapping with java api

javaelasticsearchmappinganalyzer

提问by user3618259

I have a few elasticsearch fields that I don't want to analyze before indexing. I have read that the right way to do this is by altering the index mapping. Right now my mapping looks like this:

我有一些我不想在索引之前分析的 elasticsearch 字段。我已经读到正确的方法是改变索引映射。现在我的映射如下所示:

{
  "test" : {
   "general" : {
      "properties" : {
        "message" : {
          "type" : "string"
        },
        "source" : {
          "type" : "string"
        }
      }
    }
  }
}

And I would like it to look like this:

我希望它看起来像这样:

{
  "test" : {
   "general" : {
      "properties" : {
        "message" : {
          "type" : "string",
          "index" : "not_analyzed"
        },
        "source" : {
          "type" : "string"
        }
      }
    }
  }
}

I have been trying to change the settings via

我一直在尝试通过更改设置

client.admin().indices().prepareCreate("test")
        .setSettings(getGrantSettings());

Where getGrantSettings() looks like:

getGrantSettings() 看起来像:

static Settings getGrantSettings(){
    JSONObject settingSource = new JSONObject();
    try{
        settingSource.put("mapping", new JSONObject()
        .put("message", new JSONObject()
            .put("type", "string")
            .put("index", "not_analyzed")
        ));
    } catch (JSONException e){
        e.printStackTrace();
    }


    Settings set = ImmutableSettings.settingsBuilder()
            .loadFromSource(settingSource.toString()).build();
    return set;
}

回答by Paige Cook

I have successfully applied mappings to an Elasticsearch index using the Java API like the following:

我已经使用 Java API 成功地将映射应用于 Elasticsearch 索引,如下所示:

 XContentBuilder mapping = jsonBuilder()
                              .startObject()
                                   .startObject("general")
                                        .startObject("properties")
                                            .startObject("message")
                                                .field("type", "string")
                                                .field("index", "not_analyzed")
                                             .endObject()
                                             .startObject("source")
                                                .field("type","string")
                                             .endObject()
                                        .endObject()
                                    .endObject()
                                 .endObject();

  PutMappingResponse putMappingResponse = client.admin().indices()
                .preparePutMapping("test")
                .setType("general")
                .setSource(mapping)
                .execute().actionGet();

Hope this helps.

希望这可以帮助。

回答by Charith De Silva

Adding this for future readers. Please note you need to perform mapping prior to create the actual index or you will get an exception. See following code.

为未来的读者添加这个。请注意,您需要在创建实际索引之前执行映射,否则会出现异常。请参阅以下代码。

client.admin().indices().create(new CreateIndexRequest("indexname")).actionGet();

PutMappingResponse putMappingResponse = client.admin().indices()
    .preparePutMapping("indexname")
    .setType("indextype")
    .setSource(jsonBuilder().prettyPrint()
                .startObject()
                    .startObject("indextype")
                        .startObject("properties")
                            .startObject("country").field("type", "string").field("index", "not_analyzed").endObject()
                        .endObject()
                    .endObject()
                .endObject())
    .execute().actionGet();

IndexResponse response1 = client.prepareIndex("indexname", "indextype")
    .setSource(buildIndex())
    .execute()
    .actionGet();   

// Now "Sri Lanka" considered to be a single country :) 
SearchResponse response = client.prepareSearch("indexname"
    ).addAggregation(AggregationBuilders.terms("countryfacet").field("country")).setSize(30).execute().actionGet(); 

回答by neun24

Just read the Definitive Guidecarefully:

只需仔细阅读权威指南

Although you can add to an existing mapping, you can't change existing field mappings. If a mapping already exists for a field, data from that field has probably been indexed. If you were to change the field mapping, the indexed data would be wrong and would not be properly searchable.

尽管您可以添加到现有映射,但您不能更改现有字段映射。如果某个字段的映射已存在,则该字段中的数据可能已被编入索引。如果您要更改字段映射,则索引数据将是错误的并且无法正确搜索。

Source: https://www.elastic.co/guide/en/elasticsearch/guide/current/mapping-intro.html#updating-a-mapping

来源:https: //www.elastic.co/guide/en/elasticsearch/guide/current/mapping-intro.html#updating-a-mapping

So you just have to do it when you create the field. Thats why the code from this answerworks without problems.

因此,您只需在创建字段时执行此操作。这就是为什么这个答案中的代码可以正常工作的原因。

回答by bAZtARd

So, turns out elasticsearch docs are way outdated on that topic. not_analyzed does not exist anymore and string is now text. After some trial and error I came up with this:

因此,事实证明,elasticsearch 文档在该主题上已经过时了。not_analyzed 不再存在,字符串现在是文本。经过一些试验和错误,我想出了这个:

CreateIndexRequest createIndexRequest = new CreateIndexRequest("yourIndexName");
XContentBuilder mapping = jsonBuilder()
                .startObject()
                  .startObject("properties")
                    .startObject("yourProperty")
                      .field("type", "keyword")
                    .endObject()
                  .endObject()
                .endObject();
createIndexRequest.mapping("yourEntityName", mapping);
client.indices().create(createIndexRequest);

Now yourProperty can be queried for exact value only with term query.

现在只能使用 term 查询来查询 yourProperty 的确切值。