RelDataType sourceType = sourceFields.get(i).getType(); RelDataType targetType = targetFields.get(i).getType(); if (!SqlTypeUtil.canAssignFrom(targetType, sourceType)) { String targetTypeString; String sourceTypeString; if (SqlTypeUtil.areCharacterSetsMismatched( sourceType, targetType)) {
&& SqlTypeUtil.equalSansNullability(dTFactory, call.getType(), call.operands.get(0).getType())) { return args.get(0);
private SqlNode maybeCast(SqlNode node, RelDataType currentType, RelDataType desiredType) { return currentType.equals(desiredType) || (currentType.isNullable() != desiredType.isNullable() && typeFactory.createTypeWithNullability(currentType, desiredType.isNullable()).equals(desiredType)) ? node : SqlStdOperatorTable.CAST.createCall(SqlParserPos.ZERO, node, SqlTypeUtil.convertTypeToSpec(desiredType)); }
private List<RexNode> rewriteToDateChildren(List<RexNode> childRexNodeLst) { List<RexNode> newChildRexNodeLst = new ArrayList<RexNode>(); assert childRexNodeLst.size() == 1; RexNode child = childRexNodeLst.get(0); if (SqlTypeUtil.isDatetime(child.getType()) || SqlTypeUtil.isInterval(child.getType())) { newChildRexNodeLst.add(child); } else { newChildRexNodeLst.add(makeCast(SqlTypeName.TIMESTAMP, child)); } return newChildRexNodeLst; }
RelDataType toType, RelDataType fromType) { if (isAny(toType) || isAny(fromType)) { return true; return false; return canAssignFrom(toType.getComponentType(), fromType.getComponentType()); if (areCharacterSetsMismatched(toType, fromType)) { return false;
/** * @return true if type is numeric */ public static boolean isNumeric(RelDataType type) { return isExactNumeric(type) || isApproximateNumeric(type); }
private static boolean canConvert(RelDataType fromType, RelDataType toType) { return SqlTypeUtil.canAssignFrom(toType, fromType); }
private SqlKind getOp(RexCall call) { SqlKind op = call.getKind(); if (call.getKind().equals(SqlKind.OTHER_FUNCTION) && SqlTypeUtil.inBooleanFamily(call.getType())) { SqlOperator sqlOp = call.getOperator(); String opName = (sqlOp != null) ? sqlOp.getName() : ""; if (opName.equalsIgnoreCase("in")) { op = SqlKind.IN; } } return op; }
@Override public RexNode makeCast( RelDataType type, RexNode exp, boolean matchNullability) { // Special case: bypassing Calcite for interval types if (!(exp instanceof RexLiteral) && SqlTypeUtil.isExactNumeric(type) && SqlTypeUtil.isInterval(exp.getType())) { return makeAbstractCast(type, exp); } RexNode castRexNode = super.makeCast(type, exp, matchNullability); // If we have a CAST(A, TYPE) and A is already of the same TYPE (including nullability), // then return just A. if (castRexNode instanceof RexCall && castRexNode.getKind() == SqlKind.CAST && castRexNode.getType().equals(((RexCall) castRexNode).getOperands().get(0).getType())) { return ((RexCall) castRexNode).getOperands().get(0); } return castRexNode; } }
public boolean checkSingleOperandType(SqlCallBinding callBinding, SqlNode node, int iFormalOperand, boolean throwOnFailure) { assert 0 == iFormalOperand; RelDataType type = callBinding.getValidator().deriveType(callBinding.getScope(), node); boolean valid = false; if (type.isStruct() && type.getFieldList().size() == 2) { final RelDataType t0 = type.getFieldList().get(0).getType(); final RelDataType t1 = type.getFieldList().get(1).getType(); if (SqlTypeUtil.isDatetime(t0)) { if (SqlTypeUtil.isDatetime(t1)) { // t0 must be comparable with t1; (DATE, TIMESTAMP) is not valid if (SqlTypeUtil.sameNamedType(t0, t1)) { valid = true; } } else if (SqlTypeUtil.isInterval(t1)) { valid = true; } } } if (!valid && throwOnFailure) { throw callBinding.newValidationSignatureError(); } return valid; }
@SuppressWarnings("deprecation") private RelDataType deriveRowType(RelDataTypeFactory typeFactory) { RelDataTypeFactory.FieldInfoBuilder fieldInfo = typeFactory.builder(); for (ColumnDesc column : sourceColumns) { RelDataType sqlType = createSqlType(typeFactory, column.getUpgradedType(), column.isNullable()); sqlType = SqlTypeUtil.addCharsetAndCollation(sqlType, typeFactory); fieldInfo.add(column.getName(), sqlType); } return typeFactory.createStructType(fieldInfo); }
@Test public void testTypesIsSameFamilyWithCharTypes() { assertThat(areSameFamily(ImmutableList.of(f.sqlVarchar, f.sqlVarchar)), is(true)); assertThat(areSameFamily(ImmutableList.of(f.sqlVarchar, f.sqlChar)), is(true)); assertThat(areSameFamily(ImmutableList.of(f.sqlVarchar, f.sqlVarcharNullable)), is(true)); }
private void checkPrecision(int p0, int p1, int expectedMax, int expectedComparison) { assertThat(SqlTypeUtil.maxPrecision(p0, p1), is(expectedMax)); assertThat(SqlTypeUtil.maxPrecision(p1, p0), is(expectedMax)); assertThat(SqlTypeUtil.maxPrecision(p0, p0), is(p0)); assertThat(SqlTypeUtil.maxPrecision(p1, p1), is(p1)); assertThat(SqlTypeUtil.comparePrecision(p0, p1), is(expectedComparison)); assertThat(SqlTypeUtil.comparePrecision(p0, p0), is(0)); assertThat(SqlTypeUtil.comparePrecision(p1, p1), is(0)); }
/** * Retrieves an interval or decimal node's integer representation * * @param node the interval or decimal value as an opaque type * @return an integer representation of the decimal value */ public RexNode decodeIntervalOrDecimal(RexNode node) { assert SqlTypeUtil.isDecimal(node.getType()) || SqlTypeUtil.isInterval(node.getType()); RelDataType bigintType = typeFactory.createSqlType(SqlTypeName.BIGINT); return makeReinterpretCast( matchNullability(bigintType, node), node, makeLiteral(false)); }
RelDataType returnType = callBinding.getValidator().deriveType(callBinding.getScope(), right); if (!SqlTypeUtil.canCastFrom(returnType, validatedNodeType, true)) { if (throwOnFailure) { throw callBinding.newError( if (SqlTypeUtil.areCharacterSetsMismatched( validatedNodeType, returnType)) {
private RexNode expandMod(RexCall call, List<RexNode> operands) { assert SqlTypeUtil.isExactNumeric(typeA); assert SqlTypeUtil.isExactNumeric(typeB); if (scaleA != 0 || scaleB != 0) { throw RESOURCE.argumentMustHaveScaleZero(call.getOperator().getName()) .ex(); } RexNode result = builder.makeCall( call.getOperator(), accessValue(operands.get(0)), accessValue(operands.get(1))); RelDataType retType = call.getType(); if (SqlTypeUtil.isDecimal(retType)) { return encodeValue(result, retType); } return ensureType( call.getType(), result); } }
switch (toType.getSqlTypeName()) { case CHAR: return SqlTypeUtil.comparePrecision(toType.getPrecision(), length) == 0; case VARCHAR: return SqlTypeUtil.comparePrecision(toType.getPrecision(), length) >= 0; default: throw new AssertionError(toType); switch (toType.getSqlTypeName()) { case BINARY: return SqlTypeUtil.comparePrecision(toType.getPrecision(), length) == 0; case VARBINARY: return SqlTypeUtil.comparePrecision(toType.getPrecision(), length) >= 0; default: throw new AssertionError(toType);
/** * Convenience method for reading characteristics of operands (such as * scale, precision, whole digits) into an ArithmeticExpander. The * operands are restricted by the following contraints: * * <ul> * <li>there are exactly two operands * <li>both are exact numeric types * </ul> */ private void analyzeOperands(List<RexNode> operands) { assert operands.size() == 2; typeA = operands.get(0).getType(); typeB = operands.get(1).getType(); assert SqlTypeUtil.isExactNumeric(typeA) && SqlTypeUtil.isExactNumeric(typeB); scaleA = typeA.getScale(); scaleB = typeB.getScale(); }
private Pair<RexNode, RexNode> convertOverlapsOperand(SqlRexContext cx, SqlParserPos pos, SqlNode operand) { final SqlNode a0; final SqlNode a1; switch (operand.getKind()) { case ROW: a0 = ((SqlCall) operand).operand(0); final SqlNode a10 = ((SqlCall) operand).operand(1); final RelDataType t1 = cx.getValidator().getValidatedNodeType(a10); if (SqlTypeUtil.isInterval(t1)) { // make t1 = t0 + t1 when t1 is an interval. a1 = plus(pos, a0, a10); } else { a1 = a10; } break; default: a0 = operand; a1 = operand; } final RexNode r0 = cx.convertExpression(a0); final RexNode r1 = cx.convertExpression(a1); return Pair.of(r0, r1); }
RelDataType toType, RelDataType fromType) { if (isAny(toType) || isAny(fromType)) { return true; return false; return canAssignFrom(toType.getComponentType(), fromType.getComponentType()); if (areCharacterSetsMismatched(toType, fromType)) { return false;