简体   繁体   English

Elasticsearch 2.x索引映射_id

[英]Elasticsearch 2.x index mapping _id

I ran ElasticSearch 1.x (happily) for over a year. 我(愉快地)运行ElasticSearch 1.x一年以上。 Now it's time for some upgrading - to 2.1.x. 现在是时候进行一些升级了-升级到2.1.x。 The nodes should be turned off and then (one-by-one) on again. 应该关闭节点,然后再(一对一)打开节点。 Seems easy enough. 似乎很容易。
But then I ran into troubles. 但是后来我遇到了麻烦。 The major problem is the field _uid , which I created myself so that I knew the exact location of a document from a random other one (by hashing a value). 主要问题是字段_uid ,我创建了自己的字段,以便我从另一个随机对象(通过散列值)知道文档的确切位置。 This way I knew that only that the exact one will be returned. 这样,我知道只有确切的一个将被返回。 During upgrade I got 升级期间我得到了

MapperParsingException[Field [_uid] is a metadata field and cannot be added inside a document. Use the index API request parameters.]

But when I try to map my former _uid to _id (which should also be good enough) I get something similar. 但是,当我尝试将以前的_uid映射到_id (这也应该足够好)时,我会得到类似的结果。

The reason why I used the _uid param is because the lookup time is a lot lower than a termsQuery (or the like). 我之所以使用_uid参数,是因为查找时间比termsQuery(或类似查询)低很多。
How can I still use the _uid or _id field in each document for the fast (and exact) lookup of certain exact documents? 我如何仍可以在每个文档中使用_uid_id字段来快速(精确)查找某些特定文档? Note that I have to call thousands exact ones at the time, so I need an ID like query. 请注意,我必须一次调用成千上万个确切的名称,因此我需要一个类似于查询的ID。 Also it may occur the _uid or _id of the document does not exist (in that case I want, like now, a 'false-like' result) 也可能会出现文档的_uid_id不存在(在那种情况下,我想要像现在一样,出现“假”结果)

Note: The upgrade from 1.x to 2.x is pretty big (Filters gone, no dots in names, no default access to _xxx ) 注意:从1.x到2.x的升级相当大(过滤器消失了,名称中没有点,没有对_xxx默认访问_xxx

Update (no avail): 更新(无济于事):
Updating the mapping of _uid or _id using: 使用以下命令更新_uid_id的映射:

final XContentBuilder mappingBuilder = XContentFactory.jsonBuilder().startObject().startObject(type).startObject("_id").field("enabled", "true").field("default", "xxxx").endObject()
            .endObject().endObject();
 CLIENT.admin().indices().prepareCreate(index).addMapping(type, mappingBuilder)
                .setSettings(Settings.settingsBuilder().put("number_of_shards", nShards).put("number_of_replicas", nReplicas)).execute().actionGet();

results in: 结果是:

MapperParsingException[Failed to parse mapping [XXXX]: _id is not configurable]; nested: MapperParsingException[_id is not configurable];

Update: Changed name into _id instead of _uid since the latter is build out of _type # _id . 更新:将名称更改为_id而不是_uid因为后者是根据_type_id构建的。 So then I'd need to be able to write to _id . 因此,我需要能够写入_id

Since there appears to be no way around setting the _uid and _id I'll post my solution. 由于似乎没有办法设置_uid_id我将发布解决方案。 I mapped all document which had a _uid to uid (for internal referencing). 我将所有具有_uid文档映射到uid (用于内部引用)。 At some point it came to me, you can set the relevant id 在某个时候,您可以设置相关id

To bulk insert document with id you can: 要批量插入id文档,您可以:

final BulkRequestBuilder builder = client.prepareBulk();
for (final Doc doc : docs) {
    builder.add(client.prepareIndex(index, type, doc.getId()).setSource(doc.toJson()));
}
final BulkResponse bulkResponse = builder.execute().actionGet();

Notice the third argument, this one may be null (or be a two valued argument, then the id will be generated by ES). 注意第三个参数,这个参数可以为null (或者是两个值的参数,然后id将由ES生成)。
To then get some documents by id you can: 要通过id获取一些文档,您可以:

final List<String> uids = getUidsFromSomeMethod(); // ids for documents to get
final MultiGetRequestBuilder builder = CLIENT.prepareMultiGet();
builder.add(index_name, type, uids);
final MultiGetResponse multiResponse = builder.execute().actionGet();
// in this case I simply want to know whether the doc exists
if (only_want_to_know_whether_it_exists){
    for (final MultiGetItemResponse response : multiResponse.getResponses()) {
        final boolean exists = response.getResponse().isExists();
        exist.add(exists);
    }
} else {
    // retrieve the doc as json
    final String string = builder.getSourceAsString();
    // handle JSON
}

If you only want 1: 如果只想要1:

client.prepareGet().setIndex(index).setType(type).setId(id);

Doing - the single update - using curl is mapping-id-field (note: exact copy): 做-单个更新-使用curlmapping-id-field (注意:精确副本):

# Example documents
PUT my_index/my_type/1
{
  "text": "Document with ID 1"
}

PUT my_index/my_type/2
{
  "text": "Document with ID 2"
}

GET my_index/_search
{
  "query": {
    "terms": {
      "_id": [ "1", "2" ] 
    }
  },
  "script_fields": {
    "UID": {
      "script": "doc['_id']" 
    }
  }
}

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM