# 【Datatable】Top hits Aggregationに関して

**URL:** <https://discuss.elastic.co/t/datatable-top-hits-aggregation/237414>\
**Category:** 日本語による質問・議論はこちら\
**Created:** [June 17, 2020, 7:37am UTC](https://discuss.elastic.co/t/datatable-top-hits-aggregation/237414 "2020-06-17T07:37:54Z")\
**Posts on this page:** 3\
**Page:** 1

<div class="post-metadata">

**Author:** ![harue](https://avatars.discourse-cdn.com/v4/letter/h/82dd89/32.png) [@harue](https://discuss.elastic.co/u/harue)\
**Post date:** [June 17, 2020, 7:37am UTC](https://discuss.elastic.co/t/datatable-top-hits-aggregation/237414/1 "2020-06-17T07:37:54Z")

</div>

お世話になります。  
以前質問させて頂いた、DatatableのTop hits Aggregationに関して再度質問させて頂きます。

> [@【ダッシュボード】重複行を1行にまとめて表示する方法](https://discuss.elastic.co/t/topic/236829):
>
> お世話になります。 以下のように"id"と"time"が存在するindexがあります。 id time 1 2020/6/1 10:00 1 2020/6/1 11:00 1 2020/7/1 11:00 2 2020/6/1 12:00 2 2020/6/1 12:00 3 2020/7/1 12:00 上記indexに関して、同じidの中でtimeが最も過去の日付のデータのみ、 ダッシュボードに一覧で表示させたい(下記例)のですが、実現可能でしょうか？ Discoverにて実現方法が分からず質問させて頂きました。 id time 1 2020/6/1 10:00 2 2020/6/1 12:00 3 2020/7/1 12:00 お手数ですが、回答頂けますと幸いです。 以上、宜しくお願い致します。

▼実現したいこと  
下記indexデータにおいて  
同一のnameの中でtimeが最も過去日付のデータのみ、Datatableに表示

▼indexデータ  
index patternの時間フィルター：timeを設定

| name | id | time | |
| --- | --- | --- | --- |
| AAA | 1 | Jun 1, 2020 @ 10:00:00.000 | …① |
| AAA | 1 | Feb 1, 2020 @ 10:00:00.000 | …② |

▼Datatableの設定値

 ![test1](https://us1.discourse-cdn.com/elastic/original/3X/5/0/503afcfc82cb07d7167e045549d9c3f627df2229.png)  
 ![test2](https://us1.discourse-cdn.com/elastic/original/3X/c/e/ced11adfb64272a470ea446b26df1569c301c5b8.png)  
 ![test3](https://us1.discourse-cdn.com/elastic/original/3X/1/b/1b4c7c064b3575a42207d5f32642b1bd133de6d7.png)

▼Datatableの取得結果  
1.time filterが1月(Jan 1, 2020 @ 00:00:00.000～Jan 31, 2020 @ 23:59:59.999)の場合

| name | id | time | |
| --- | --- | --- | --- |
| AAA | 1 | Jun 1, 2020 @ 10:00:00.000 | …① |

2.time filterが2月(Feb 1, 2020 @ 00:00:00.000～Feb 29, 2020 @ 23:59:59.999)の場合

| name | id | time | |
| --- | --- | --- | --- |
| AAA | 1 | Feb 1, 2020 @ 10:00:00.000 | …② |

◆ご質問  
indexの全体期間を対象とすると①が最も過去日付のため、2.の場合は②を表示させないようにしたいです。

dataTableのtime filter(timeが時間軸)が2月データを対象としているため、②が表示される(①は対象外)のですが、  
top hit aggregationの取得期間は全体期間かつdataTableのtime filterは対象月を指定する方法はありますでしょうか？

お手数ですが、回答頂けますと幸いです。  
以上、宜しくお願い致します。

---

<div class="post-metadata">

**Author:** ![Koji\_Kawamura](https://sea2.discourse-cdn.com/elastic/user_avatar/discuss.elastic.co/koji_kawamura/32/93938_2.png) [@Koji\_Kawamura](https://discuss.elastic.co/u/Koji_Kawamura)\
**Post date:** [July 14, 2020, 8:44am UTC](https://discuss.elastic.co/t/datatable-top-hits-aggregation/237414/2 "2020-07-14T08:44:39Z")

</div>

@harue さん、  
なかなか難しいですね、Data Tableでの実現方法は思いつきませんでした。できないと思います。ちょっとデータテーブルとは表示結果が異なりますが、Vegaならやりたいことはできそうです。ご参考になれば幸いです。

まず、こちらは 次のデータセットで試しました:

```auto
POST forum_237414/_bulk
{"index":{"_id":"1"}}
{"name":"A","time":"2020-01-01T10:00:00+09:00"}
{"index":{"_id":"2"}}
{"name":"A","time":"2020-01-01T20:00:00+09:00"}
{"index":{"_id":"3"}}
{"name":"A","time":"2020-02-01T10:00:00+09:00"}
{"index":{"_id":"4"}}
{"name":"A","time":"2020-02-01T20:00:00+09:00"}
{"index":{"_id":"5"}}
{"name":"B","time":"2020-02-10T10:00:00+09:00"}
{"index":{"_id":"6"}}
{"name":"B","time":"2020-02-20T20:00:00+09:00"}

```

上記データセットを使った際のVega描画結果が以下になります。  
まず、タイムピッカーで全データセットを範囲内に収めた場合です。

 ![image](https://us1.discourse-cdn.com/elastic/original/3X/5/a/5a568fe5fd085bff93799d772e1f98a4937d1fdd.png)

ここでは`A`, `B`共に、それぞれの一番古い日付が表示できています。

次に、タイムピッカーで、`A`の最も古い日付は範囲外だが、それ以外の日付は範囲内に存在するケースです。これが本質問で非表示にされたいケースだと思います。`B`については最も古い日付が範囲内に収まっているので、表示されています。

 ![image](https://us1.discourse-cdn.com/elastic/original/3X/2/9/2981bd859a73420d45a0b81da848eeca68b20551.png)

今回の例では意図的に`A`のレコードは描画したまま、日付のみ`not found`としました。レコードを描画しないことも可能です。

データテーブルと見え方は違えど、やりたいことはこれでできるかな、と思います。あとは見せ方を調整してもう少し表っぽくみせたり、場合によってはX軸の時系列をうまく使って、表形式よりも分かりやすい可視化が可能かもしれません。

この例では以下のVega Liteスペックを書いてみました。ポイントは:

- `query`は記述せず、フィルタリングしないで全データセットを使って`oldest`アグリゲーションを実行している
- 最も古いタイムスタンプを探すのは `terms` を使う。ここで `top_hits` を使ってしまうと、それ以上何もできないので
- その後、Kibana Vegaのタイムピッカーマッピング `{"%timefilter%": "min"}` とmaxを使って最終データを絞り込みます。
- 最後に、`top_hits`で該当ドキュメントを取得
- 対象外となった場合、`calculate` を使って `not found` としていますが、ここで `filter` を使えばレコード自体を非表示にすることも可能と思います

```auto
{
  "$schema": "https://vega.github.io/schema/vega-lite/v2.json",
  "title": "全日付範囲でaggしつつ結果はTimeFilterで絞る",
  "data": {
    "url": {
      "index": "forum_237414",
      "body": {
        "size": 0,
        "aggs": {
          "by_name": {
            "terms": {"field": "name.keyword", "size": 10},
            "aggs": {
              "oldest": {
                "terms": {"size": 1, "field": "time", "order": {"_key": "asc"}},
                "aggs": {
                  "timefilter": {
                    "filter": {
                      "range": {
                        "time": {
                          "gte": {"%timefilter%": "min"},
                          "lt": {"%timefilter%": "max"}
                        }
                      }
                    },
                    "aggs": {"timefiltered": {"top_hits": {"size": 1}}}
                  }
                }
              }
            }
          }
        }
      }
    },
    "format": {"property": "aggregations.by_name.buckets"}
  },
  "transform": [
    {
      "calculate": "datum.oldest.buckets[0].timefilter.timefiltered.hits.total.value > 0 ? datum.oldest.buckets[0].timefilter.timefiltered.hits.hits[0] : null",
      "as": "timefiltered"
    },
    {
      "calculate": "datum.timefiltered ? datum.timefiltered._source.time : 'not found'",
      "as": "time"
    }
  ],
  "encoding": {
    "y": {"field": "key", "type": "ordinal", "axis": {"title": "name"}}
  },
  "layer": [
    {
      "mark": {"type": "point", "filled": true, "size": 100},
      "encoding": {
        "x": {
          "field": "oldest.buckets[0].timefilter.timefiltered.hits.hits[0]._source.time",
          "type": "temporal",
          "axis": {"title": false, "grid": false}
        }
      }
    },
    {"mark": "text", "encoding": {"text": {"field": "time", "type": "nominal"}}}
  ]
}

```

---

<div class="post-metadata">

**Author:** ![system](https://us1.discourse-cdn.com/elastic/original/3X/1/a/1ac57faf039f6b580b3f104ef42a2a89e41014de.png) [@system](https://discuss.elastic.co/u/system)\
**Post date:** [August 11, 2020, 8:44am UTC](https://discuss.elastic.co/t/datatable-top-hits-aggregation/237414/3 "2020-08-11T08:44:41Z")

</div>

This topic was automatically closed 28 days after the last reply. New replies are no longer allowed.
