55

弹性搜索专家,

我一直无法找到一种简单的方法来告诉 ElasticSearch 为所有索引(和所有文档类型)中添加的所有文档插入 _timestamp 字段。

我看到了特定类型的示例: http ://www.elasticsearch.org/guide/reference/mapping/timestamp-field/

并查看特定类型的所有索引的示例(使用 _all): http ://www.elasticsearch.org/guide/reference/api/admin-indices-put-mapping/

但我找不到任何关于默认添加它的文档,无论索引和类型如何,所有添加的文档都是如此。

4

6 回答 6

57

Elasticsearch 曾经支持自动为被索引的文档添加时间戳,但在 2.0.0 中弃用了此功能

从版本 5.5文档

_timestamp 和 _ttl 字段已被弃用,现在已被删除。作为 _timestamp 的替代,您应该使用应用程序端的当前时间戳填充常规日期字段

于 2017-04-20T13:36:16.087 回答
48

您可以通过在创建索引时提供它来做到这一点。

$curl -XPOST localhost:9200/test -d '{
"settings" : {
    "number_of_shards" : 1
},
"mappings" : {
    "_default_":{
        "_timestamp" : {
            "enabled" : true,
            "store" : true
        }
    }
  }
}'

然后,它将为您放入索引中的所有内容自动创建一个_timestamp 。然后在请求 _timestamp 字段时索引某些内容后,它将被返回。

于 2013-06-17T11:13:40.417 回答
19

添加另一种获取索引时间戳的方法。希望这可以帮助某人。

摄取管道可用于在文档被索引时添加时间戳。这是一个示例:

PUT _ingest/pipeline/indexed_at
{
  "description": "Adds indexed_at timestamp to documents",
  "processors": [
    {
      "set": {
        "field": "_source.indexed_at",
        "value": "{{_ingest.timestamp}}"
      }
    }
  ]
}

早些时候,弹性搜索使用命名管道,因为需要在用于编写/索引文档的弹性搜索端点中指定“管道”参数。(参考:链接)这有点麻烦,因为您需要在应用程序端对端点进行更改。

在弹性搜索版本 >= 6.5 的情况下,您现在可以使用index.default_pipeline设置为索引指定默认管道。(详情参考链接

这是设置默认管道:

PUT ms-test/_settings
{
  "index.default_pipeline": "indexed_at"
}

我还没有尝试过,因为没有升级到 ES 6.5,但是上面的命令应该可以工作。

于 2019-03-29T09:32:37.967 回答
5

您可以利用默认索引管道,利用脚本处理器,从而模拟auto_now_add您可能从DjangoSQL了解的功能。DEFAULT GETDATE()

添加默认yyyy-MM-dd HH:mm:ss日期的过程如下所示:

1. 创建管道并指定允许在哪些索引上运行:

PUT _ingest/pipeline/auto_now_add
{
  "description": "Assigns the current date if not yet present and if the index name is whitelisted",
  "processors": [
    {
      "script": {
        "source": """
          // skip if not whitelisted
          if (![ "myindex",
                 "logs-index",
                 "..."
              ].contains(ctx['_index'])) { return; }
          
          // don't overwrite if present
          if (ctx['created_at'] != null) { return; }
          
          ctx['created_at'] = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss").format(new Date());
        """
      }
    }
  ]
}

旁注:摄取处理器的无痛脚本上下文在此处记录。

2. 更新所有索引default_pipeline中的设置:

PUT _all/_settings
{
  "index": {
    "default_pipeline": "auto_now_add"
  }
}

旁注:您可以使用多目标语法限制目标索引:

PUT myindex,logs-2021-*/_settings?allow_no_indices=true
{
  "index": {
    "default_pipeline": "auto_now_add"
  }
}

3. 将文档摄取到配置的索引之一:

PUT myindex/_doc/1
{
  "abc": "def"
}

4. 验证是否已添加日期字符串:

GET myindex/_search
于 2021-04-05T18:53:35.380 回答
1

Python 3 中 ElasticSearch 6.6.2 的示例:

from elasticsearch import Elasticsearch

es = Elasticsearch(hosts=["localhost"])

timestamp_pipeline_setting = {
  "description": "insert timestamp field for all documents",
  "processors": [
    {
      "set": {
        "field": "ingest_timestamp",
        "value": "{{_ingest.timestamp}}"
      }
    }
  ]
}

es.ingest.put_pipeline("timestamp_pipeline", timestamp_pipeline_setting)

conf = {
    "settings": {
        "number_of_shards": 2,
        "number_of_replicas": 1,
        "default_pipeline": "timestamp_pipeline"
    },
    "mappings": {
        "articles":{
            "dynamic": "false",
            "_source" : {"enabled" : "true" },
            "properties": {
                "title": {
                    "type": "text",
                },
                "content": {
                    "type": "text",
                },
            }
        }
    }
}

response = es.indices.create(
    index="articles_index",
    body=conf,
    ignore=400 # ignore 400 already exists code
)

print ('\nresponse:', response) 

doc = {
    'title': 'automatically adding a timestamp to documents',
    'content': 'prior to version 5 of Elasticsearch, documents had a metadata field called _timestamp. When enabled, this _timestamp was automatically added to every document. It would tell you the exact time a document had been indexed.',
}
res = es.index(index="articles_index", doc_type="articles", id=100001, body=doc)
print(res)

res = es.get(index="articles_index", doc_type="articles", id=100001)
print(res)

关于 ES 7.x,该示例在删除 doc_type 相关参数后应该可以工作,因为它不再受支持。

于 2020-08-06T08:53:13.633 回答
0

首先创建索引和索引的属性,例如字段和数据类型,然后使用其余 API 插入数据。

下面是使用字段属性创建索引的方法。在 kibana 控制台中执行以下操作

`PUT /vfq-jenkins
{
"mappings": {
"properties": {
"BUILD_NUMBER": { "type" : "double"},
"BUILD_ID" : { "type" : "double" },
"JOB_NAME" : { "type" : "text" },
"JOB_STATUS" : { "type" : "keyword" },
"time" : { "type" : "date" }
 }}}`    

下一步是将数据插入该索引:

curl -u elastic:changeme -X POST http://elasticsearch:9200/vfq-jenkins/_doc/?pretty 
-H Content-Type: application/json -d '{ 
"BUILD_NUMBER":"83","BUILD_ID":"83","JOB_NAME":"OMS_LOG_ANA","JOB_STATUS":"SUCCESS" , 
"time" : "2019-09-08'T'12:39:00" }'
于 2019-09-07T23:52:01.383 回答