You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@pinot.apache.org by ji...@apache.org on 2019/04/23 18:11:25 UTC

[incubator-pinot] branch master updated: [TE] detection - two side threshold filter (#4148)

This is an automated email from the ASF dual-hosted git repository.

jihao pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/incubator-pinot.git


The following commit(s) were added to refs/heads/master by this push:
     new f69e3d3  [TE] detection - two side threshold filter (#4148)
f69e3d3 is described below

commit f69e3d32386066e14a9f40ceba6e3667dd616de1
Author: Jihao Zhang <ji...@linkedin.com>
AuthorDate: Tue Apr 23 11:11:21 2019 -0700

    [TE] detection - two side threshold filter (#4148)
    
    This PR makes it possible to set different threshold in different anomaly pattern in percentage change anomaly filter.
    
    Also, fixing baseline values gathering in rule-based anomaly filters. Previously, the calculation of the baseline values in some anomaly filters only considers the first metric slice's value, which might result in wrong values in some cases.
    
    Unit tests.
---
 .../thirdeye/detection/DefaultDataProvider.java    |  6 +++-
 .../AbsoluteChangeRuleAnomalyFilter.java           | 18 +++-------
 .../PercentageChangeRuleAnomalyFilter.java         | 42 ++++++++++++----------
 .../SitewideImpactRuleAnomalyFilter.java           |  8 ++---
 .../PercentageChangeRuleAnomalyFilterSpec.java     | 20 ++++++++++-
 .../AbsoluteChangeRuleAnomalyFilterTest.java       |  8 ++---
 .../PercentageChangeRuleAnomalyFilterTest.java     | 39 +++++++++++++++-----
 .../SitewideImpactRuleAnomalyFilterTest.java       |  8 ++---
 8 files changed, 93 insertions(+), 56 deletions(-)

diff --git a/thirdeye/thirdeye-pinot/src/main/java/org/apache/pinot/thirdeye/detection/DefaultDataProvider.java b/thirdeye/thirdeye-pinot/src/main/java/org/apache/pinot/thirdeye/detection/DefaultDataProvider.java
index a512974..81b5bd1 100644
--- a/thirdeye/thirdeye-pinot/src/main/java/org/apache/pinot/thirdeye/detection/DefaultDataProvider.java
+++ b/thirdeye/thirdeye-pinot/src/main/java/org/apache/pinot/thirdeye/detection/DefaultDataProvider.java
@@ -42,6 +42,7 @@ import java.util.concurrent.TimeUnit;
 import java.util.stream.Collectors;
 import org.apache.pinot.thirdeye.common.time.TimeGranularity;
 import org.apache.pinot.thirdeye.dataframe.DataFrame;
+import org.apache.pinot.thirdeye.dataframe.LongSeries;
 import org.apache.pinot.thirdeye.dataframe.util.MetricSlice;
 import org.apache.pinot.thirdeye.datalayer.bao.DatasetConfigManager;
 import org.apache.pinot.thirdeye.datalayer.bao.EventManager;
@@ -194,7 +195,10 @@ public class DefaultDataProvider implements DataProvider {
       final long deadline = System.currentTimeMillis() + TIMEOUT;
       Map<MetricSlice, DataFrame> output = new HashMap<>();
       for (MetricSlice slice : slices) {
-        output.put(slice, futures.get(slice).get(makeTimeout(deadline), TimeUnit.MILLISECONDS));
+        DataFrame result = futures.get(slice).get(makeTimeout(deadline), TimeUnit.MILLISECONDS);
+        // fill in time stamps
+        result.dropSeries(COL_TIME).addSeries(COL_TIME, LongSeries.fillValues(result.size(), slice.getStart())).setIndex(COL_TIME);
+        output.put(slice, result);
       }
       return output;
 
diff --git a/thirdeye/thirdeye-pinot/src/main/java/org/apache/pinot/thirdeye/detection/components/AbsoluteChangeRuleAnomalyFilter.java b/thirdeye/thirdeye-pinot/src/main/java/org/apache/pinot/thirdeye/detection/components/AbsoluteChangeRuleAnomalyFilter.java
index 27ec5f4..6e4618d 100644
--- a/thirdeye/thirdeye-pinot/src/main/java/org/apache/pinot/thirdeye/detection/components/AbsoluteChangeRuleAnomalyFilter.java
+++ b/thirdeye/thirdeye-pinot/src/main/java/org/apache/pinot/thirdeye/detection/components/AbsoluteChangeRuleAnomalyFilter.java
@@ -59,27 +59,22 @@ public class AbsoluteChangeRuleAnomalyFilter implements AnomalyFilter<AbsoluteCh
     slices.add(currentSlice);
 
     // customize baseline offset
-    MetricSlice baselineSlice = null;
     if (baseline != null) {
-      baselineSlice = this.baseline.scatter(currentSlice).get(0);
-      slices.add(baselineSlice);
+      slices.addAll(this.baseline.scatter(currentSlice));
     }
 
     Map<MetricSlice, DataFrame> aggregates =
         this.dataFetcher.fetchData(new InputDataSpec().withAggregateSlices(slices)).getAggregates();
 
-    double currentValue = getValueFromAggregates(currentSlice, aggregates);
+    double currentValue = aggregates.get(currentSlice).getDouble(COL_VALUE, 0);
     double baselineValue =
-        baselineSlice == null ? anomaly.getAvgBaselineVal() : getValueFromAggregates(baselineSlice, aggregates);
+        baseline == null ? anomaly.getAvgBaselineVal() : this.baseline.gather(currentSlice, aggregates).getDouble(COL_VALUE, 0);
     // if inconsistent with up/down, filter the anomaly
     if (!pattern.equals(Pattern.UP_OR_DOWN) && (currentValue < baselineValue && pattern.equals(Pattern.UP)) || (
         currentValue > baselineValue && pattern.equals(Pattern.DOWN))) {
       return false;
     }
-    if (Math.abs(currentValue - baselineValue) < this.threshold) {
-      return false;
-    }
-    return true;
+    return Math.abs(currentValue - baselineValue) >= this.threshold;
   }
 
   @Override
@@ -92,9 +87,4 @@ public class AbsoluteChangeRuleAnomalyFilter implements AnomalyFilter<AbsoluteCh
     }
     this.threshold = spec.getThreshold();
   }
-
-  private double getValueFromAggregates(MetricSlice slice, Map<MetricSlice, DataFrame> aggregates) {
-    return aggregates.get(slice).getDouble(COL_VALUE, 0);
-  }
-
 }
