【问题标题】:elasticsearch-painless - Manipulate dateelasticsearch-painless - 操作日期
【发布时间】:2017-08-24 14:25:49
【问题描述】:

我正在尝试使用 elasticsearch 的脚本语言 painless 来操作日期。 具体来说,我尝试增加 4 小时,即 14,400 秒。

{
  "script_fields": {
    "new_date_field": {
      "script": {
        "inline": "doc['date_field'] + 14400"
      }
    }
  }
}

这会抛出Cannot apply [+] operation to types [org.elasticsearch.index.fielddata.ScriptDocValues.Longs] and [java.lang.Integer].

谢谢

【问题讨论】:

    标签: elasticsearch elasticsearch-painless


    【解决方案1】:

    解决方案是使用.value

    {
      "script_fields": {
        "new_date_field": {
          "script": {
            "inline": "doc['date_field'].value + 14400"
          }
        }
      }
    }
    

    但是,我实际上想将它用于重新索引,其中格式有点不同。 这是我在_reindex api 中操纵时间的版本

    POST _reindex
    {
      "source": {
        "index": "some_index_v1"
      },
      "dest": {
        "index": "some_index_v2"
      },
      "script": {
        "inline": "def sf = new SimpleDateFormat(\"yyyy-MM-dd'T'HH:mm:ss\"); def dt = sf.parse(ctx._source.date_field); def calendar = sf.getCalendar(); calendar.setTime(dt); def instant = calendar.toInstant(); def localDateTime = LocalDateTime.ofInstant(instant, ZoneOffset.UTC); ctx._source.date_field = localDateTime.plusHours(4);"
      }
    }
    

    这是可读版本的内联脚本

    def sf = new SimpleDateFormat(\"yyyy-MM-dd'T'HH:mm:ss\");
    def dt = sf.parse(ctx._source.date_field);
    def calendar = sf.getCalendar();
    calendar.setTime(dt);
    def instant = calendar.toInstant();
    def localDateTime = LocalDateTime.ofInstant(instant, ZoneOffset.UTC);
    ctx._source.date_field = localDateTime.plusHours(4);
    

    Here是painless支持的功能列表,很痛苦。

    【讨论】:

    • 这对我处理带有小数秒的日期字符串格式 (2018-05-28T13:49:40.03Z) 非常有帮助。到 repo 的链接帮助我了解到 java.time 类(尤其是 Instant)在无痛脚本中得到支持,因此我可以编写 def existLastSeen = Instant.parse(ctx._source.last_seen_ts); def thisLastSeen = Instant.parse(params.last_seen_ts); if (thisLastSeen.isAfter(existLastSeen)) { ctx._source.last_seen_ts = params.last_seen_ts; }
    • 感谢无痛支持功能的链接,非常有用!
    • 由于某种原因,日期格式中 T 字符周围的单引号在被 ES 读取时会被剥离。我正在使用def df = DateTimeFormatter.ofPattern(\"yyyy-MM-dd'T'HH:mm:ss\");
    • 很痛苦!
    【解决方案2】:

    一个补充。将日期转换为字符串,我相信您的第一部分可以通过以下方式完成:

    def dt = String.valueOf(ctx._source.date_field);
    

    刚刚花了几个小时玩这个..所以我可以连接一个日期字段(以UTC格式添加00:00:00)..到一个带有时间的字符串,以获得一个有效的日期时间添加到ES。不要问它为什么被拆分。它是一个旧的 Oracle 系统

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2018-06-13
      • 2021-12-04
      • 2022-10-13
      • 1970-01-01
      • 1970-01-01
      • 2021-12-18
      • 2017-08-17
      • 2015-05-06
      相关资源
      最近更新 更多