mihaibudiu commented on code in PR #5211:
URL: https://github.com/apache/calcite/pull/5211#discussion_r3865570280
##########
core/src/main/java/org/apache/calcite/adapter/enumerable/EnumerableTableModifyRule.java:
##########
@@ -44,18 +93,89 @@ protected EnumerableTableModifyRule(Config config) {
@Override public @Nullable RelNode convert(RelNode rel) {
final TableModify modify = (TableModify) rel;
+ final RelOptCluster cluster = modify.getCluster();
final ModifiableTable modifiableTable =
modify.getTable().unwrap(ModifiableTable.class);
if (modifiableTable == null) {
return null;
}
final RelTraitSet traitSet =
modify.getTraitSet().replace(EnumerableConvention.INSTANCE);
+ RelNode input = convert(modify.getInput(), traitSet);
+ if (modify.isInsert() || modify.isUpdate()) {
+ // INSERT assigns stored columns; UPDATE assigns columns in the SET list.
+ RelDataType assignmentType = modify.isInsert()
+ ? RelOptTableImpl.realRowType(modify.getTable())
+ : modify.getCatalogReader().createTypeFromProjection(
+ modify.getTable().getRowType(),
+ requireNonNull(modify.getUpdateColumnList(),
"updateColumnList"));
+ if (modify.isFlattened()) {
+ // TableModify flattens its input, so flatten the target fields too.
+ assignmentType =
+ SqlTypeUtil.flattenRecordType(cluster.getTypeFactory(),
assignmentType, null);
+ }
+
+ final RexBuilder rexBuilder = cluster.getRexBuilder();
+ final List<RexNode> projects =
+ new ArrayList<>(rexBuilder.identityProjects(input.getRowType()));
+ final List<RexNode> checks = new ArrayList<>();
+ // UPDATE appends SET values to the old row; INSERT has only new values.
+ final int assignmentOffset = projects.size() -
assignmentType.getFieldCount();
+ for (RelDataTypeField field : assignmentType.getFieldList()) {
+ final int sourceOrdinal = assignmentOffset + field.getIndex();
+ final RexNode source = projects.get(sourceOrdinal);
+ final RelDataType targetType = field.getType();
+ final SqlTypeName targetName = targetType.getSqlTypeName();
+ if (SqlTypeUtil.inCharOrBinaryFamilies(targetType)) {
+ if (targetType.getPrecision() < 0) {
+ continue;
+ }
+ // Check character and binary lengths because their casts may
truncate.
Review Comment:
Yes, some kind of hook would be nice. I expect different systems have
different validation strategies for what is legal data. But I don't know how
the hook can be described in a generic way and what API one could use to
specify the hooks. This calls for a discussion in JIRA.
Perhaps the hook is just this rule: EnumerableTableModify; people can plug
in different implementations?
Perhaps the rule can take as parameter an Interface which provides a hook
for each type?
--
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.
To unsubscribe, e-mail: [email protected]
For queries about this service, please contact Infrastructure at:
[email protected]