Search in sources :

Example 1 with ColumnReferenceExp

use of io.confluent.ksql.execution.expression.tree.ColumnReferenceExp in project ksql by confluentinc.

the class FinalProjectNode method validateProjection.

/**
 * Called to validate that columns referenced in the projection are valid.
 *
 * <p>This is necessary as some joins can create synthetic key columns that do not come
 * from any data source.  This means the normal column validation done during analysis can not
 * fail on unknown column with generated column names.
 *
 * <p>Once the logical model has been built the synthetic key names are known and generated
 * column names can be validated.
 */
private void validateProjection() {
    // Validate any column in the projection that might be a synthetic
    // Only really need to include any that might be, but we include all:
    final RequiredColumns requiredColumns = RequiredColumns.builder().addAll(projection.singleExpressions()).build();
    final Set<ColumnReferenceExp> unknown = getSource().validateColumns(requiredColumns);
    if (!unknown.isEmpty()) {
        final String errors = unknown.stream().map(columnRef -> NodeLocation.asPrefix(columnRef.getLocation()) + "Column '" + columnRef + "' cannot be resolved.").collect(Collectors.joining(System.lineSeparator()));
        throw new KsqlException(errors);
    }
}
Also used : DataSource(io.confluent.ksql.metastore.model.DataSource) ColumnName(io.confluent.ksql.name.ColumnName) SourceName(io.confluent.ksql.name.SourceName) GrammaticalJoiner(io.confluent.ksql.util.GrammaticalJoiner) UnqualifiedColumnReferenceExp(io.confluent.ksql.execution.expression.tree.UnqualifiedColumnReferenceExp) Name(io.confluent.ksql.name.Name) HashMap(java.util.HashMap) SelectItem(io.confluent.ksql.parser.tree.SelectItem) HashSet(java.util.HashSet) AsValue(io.confluent.ksql.function.udf.AsValue) Pair(io.confluent.ksql.util.Pair) ImmutableList(com.google.common.collect.ImmutableList) Analysis(io.confluent.ksql.analyzer.Analysis) Map(java.util.Map) MetaStore(io.confluent.ksql.metastore.MetaStore) Projection(io.confluent.ksql.planner.Projection) ColumnReferenceExp(io.confluent.ksql.execution.expression.tree.ColumnReferenceExp) RequiredColumns(io.confluent.ksql.planner.RequiredColumns) SystemColumns(io.confluent.ksql.schema.ksql.SystemColumns) Set(java.util.Set) KsqlConfig(io.confluent.ksql.util.KsqlConfig) LogicalSchema(io.confluent.ksql.schema.ksql.LogicalSchema) Collectors(java.util.stream.Collectors) SelectExpression(io.confluent.ksql.execution.plan.SelectExpression) Builder(io.confluent.ksql.schema.ksql.LogicalSchema.Builder) NodeLocation(io.confluent.ksql.parser.NodeLocation) List(java.util.List) Entry(java.util.Map.Entry) KsqlException(io.confluent.ksql.util.KsqlException) Optional(java.util.Optional) SuppressFBWarnings(edu.umd.cs.findbugs.annotations.SuppressFBWarnings) UnqualifiedColumnReferenceExp(io.confluent.ksql.execution.expression.tree.UnqualifiedColumnReferenceExp) ColumnReferenceExp(io.confluent.ksql.execution.expression.tree.ColumnReferenceExp) RequiredColumns(io.confluent.ksql.planner.RequiredColumns) KsqlException(io.confluent.ksql.util.KsqlException)

Example 2 with ColumnReferenceExp

use of io.confluent.ksql.execution.expression.tree.ColumnReferenceExp in project ksql by confluentinc.

the class LogicalPlanner method buildJoin.

/**
 * @param root    the root of the Join Tree
 * @param prefix  the prefix to uniquely identify the plan node
 * @return the PlanNode representing this Join Tree
 */