diff --git a/thirdeye/thirdeye-pinot/src/main/java/org/apache/pinot/thirdeye/detection/components/PercentageChangeRuleAnomalyFilter.java b/thirdeye/thirdeye-pinot/src/main/java/org/apache/pinot/thirdeye/detection/components/PercentageChangeRuleAnomalyFilter.java
index a44e626..115f7bc 100644
--- a/thirdeye/thirdeye-pinot/src/main/java/org/apache/pinot/thirdeye/detection/components/PercentageChangeRuleAnomalyFilter.java
+++ b/thirdeye/thirdeye-pinot/src/main/java/org/apache/pinot/thirdeye/detection/components/PercentageChangeRuleAnomalyFilter.java
@@ -49,6 +49,8 @@ import static org.apache.pinot.thirdeye.dataframe.util.DataFrameUtils.*;
 public class PercentageChangeRuleAnomalyFilter implements AnomalyFilter<PercentageChangeRuleAnomalyFilterSpec> {
   private static final Logger LOG = LoggerFactory.getLogger(PercentageChangeRuleAnomalyFilter.class);
   private double threshold;
+  private double upThreshold;
+  private double downThreshold;
   private InputDataFetcher dataFetcher;
   private Baseline baseline;
   private Pattern pattern;
@@ -57,15 +59,12 @@ public class PercentageChangeRuleAnomalyFilter implements AnomalyFilter<Percenta
   public boolean isQualified(MergedAnomalyResultDTO anomaly) {
     MetricEntity me = MetricEntity.fromURN(anomaly.getMetricUrn());
     List<MetricSlice> slices = new ArrayList<>();
-    MetricSlice currentSlice =
-        MetricSlice.from(me.getId(), anomaly.getStartTime(), anomaly.getEndTime(), me.getFilters());
+    MetricSlice currentSlice = MetricSlice.from(me.getId(), anomaly.getStartTime(), anomaly.getEndTime(), me.getFilters());
     slices.add(currentSlice);
 
     // customize baseline offset
-    MetricSlice baselineSlice = null;
     if (baseline != null) {
-      baselineSlice = this.baseline.scatter(currentSlice).get(0);
-      slices.add(baselineSlice);
+      slices.addAll(this.baseline.scatter(currentSlice));
     }
 
     Map<MetricSlice, DataFrame> aggregates =
@@ -75,18 +74,20 @@ public class PercentageChangeRuleAnomalyFilter implements AnomalyFilter<Percenta
     if (aggregates.get(currentSlice).isEmpty()) {
       currentValue = anomaly.getAvgCurrentVal();
     } else {
-      currentValue = getValueFromAggregates(currentSlice, aggregates);
+      currentValue = aggregates.get(currentSlice).getDouble(COL_VALUE, 0);
     }
 
     double baselineValue;
-    if (baselineSlice == null) {
+    if (baseline == null) {
       baselineValue = anomaly.getAvgBaselineVal();
-    } else if (aggregates.get(baselineSlice).isEmpty()) {
-      baselineValue = anomaly.getAvgBaselineVal();
-      LOG.warn("Unable to fetch data for baseline slice for anomaly {}. start = {} end = {} filters = {}. Using anomaly"
-              + " baseline ", anomaly.getId(), anomaly.getStartTime(), anomaly.getEndTime(), me.getFilters());
     } else {
-      baselineValue = getValueFromAggregates(baselineSlice, aggregates);
+      try {
+        baselineValue = this.baseline.gather(currentSlice, aggregates).getDouble(COL_VALUE, 0);
+      } catch (Exception e) {
+        baselineValue = anomaly.getAvgBaselineVal();
+        LOG.warn("Unable to fetch baseline for anomaly {}. start = {} end = {} filters = {}. Using anomaly"
+            + " baseline ", anomaly.getId(), anomaly.getStartTime(), anomaly.getEndTime(), me.getFilters(), e);
+      }
     }
 
     // if inconsistent with up/down, filter the anomaly
@@ -94,10 +95,15 @@ public class PercentageChangeRuleAnomalyFilter implements AnomalyFilter<Percenta
         currentValue > baselineValue && pattern.equals(Pattern.DOWN))) {
       return false;
     }
-    if (baselineValue != 0 && Math.abs(currentValue / baselineValue - 1) < this.threshold) {
-      return false;
+
+    double percentageChange = Math.abs(currentValue / baselineValue - 1);
+    if (currentValue < baselineValue) {
+      double downThreshold = Double.isNaN(this.downThreshold) ? this.threshold : this.downThreshold;
+      return Double.compare(downThreshold, percentageChange) <= 0;
+    } else {
+      double upThreshold = Double.isNaN(this.upThreshold) ? this.threshold : this.upThreshold;
+      return Double.compare(upThreshold, percentageChange) <= 0;
     }
-    return true;
   }
 
   @Override
@@ -109,9 +115,7 @@ public class PercentageChangeRuleAnomalyFilter implements AnomalyFilter<Percenta
       this.baseline = BaselineParsingUtils.parseOffset(spec.getOffset(), spec.getTimezone());
     }
     this.threshold = spec.getThreshold();
