Ver Fonte

fix: missing fields in range aggregation response for date fields (#82732)

When running a range aggregation on a date field both `fromAsStr` and
`toAsStr` need to be parsed to extract the correct range boundaries.
Not doing so results in +/- infinite values in `to`, `from`, `originalTo`
and `originalFrom` which in turn result in:
* incorrect key values (wildcard character used for infinite values);
* missing fields in the response (to, from, to_as_string, from_as_string)
  due to checks for initite values in the serialization logic;
Salvatore Campagna há 3 anos atrás
pai
commit
1186e90d09

+ 64 - 0
rest-api-spec/src/yamlRestTest/resources/rest-api-spec/test/search.aggregation/40_range.yml

@@ -16,6 +16,18 @@ setup:
                 half_float:
                   type: half_float
 
+  - do:
+      indices.create:
+        index: date_range_test
+        body:
+          settings:
+            number_of_replicas: 0
+          mappings:
+            properties:
+              date:
+                type: date
+                format: strict_date_time||strict_date
+
   - do:
       cluster.health:
         wait_for_status: yellow
@@ -35,6 +47,22 @@ setup:
          - {"index": {}}
          - {}
 
+  - do:
+      bulk:
+        index: date_range_test
+        refresh: true
+        body:
+          - { "index": { } }
+          - { "date": "2021-05-01T07:10:00Z" }
+          - { "index": { } }
+          - { "date": "2021-05-02T08:34:00Z" }
+          - { "index": { } }
+          - { "date": "2021-05-03T08:36:00Z" }
+          - { "index": { } }
+          - { "date": "2021-05-04T09:05:00Z" }
+          - { "index": { } }
+          - { "date": "2021-05-06T09:22:00Z" }
+
 ---
 "Float Endpoint Exclusive":
   - skip:
@@ -42,6 +70,7 @@ setup:
       reason:  Bug fixed in 7.16.0
   - do:
       search:
+        index: test
         body:
           size: 0
           aggs:
@@ -70,6 +99,7 @@ setup:
       reason:  Bug fixed in 7.16.0
   - do:
       search:
+        index: test
         body:
           size: 0
           aggs:
@@ -98,6 +128,7 @@ setup:
       reason: Bug fixed in 8.1.0 and backported to 7.17.0
   - do:
       search:
+        index: test
         body:
           size: 0
           aggs:
@@ -136,6 +167,7 @@ setup:
       reason: Bug fixed in 8.1.0 and backported to 7.17.0
   - do:
       search:
+        index: test
         body:
           size: 0
           aggs:
@@ -171,6 +203,7 @@ setup:
 "Double range no decimal":
   - do:
       search:
+        index: test
         body:
           size: 0
           aggs:
@@ -206,6 +239,7 @@ setup:
 "Double range with missing value":
   - do:
       search:
+        index: test
         body:
           size: 0
           aggs:
@@ -242,6 +276,7 @@ setup:
 "Null to and from":
   - do:
       search:
+        index: test
         body:
           size: 0
           aggs:
@@ -279,6 +314,7 @@ setup:
 "Range agg on long field":
   - do:
       search:
+        index: test
         body:
           size: 0
           aggs:
@@ -314,6 +350,7 @@ setup:
 "Double range default keyed response":
   - do:
       search:
+        index: test
         body:
           size: 0
           aggs:
@@ -345,3 +382,30 @@ setup:
   - match: { aggregations.double_range.buckets.last.from: 150.0 }
   - is_false:  aggregations.double_range.buckets.last.to
   - match: { aggregations.double_range.buckets.last.doc_count: 0 }
+
+---
+"Range aggregation on date field":
+  - skip:
+      version: " - 8.0.99"
+      reason: Fixed in 8.1.0
+
+  - do:
+      search:
+        index: date_range_test
+        body:
+          size: 0
+          aggs:
+            date_range:
+              range:
+                field: date
+                ranges:
+                  { from: 2021-05-01T00:00:00Z, to: 2021-05-05T00:00:00Z }
+
+  - match: { hits.total.value: 5 }
+  - length: { aggregations.date_range.buckets: 1 }
+  - match: { aggregations.date_range.buckets.0.doc_count: 4 }
+  - match: { aggregations.date_range.buckets.0.key: "2021-05-01T00:00:00.000Z-2021-05-05T00:00:00.000Z" }
+  - match: { aggregations.date_range.buckets.0.from: 1619827200000 }
+  - match: { aggregations.date_range.buckets.0.from_as_string: "2021-05-01T00:00:00.000Z" }
+  - match: { aggregations.date_range.buckets.0.to: 1620172800000 }
+  - match: { aggregations.date_range.buckets.0.to_as_string: "2021-05-05T00:00:00.000Z" }

+ 4 - 2
server/src/main/java/org/elasticsearch/search/aggregations/bucket/range/RangeAggregationBuilder.java

@@ -171,8 +171,10 @@ public class RangeAggregationBuilder extends AbstractRangeBuilder<RangeAggregati
             if (range.toAsStr != null) {
                 to = parser.parseDouble(range.toAsStr, false, context::nowInMillis);
             }
-            String key = range.key != null ? range.key : generateKey(range.originalFrom, range.originalTo, config.format());
-            return new Range(key, from, range.from, range.fromAsStr, to, range.to, range.toAsStr);
+            double originalFrom = range.fromAsStr != null ? from : range.from;
+            double originalTo = range.toAsStr != null ? to : range.to;
+            String key = range.key != null ? range.key : generateKey(originalFrom, originalTo, config.format());
+            return new Range(key, from, originalFrom, range.fromAsStr, to, originalTo, range.toAsStr);
         });
         if (ranges.length == 0) {
             throw new IllegalArgumentException("No [ranges] specified for the [" + this.getName() + "] aggregation");