private JoinNode buildJoin(final Join root, final String prefix, final boolean isWindowed) {
    final PlanNode preRepartitionLeft;
    if (root.getLeft() instanceof JoinTree.Join) {
        preRepartitionLeft = buildJoin((Join) root.getLeft(), prefix + "L_", isWindowed);
    } else {
        final JoinTree.Leaf leaf = (Leaf) root.getLeft();
        preRepartitionLeft = new DataSourceNode(new PlanNodeId("KafkaTopic_" + prefix + "Left"), leaf.getSource().getDataSource(), leaf.getSource().getAlias(), isWindowed, ksqlConfig);
    }
    final PlanNode preRepartitionRight;
    if (root.getRight() instanceof JoinTree.Join) {
        preRepartitionRight = buildJoin((Join) root.getRight(), prefix + "R_", isWindowed);
    } else {
        final JoinTree.Leaf leaf = (Leaf) root.getRight();
        preRepartitionRight = new DataSourceNode(new PlanNodeId("KafkaTopic_" + prefix + "Right"), leaf.getSource().getDataSource(), leaf.getSource().getAlias(), isWindowed, ksqlConfig);
    }
    final Optional<Expression> fkExpression = verifyJoin(root.getInfo(), preRepartitionLeft, preRepartitionRight);
    final JoinKey joinKey = fkExpression.map(columnReferenceExp -> buildForeignJoinKey(root, fkExpression.get())).orElseGet(() -> buildJoinKey(root));
    final PlanNode left = prepareSourceForJoin(root.getLeft(), preRepartitionLeft, prefix + "Left", root.getInfo().getLeftJoinExpression(), fkExpression.isPresent());
    final PlanNode right = prepareSourceForJoin(root.getRight(), preRepartitionRight, prefix + "Right", root.getInfo().getRightJoinExpression(), fkExpression.isPresent());
    return new JoinNode(new PlanNodeId(prefix + "Join"), root.getInfo().getType(), joinKey.rewriteWith(refRewriter::process), prefix.isEmpty(), left, right, root.getInfo().getWithinExpression(), ksqlConfig.getString(KsqlConfig.KSQL_DEFAULT_KEY_FORMAT_CONFIG));
}
Also used : PlanNodeId(io.confluent.ksql.planner.plan.PlanNodeId) JoinInfo(io.confluent.ksql.analyzer.Analysis.JoinInfo) DataSource(io.confluent.ksql.metastore.model.DataSource) Leaf(io.confluent.ksql.planner.JoinTree.Leaf) AggregateAnalysisResult(io.confluent.ksql.analyzer.AggregateAnalysisResult) Into(io.confluent.ksql.analyzer.Analysis.Into) ColumnName(io.confluent.ksql.name.ColumnName) SourceName(io.confluent.ksql.name.SourceName) BiFunction(java.util.function.BiFunction) AggregateAnalyzer(io.confluent.ksql.analyzer.AggregateAnalyzer) FilterNode(io.confluent.ksql.planner.plan.FilterNode) SerdeFeaturesFactory(io.confluent.ksql.serde.SerdeFeaturesFactory) JoinKey(io.confluent.ksql.planner.plan.JoinNode.JoinKey) CodeGenRunner(io.confluent.ksql.execution.codegen.CodeGenRunner) WindowInfo(io.confluent.ksql.serde.WindowInfo) RewrittenAnalysis(io.confluent.ksql.analyzer.RewrittenAnalysis) QueryLimitNode(io.confluent.ksql.planner.plan.QueryLimitNode) AggregateNode(io.confluent.ksql.planner.plan.AggregateNode) AliasedDataSource(io.confluent.ksql.analyzer.Analysis.AliasedDataSource) TimestampExtractionPolicyFactory(io.confluent.ksql.execution.streams.timestamp.TimestampExtractionPolicyFactory) ExpressionTypeManager(io.confluent.ksql.execution.util.ExpressionTypeManager) KsqlBareOutputNode(io.confluent.ksql.planner.plan.KsqlBareOutputNode) SelectionUtil(io.confluent.ksql.planner.plan.SelectionUtil) PartitionBy(io.confluent.ksql.parser.tree.PartitionBy) ColumnReferenceExp(io.confluent.ksql.execution.expression.tree.ColumnReferenceExp) PreJoinProjectNode(io.confluent.ksql.planner.plan.PreJoinProjectNode) VisitParentExpressionVisitor(io.confluent.ksql.execution.expression.tree.VisitParentExpressionVisitor) FinalProjectNode(io.confluent.ksql.planner.plan.FinalProjectNode) ColumnNames(io.confluent.ksql.schema.ksql.ColumnNames) RefinementInfo(io.confluent.ksql.serde.RefinementInfo) ImmutableAnalysis(io.confluent.ksql.analyzer.ImmutableAnalysis) ExpressionEvaluator(io.confluent.ksql.execution.transform.ExpressionEvaluator) Expression(io.confluent.ksql.execution.expression.tree.Expression) JoinType(io.confluent.ksql.planner.plan.JoinNode.JoinType) Set(java.util.Set) QueryFilterNode(io.confluent.ksql.planner.plan.QueryFilterNode) KsqlConfig(io.confluent.ksql.util.KsqlConfig) LogicalSchema(io.confluent.ksql.schema.ksql.LogicalSchema) Collectors(java.util.stream.Collectors) TimestampColumn(io.confluent.ksql.execution.timestamp.TimestampColumn) PlanNodeId(io.confluent.ksql.planner.plan.PlanNodeId) SingleSourcePlanNode(io.confluent.ksql.planner.plan.SingleSourcePlanNode) Builder(io.confluent.ksql.schema.ksql.LogicalSchema.Builder) Objects(java.util.Objects) Join(io.confluent.ksql.planner.JoinTree.Join) List(java.util.List) KsqlException(io.confluent.ksql.util.KsqlException) Optional(java.util.Optional) QueryProjectNode(io.confluent.ksql.planner.plan.QueryProjectNode) Column(io.confluent.ksql.schema.ksql.Column) FormatInfo(io.confluent.ksql.serde.FormatInfo) ProjectNode(io.confluent.ksql.planner.plan.ProjectNode) Iterables(com.google.common.collect.Iterables) FormatFactory(io.confluent.ksql.serde.FormatFactory) GrammaticalJoiner(io.confluent.ksql.util.GrammaticalJoiner) KeyFormat(io.confluent.ksql.serde.KeyFormat) JoinNode(io.confluent.ksql.planner.plan.JoinNode) SuppressNode(io.confluent.ksql.planner.plan.SuppressNode) UnqualifiedColumnReferenceExp(io.confluent.ksql.execution.expression.tree.UnqualifiedColumnReferenceExp) PartitionByParamsFactory(io.confluent.ksql.execution.streams.PartitionByParamsFactory) DataSourceType(io.confluent.ksql.metastore.model.DataSource.DataSourceType) Function(java.util.function.Function) NoneFormat(io.confluent.ksql.serde.none.NoneFormat) AsValue(io.confluent.ksql.function.udf.AsValue) QualifiedColumnReferenceExp(io.confluent.ksql.execution.expression.tree.QualifiedColumnReferenceExp) MetaStore(io.confluent.ksql.metastore.MetaStore) GroupBy(io.confluent.ksql.parser.tree.GroupBy) KsqlStructuredDataOutputNode(io.confluent.ksql.planner.plan.KsqlStructuredDataOutputNode) UserRepartitionNode(io.confluent.ksql.planner.plan.UserRepartitionNode) WindowExpression(io.confluent.ksql.parser.tree.WindowExpression) SqlType(io.confluent.ksql.schema.ksql.types.SqlType) SerdeFeatures(io.confluent.ksql.serde.SerdeFeatures) DataSourceNode(io.confluent.ksql.planner.plan.DataSourceNode) NewTopic(io.confluent.ksql.analyzer.Analysis.Into.NewTopic) KsqlWindowExpression(io.confluent.ksql.execution.windows.KsqlWindowExpression) OutputNode(io.confluent.ksql.planner.plan.OutputNode) FilterTypeValidator(io.confluent.ksql.analyzer.FilterTypeValidator) FlatMapNode(io.confluent.ksql.planner.plan.FlatMapNode) ValueFormat(io.confluent.ksql.serde.ValueFormat) SelectExpression(io.confluent.ksql.execution.plan.SelectExpression) NodeLocation(io.confluent.ksql.parser.NodeLocation) PreJoinRepartitionNode(io.confluent.ksql.planner.plan.PreJoinRepartitionNode) FunctionCall(io.confluent.ksql.execution.expression.tree.FunctionCall) KsqlTopic(io.confluent.ksql.execution.ddl.commands.KsqlTopic) PlanNode(io.confluent.ksql.planner.plan.PlanNode) Context(io.confluent.ksql.engine.rewrite.ExpressionTreeRewriter.Context) ExpressionTreeRewriter(io.confluent.ksql.engine.rewrite.ExpressionTreeRewriter) OutputRefinement(io.confluent.ksql.parser.OutputRefinement) FilterType(io.confluent.ksql.analyzer.FilterTypeValidator.FilterType) Collections(java.util.Collections) DataSourceNode(io.confluent.ksql.planner.plan.DataSourceNode) SingleSourcePlanNode(io.confluent.ksql.planner.plan.SingleSourcePlanNode) PlanNode(io.confluent.ksql.planner.plan.PlanNode) JoinKey(io.confluent.ksql.planner.plan.JoinNode.JoinKey) Expression(io.confluent.ksql.execution.expression.tree.Expression) WindowExpression(io.confluent.ksql.parser.tree.WindowExpression) KsqlWindowExpression(io.confluent.ksql.execution.windows.KsqlWindowExpression) SelectExpression(io.confluent.ksql.execution.plan.SelectExpression) JoinNode(io.confluent.ksql.planner.plan.JoinNode) Join(io.confluent.ksql.planner.JoinTree.Join) Leaf(io.confluent.ksql.planner.JoinTree.Leaf) Leaf(io.confluent.ksql.planner.JoinTree.Leaf)