-  }
-
-  private double getValueFromAggregates(MetricSlice slice, Map<MetricSlice, DataFrame> aggregates) {
-    return aggregates.get(slice).getDouble(COL_VALUE, 0);
+    this.upThreshold = spec.getUpThreshold();
+    this.downThreshold = spec.getDownThreshold();
   }
 }
diff --git a/thirdeye/thirdeye-pinot/src/main/java/org/apache/pinot/thirdeye/detection/components/SitewideImpactRuleAnomalyFilter.java b/thirdeye/thirdeye-pinot/src/main/java/org/apache/pinot/thirdeye/detection/components/SitewideImpactRuleAnomalyFilter.java
index 92026da..42f4781 100644
--- a/thirdeye/thirdeye-pinot/src/main/java/org/apache/pinot/thirdeye/detection/components/SitewideImpactRuleAnomalyFilter.java
+++ b/thirdeye/thirdeye-pinot/src/main/java/org/apache/pinot/thirdeye/detection/components/SitewideImpactRuleAnomalyFilter.java
@@ -92,16 +92,16 @@ public class SitewideImpactRuleAnomalyFilter implements AnomalyFilter<SitewideIm
         .getAggregates();
 
     double currentValue = getValueFromAggregates(currentSlice, aggregates);
-    double baselineValue = baselineSlice == null ? anomaly.getAvgBaselineVal() : getValueFromAggregates(baselineSlice, aggregates);
-    double siteWideBaselineValue = getValueFromAggregates(siteWideSlice, aggregates);
+    double baselineValue = baseline == null ? anomaly.getAvgBaselineVal() :  this.baseline.gather(currentSlice, aggregates).getDouble(COL_VALUE, 0);
+    double siteWideValue = getValueFromAggregates(siteWideSlice, aggregates);
 
     // if inconsistent with up/down, filter the anomaly
     if (!pattern.equals(Pattern.UP_OR_DOWN) && (currentValue < baselineValue && pattern.equals(Pattern.UP)) || (currentValue > baselineValue && pattern.equals(Pattern.DOWN))) {
       return false;
     }
     // if doesn't pass the threshold, filter the anomaly
