use of io.confluent.ksql.schema.ksql.LogicalSchema in project ksql by confluentinc.
the class CreateSourceFactory method createStreamCommand.
// This method is called by simple CREATE statements
public CreateStreamCommand createStreamCommand(final CreateStream statement, final KsqlConfig ksqlConfig) {
final SourceName sourceName = statement.getName();
final CreateSourceProperties props = statement.getProperties();
final String topicName = ensureTopicExists(props, serviceContext);
final LogicalSchema schema = buildSchema(statement.getElements(), ksqlConfig);
final Optional<TimestampColumn> timestampColumn = buildTimestampColumn(ksqlConfig, props, schema);
final DataSource dataSource = metaStore.getSource(sourceName);
if (dataSource != null && !statement.isOrReplace() && !statement.isNotExists()) {
final String sourceType = dataSource.getDataSourceType().getKsqlType();
throw new KsqlException(String.format("Cannot add stream '%s': A %s with the same name already exists", sourceName.text(), sourceType.toLowerCase()));
}
throwIfCreateOrReplaceOnSourceStreamOrTable(statement, dataSource);
return new CreateStreamCommand(sourceName, schema, timestampColumn, topicName, buildFormats(statement.getName(), schema, props, ksqlConfig), getWindowInfo(props), Optional.of(statement.isOrReplace()), Optional.of(statement.isSource()));
}
use of io.confluent.ksql.schema.ksql.LogicalSchema in project ksql by confluentinc.
the class CreateSourceFactory method createTableCommand.
// This method is called by simple CREATE statements
public CreateTableCommand createTableCommand(final CreateTable statement, final KsqlConfig ksqlConfig) {
final SourceName sourceName = statement.getName();
final CreateSourceProperties props = statement.getProperties();
final String topicName = ensureTopicExists(props, serviceContext);
final LogicalSchema schema = buildSchema(statement.getElements(), ksqlConfig);
final DataSource dataSource = metaStore.getSource(sourceName);
if (dataSource != null && !statement.isOrReplace() && !statement.isNotExists()) {
final String sourceType = dataSource.getDataSourceType().getKsqlType();
throw new KsqlException(String.format("Cannot add table '%s': A %s with the same name already exists", sourceName.text(), sourceType.toLowerCase()));
}
if (schema.key().isEmpty()) {
final boolean usingSchemaInference = props.getValueSchemaId().isPresent();
final String additional = usingSchemaInference ? System.lineSeparator() + "Use a partial schema to define the primary key and still load the value columns from " + "the Schema Registry, for example:" + System.lineSeparator() + "\tCREATE TABLE " + sourceName.text() + " (ID INT PRIMARY KEY) WITH (...);" : "";
throw new KsqlException("Tables require a PRIMARY KEY. Please define the PRIMARY KEY." + additional);
}
throwIfCreateOrReplaceOnSourceStreamOrTable(statement, dataSource);
final Optional<TimestampColumn> timestampColumn = buildTimestampColumn(ksqlConfig, props, schema);
return new CreateTableCommand(sourceName, schema, timestampColumn, topicName, buildFormats(statement.getName(), schema, props, ksqlConfig), getWindowInfo(props), Optional.of(statement.isOrReplace()), Optional.of(statement.isSource()));
}
use of io.confluent.ksql.schema.ksql.LogicalSchema in project ksql by confluentinc.
the class GenericRecordFactory method build.
public KsqlGenericRecord build(final List<ColumnName> columnNames, final List<Expression> expressions, final LogicalSchema schema, final DataSourceType dataSourceType) {
final List<ColumnName> columns = columnNames.isEmpty() ? implicitColumns(schema) : columnNames;
if (columns.size() != expressions.size()) {
throw new KsqlException("Expected a value for each column." + " Expected Columns: " + columnNames + ". Got " + expressions);
}
final LogicalSchema schemaWithPseudoColumns = withPseudoColumns(schema, config);
for (ColumnName col : columns) {
if (!schemaWithPseudoColumns.findColumn(col).isPresent()) {
throw new KsqlException("Column name " + col + " does not exist.");
}
if (SystemColumns.isDisallowedForInsertValues(col, config)) {
throw new KsqlException("Inserting into column " + col + " is not allowed.");
}
}
final Map<ColumnName, Object> values = resolveValues(columns, expressions, schemaWithPseudoColumns, functionRegistry, config);
if (dataSourceType == DataSourceType.KTABLE) {
final String noValue = schemaWithPseudoColumns.key().stream().map(Column::name).filter(colName -> !values.containsKey(colName)).map(ColumnName::text).collect(Collectors.joining(", "));
if (!noValue.isEmpty()) {
throw new KsqlException("Value for primary key column(s) " + noValue + " is required for tables");
}
}
final long ts = (long) values.getOrDefault(SystemColumns.ROWTIME_NAME, clock.getAsLong());
final GenericKey key = buildKey(schema, values);
final GenericRow value = buildValue(schema, values);
return KsqlGenericRecord.of(key, value, ts);
}
use of io.confluent.ksql.schema.ksql.LogicalSchema in project ksql by confluentinc.
the class GenericRecordFactoryTest method shouldAcceptNullsForAnyColumn.
@Test
public void shouldAcceptNullsForAnyColumn() {
// Given:
final LogicalSchema schema = LogicalSchema.builder().keyColumn(KEY, SqlTypes.STRING).valueColumn(COL0, SqlTypes.BIGINT).build();
final List<ColumnName> names = ImmutableList.of(KEY, COL0);
// When:
final KsqlGenericRecord record = recordFactory.build(names, ImmutableList.of(new NullLiteral(), new NullLiteral()), schema, DataSourceType.KSTREAM);
// Then:
assertThat(record, is(KsqlGenericRecord.of(GenericKey.genericKey((Object) null), GenericRow.genericRow((Object) null), 0)));
}
use of io.confluent.ksql.schema.ksql.LogicalSchema in project ksql by confluentinc.
the class GenericRecordFactoryTest method shouldThrowOnTypeMismatchCannotCoerce.
@Test
public void shouldThrowOnTypeMismatchCannotCoerce() {
// Given:
final LogicalSchema schema = LogicalSchema.builder().keyColumn(KEY, SqlTypes.STRING).valueColumn(COL0, SqlTypes.INTEGER).build();
final List<ColumnName> names = ImmutableList.of(KEY, COL0);
final Expression exp = new StringLiteral("a");
// When:
final KsqlException e = assertThrows(KsqlException.class, () -> recordFactory.build(names, ImmutableList.of(exp, exp), schema, DataSourceType.KSTREAM));
// Then:
assertThat(e.getMessage(), containsString("Expected type"));
}
Aggregations