package charts.builder;
import java.util.List;
import java.util.Map;
import javax.annotation.Nullable;
import scala.concurrent.Await;
import scala.concurrent.Future;
import scala.concurrent.duration.Duration;
import akka.util.Timeout;
import charts.Chart;
import charts.ChartType;
import charts.Region;
import com.google.common.base.Predicate;
import com.google.common.collect.Lists;
import com.google.common.collect.Maps;
import com.google.inject.Inject;
import com.google.inject.Singleton;
@Singleton
public class CachedChartBuilder implements ChartBuilder {
private final Timeout timeout = new Timeout(Duration.create(60, "seconds"));
private final ChartCache chartCache;
@Inject
public CachedChartBuilder(ChartCache chartCache) {
this.chartCache = chartCache;
}
@Override
public List<Chart> getCharts(String id,
ChartType type, List<Region> regions, Map<String, String> parameters)
throws Exception {
final Future<List<Chart>> futureCharts = chartCache.getCharts(id);
// We leverage Await.result() here to throw any exception that the actor
// may have encountered.
final List<Chart> charts = Await.result(futureCharts, timeout.duration());
return filter(charts, type, regions, parameters);
}
private List<Chart> filter(List<Chart> charts, ChartType type,
List<Region> regions, Map<String, String> parameters) {
List<Chart> filtered = Lists.newArrayList();
if(charts != null) {
for(Chart chart : charts) {
if(type != null && type != chart.getDescription().getType()) {
continue;
}
if(regions != null && !regions.isEmpty() && !regions.contains(chart.getDescription().getRegion())) {
continue;
}
final Map<String, String> cparams = chart.getDescription().getParameters();
if(parameters != null && cparams != null) {
if(!Maps.difference(Maps.filterKeys(parameters, new Predicate<String>() {
@Override
public boolean apply(@Nullable String key) {
return cparams.containsKey(key);
}}), cparams).areEqual()) {
continue;
}
}
filtered.add(chart);
}
}
return filtered;
}
}