org.apache.calcite.sql2rel.SqlRexContext Java Examples

The following examples show how to use org.apache.calcite.sql2rel.SqlRexContext. You can vote up the ones you like or vote down the ones you don't like, and go to the original project or source file by following the links above each example. You may check out the related API usage on the sidebar.
Example #1
Source File: DrillAvgVarianceConvertlet.java    From Bats with Apache License 2.0 6 votes vote down vote up
public RexNode convertCall(SqlRexContext cx, SqlCall call) {
  assert call.operandCount() == 1;
  final SqlNode arg = call.operand(0);
  final SqlNode expr;
  switch (subtype) {
    case AVG:
      expr = expandAvg(arg);
      break;
    case STDDEV_POP:
      expr = expandVariance(arg, true, true);
      break;
    case STDDEV_SAMP:
      expr = expandVariance(arg, false, true);
      break;
    case VAR_POP:
      expr = expandVariance(arg, true, false);
      break;
    case VAR_SAMP:
      expr = expandVariance(arg, false, false);
      break;
    default:
      throw Util.unexpected(subtype);
  }
  return cx.convertExpression(expr);
}
 
Example #2
Source File: FlattenConvertlet.java    From dremio-oss with Apache License 2.0 6 votes vote down vote up
@Override
public RexNode convertCall(SqlRexContext cx, SqlCall call) {
  SqlFlattenOperator operator = (SqlFlattenOperator) call.getOperator();
  final List<RexNode> exprs = new LinkedList<>();

  for (SqlNode node : call.getOperandList()) {
    exprs.add(cx.convertExpression(node));
  }

  SqlFlattenOperator indexedOperator = operator.withIndex(((SqlValidatorImpl)cx.getValidator()).nextFlattenIndex());
  final RexBuilder rexBuilder = cx.getRexBuilder();
  // Since we don't have any way of knowing if the output of the flatten is nullable, we should always assume it is.
  // This is especially important when accelerating a count(column) query, because the normalizer will convert it to
  // a count(1) if it thinks this column is non-nullable, and then remove the flatten altogether. This is actually a
  // problem with the fact that flatten is not really a project operator (because it can output more than one row per input).
  RelDataType type = rexBuilder
    .getTypeFactory()
    .createTypeWithNullability(
      rexBuilder
        .getTypeFactory()
        .createSqlType(SqlTypeName.ANY),
      true
    );
  return rexBuilder.makeCall(type, indexedOperator, exprs);

}
 
Example #3
Source File: SqlDatePartOperator.java    From dremio-oss with Apache License 2.0 6 votes vote down vote up
@Override
public RexNode convertCall(SqlRexContext cx, SqlCall call) {
  final RexBuilder rexBuilder = cx.getRexBuilder();

  final SqlLiteral literal = (SqlLiteral) call.getOperandList().get(0);
  final String value = ((NlsString)literal.getValue()).getValue();
  TimeUnitRange range = VALID_PERIODS.get(value.toLowerCase());
  Preconditions.checkNotNull(range, "Unhandle range type: %s.", value);
  List<RexNode> exprs = new ArrayList<>();

  exprs.add(rexBuilder.makeFlag(range));
  exprs.add(cx.convertExpression(call.getOperandList().get(1)));

  RelDataTypeFactory typeFactory = cx.getTypeFactory();
  final RelDataType returnType
      = typeFactory.createTypeWithNullability(typeFactory.createSqlType(SqlTypeName.BIGINT), exprs.get(1).getType().isNullable());
  return rexBuilder.makeCall(returnType, SqlStdOperatorTable.EXTRACT, exprs);
}
 
Example #4
Source File: ConvertletTable.java    From dremio-oss with Apache License 2.0 6 votes vote down vote up
/** Converts a {@link SqlCall} to a {@link RexCall} with a perhaps different
 * operator. */
private RexNode convertCall(
    SqlRexContext cx,
    SqlCall call,
    SqlOperator op) {
  final List<SqlNode> operands = call.getOperandList();
  final RexBuilder rexBuilder = cx.getRexBuilder();
  final SqlOperandTypeChecker.Consistency consistency =
      op.getOperandTypeChecker() == null
          ? SqlOperandTypeChecker.Consistency.NONE
          : op.getOperandTypeChecker().getConsistency();
  final List<RexNode> exprs =
      convertExpressionList(cx, operands, consistency);
  RelDataType type = rexBuilder.deriveReturnType(op, exprs);
  return rexBuilder.makeCall(type, op, RexUtil.flatten(exprs, op));
}
 
