Search in sources :

Example 11 with Filter

use of io.crate.planner.operators.Filter in project crate by crate.

the class MergeFilters method apply.

@Override
public Filter apply(Filter plan, Captures captures, TableStats tableStats, TransactionContext txnCtx, NodeContext nodeCtx) {
    Filter childFilter = captures.get(child);
    Symbol parentQuery = plan.query();
    Symbol childQuery = childFilter.query();
    return new Filter(childFilter.source(), AndOperator.of(parentQuery, childQuery));
}
Also used : Filter(io.crate.planner.operators.Filter) Symbol(io.crate.expression.symbol.Symbol)

Example 12 with Filter

use of io.crate.planner.operators.Filter in project crate by crate.

the class MoveFilterBeneathGroupBy method apply.

@Override
public LogicalPlan apply(Filter filter, Captures captures, TableStats tableStats, TransactionContext txnCtx, NodeContext nodeCtx) {
    // Since something like `SELECT x, sum(y) FROM t GROUP BY x HAVING y > 10` is not valid
    // (y would have to be declared as group key) any parts of a HAVING that is not an aggregation can be moved.
    Symbol predicate = filter.query();
    List<Symbol> parts = AndOperator.split(predicate);
    ArrayList<Symbol> withAggregates = new ArrayList<>();
    ArrayList<Symbol> withoutAggregates = new ArrayList<>();
    for (Symbol part : parts) {
        if (SymbolVisitors.any(Symbols::isAggregate, part)) {
            withAggregates.add(part);
        } else {
            withoutAggregates.add(part);
        }
    }
    if (withoutAggregates.isEmpty()) {
        return null;
    }
    GroupHashAggregate groupBy = captures.get(groupByCapture);
    if (withoutAggregates.size() == parts.size()) {
        return transpose(filter, groupBy);
    }
    /* HAVING `count(*) > 1 AND x = 10`
         * withAggregates:    [count(*) > 1]
         * withoutAggregates: [x = 10]
         *
         * Filter
         *  |
         * GroupBy
         *
         * transforms to
         *
         * Filter (count(*) > 1)
         *  |
         * GroupBy
         *  |
         * Filter (x = 10)
         */
    LogicalPlan newGroupBy = groupBy.replaceSources(List.of(new Filter(groupBy.source(), AndOperator.join(withoutAggregates))));
    return new Filter(newGroupBy, AndOperator.join(withAggregates));
}
Also used : Filter(io.crate.planner.operators.Filter) Symbol(io.crate.expression.symbol.Symbol) Symbols(io.crate.expression.symbol.Symbols) ArrayList(java.util.ArrayList) GroupHashAggregate(io.crate.planner.operators.GroupHashAggregate) LogicalPlan(io.crate.planner.operators.LogicalPlan)

Example 13 with Filter

use of io.crate.planner.operators.Filter in project crate by crate.

the class MoveFilterBeneathProjectSet method apply.

@Override
public LogicalPlan apply(Filter filter, Captures captures, TableStats tableStats, TransactionContext txnCtx, NodeContext nodeCtx) {
    var projectSet = captures.get(projectSetCapture);
    var queryParts = AndOperator.split(filter.query());
    ArrayList<Symbol> toPushDown = new ArrayList<>();
    ArrayList<Symbol> toKeep = new ArrayList<>();
    for (var part : queryParts) {
        if (!SymbolVisitors.any(MoveFilterBeneathProjectSet::isTableFunction, part) && projectSet.standaloneOutputs().containsAll(extractColumns(part))) {
            toPushDown.add(part);
        } else {
            toKeep.add(part);
        }
    }
    if (toPushDown.isEmpty()) {
        return null;
    } else if (toKeep.isEmpty()) {
        return transpose(filter, projectSet);
    } else {
        var newProjectSet = projectSet.replaceSources(List.of(new Filter(projectSet.source(), AndOperator.join(toPushDown))));
        return new Filter(newProjectSet, AndOperator.join(toKeep));
    }
}
Also used : Filter(io.crate.planner.operators.Filter) Symbol(io.crate.expression.symbol.Symbol) ArrayList(java.util.ArrayList)

Example 14 with Filter

use of io.crate.planner.operators.Filter in project crate by crate.

the class MergeFiltersTest method testMergeFiltersMatchesOnAFilterWithAnotherFilterAsChild.

@Test
public void testMergeFiltersMatchesOnAFilterWithAnotherFilterAsChild() {
    Collect source = new Collect(tr1, Collections.emptyList(), WhereClause.MATCH_ALL, 100, 10);
    Filter sourceFilter = new Filter(source, e.asSymbol("x > 10"));
    Filter parentFilter = new Filter(sourceFilter, e.asSymbol("y > 10"));
    MergeFilters mergeFilters = new MergeFilters();
    Match<Filter> match = mergeFilters.pattern().accept(parentFilter, Captures.empty());
    assertThat(match.isPresent(), Matchers.is(true));
    assertThat(match.value(), Matchers.sameInstance(parentFilter));
    Filter mergedFilter = mergeFilters.apply(match.value(), match.captures(), new TableStats(), CoordinatorTxnCtx.systemTransactionContext(), e.nodeCtx);
    assertThat(mergedFilter.query(), isSQL("((doc.t2.y > 10) AND (doc.t1.x > 10))"));
}
Also used : Collect(io.crate.planner.operators.Collect) Filter(io.crate.planner.operators.Filter) TableStats(io.crate.statistics.TableStats) Test(org.junit.Test) CrateDummyClusterServiceUnitTest(io.crate.test.integration.CrateDummyClusterServiceUnitTest)

Aggregations

Filter (io.crate.planner.operators.Filter)14 Symbol (io.crate.expression.symbol.Symbol)11 LogicalPlan (io.crate.planner.operators.LogicalPlan)10 TableStats (io.crate.statistics.TableStats)7 Test (org.junit.Test)7 WindowFunction (io.crate.expression.symbol.WindowFunction)6 WindowAgg (io.crate.planner.operators.WindowAgg)6 CrateDummyClusterServiceUnitTest (io.crate.test.integration.CrateDummyClusterServiceUnitTest)6 ArrayList (java.util.ArrayList)3 RelationName (io.crate.metadata.RelationName)2 Set (java.util.Set)2 SymbolEvaluator (io.crate.analyze.SymbolEvaluator)1 WindowDefinition (io.crate.analyze.WindowDefinition)1 AndOperator (io.crate.expression.operator.AndOperator)1 SymbolVisitors (io.crate.expression.symbol.SymbolVisitors)1 Symbols (io.crate.expression.symbol.Symbols)1 NodeContext (io.crate.metadata.NodeContext)1 TransactionContext (io.crate.metadata.TransactionContext)1 Collect (io.crate.planner.operators.Collect)1 GroupHashAggregate (io.crate.planner.operators.GroupHashAggregate)1