/*
* If either the left or right operands are non-string, non-bit types,
* then we generate an implicit cast to VARCHAR.
*/
TypeCompiler tc = leftOperand.getTypeCompiler();
if (!(leftOperand.getTypeId().isStringTypeId() || leftOperand
.getTypeId().isBitTypeId())) {
DataTypeDescriptor dtd = DataTypeDescriptor.getBuiltInDataTypeDescriptor(
Types.VARCHAR, true, tc
.getCastToCharWidth(leftOperand .getTypeServices()));
// DERBY-2910 - Match current schema collation for implicit cast as we do for
// explicit casts per SQL Spec 6.12 (10)
dtd.setCollationType(getSchemaDescriptor(null).getCollationType());
dtd.setCollationDerivation(StringDataValue.COLLATION_DERIVATION_IMPLICIT);
leftOperand = (ValueNode) getNodeFactory().getNode(
C_NodeTypes.CAST_NODE,
leftOperand,
dtd,
getContextManager());
((CastNode) leftOperand).bindCastNodeOnly();
}
tc = rightOperand.getTypeCompiler();
if (!(rightOperand.getTypeId().isStringTypeId() || rightOperand
.getTypeId().isBitTypeId())) {
DataTypeDescriptor dtd = DataTypeDescriptor.getBuiltInDataTypeDescriptor(
Types.VARCHAR, true, tc
.getCastToCharWidth(rightOperand
.getTypeServices()));
// DERBY-2910 - Match current schema collation for implicit cast as we do for
// explicit casts per SQL Spec 6.12 (10)
dtd.setCollationType(getSchemaDescriptor(null).getCollationType());
dtd.setCollationDerivation(StringDataValue.COLLATION_DERIVATION_IMPLICIT);
rightOperand = (ValueNode) getNodeFactory().getNode(
C_NodeTypes.CAST_NODE,
rightOperand,
dtd,
getContextManager());
((CastNode) rightOperand).bindCastNodeOnly();
}
/*
* * Set the result type of this operator based on the operands. * By
* convention, the left operand gets to decide the result type * of a
* binary operator.
*/
tc = leftOperand.getTypeCompiler();
setType(resolveConcatOperation(leftOperand.getTypeServices(),
rightOperand.getTypeServices()));
/*
* * Make sure the maximum width set for the result doesn't exceed the
* result type's maximum width
*/
if (SanityManager.DEBUG) {
if (getTypeServices().getMaximumWidth() > getTypeId()
.getMaximumMaximumWidth()) {
SanityManager
.THROWASSERT("The maximum length "
+ getTypeServices().getMaximumWidth()
+ " for the result type "
+ getTypeId().getSQLTypeName()
+ " can't be greater than it's maximum width of result's typeid"
+ getTypeId().getMaximumMaximumWidth());
}
}
/*
* * Now that we know the target interface type, set it. This assumes *
* that both operands have the same interface type, which is a safe *
* assumption for the concatenation operator.
*/
this.setLeftRightInterfaceType(tc.interfaceName());
return this;
}