Example 3 with ColumnReferenceExp

use of io.confluent.ksql.execution.expression.tree.ColumnReferenceExp in project ksql by confluentinc.

the class JoinNode method validateColumns.

@Override
protected Set<ColumnReferenceExp> validateColumns(final RequiredColumns requiredColumns) {
    final boolean noSyntheticKey = !finalJoin || !joinKey.isSynthetic();
    final RequiredColumns updated = noSyntheticKey ? requiredColumns : requiredColumns.asBuilder().remove(new UnqualifiedColumnReferenceExp(getOnlyElement(schema.key()).name())).build();
    final Set<ColumnReferenceExp> leftUnknown = left.validateColumns(updated);
    final Set<ColumnReferenceExp> rightUnknown = right.validateColumns(updated);
    return Sets.intersection(leftUnknown, rightUnknown);
}
Also used : ColumnReferenceExp(io.confluent.ksql.execution.expression.tree.ColumnReferenceExp) UnqualifiedColumnReferenceExp(io.confluent.ksql.execution.expression.tree.UnqualifiedColumnReferenceExp) QualifiedColumnReferenceExp(io.confluent.ksql.execution.expression.tree.QualifiedColumnReferenceExp) RequiredColumns(io.confluent.ksql.planner.RequiredColumns) UnqualifiedColumnReferenceExp(io.confluent.ksql.execution.expression.tree.UnqualifiedColumnReferenceExp)