Example #5
Source File: ConvertletTable.java    From dremio-oss with Apache License 2.0 6 votes vote down vote up
private static List<RexNode> convertExpressionList(SqlRexContext cx,
    List<SqlNode> nodes, SqlOperandTypeChecker.Consistency consistency) {
  final List<RexNode> exprs = Lists.newArrayList();
  for (SqlNode node : nodes) {
    exprs.add(cx.convertExpression(node));
  }
  if (exprs.size() > 1) {
    final RelDataType type =
        consistentType(cx, consistency, RexUtil.types(exprs));
    if (type != null) {
      final List<RexNode> oldExprs = Lists.newArrayList(exprs);
      exprs.clear();
      for (RexNode expr : oldExprs) {
        exprs.add(cx.getRexBuilder().ensureType(type, expr, true));
      }
    }
  }
  return exprs;
}
 
Example #6
Source File: ChronoConvertlets.java    From dremio-oss with Apache License 2.0 6 votes vote down vote up
@Override
public RexNode convertCall(SqlRexContext cx, SqlCall call) {
  final int timeZoneIndex = getContextInformation().getRootFragmentTimeZone();
  final DateTimeZone timeZone = DateTimeZone.forID(JodaDateUtility.getTimeZone(timeZoneIndex));
  final LocalDateTime dateTime = new LocalDateTime(getContextInformation().getQueryStartTime(), timeZone);
  final long queryStartTime =
      (dateTime.getHourOfDay() * DateUtility.hoursToMillis) +
          (dateTime.getMinuteOfHour() * DateUtility.minutesToMillis) +
          (dateTime.getSecondOfMinute() * DateUtility.secondsToMillis) +
          (dateTime.getMillisOfSecond());

  return cx.getRexBuilder()
      .makeTimeLiteral(
          DateTimes.toDateTime(new LocalDateTime(queryStartTime, DateTimeZone.UTC))
              .toCalendar(null), // null sets locale to default locale
          getReturnTypePrecision(cx, call));
}
 
Example #7
Source File: ChronoConvertlets.java    From dremio-oss with Apache License 2.0 6 votes vote down vote up
@Override
public RexNode convertCall(SqlRexContext cx, SqlCall call) {
  final int timeZoneIndex = getContextInformation().getRootFragmentTimeZone();
  final DateTimeZone timeZone = DateTimeZone.forID(JodaDateUtility.getTimeZone(timeZoneIndex));
  final LocalDateTime dateTime = new LocalDateTime(getContextInformation().getQueryStartTime(), timeZone);
  final long midNightAsMillis =
      new DateMidnight(dateTime.getYear(), dateTime.getMonthOfYear(), dateTime.getDayOfMonth(),
          timeZone)
          .withZoneRetainFields(DateTimeZone.UTC)
          .getMillis();

  return cx.getRexBuilder()
      .makeDateLiteral(DateTimes.toDateTime(
          new LocalDateTime(midNightAsMillis, DateTimeZone.UTC))
          .toCalendar(null)); // null sets locale to default locale
}
 
Example #8
Source File: DrillExtractConvertlet.java    From Bats with Apache License 2.0 5 votes vote down vote up
@Override
public RexNode convertCall(SqlRexContext cx, SqlCall call) {
  final RexBuilder rexBuilder = cx.getRexBuilder();
  final List<SqlNode> operands = call.getOperandList();
  final List<RexNode> exprs = new LinkedList<>();

  String timeUnit = ((SqlIntervalQualifier) operands.get(0)).timeUnitRange.toString();

  RelDataTypeFactory typeFactory = cx.getTypeFactory();

  //RelDataType nullableReturnType =

  for (SqlNode node: operands) {
     exprs.add(cx.convertExpression(node));
  }

  final RelDataType returnType;
  if(call.getOperator() == SqlStdOperatorTable.EXTRACT) {
    // Legacy code:
    // The return type is wrong!
    // Legacy code choose SqlTypeName.BIGINT simply to avoid conflicting against Calcite's inference mechanism
    // (, which chose BIGINT in validation phase already)
    // Determine NULL-able using 2nd argument's Null-able.
    returnType = typeFactory.createTypeWithNullability(typeFactory.createSqlType(SqlTypeName.BIGINT), exprs.get(1).getType().isNullable());
  } else {
    // Determine NULL-able using 2nd argument's Null-able.
    returnType = typeFactory.createTypeWithNullability(
        typeFactory.createSqlType(
            TypeInferenceUtils.getSqlTypeNameForTimeUnit(timeUnit)),
        exprs.get(1).getType().isNullable());
  }

  return rexBuilder.makeCall(returnType, call.getOperator(), exprs);
}
 