-    if (siteWideBaselineValue != 0
-        && (Math.abs(currentValue - baselineValue) / siteWideBaselineValue) < this.threshold) {
+    if (siteWideValue != 0
+        && (Math.abs(currentValue - baselineValue) / siteWideValue) < this.threshold) {
       return false;
     }
 
diff --git a/thirdeye/thirdeye-pinot/src/main/java/org/apache/pinot/thirdeye/detection/spec/PercentageChangeRuleAnomalyFilterSpec.java b/thirdeye/thirdeye-pinot/src/main/java/org/apache/pinot/thirdeye/detection/spec/PercentageChangeRuleAnomalyFilterSpec.java
index 2dc9b8f..a555115 100644
--- a/thirdeye/thirdeye-pinot/src/main/java/org/apache/pinot/thirdeye/detection/spec/PercentageChangeRuleAnomalyFilterSpec.java
+++ b/thirdeye/thirdeye-pinot/src/main/java/org/apache/pinot/thirdeye/detection/spec/PercentageChangeRuleAnomalyFilterSpec.java
@@ -21,9 +21,11 @@ package org.apache.pinot.thirdeye.detection.spec;
 
 public class PercentageChangeRuleAnomalyFilterSpec extends AbstractSpec {
   private String timezone = "UTC";
-  private double threshold = Double.NaN;
   private String offset;
   private String pattern= "UP_OR_DOWN";
+  private double threshold = 0.0; // by default set threshold to 0 to pass all anomalies
+  private double upThreshold = Double.NaN;
+  private double downThreshold = Double.NaN;
 
   public String getTimezone() {
     return timezone;
@@ -56,4 +58,20 @@ public class PercentageChangeRuleAnomalyFilterSpec extends AbstractSpec {
   public void setPattern(String pattern) {
     this.pattern = pattern;
   }
+
+  public double getUpThreshold() {
+    return upThreshold;
+  }
+
+  public void setUpThreshold(double upThreshold) {
+    this.upThreshold = upThreshold;
+  }
+
+  public double getDownThreshold() {
+    return downThreshold;
+  }
+
+  public void setDownThreshold(double downThreshold) {
+    this.downThreshold = downThreshold;
+  }
 }
diff --git a/thirdeye/thirdeye-pinot/src/test/java/org/apache/pinot/thirdeye/detection/components/AbsoluteChangeRuleAnomalyFilterTest.java b/thirdeye/thirdeye-pinot/src/test/java/org/apache/pinot/thirdeye/detection/components/AbsoluteChangeRuleAnomalyFilterTest.java
index 5707f7c..81b61e9 100644
--- a/thirdeye/thirdeye-pinot/src/test/java/org/apache/pinot/thirdeye/detection/components/AbsoluteChangeRuleAnomalyFilterTest.java
+++ b/thirdeye/thirdeye-pinot/src/test/java/org/apache/pinot/thirdeye/detection/components/AbsoluteChangeRuleAnomalyFilterTest.java
@@ -58,10 +58,10 @@ public class AbsoluteChangeRuleAnomalyFilterTest {
     MetricSlice baselineSlice2 = this.baseline.scatter(slice2).get(0);
 
     Map<MetricSlice, DataFrame> aggregates = new HashMap<>();
-    aggregates.put(slice1, new DataFrame().addSeries(COL_VALUE, 150));
-    aggregates.put(baselineSlice1, new DataFrame().addSeries(COL_VALUE, 200));
-    aggregates.put(slice2, new DataFrame().addSeries(COL_VALUE, 500));
-    aggregates.put(baselineSlice2, new DataFrame().addSeries(COL_VALUE, 1000));
+    aggregates.put(slice1, new DataFrame().addSeries(COL_VALUE, 150).addSeries(COL_TIME, slice1.getStart()).setIndex(COL_TIME));
+    aggregates.put(baselineSlice1, new DataFrame().addSeries(COL_VALUE, 200).addSeries(COL_TIME, baselineSlice1.getStart()).setIndex(COL_TIME));
+    aggregates.put(slice2, new DataFrame().addSeries(COL_VALUE, 500).addSeries(COL_TIME, slice2.getStart()).setIndex(COL_TIME));
+    aggregates.put(baselineSlice2, new DataFrame().addSeries(COL_VALUE, 1000).addSeries(COL_TIME, baselineSlice2.getStart()).setIndex(COL_TIME));
 
     this.testDataProvider = new MockDataProvider().setAggregates(aggregates);
   }
diff --git a/thirdeye/thirdeye-pinot/src/test/java/org/apache/pinot/thirdeye/detection/components/PercentageChangeRuleAnomalyFilterTest.java b/thirdeye/thirdeye-pinot/src/test/java/org/apache/pinot/thirdeye/detection/components/PercentageChangeRuleAnomalyFilterTest.java
index 913a26c..edc088e 100644
--- a/thirdeye/thirdeye-pinot/src/test/java/org/apache/pinot/thirdeye/detection/components/PercentageChangeRuleAnomalyFilterTest.java
+++ b/thirdeye/thirdeye-pinot/src/test/java/org/apache/pinot/thirdeye/detection/components/PercentageChangeRuleAnomalyFilterTest.java
@@ -16,6 +16,7 @@
 
 package org.apache.pinot.thirdeye.detection.components;
 
+import java.util.stream.Stream;
 import org.apache.pinot.thirdeye.dataframe.DataFrame;
 import org.apache.pinot.thirdeye.dataframe.util.MetricSlice;
 import org.apache.pinot.thirdeye.datalayer.dto.MergedAnomalyResultDTO;
@@ -49,18 +50,22 @@ public class PercentageChangeRuleAnomalyFilterTest {
 
   @BeforeMethod
   public void beforeMethod() {
-    this.baseline = BaselineAggregate.fromWeekOverWeek(BaselineAggregateType.MEDIAN, 1, 1, DateTimeZone.forID("UTC"));
+    this.baseline = BaselineAggregate.fromWeekOverWeek(BaselineAggregateType.MEAN, 1, 1, DateTimeZone.forID("UTC"));
 
-    MetricSlice slice1 = MetricSlice.from(123L, 0, 2);
+    MetricSlice slice1 = MetricSlice.from(123L, 1555570800000L, 1555693200000L);
     MetricSlice baselineSlice1 = this.baseline.scatter(slice1).get(0);
-    MetricSlice slice2 = MetricSlice.from(123L, 4, 6);
+    MetricSlice slice2 = MetricSlice.from(123L, 1554163200000L, 1554249600000L);
     MetricSlice baselineSlice2 = this.baseline.scatter(slice2).get(0);
+    MetricSlice slice3 = MetricSlice.from(123L, 1554076800000L, 1554163200000L);
+    MetricSlice baselineSlice3 = this.baseline.scatter(slice3).get(0);
 
     Map<MetricSlice, DataFrame> aggregates = new HashMap<>();
-    aggregates.put(slice1, new DataFrame().addSeries(COL_VALUE, 150));
-    aggregates.put(baselineSlice1, new DataFrame().addSeries(COL_VALUE, 200));
-    aggregates.put(slice2, new DataFrame().addSeries(COL_VALUE, 500));
-    aggregates.put(baselineSlice2, new DataFrame().addSeries(COL_VALUE, 1000));
+    aggregates.put(slice1, new DataFrame().addSeries(COL_TIME, slice1.getStart()).addSeries(COL_VALUE, 150).setIndex(COL_TIME));
+    aggregates.put(baselineSlice1, new DataFrame().addSeries(COL_TIME, baselineSlice1.getStart()).addSeries(COL_VALUE, 200).setIndex(COL_TIME));
+    aggregates.put(slice2, new DataFrame().addSeries(COL_VALUE, 500).addSeries(COL_TIME, slice2.getStart()).setIndex(COL_TIME));
+    aggregates.put(baselineSlice2, new DataFrame().addSeries(COL_VALUE, 1000).addSeries(COL_TIME, baselineSlice2.getStart()).setIndex(COL_TIME));
+    aggregates.put(slice3, new DataFrame().addSeries(COL_VALUE, 200).addSeries(COL_TIME, slice3.getStart()).setIndex(COL_TIME));
+    aggregates.put(baselineSlice3, new DataFrame().addSeries(COL_VALUE, 150).addSeries(COL_TIME, baselineSlice3.getStart()).setIndex(COL_TIME));
 
     this.testDataProvider = new MockDataProvider().setAggregates(aggregates);
   }
@@ -68,17 +73,33 @@ public class PercentageChangeRuleAnomalyFilterTest {
   @Test
   public void testPercentageChangeFilter(){
     PercentageChangeRuleAnomalyFilterSpec spec = new PercentageChangeRuleAnomalyFilterSpec();
-    spec.setOffset("median1w");
+    spec.setOffset("mean1w");
     spec.setThreshold(0.5);
     spec.setPattern("up_or_down");
     AnomalyFilter filter = new PercentageChangeRuleAnomalyFilter();
     filter.init(spec, new DefaultInputDataFetcher(this.testDataProvider, 125L));
     List<Boolean> results =
-        Arrays.asList(makeAnomaly(0, 2), makeAnomaly(4, 6)).stream().map(anomaly -> filter.isQualified(anomaly)).collect(
+        Stream.of(makeAnomaly(1555570800000L, 1555693200000L), makeAnomaly(1554163200000L, 1554249600000L)).map(anomaly -> filter.isQualified(anomaly)).collect(
             Collectors.toList());
     Assert.assertEquals(results, Arrays.asList(false, true));
   }
 
+  @Test
+  public void testPercentageChangeFilterTwoSide(){
+    PercentageChangeRuleAnomalyFilterSpec spec = new PercentageChangeRuleAnomalyFilterSpec();
+    spec.setOffset("mean1w");
+    spec.setUpThreshold(0.25);
+    spec.setDownThreshold(0.5);
+    spec.setPattern("up_or_down");
+    AnomalyFilter filter = new PercentageChangeRuleAnomalyFilter();
+    filter.init(spec, new DefaultInputDataFetcher(this.testDataProvider, 125L));
+    List<Boolean> results =
+        Stream.of(makeAnomaly(1555570800000L, 1555693200000L), makeAnomaly(1554163200000L, 1554249600000L), makeAnomaly(1554076800000L, 1554163200000L)).map(anomaly -> filter.isQualified(anomaly)).collect(
+            Collectors.toList());
+    Assert.assertEquals(results, Arrays.asList(false, true, true));
+  }
+
+
 
   private static MergedAnomalyResultDTO makeAnomaly(long start, long end) {
     Map<String, String> dimensions = new HashMap<>();
diff --git a/thirdeye/thirdeye-pinot/src/test/java/org/apache/pinot/thirdeye/detection/components/SitewideImpactRuleAnomalyFilterTest.java b/thirdeye/thirdeye-pinot/src/test/java/org/apache/pinot/thirdeye/detection/components/SitewideImpactRuleAnomalyFilterTest.java
index 9b34258..cc27e8a 100644
--- a/thirdeye/thirdeye-pinot/src/test/java/org/apache/pinot/thirdeye/detection/components/SitewideImpactRuleAnomalyFilterTest.java
+++ b/thirdeye/thirdeye-pinot/src/test/java/org/apache/pinot/thirdeye/detection/components/SitewideImpactRuleAnomalyFilterTest.java
@@ -56,10 +56,10 @@ public class SitewideImpactRuleAnomalyFilterTest {
     MetricSlice baselineSlice2 = this.baseline.scatter(slice2).get(0);
 
     Map<MetricSlice, DataFrame> aggregates = new HashMap<>();
-    aggregates.put(slice1, new DataFrame().addSeries(COL_VALUE, 150));
-    aggregates.put(baselineSlice1, new DataFrame().addSeries(COL_VALUE, 200));
-    aggregates.put(slice2, new DataFrame().addSeries(COL_VALUE, 500));
-    aggregates.put(baselineSlice2, new DataFrame().addSeries(COL_VALUE, 1000));
+    aggregates.put(slice1, new DataFrame().addSeries(COL_VALUE, 150).addSeries(COL_TIME, slice1.getStart()).setIndex(COL_TIME));
+    aggregates.put(baselineSlice1, new DataFrame().addSeries(COL_VALUE, 200).addSeries(COL_TIME, baselineSlice1.getStart()).setIndex(COL_TIME));
+    aggregates.put(slice2, new DataFrame().addSeries(COL_VALUE, 500).addSeries(COL_TIME, slice2.getStart()).setIndex(COL_TIME));
+    aggregates.put(baselineSlice2, new DataFrame().addSeries(COL_VALUE, 1000).addSeries(COL_TIME, baselineSlice2.getStart()).setIndex(COL_TIME));
 
     this.testDataProvider = new MockDataProvider().setAggregates(aggregates);
   }


---------------------------------------------------------------------
To unsubscribe, e-mail: commits-unsubscribe@pinot.apache.org
For additional commands, e-mail: commits-help@pinot.apache.org