Example 4 with ColumnReferenceExp

use of io.confluent.ksql.execution.expression.tree.ColumnReferenceExp in project ksql by confluentinc.

the class PartitionByParamsFactory method build.

public static <K> PartitionByParams<K> build(final LogicalSchema sourceSchema, final ExecutionKeyFactory<K> serdeFactory, final List<Expression> partitionBys, final KsqlConfig ksqlConfig, final FunctionRegistry functionRegistry, final ProcessingLogger logger) {
    final List<PartitionByColumn> partitionByCols = getPartitionByColumnName(sourceSchema, partitionBys);
    final LogicalSchema resultSchema = buildSchema(sourceSchema, partitionBys, functionRegistry, partitionByCols);
    final Mapper<K> mapper;
    if (isPartitionByNull(partitionBys)) {
        // In case of PARTITION BY NULL, it is sufficient to set the new key to null as the old key
        // is already present in the current value
        mapper = (k, v) -> new KeyValue<>(null, v);
    } else {
        final List<PartitionByExpressionEvaluator> evaluators = partitionBys.stream().map(pby -> {
            final Set<? extends ColumnReferenceExp> sourceColsInPartitionBy = ColumnExtractor.extractColumns(pby);
            final boolean partitionByInvolvesKeyColsOnly = sourceColsInPartitionBy.stream().map(ColumnReferenceExp::getColumnName).allMatch(sourceSchema::isKeyColumn);
            return buildExpressionEvaluator(sourceSchema, pby, ksqlConfig, functionRegistry, logger, partitionByInvolvesKeyColsOnly);
        }).collect(Collectors.toList());
        mapper = buildMapper(partitionByCols, evaluators, serdeFactory);
    }
    return new PartitionByParams<>(resultSchema, mapper);
}
Also used : ColumnExtractor(io.confluent.ksql.execution.util.ColumnExtractor) ColumnName(io.confluent.ksql.name.ColumnName) CompiledExpression(io.confluent.ksql.execution.codegen.CompiledExpression) KeyUtil(io.confluent.ksql.execution.util.KeyUtil) Supplier(java.util.function.Supplier) CodeGenRunner(io.confluent.ksql.execution.codegen.CodeGenRunner) ExpressionTypeManager(io.confluent.ksql.execution.util.ExpressionTypeManager) ProcessingLogger(io.confluent.ksql.logging.processing.ProcessingLogger) NullLiteral(io.confluent.ksql.execution.expression.tree.NullLiteral) ColumnReferenceExp(io.confluent.ksql.execution.expression.tree.ColumnReferenceExp) Mapper(io.confluent.ksql.execution.streams.PartitionByParams.Mapper) SqlType(io.confluent.ksql.schema.ksql.types.SqlType) ColumnNames(io.confluent.ksql.schema.ksql.ColumnNames) Expression(io.confluent.ksql.execution.expression.tree.Expression) FunctionRegistry(io.confluent.ksql.function.FunctionRegistry) KeyValue(org.apache.kafka.streams.KeyValue) Set(java.util.Set) KsqlConfig(io.confluent.ksql.util.KsqlConfig) ExecutionKeyFactory(io.confluent.ksql.execution.plan.ExecutionKeyFactory) LogicalSchema(io.confluent.ksql.schema.ksql.LogicalSchema) Collectors(java.util.stream.Collectors) Builder(io.confluent.ksql.schema.ksql.LogicalSchema.Builder) Objects(java.util.Objects) List(java.util.List) ColumnAliasGenerator(io.confluent.ksql.schema.ksql.ColumnAliasGenerator) Stream(java.util.stream.Stream) GenericRow(io.confluent.ksql.GenericRow) KsqlException(io.confluent.ksql.util.KsqlException) GenericKey(io.confluent.ksql.GenericKey) Column(io.confluent.ksql.schema.ksql.Column) ColumnReferenceExp(io.confluent.ksql.execution.expression.tree.ColumnReferenceExp) Set(java.util.Set) LogicalSchema(io.confluent.ksql.schema.ksql.LogicalSchema)