Example #9
Source File: EqualityConvertlet.java    From dremio-oss with Apache License 2.0 5 votes vote down vote up
private static List<RexNode> convertExpressionList(SqlRexContext cx,
                                                   List<SqlNode> nodes) {
  final List<RexNode> exprs = Lists.newArrayList();
  for (SqlNode node : nodes) {
    exprs.add(cx.convertExpression(node));
  }
  if (exprs.size() > 1) {
    final SqlOperandTypeChecker.Consistency consistency = Consistency.LEAST_RESTRICTIVE;
    final List<RelDataType> types = RexUtil.types(exprs);
    final RelDataType type;
    if (allExactNumeric(types) && anyDecimal(types)) {
      // for mixed types, INT and BIGINT will be treated as DECIMAL(10,0) and DECIMAL(19,0) respectively
      type = consistentDecimalType(cx.getTypeFactory(), types);
    } else {
      // if there are no Decimal types or some of the types are non-exact, fall back to default Calcite
      // behavior which will convert to Double
      type = SqlTypeUtil.consistentType(cx.getTypeFactory(), consistency, types);
    }
    if (type != null) {
      final List<RexNode> oldExprs = Lists.newArrayList(exprs);
      exprs.clear();
      for (RexNode expr : oldExprs) {
        exprs.add(cx.getRexBuilder().ensureType(type, expr, true));
      }
    }
  }
  return exprs;
}
 
Example #10
Source File: ConvertletTable.java    From dremio-oss with Apache License 2.0 5 votes vote down vote up
@Override
public RexNode convertCall(SqlRexContext cx, SqlCall call) {
  final List<SqlNode> operands = call.getOperandList();
  final List<RexNode> exprs = new LinkedList<>();

  for (SqlNode node: operands) {
    exprs.add(cx.convertExpression(node));
  }

  final RelDataType returnType = cx.getRexBuilder().deriveReturnType(call.getOperator(), exprs);
  return cx.getRexBuilder().makeCall(returnType, call.getOperator(), exprs);
}
 
Example #11
Source File: ChronoConvertlets.java    From dremio-oss with Apache License 2.0 5 votes vote down vote up
static int getReturnTypePrecision(SqlRexContext cx, SqlCall call) {
  return cx.getRexBuilder()
      .deriveReturnType(call.getOperator(),
          call.getOperandList()
              .stream()
              .map(cx::convertExpression)
              .collect(Collectors.toList()))
      .getPrecision();
}
 
Example #12
Source File: ChronoConvertlets.java    From dremio-oss with Apache License 2.0 5 votes vote down vote up
@Override
public RexNode convertCall(SqlRexContext cx, SqlCall call) {
  return cx.getRexBuilder()
      .makeTimestampLiteral(
          DateTimes.toDateTime(
              new LocalDateTime(getContextInformation().getQueryStartTime(),
                  DateTimeZone.UTC))
              .toCalendar(null), // null sets locale to default locale
          getReturnTypePrecision(cx, call));
}
 
Example #13
Source File: HiveConvertletTable.java    From marble with Apache License 2.0 4 votes vote down vote up
@Override protected RexNode convertCast(SqlRexContext cx,
    SqlCall call) {
  RelDataTypeFactory typeFactory = cx.getTypeFactory();
  assert call.getKind() == SqlKind.CAST;
  final SqlNode left = call.operand(0);
  final SqlNode right = call.operand(1);
  if (right instanceof SqlIntervalQualifier) {
    final SqlIntervalQualifier intervalQualifier =
        (SqlIntervalQualifier) right;
    if (left instanceof SqlIntervalLiteral) {
      RexLiteral sourceInterval =
          (RexLiteral) cx.convertExpression(left);
      BigDecimal sourceValue =
          (BigDecimal) sourceInterval.getValue();
      RexLiteral castedInterval =
          cx.getRexBuilder().makeIntervalLiteral(sourceValue,
              intervalQualifier);
      return castToValidatedType(cx, call, castedInterval);
    } else if (left instanceof SqlNumericLiteral) {
      RexLiteral sourceInterval =
          (RexLiteral) cx.convertExpression(left);
      BigDecimal sourceValue =
          (BigDecimal) sourceInterval.getValue();
      final BigDecimal multiplier = intervalQualifier.getUnit().multiplier;
      sourceValue = sourceValue.multiply(multiplier);
      RexLiteral castedInterval =
          cx.getRexBuilder().makeIntervalLiteral(
              sourceValue,
              intervalQualifier);
      return castToValidatedType(cx, call, castedInterval);
    }
    return castToValidatedType(cx, call, cx.convertExpression(left));
  }
  SqlDataTypeSpec dataType = (SqlDataTypeSpec) right;
  //considering hive cast: select cast('' as double) will return null,
  // so we make a cast call always be nullable
  RelDataType type = dataType.deriveType(typeFactory, true);
  if (SqlUtil.isNullLiteral(left, false)) {
    final SqlValidatorImpl validator = (SqlValidatorImpl) cx.getValidator();
    validator.setValidatedNodeType(left, type);
    return cx.convertExpression(left);
  }
  RexNode arg = cx.convertExpression(left);
  if (type == null) {
    type = cx.getValidator().getValidatedNodeType(dataType.getTypeName());
  }
  if (arg.getType().isNullable()) {
    type = typeFactory.createTypeWithNullability(type, true);
  }
  if (null != dataType.getCollectionsTypeName()) {
    final RelDataType argComponentType =
        arg.getType().getComponentType();
    final RelDataType componentType = type.getComponentType();
    if (argComponentType.isStruct()
        && !componentType.isStruct()) {
      RelDataType tt =
          typeFactory.builder()
              .add(
                  argComponentType.getFieldList().get(0).getName(),
                  componentType)
              .build();
      tt = typeFactory.createTypeWithNullability(
          tt,
          componentType.isNullable());
      boolean isn = type.isNullable();
      type = typeFactory.createMultisetType(tt, -1);
      type = typeFactory.createTypeWithNullability(type, isn);
    }
  }
  return cx.getRexBuilder().makeCast(type, arg);
}
 