Example 5 with ColumnReferenceExp

use of io.confluent.ksql.execution.expression.tree.ColumnReferenceExp in project ksql by confluentinc.

the class GroupByParamsFactory method expressionSchema.

private static LogicalSchema expressionSchema(final LogicalSchema sourceSchema, final List<CompiledExpression> groupBys) {
    final ColumnAliasGenerator columnAliasGenerator = ColumnNames.columnAliasGenerator(Stream.of(sourceSchema));
    final LogicalSchema.Builder schemaBuilder = LogicalSchema.builder();
    for (final CompiledExpression groupBy : groupBys) {
        final Expression groupByExp = groupBy.getExpression();
        final ColumnName columnName = groupByExp instanceof ColumnReferenceExp ? ((ColumnReferenceExp) groupByExp).getColumnName() : columnAliasGenerator.uniqueAliasFor(groupByExp);
        schemaBuilder.keyColumn(columnName, groupBy.getExpressionType());
    }
    schemaBuilder.valueColumns(sourceSchema.value());
    return schemaBuilder.build();
}
Also used : ColumnName(io.confluent.ksql.name.ColumnName) ColumnReferenceExp(io.confluent.ksql.execution.expression.tree.ColumnReferenceExp) Expression(io.confluent.ksql.execution.expression.tree.Expression) CompiledExpression(io.confluent.ksql.execution.codegen.CompiledExpression) LogicalSchema(io.confluent.ksql.schema.ksql.LogicalSchema) ColumnAliasGenerator(io.confluent.ksql.schema.ksql.ColumnAliasGenerator) CompiledExpression(io.confluent.ksql.execution.codegen.CompiledExpression)

Aggregations

ColumnReferenceExp (io.confluent.ksql.execution.expression.tree.ColumnReferenceExp)10 ColumnName (io.confluent.ksql.name.ColumnName)9 LogicalSchema (io.confluent.ksql.schema.ksql.LogicalSchema)8 Expression (io.confluent.ksql.execution.expression.tree.Expression)7 UnqualifiedColumnReferenceExp (io.confluent.ksql.execution.expression.tree.UnqualifiedColumnReferenceExp)7 List (java.util.List)7 Set (java.util.Set)7 Collectors (java.util.stream.Collectors)7 SelectExpression (io.confluent.ksql.execution.plan.SelectExpression)6 Builder (io.confluent.ksql.schema.ksql.LogicalSchema.Builder)6 Optional (java.util.Optional)6 ExpressionTypeManager (io.confluent.ksql.execution.util.ExpressionTypeManager)5 SourceName (io.confluent.ksql.name.SourceName)5 Column (io.confluent.ksql.schema.ksql.Column)5 ColumnNames (io.confluent.ksql.schema.ksql.ColumnNames)5 SqlType (io.confluent.ksql.schema.ksql.types.SqlType)5 CodeGenRunner (io.confluent.ksql.execution.codegen.CodeGenRunner)4 QualifiedColumnReferenceExp (io.confluent.ksql.execution.expression.tree.QualifiedColumnReferenceExp)4 Iterables (com.google.common.collect.Iterables)3 AggregateAnalysisResult (io.confluent.ksql.analyzer.AggregateAnalysisResult)3