Example #14
Source File: EqualityConvertlet.java    From dremio-oss with Apache License 2.0 4 votes vote down vote up
@Override
public RexNode convertCall(SqlRexContext cx, SqlCall call) {
  return convertEquality(cx, call);
}
 
Example #15
Source File: EqualityConvertlet.java    From dremio-oss with Apache License 2.0 4 votes vote down vote up
private static RexNode convertEquality(SqlRexContext cx, SqlCall call) {

    final List<SqlNode> operands = call.getOperandList();
    final RexBuilder rexBuilder = cx.getRexBuilder();
    final List<RexNode> exprs =
      convertExpressionList(cx, operands);
    SqlOperator op = call.getOperator();
    RelDataType type = rexBuilder.deriveReturnType(op, exprs);
    RexCall convertedCall = (RexCall) rexBuilder.makeCall(type, op, RexUtil.flatten(exprs, op));

    // The following is copied from Calcite's StdConvertletTable.convertEqualsOrNotEquals()
    final RexNode op0 = convertedCall.getOperands().get(0);
    final RexNode op1 = convertedCall.getOperands().get(1);
    final RexNode booleanOp;
    final RexNode integerOp;

    if (op0.getType().getSqlTypeName() == SqlTypeName.BOOLEAN
      && SqlTypeName.INT_TYPES.contains(op1.getType().getSqlTypeName())) {
      booleanOp = op0;
      integerOp = op1;
    } else if (SqlTypeName.INT_TYPES.contains(op0.getType().getSqlTypeName())
      && op1.getType().getSqlTypeName() == SqlTypeName.BOOLEAN) {
      booleanOp = op1;
      integerOp = op0;
    } else {
      return convertedCall;
    }

    SqlOperator newOp = (op.getKind() == SqlKind.EQUALS || op.getKind() == SqlKind.NOT_EQUALS) ?
      SqlStdOperatorTable.EQUALS :
      SqlStdOperatorTable.IS_NOT_DISTINCT_FROM;

    return rexBuilder.makeCall(call.getOperator(),
      booleanOp,
      rexBuilder.makeCall(
        SqlStdOperatorTable.CASE,
        rexBuilder.makeCall(
          newOp,
          integerOp,
          rexBuilder.makeZeroLiteral(integerOp.getType())),
        rexBuilder.makeLiteral(false),
        rexBuilder.makeLiteral(true)));
  }
 
Example #16
Source File: ConvertletTable.java    From dremio-oss with Apache License 2.0 4 votes vote down vote up
private static RelDataType consistentType(SqlRexContext cx,
    SqlOperandTypeChecker.Consistency consistency, List<RelDataType> types) {
  switch (consistency) {
  case COMPARE:
    final Set<RelDataTypeFamily> families =
        Sets.newHashSet(RexUtil.families(types));
    if (families.size() < 2) {
      // All arguments are of same family. No need for explicit casts.
      return null;
    }
    final List<RelDataType> nonCharacterTypes = Lists.newArrayList();
    for (RelDataType type : types) {
      if (type.getFamily() != SqlTypeFamily.CHARACTER) {
        nonCharacterTypes.add(type);
      }
    }
    if (!nonCharacterTypes.isEmpty()) {
      final int typeCount = types.size();
      types = nonCharacterTypes;
      if (nonCharacterTypes.size() < typeCount) {
        final RelDataTypeFamily family =
            nonCharacterTypes.get(0).getFamily();
        if (family instanceof SqlTypeFamily) {
          // The character arguments might be larger than the numeric
          // argument. Give ourselves some headroom.
          switch ((SqlTypeFamily) family) {
          case INTEGER:
          case NUMERIC:
            nonCharacterTypes.add(
                cx.getTypeFactory().createSqlType(SqlTypeName.BIGINT));
          }
        }
      }
    }
    // fall through
  case LEAST_RESTRICTIVE:
    return cx.getTypeFactory().leastRestrictive(types);
  default:
    return null;
  }
}