fix print type scale bug
This commit is contained in:
parent
65e00203c5
commit
c19f7ea941
36
deps/oblib/src/common/object/ob_obj_type.cpp
vendored
36
deps/oblib/src/common/object/ob_obj_type.cpp
vendored
@ -191,7 +191,7 @@ typedef int (*obSqlTypeStrWithoutAccuracyFunc)(char* buff, int64_t buff_length,
|
||||
}
|
||||
|
||||
// For datetime/timestamp/time
|
||||
#define DEF_TYPE_STR_FUNCS_SCALE(TYPE, STYPE1, STYPE2, STYPE3) \
|
||||
#define DEF_TYPE_STR_FUNCS_SCALE_DEFAULT_ZERO(TYPE, STYPE1, STYPE2, STYPE3) \
|
||||
int ob_##TYPE##_str(char* buff, \
|
||||
int64_t buff_length, \
|
||||
int64_t& pos, \
|
||||
@ -216,6 +216,28 @@ typedef int (*obSqlTypeStrWithoutAccuracyFunc)(char* buff, int64_t buff_length,
|
||||
return ret; \
|
||||
}
|
||||
|
||||
// For otimestamp, need print (0) if scale is zero
|
||||
#define DEF_TYPE_STR_FUNCS_SCALE(TYPE, STYPE1, STYPE2) \
|
||||
int ob_##TYPE##_str(char *buff, \
|
||||
int64_t buff_length, \
|
||||
int64_t &pos, \
|
||||
int64_t length, \
|
||||
int64_t precision, \
|
||||
int64_t scale, \
|
||||
ObCollationType coll_type) \
|
||||
{ \
|
||||
int ret = OB_SUCCESS; \
|
||||
UNUSED(length); \
|
||||
UNUSED(precision); \
|
||||
UNUSED(coll_type); \
|
||||
if (scale < 0) { \
|
||||
ret = databuff_printf(buff, buff_length, pos, STYPE1 STYPE2); \
|
||||
} else { \
|
||||
ret = databuff_printf(buff, buff_length, pos, STYPE1 "(%ld)" STYPE2, scale); \
|
||||
} \
|
||||
return ret; \
|
||||
}
|
||||
|
||||
// For number/float/double (unsigned)
|
||||
#define DEF_TYPE_STR_FUNCS_PRECISION_SCALE(TYPE, STYPE1, STYPE2, STYPE3) \
|
||||
int ob_##TYPE##_str(char* buff, \
|
||||
@ -361,14 +383,14 @@ DEF_TYPE_STR_FUNCS_PRECISION_SCALE(ufloat, "float", " unsigned", "");
|
||||
DEF_TYPE_STR_FUNCS_PRECISION_SCALE(udouble, "double", " unsigned", "");
|
||||
DEF_TYPE_STR_FUNCS_PRECISION_SCALE(number, "decimal", "", "number");
|
||||
DEF_TYPE_STR_FUNCS_PRECISION_SCALE(unumber, "decimal", " unsigned", "");
|
||||
DEF_TYPE_STR_FUNCS_SCALE(datetime, "datetime", "", "date");
|
||||
DEF_TYPE_STR_FUNCS_SCALE(timestamp, "timestamp", "", "timestamp");
|
||||
DEF_TYPE_STR_FUNCS_SCALE_DEFAULT_ZERO(datetime, "datetime", "", "date");
|
||||
DEF_TYPE_STR_FUNCS_SCALE_DEFAULT_ZERO(timestamp, "timestamp", "", "timestamp");
|
||||
DEF_TYPE_STR_FUNCS(date, "date", "");
|
||||
DEF_TYPE_STR_FUNCS_SCALE(time, "time", "", "time");
|
||||
DEF_TYPE_STR_FUNCS_SCALE_DEFAULT_ZERO(time, "time", "", "time");
|
||||
DEF_TYPE_STR_FUNCS_PRECISION(year, "year", "");
|
||||
DEF_TYPE_STR_FUNCS_SCALE(timestamp_tz, "timestamp", " with time zone", "timestamp");
|
||||
DEF_TYPE_STR_FUNCS_SCALE(timestamp_ltz, "timestamp", " with local time zone", "timestamp");
|
||||
DEF_TYPE_STR_FUNCS_SCALE(timestamp_nano, "timestamp", "", "timestamp");
|
||||
DEF_TYPE_STR_FUNCS_SCALE(timestamp_tz, "timestamp", " with time zone");
|
||||
DEF_TYPE_STR_FUNCS_SCALE(timestamp_ltz, "timestamp", " with local time zone");
|
||||
DEF_TYPE_STR_FUNCS_SCALE(timestamp_nano, "timestamp", "");
|
||||
DEF_TYPE_STR_FUNCS_LENGTH(varchar, "varchar", "varbinary", "varchar2");
|
||||
DEF_TYPE_STR_FUNCS_LENGTH(char, "char", "binary", "char");
|
||||
DEF_TYPE_STR_FUNCS_LENGTH(hex_string, "hex_string", "hex_string", "hex_string");
|
||||
|
18
deps/oblib/src/lib/timezone/ob_time_convert.cpp
vendored
18
deps/oblib/src/lib/timezone/ob_time_convert.cpp
vendored
@ -5807,19 +5807,25 @@ int ObTimeConverter::otimestamp_add_nsecond(const ObOTimestampData ori_value, co
|
||||
return ret;
|
||||
}
|
||||
|
||||
int ObTimeConverter::calc_last_date_of_the_month(const int64_t ori_date_value, int64_t& result_date_value, const ObObjType dest_type)
|
||||
int ObTimeConverter::calc_last_date_of_the_month(
|
||||
const int64_t ori_datetime_value, int64_t &result_date_value, const ObObjType dest_type, const bool is_dayofmonth)
|
||||
{
|
||||
int ret = OB_SUCCESS;
|
||||
ObTime ob_time(DT_TYPE_DATETIME);
|
||||
ObTimeConvertCtx cvrt_ctx(NULL, false); // utc time no timezone
|
||||
|
||||
if (OB_FAIL(datetime_to_ob_time(ori_date_value, NULL, ob_time))) {
|
||||
LOG_WARN("failed to convert date to obtime parts", K(ret), K(ori_date_value));
|
||||
const bool is_oracle_mode = lib::is_oracle_mode();
|
||||
if (!is_oracle_mode && ZERO_DATETIME == ori_datetime_value) {
|
||||
ret = OB_INVALID_DATE_VALUE;
|
||||
LOG_WARN("invalid datetime", K(ret), K(ori_datetime_value));
|
||||
} else if (OB_FAIL(datetime_to_ob_time(ori_datetime_value, NULL, ob_time))) {
|
||||
LOG_WARN("failed to convert date to obtime parts", K(ret), K(ori_datetime_value));
|
||||
} else {
|
||||
int is_leap = IS_LEAP_YEAR(ob_time.parts_[DT_YEAR]);
|
||||
ob_time.parts_[DT_MDAY] = DAYS_PER_MON[is_leap][ob_time.parts_[DT_MON]];
|
||||
|
||||
if (OB_FAIL(validate_basic_part_of_ob_time_oracle(ob_time))) {
|
||||
if (is_oracle_mode && OB_FAIL(validate_basic_part_of_ob_time_oracle(ob_time))) {
|
||||
LOG_WARN("failed to validate ob_time", K(ret), K(ob_time));
|
||||
} else if (!is_oracle_mode && OB_FAIL(validate_datetime(ob_time, is_dayofmonth))) {
|
||||
LOG_WARN("failed to validate ob_time", K(ret), K(ob_time));
|
||||
} else {
|
||||
ob_time.parts_[DT_DATE] = ob_time_to_date(ob_time);
|
||||
@ -5839,7 +5845,7 @@ int ObTimeConverter::calc_last_date_of_the_month(const int64_t ori_date_value, i
|
||||
|
||||
}
|
||||
}
|
||||
LOG_DEBUG("debug calc_last_mday", K(ob_time), K(ori_date_value), K(result_date_value));
|
||||
LOG_DEBUG("debug calc_last_mday", K(ob_time), K(ori_datetime_value), K(result_date_value));
|
||||
return ret;
|
||||
}
|
||||
|
||||
|
@ -416,7 +416,8 @@ public:
|
||||
const ObTimeZoneInfo* tz_info, const int64_t nmonth, ObOTimestampData& result_value);
|
||||
static int otimestamp_add_nsecond(const ObOTimestampData ori_value, const int64_t nsecond,
|
||||
const int32_t fractional_second, ObOTimestampData& result_value);
|
||||
static int calc_last_date_of_the_month(const int64_t ori_date_value, int64_t& result_date_value, const ObObjType dest_type);
|
||||
static int calc_last_date_of_the_month(
|
||||
const int64_t ori_date_value, int64_t& result_date_value, const ObObjType dest_type, const bool is_dayofmonth);
|
||||
static int calc_next_date_of_the_wday(
|
||||
const int64_t ori_date_value, const ObString& wday_name, int64_t& result_date_value);
|
||||
static int calc_days_and_months_between_dates(
|
||||
|
@ -8272,7 +8272,7 @@ int ob_obj_accuracy_check_only(const ObAccuracy& accuracy, const ObCollationType
|
||||
}
|
||||
|
||||
int ob_obj_to_ob_time_with_date(
|
||||
const ObObj& obj, const ObTimeZoneInfo* tz_info, ObTime& ob_time, bool is_dayofmonth /*false*/)
|
||||
const ObObj& obj, const ObTimeZoneInfo* tz_info, ObTime& ob_time, const int64_t cur_ts_value, bool is_dayofmonth /*false*/)
|
||||
{
|
||||
int ret = OB_SUCCESS;
|
||||
switch (obj.get_type_class()) {
|
||||
@ -8296,6 +8296,15 @@ int ob_obj_to_ob_time_with_date(
|
||||
break;
|
||||
}
|
||||
case ObTimeTC: {
|
||||
int64_t datetime_val = 0;
|
||||
if (OB_FAIL(
|
||||
ObTimeConverter::time_to_datetime(obj.get_time(), cur_ts_value, NULL, datetime_val, ObDateTimeType))) {
|
||||
LOG_WARN("time_to_datetime failed", K(ret), K(obj), K(cur_ts_value));
|
||||
} else if (OB_FAIL(ObTimeConverter::datetime_to_ob_time(datetime_val, NULL, ob_time))) {
|
||||
LOG_WARN("datetime to time failed", K(ret));
|
||||
}
|
||||
break;
|
||||
|
||||
ret = ObTimeConverter::time_to_ob_time(obj.get_time(), ob_time);
|
||||
break;
|
||||
}
|
||||
|
@ -257,7 +257,7 @@ typedef int (*ObCastEnumOrSetFunc)(
|
||||
bool cast_supported(const ObObjType orig_type, const ObCollationType orig_cs_type, const ObObjType expect_type,
|
||||
const ObCollationType expect_cs_type);
|
||||
int ob_obj_to_ob_time_with_date(
|
||||
const ObObj& obj, const ObTimeZoneInfo* tz_info, ObTime& ob_time, bool is_dayofmonth = false);
|
||||
const ObObj& obj, const ObTimeZoneInfo* tz_info, ObTime& ob_time, const int64_t cur_ts_value, bool is_dayofmonth = false);
|
||||
int ob_obj_to_ob_time_without_date(const ObObj& obj, const ObTimeZoneInfo* tz_info, ObTime& ob_time);
|
||||
|
||||
// CM_STRING_INTEGER_TRUNC only affect string to [unsigned] integer cast.
|
||||
|
@ -900,6 +900,7 @@ static OB_INLINE int common_string_datetime(
|
||||
if (CAST_FAIL(ObTimeConverter::str_to_datetime(in_str, cvrt_ctx, out_val, &res_scale))) {
|
||||
LOG_WARN("str_to_datetime failed", K(ret), K(in_str));
|
||||
}
|
||||
LOG_INFO("stt, commont string to datetime", K(in_str), K(out_val), K(ret));
|
||||
}
|
||||
if (OB_SUCC(ret)) {
|
||||
SET_RES_DATETIME(out_val);
|
||||
|
@ -610,14 +610,26 @@ int ObExprLastDay::calc_result1(common::ObObj& result, const common::ObObj& obj,
|
||||
UNUSED(expr_ctx);
|
||||
int64_t ori_date_utc = 0;
|
||||
int64_t res_date_utc = 0;
|
||||
|
||||
const ObObjType res_type = is_oracle_mode() ? ObDateTimeType : ObDateType;
|
||||
if (obj.is_null()) {
|
||||
ObSQLSessionInfo *session = NULL;
|
||||
if (OB_ISNULL(session = expr_ctx.my_session_)) {
|
||||
ret = OB_ERR_UNEXPECTED;
|
||||
LOG_WARN("session is null", K(ret));
|
||||
} else if (obj.is_null()) {
|
||||
result.set_null();
|
||||
} else if (OB_FAIL(obj.get_datetime(ori_date_utc))) {
|
||||
LOG_WARN("fail to get datetime", K(ret));
|
||||
} else if (OB_FAIL(ObTimeConverter::calc_last_date_of_the_month(ori_date_utc, res_date_utc,
|
||||
res_type))) {
|
||||
} else if (OB_FAIL(ObTimeConverter::calc_last_date_of_the_month(ori_date_utc, res_date_utc, res_type, false))) {
|
||||
LOG_WARN("fail to calc last mday", K(ret), K(ori_date_utc), K(res_type));
|
||||
if (!is_oracle_mode()) {
|
||||
uint64_t cast_mode = 0;
|
||||
ObSQLUtils::get_default_cast_mode(session->get_stmt_type(), session, cast_mode);
|
||||
if (CM_IS_WARN_ON_FAIL(cast_mode)) {
|
||||
result.set_null();
|
||||
ret = OB_SUCCESS;
|
||||
}
|
||||
}
|
||||
} else {
|
||||
if (is_oracle_mode()) {
|
||||
result.set_datetime(res_date_utc);
|
||||
@ -649,8 +661,12 @@ int ObExprLastDay::cg_expr(ObExprCGCtx& op_cg_ctx, const ObRawExpr& raw_expr, Ob
|
||||
int ObExprLastDay::calc_last_day(const ObExpr& expr, ObEvalCtx& ctx, ObDatum& expr_datum)
|
||||
{
|
||||
int ret = OB_SUCCESS;
|
||||
ObDatum* param1 = NULL;
|
||||
if (OB_FAIL(expr.args_[0]->eval(ctx, param1))) {
|
||||
ObDatum *param1 = NULL;
|
||||
ObSQLSessionInfo *session = NULL;
|
||||
if (OB_ISNULL(session = ctx.exec_ctx_.get_my_session())) {
|
||||
ret = OB_ERR_UNEXPECTED;
|
||||
LOG_WARN("session is null", K(ret));
|
||||
} else if (OB_FAIL(expr.args_[0]->eval(ctx, param1))) {
|
||||
LOG_WARN("eval first param value failed");
|
||||
} else if (param1->is_null()) {
|
||||
expr_datum.set_null();
|
||||
@ -658,9 +674,17 @@ int ObExprLastDay::calc_last_day(const ObExpr& expr, ObEvalCtx& ctx, ObDatum& ex
|
||||
const ObObjType res_type = is_oracle_mode() ? ObDateTimeType : ObDateType;
|
||||
int64_t ori_date_utc = param1->get_datetime();
|
||||
int64_t res_date_utc = 0;
|
||||
if (OB_FAIL(ObTimeConverter::calc_last_date_of_the_month(ori_date_utc, res_date_utc,
|
||||
res_type))) {
|
||||
LOG_WARN("fail to calc last mday", K(ret));
|
||||
if (OB_FAIL(ObTimeConverter::calc_last_date_of_the_month(
|
||||
ori_date_utc, res_date_utc, res_type, false))) {
|
||||
LOG_WARN("fail to calc last mday", K(ret), K(ori_date_utc), K(res_date_utc));
|
||||
if (!is_oracle_mode()) {
|
||||
uint64_t cast_mode = 0;
|
||||
ObSQLUtils::get_default_cast_mode(session->get_stmt_type(), session, cast_mode);
|
||||
if (CM_IS_WARN_ON_FAIL(cast_mode)) {
|
||||
expr_datum.set_null();
|
||||
ret = OB_SUCCESS;
|
||||
}
|
||||
}
|
||||
} else {
|
||||
if (is_oracle_mode()) {
|
||||
expr_datum.set_datetime(res_date_utc);
|
||||
|
@ -50,12 +50,10 @@ int ObExprDateFormat::calc_result2(ObObj& result, const ObObj& date, const ObObj
|
||||
} else if (OB_ISNULL(buf = static_cast<char*>(expr_ctx.calc_buf_->alloc(buf_len)))) {
|
||||
ret = OB_ALLOCATE_MEMORY_FAILED;
|
||||
LOG_ERROR("no more memory to alloc for buf");
|
||||
} else if (OB_FAIL(ob_obj_to_ob_time_with_date(date, get_timezone_info(expr_ctx.my_session_), ob_time))) {
|
||||
} else if (OB_FAIL(ob_obj_to_ob_time_with_date(date, get_timezone_info(expr_ctx.my_session_), ob_time,
|
||||
get_cur_time(expr_ctx.exec_ctx_->get_physical_plan_ctx())))) {
|
||||
LOG_WARN("failed to convert obj to ob time");
|
||||
check_reset_status(expr_ctx, ret, result);
|
||||
} else if (ObTimeType == date.get_type() && OB_FAIL(set_cur_date(get_timezone_info(expr_ctx.my_session_), ob_time))) {
|
||||
LOG_WARN("failed to set current date to ob time");
|
||||
check_reset_status(expr_ctx, ret, result);
|
||||
} else if (OB_UNLIKELY(format.get_string().empty())) {
|
||||
result.set_null();
|
||||
} else if (OB_FAIL(
|
||||
@ -70,23 +68,6 @@ int ObExprDateFormat::calc_result2(ObObj& result, const ObObj& date, const ObObj
|
||||
return ret;
|
||||
}
|
||||
|
||||
int ObExprDateFormat::set_cur_date(const ObTimeZoneInfo* tz_info, ObTime& ob_time)
|
||||
{
|
||||
int ret = OB_SUCCESS;
|
||||
ObTime cur_date;
|
||||
if (OB_FAIL(ObTimeConverter::datetime_to_ob_time(ObTimeUtility::current_time(), tz_info, cur_date))) {
|
||||
LOG_WARN("failed to convert current datetime to ob time");
|
||||
} else {
|
||||
ob_time.parts_[DT_YEAR] = cur_date.parts_[DT_YEAR];
|
||||
ob_time.parts_[DT_MON] = cur_date.parts_[DT_MON];
|
||||
ob_time.parts_[DT_MDAY] = cur_date.parts_[DT_MDAY];
|
||||
ob_time.parts_[DT_DATE] = cur_date.parts_[DT_DATE];
|
||||
ob_time.parts_[DT_YDAY] = cur_date.parts_[DT_YDAY];
|
||||
ob_time.parts_[DT_WDAY] = cur_date.parts_[DT_WDAY];
|
||||
}
|
||||
return ret;
|
||||
}
|
||||
|
||||
void ObExprDateFormat::check_reset_status(ObExprCtx& expr_ctx, int& ret, ObObj& result)
|
||||
{
|
||||
if (CM_IS_WARN_ON_FAIL(expr_ctx.cast_mode_)) {
|
||||
@ -149,13 +130,6 @@ int ObExprDateFormat::calc_date_format(const ObExpr& expr, ObEvalCtx& ctx, ObDat
|
||||
ret = OB_SUCCESS;
|
||||
expr_datum.set_null();
|
||||
}
|
||||
} else if (ObTimeType == expr.args_[0]->datum_meta_.type_ &&
|
||||
OB_FAIL(set_cur_date(get_timezone_info(session), ob_time))) {
|
||||
LOG_WARN("failed to set current date to ob time");
|
||||
if (CM_IS_WARN_ON_FAIL(cast_mode) && OB_ALLOCATE_MEMORY_FAILED != ret) {
|
||||
ret = OB_SUCCESS;
|
||||
expr_datum.set_null();
|
||||
}
|
||||
} else if (OB_UNLIKELY(format->get_string().empty())) {
|
||||
expr_datum.set_null();
|
||||
} else if (OB_FAIL(
|
||||
|
@ -35,7 +35,6 @@ private:
|
||||
// disallow copy
|
||||
DISALLOW_COPY_AND_ASSIGN(ObExprDateFormat);
|
||||
|
||||
static int set_cur_date(const common::ObTimeZoneInfo* tz_info, common::ObTime& ob_time);
|
||||
static const int64_t OB_MAX_DATE_FORMAT_BUF_LEN = 1024;
|
||||
static void check_reset_status(common::ObExprCtx& expr_ctx, int& ret, common::ObObj& result);
|
||||
};
|
||||
|
@ -77,14 +77,18 @@ int ObExprToSeconds::calc_result1(ObObj& result, const ObObj& obj, ObExprCtx& ex
|
||||
const ObObj* p_obj = NULL;
|
||||
EXPR_CAST_OBJ_V2(ObDateType, obj, p_obj);
|
||||
if (OB_SUCC(ret)) {
|
||||
if (OB_ISNULL(p_obj)) {
|
||||
if (OB_ISNULL(expr_ctx.my_session_) || OB_ISNULL(expr_ctx.exec_ctx_)) {
|
||||
ret = OB_NOT_INIT;
|
||||
LOG_WARN("session ptr or exec ctx is null", K(ret), K(expr_ctx.my_session_));
|
||||
} else if (OB_ISNULL(p_obj)) {
|
||||
ret = OB_ERR_UNEXPECTED;
|
||||
LOG_WARN("p_obj is null", K(ret));
|
||||
} else if (OB_UNLIKELY(p_obj->is_null() || OB_INVALID_DATE_VALUE == cast_ctx.warning_)) {
|
||||
result.set_null();
|
||||
} else {
|
||||
ObTime ot;
|
||||
if (OB_FAIL(ob_obj_to_ob_time_with_date(obj, get_timezone_info(expr_ctx.my_session_), ot))) {
|
||||
if (OB_FAIL(ob_obj_to_ob_time_with_date(obj, get_timezone_info(expr_ctx.my_session_), ot,
|
||||
get_cur_time(expr_ctx.exec_ctx_->get_physical_plan_ctx())))) {
|
||||
LOG_WARN("cast to ob time failed", K(ret), K(obj), K(expr_ctx.cast_mode_));
|
||||
if (CM_IS_WARN_ON_FAIL(expr_ctx.cast_mode_)) {
|
||||
ret = OB_SUCCESS;
|
||||
@ -392,88 +396,109 @@ int ObExprSubtime::calc_result_type2(
|
||||
int ObExprSubtime::calc_result2(common::ObObj& result, const common::ObObj& date_arg, const common::ObObj& time_arg,
|
||||
common::ObExprCtx& expr_ctx) const
|
||||
{
|
||||
ObTime ot;
|
||||
ObTime ot2(DT_TYPE_TIME);
|
||||
int ret = OB_SUCCESS;
|
||||
int ret1 = OB_SUCCESS;
|
||||
int ret2 = OB_SUCCESS;
|
||||
int64_t t_val1 = 0;
|
||||
int64_t t_val2 = 0;
|
||||
bool is_string_with_time_fmt = false;
|
||||
ObTime ot1(DT_TYPE_TIME);
|
||||
bool param_with_date = true;
|
||||
ObObjType result_type = get_result_type().get_type();
|
||||
const ObSQLSessionInfo *session = NULL;
|
||||
|
||||
EXPR_DEFINE_CAST_CTX(expr_ctx, CM_NONE);
|
||||
if (date_arg.get_type() == ObVarcharType) {
|
||||
ret1 = ob_obj_to_ob_time_with_date(date_arg, get_timezone_info(expr_ctx.my_session_), ot);
|
||||
if (OB_SUCCESS != ret1) {
|
||||
ret2 = ob_obj_to_ob_time_without_date(date_arg, get_timezone_info(expr_ctx.my_session_), ot2);
|
||||
is_string_with_time_fmt = true;
|
||||
} else if (0 == ot.parts_[DT_YEAR] && 0 == ot.parts_[DT_MON] && 0 == ot.parts_[DT_MDAY]) {
|
||||
is_string_with_time_fmt = true;
|
||||
}
|
||||
} else { /* do nothing */
|
||||
}
|
||||
|
||||
if (OB_SUCCESS != ret1 && OB_SUCCESS != ret2) {
|
||||
if (OB_UNLIKELY(date_arg.is_null() || time_arg.is_null())) {
|
||||
result.set_null();
|
||||
} else if (OB_ISNULL(expr_ctx.calc_buf_)) {
|
||||
} else if (OB_ISNULL(expr_ctx.calc_buf_) || OB_ISNULL(session = expr_ctx.my_session_)) {
|
||||
ret = OB_ERR_UNEXPECTED;
|
||||
LOG_WARN("allocator is null", K(ret));
|
||||
} else if (OB_UNLIKELY(date_arg.is_null() || time_arg.is_null())) {
|
||||
result.set_null();
|
||||
LOG_WARN("allocator or session is null", K(ret), K(expr_ctx.calc_buf_));
|
||||
} else {
|
||||
if (ObVarcharType == time_arg.get_type()) {
|
||||
EXPR_GET_TIME_V2(time_arg, t_val2);
|
||||
} else {
|
||||
TYPE_CHECK(time_arg, ObTimeType);
|
||||
t_val2 = time_arg.get_time();
|
||||
if (ObVarcharType == result_type) {
|
||||
if (OB_FAIL(ob_obj_to_ob_time_without_date(date_arg,
|
||||
get_timezone_info(session), ot1))) {
|
||||
LOG_WARN("obj to ob time without date failed", K(ret), K(date_arg));
|
||||
} else {
|
||||
if (0 == ot1.parts_[DT_YEAR] && 0 == ot1.parts_[DT_MON] && 0 == ot1.parts_[DT_MDAY]) {
|
||||
param_with_date = false;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (ObTimeType == date_arg.get_type() || is_string_with_time_fmt) { // a#, subtime(t1, t2)
|
||||
if (ObVarcharType == date_arg.get_type()) {
|
||||
EXPR_GET_TIME_V2(date_arg, t_val1);
|
||||
if (OB_SUCC(ret)) {
|
||||
if (ObTimeType == time_arg.get_type()) {
|
||||
t_val2 = time_arg.get_time();
|
||||
} else {
|
||||
TYPE_CHECK(date_arg, ObTimeType);
|
||||
t_val1 = date_arg.get_time();
|
||||
ObTime ot2(DT_TYPE_TIME);
|
||||
if (OB_FAIL(ob_obj_to_ob_time_without_date(time_arg, get_timezone_info(session), ot2))) {
|
||||
LOG_WARN("cast the second param failed", K(ret));
|
||||
} else {
|
||||
t_val2 = ObTimeConverter::ob_time_to_time(ot2);
|
||||
}
|
||||
}
|
||||
if (OB_SUCC(ret)) {
|
||||
int64_t int_usec = t_val1 - t_val2;
|
||||
// LOG_WARN("@songxin, ObExprSubtime#time-time", K(t_val1), K(t_val2), K(int_usec));
|
||||
if (OB_FAIL(ObTimeConverter::time_overflow_trunc(int_usec))) {
|
||||
if (CM_IS_WARN_ON_FAIL(cast_ctx.cast_mode_)) {
|
||||
ret = OB_SUCCESS;
|
||||
} else {
|
||||
LOG_WARN("time value is out of range", K(ret), K(int_usec));
|
||||
if (OB_FAIL(ret)) {
|
||||
} else if (ObTimeType == result_type || !param_with_date) { // a#, subtime(时间1, 时间2)
|
||||
if (ObVarcharType == result_type) {
|
||||
t_val1 = ObTimeConverter::ob_time_to_time(ot1);
|
||||
if (IS_NEG_TIME(ot1.mode_)) {
|
||||
t_val1 = -t_val1;
|
||||
}
|
||||
} else {
|
||||
result.set_time(int_usec);
|
||||
TYPE_CHECK(date_arg, ObTimeType);
|
||||
t_val1 = date_arg.get_time();
|
||||
}
|
||||
}
|
||||
} else { // b#, subtime(t1, t2)
|
||||
if (ObVarcharType == date_arg.get_type()) {
|
||||
EXPR_GET_DATETIME_V2(date_arg, t_val1);
|
||||
} else {
|
||||
TYPE_CHECK(date_arg, ObDateTimeType);
|
||||
t_val1 = date_arg.get_datetime();
|
||||
}
|
||||
if (OB_SUCC(ret)) {
|
||||
int64_t int_usec = t_val1 - t_val2;
|
||||
// LOG_WARN("@songxin, ObExprSubtime#datetime-time", K(t_val1), K(t_val2), K(int_usec));
|
||||
if (ObTimeConverter::is_valid_datetime(int_usec)) {
|
||||
result.set_datetime(int_usec);
|
||||
if (OB_SUCC(ret)) {
|
||||
int64_t int_usec = t_val1 - t_val2;
|
||||
if (OB_FAIL(ObTimeConverter::time_overflow_trunc(int_usec))) {
|
||||
if (CM_IS_WARN_ON_FAIL(cast_ctx.cast_mode_)) {
|
||||
ret = OB_SUCCESS;
|
||||
} else {
|
||||
LOG_WARN("time value is out of range", K(ret), K(int_usec));
|
||||
}
|
||||
} else {
|
||||
result.set_time(int_usec);
|
||||
}
|
||||
}
|
||||
} else { // b#, subtime(日期时间1, 时间2)
|
||||
const ObTimeZoneInfo *tz_info = NULL;
|
||||
if (OB_ISNULL(tz_info = get_timezone_info(expr_ctx.my_session_))) {
|
||||
ret = OB_ERR_UNEXPECTED;
|
||||
LOG_WARN("tz info is null", K(ret));
|
||||
} else if (ObVarcharType == result_type) {
|
||||
ObTimeConvertCtx cvrt_ctx(tz_info, false);
|
||||
if (OB_FAIL(ObTimeConverter::ob_time_to_datetime(ot1, cvrt_ctx, t_val1))) {
|
||||
LOG_WARN("ob_time_to_datetime failed", K(ret));
|
||||
}
|
||||
} else {
|
||||
result.set_null();
|
||||
if (ObDateTimeType != date_arg.get_type() && ObTimestampType != date_arg.get_type()) {
|
||||
ret = OB_INVALID_ARGUMENT;
|
||||
LOG_WARN("invalid date arg type", K(ret));
|
||||
} else {
|
||||
int64_t offset = ObTimestampType == date_arg.get_type() ? tz_info->get_offset() : 0;
|
||||
t_val1 = date_arg.get_datetime() + offset * USECS_PER_SEC;
|
||||
}
|
||||
}
|
||||
if (OB_SUCC(ret)) {
|
||||
int64_t int_usec = t_val1 - t_val2;
|
||||
if (ObTimeConverter::is_valid_datetime(int_usec)) {
|
||||
result.set_datetime(int_usec);
|
||||
} else {
|
||||
result.set_null();
|
||||
}
|
||||
}
|
||||
}
|
||||
if (OB_SUCC(ret) && ObVarcharType == result_type) {
|
||||
if (OB_FAIL(ObObjCaster::to_type(ObVarcharType, cast_ctx, result, result))) {
|
||||
LOG_WARN("failed to cast object to ObVarcharType ", K(result), K(ret));
|
||||
}
|
||||
}
|
||||
}
|
||||
if (OB_SUCC(ret) && date_arg.get_type() == ObVarcharType) {
|
||||
if (OB_FAIL(ObObjCaster::to_type(ObVarcharType, cast_ctx, result, result))) {
|
||||
LOG_WARN("failed to cast object to ObVarcharType ", K(result), K(ret));
|
||||
if (OB_FAIL(ret)) {
|
||||
uint64_t cast_mode = 0;
|
||||
ObSQLUtils::get_default_cast_mode(session->get_stmt_type(), session, cast_mode);
|
||||
if (CM_IS_WARN_ON_FAIL(cast_mode) && OB_ALLOCATE_MEMORY_FAILED != ret) {
|
||||
ret = OB_SUCCESS;
|
||||
result.set_null();
|
||||
}
|
||||
}
|
||||
}
|
||||
if (OB_FAIL(ret)) {
|
||||
result.set_null();
|
||||
ret = OB_SUCCESS;
|
||||
}
|
||||
return ret;
|
||||
}
|
||||
|
||||
|
@ -697,8 +697,8 @@ static ObExpr::EvalFunc g_expr_eval_functions[] = {
|
||||
NULL, /* 438 */
|
||||
NULL, /* 439 */
|
||||
NULL, /* 440 */
|
||||
NULL, /* 441 */
|
||||
NULL, /* 442 */
|
||||
ObExprTimestamp::calc_timestamp1, /* 441 */
|
||||
ObExprTimestamp::calc_timestamp2, /* 442 */
|
||||
NULL, /* 443 */
|
||||
NULL, /* 444 */
|
||||
NULL, /* 445 */
|
||||
|
@ -90,8 +90,7 @@ inline int obj_to_time<ObObj, true>(
|
||||
const ObObj& date, ObObjType type, const ObTimeZoneInfo* tz_info, ObTime& ob_time, const int64_t cur_ts_value)
|
||||
{
|
||||
UNUSED(type);
|
||||
UNUSED(cur_ts_value);
|
||||
return ob_obj_to_ob_time_with_date(date, tz_info, ob_time);
|
||||
return ob_obj_to_ob_time_with_date(date, tz_info, ob_time, cur_ts_value);
|
||||
}
|
||||
template <>
|
||||
inline int obj_to_time<ObObj, false>(
|
||||
|
@ -119,9 +119,9 @@ int ObExprFromUnixTime::calc(ObObj& result, const ObObj& param, const ObObj& for
|
||||
result.set_null();
|
||||
} else if (OB_UNLIKELY(ObStringTC != format.get_type_class())) {
|
||||
result = format;
|
||||
} else if (OB_UNLIKELY(NULL == expr_ctx.calc_buf_)) {
|
||||
} else if (OB_UNLIKELY(NULL == expr_ctx.calc_buf_) || OB_ISNULL(expr_ctx.exec_ctx_)) {
|
||||
ret = OB_NOT_INIT;
|
||||
LOG_WARN("string_buf is null");
|
||||
LOG_WARN("string_buf is null", K(ret), K(expr_ctx.calc_buf_));
|
||||
} else if (OB_UNLIKELY(NULL == (buf = reinterpret_cast<char*>(expr_ctx.calc_buf_->alloc(BUF_LEN))))) {
|
||||
ret = OB_ALLOCATE_MEMORY_FAILED;
|
||||
LOG_ERROR("no more memory to alloc for buf");
|
||||
@ -133,7 +133,8 @@ int ObExprFromUnixTime::calc(ObObj& result, const ObObj& param, const ObObj& for
|
||||
ObTime ob_time;
|
||||
if (OB_UNLIKELY(value < 0)) {
|
||||
result.set_null();
|
||||
} else if (OB_FAIL(ob_obj_to_ob_time_with_date(tmp, get_timezone_info(expr_ctx.my_session_), ob_time))) {
|
||||
} else if (OB_FAIL(ob_obj_to_ob_time_with_date(tmp, get_timezone_info(expr_ctx.my_session_), ob_time,
|
||||
get_cur_time(expr_ctx.exec_ctx_->get_physical_plan_ctx())))) {
|
||||
LOG_WARN("failed to convert obj to ob time");
|
||||
} else if (OB_UNLIKELY(format.get_string().empty())) {
|
||||
result.set_null();
|
||||
|
@ -394,14 +394,20 @@ int ObExprFuncRound::calc_with_date(ObObj& result, const ObObj& source, const Ob
|
||||
{
|
||||
int ret = OB_SUCCESS;
|
||||
ObTime ob_time;
|
||||
if (OB_UNLIKELY(ObDateTimeTC != source.get_type_class())) {
|
||||
if (OB_ISNULL(expr_ctx.exec_ctx_)) {
|
||||
ret = OB_ERR_UNEXPECTED;
|
||||
LOG_WARN("exec ctx is null", K(ret));
|
||||
} else if (OB_UNLIKELY(ObDateTimeTC != source.get_type_class())) {
|
||||
ret = OB_INVALID_ARGUMENT;
|
||||
LOG_WARN("invalid argument.", K(ret), K(source), K(format));
|
||||
} else if (OB_UNLIKELY(ObStringTC != format.get_type_class())) {
|
||||
ret = OB_ERR_INVALID_TYPE_FOR_OP;
|
||||
LOG_WARN("inconsistent datatypes", K(ret), K(format));
|
||||
LOG_USER_ERROR(OB_ERR_INVALID_TYPE_FOR_OP, ob_obj_type_str(source.get_type()), ob_obj_type_str(format.get_type()));
|
||||
} else if (OB_FAIL(ob_obj_to_ob_time_with_date(source, get_timezone_info(expr_ctx.my_session_), ob_time))) {
|
||||
} else if (OB_FAIL(ob_obj_to_ob_time_with_date(source,
|
||||
get_timezone_info(expr_ctx.my_session_),
|
||||
ob_time,
|
||||
get_cur_time(expr_ctx.exec_ctx_->get_physical_plan_ctx())))) {
|
||||
LOG_WARN("failed to convert obj to ob time", K(ret), K(source), K(format));
|
||||
} else {
|
||||
LOG_DEBUG("succ to get ob_time", K(ob_time), K(source));
|
||||
|
@ -102,14 +102,20 @@ int ObExprOracleTrunc::calc_with_date(
|
||||
{
|
||||
int ret = OB_SUCCESS;
|
||||
ObTime ob_time;
|
||||
if (OB_UNLIKELY(ObDateTimeTC != source.get_type_class())) {
|
||||
if (OB_ISNULL(expr_ctx.exec_ctx_)) {
|
||||
ret = OB_ERR_UNEXPECTED;
|
||||
LOG_WARN("exec ctx is null", K(ret));
|
||||
} else if (OB_UNLIKELY(ObDateTimeTC != source.get_type_class())) {
|
||||
ret = OB_INVALID_ARGUMENT;
|
||||
LOG_WARN("invalid argument.", K(ret), K(source), K(format));
|
||||
} else if (OB_UNLIKELY(ObStringTC != format.get_type_class())) {
|
||||
ret = OB_ERR_INVALID_TYPE_FOR_OP;
|
||||
LOG_WARN("inconsistent datatypes", K(ret), K(format));
|
||||
LOG_USER_ERROR(OB_ERR_INVALID_TYPE_FOR_OP, ob_obj_type_str(source.get_type()), ob_obj_type_str(format.get_type()));
|
||||
} else if (OB_FAIL(ob_obj_to_ob_time_with_date(source, get_timezone_info(expr_ctx.my_session_), ob_time))) {
|
||||
} else if (OB_FAIL(ob_obj_to_ob_time_with_date(source,
|
||||
get_timezone_info(expr_ctx.my_session_),
|
||||
ob_time,
|
||||
get_cur_time(expr_ctx.exec_ctx_->get_physical_plan_ctx())))) {
|
||||
LOG_WARN("failed to convert obj to ob time", K(ret), K(source), K(format));
|
||||
} else {
|
||||
LOG_DEBUG("succ to get ob_time", K(ob_time), K(source));
|
||||
|
@ -39,9 +39,13 @@ int ObExprQuarter::calc_result1(ObObj& result, const ObObj& obj, ObExprCtx& expr
|
||||
int ret = OB_SUCCESS;
|
||||
int64_t quarter = 0;
|
||||
ObTime ot;
|
||||
if (OB_UNLIKELY(obj.is_null())) {
|
||||
if (OB_ISNULL(expr_ctx.my_session_) || OB_ISNULL(expr_ctx.exec_ctx_)) {
|
||||
ret = OB_NOT_INIT;
|
||||
LOG_WARN("session ptr or exec ctx is null", K(ret), K(expr_ctx.my_session_));
|
||||
} else if (OB_UNLIKELY(obj.is_null())) {
|
||||
result.set_null();
|
||||
} else if (OB_FAIL(ob_obj_to_ob_time_with_date(obj, get_timezone_info(expr_ctx.my_session_), ot, false))) {
|
||||
} else if (OB_FAIL(ob_obj_to_ob_time_with_date(obj, get_timezone_info(expr_ctx.my_session_), ot,
|
||||
get_cur_time(expr_ctx.exec_ctx_->get_physical_plan_ctx()), false))) {
|
||||
LOG_WARN("cast to ob time failed", K(ret), K(obj), K(expr_ctx.cast_mode_));
|
||||
if (CM_IS_WARN_ON_FAIL(expr_ctx.cast_mode_)) {
|
||||
ret = OB_SUCCESS;
|
||||
|
@ -103,7 +103,11 @@ static int ob_expr_convert_to_dt_or_time(
|
||||
int ret = OB_SUCCESS;
|
||||
if (with_date) {
|
||||
ObTime ot1;
|
||||
if (OB_FAIL(ob_obj_to_ob_time_with_date(obj, get_timezone_info(expr_ctx.my_session_), ot1, is_dayofmonth))) {
|
||||
if (OB_ISNULL(expr_ctx.my_session_) || OB_ISNULL(expr_ctx.exec_ctx_)) {
|
||||
ret = OB_NOT_INIT;
|
||||
LOG_WARN("session or exec ctx is null", K(ret), K(expr_ctx.my_session_));
|
||||
} else if (OB_FAIL(ob_obj_to_ob_time_with_date(obj, get_timezone_info(expr_ctx.my_session_), ot1,
|
||||
get_cur_time(expr_ctx.exec_ctx_->get_physical_plan_ctx()), is_dayofmonth))) {
|
||||
LOG_WARN("convert to obtime failed", K(ret));
|
||||
} else {
|
||||
ot = ot1;
|
||||
|
@ -277,7 +277,7 @@ int ObExprToTimestampTZ::set_my_result_from_ob_time(ObExprCtx& expr_ctx, ObTime&
|
||||
|
||||
|
||||
ObExprTimestamp::ObExprTimestamp(ObIAllocator &alloc)
|
||||
: ObFuncExprOperator(alloc, T_FUN_SYS_TIMESTAMP, N_TIMESTAMP, 1, NOT_ROW_DIMENSION)
|
||||
: ObFuncExprOperator(alloc, T_FUN_SYS_TIMESTAMP, N_TIMESTAMP, ONE_OR_TWO, NOT_ROW_DIMENSION)
|
||||
{
|
||||
}
|
||||
|
||||
@ -285,37 +285,121 @@ ObExprTimestamp::~ObExprTimestamp()
|
||||
{
|
||||
}
|
||||
|
||||
int ObExprTimestamp::calc_result_type1(ObExprResType &type,
|
||||
ObExprResType &type1,
|
||||
int ObExprTimestamp::calc_result_typeN(ObExprResType &type,
|
||||
ObExprResType *types_array,
|
||||
int64_t param_num,
|
||||
ObExprTypeCtx &type_ctx) const
|
||||
{
|
||||
int ret = OB_SUCCESS;
|
||||
//param will be casted to ObDatetimeType before calculation
|
||||
type1.set_calc_type(ObDateTimeType);
|
||||
type.set_type(ObDateTimeType);
|
||||
//deduce scale now.
|
||||
int16_t scale1 = MIN(type1.get_scale(), MAX_SCALE_FOR_TEMPORAL);
|
||||
int16_t scale = (SCALE_UNKNOWN_YET == scale1) ? MAX_SCALE_FOR_TEMPORAL : scale1;
|
||||
type.set_scale(scale);
|
||||
type_ctx.set_cast_mode(type_ctx.get_cast_mode() | CM_NULL_ON_WARN);
|
||||
if (OB_UNLIKELY(1 != param_num && 2 != param_num)) {
|
||||
ret = OB_ERR_PARAM_SIZE;
|
||||
LOG_WARN("invalid argument count of funtion timestmap", K(ret));
|
||||
} else {
|
||||
//param will be casted to ObDatetimeType before calculation
|
||||
type.set_type(ObDateTimeType);
|
||||
types_array[0].set_calc_type(ObDateTimeType);
|
||||
if (2 == param_num) {
|
||||
types_array[1].set_calc_type(ObTimeType);
|
||||
}
|
||||
//deduce scale now.
|
||||
int16_t scale1 = MIN(types_array[0].get_scale(), MAX_SCALE_FOR_TEMPORAL);
|
||||
scale1 = (SCALE_UNKNOWN_YET == scale1) ? MAX_SCALE_FOR_TEMPORAL : scale1;
|
||||
int16_t scale2 = 0;
|
||||
if (2 == param_num) {
|
||||
scale2 = MIN(types_array[1].get_scale(), MAX_SCALE_FOR_TEMPORAL);
|
||||
scale2 = (SCALE_UNKNOWN_YET == scale2) ? MAX_SCALE_FOR_TEMPORAL : scale2;
|
||||
}
|
||||
type.set_scale(MAX(scale1, scale2));
|
||||
type_ctx.set_cast_mode(type_ctx.get_cast_mode() | CM_NULL_ON_WARN);
|
||||
}
|
||||
return ret;
|
||||
}
|
||||
|
||||
int ObExprTimestamp::calc_result1(ObObj &result,
|
||||
const ObObj &obj,
|
||||
ObExprCtx &expr_ctx) const
|
||||
int ObExprTimestamp::calc_resultN(ObObj &result,
|
||||
const common::ObObj *objs_array,
|
||||
int64_t param_num,
|
||||
ObExprCtx &expr_ctx) const
|
||||
{
|
||||
int ret = OB_SUCCESS;
|
||||
if (OB_UNLIKELY(obj.is_null())) {
|
||||
if (OB_UNLIKELY(objs_array[0].is_null())) {
|
||||
result.set_null();
|
||||
} else {
|
||||
TYPE_CHECK(obj, ObDateTimeType);
|
||||
result = obj;
|
||||
TYPE_CHECK(objs_array[0], ObDateTimeType);
|
||||
if (OB_FAIL(ret)) {
|
||||
} else if (1 == param_num) {
|
||||
result = objs_array[0];
|
||||
} else if (2 == param_num) {
|
||||
if (objs_array[1].is_null()) {
|
||||
result.set_null();
|
||||
} else if (ObTimeType != objs_array[1].get_type()) {
|
||||
ret = OB_INVALID_ARGUMENT;
|
||||
LOG_WARN("expect time type param", K(ret), K(objs_array[1]));
|
||||
} else {
|
||||
int64_t datetime = objs_array[0].get_datetime();
|
||||
int64_t time = objs_array[1].get_time();
|
||||
result.set_datetime(datetime + time);
|
||||
}
|
||||
}
|
||||
}
|
||||
UNUSED(expr_ctx);
|
||||
return ret;
|
||||
}
|
||||
|
||||
int ObExprTimestamp::cg_expr(ObExprCGCtx &expr_cg_ctx, const ObRawExpr &raw_expr,
|
||||
ObExpr &rt_expr) const
|
||||
{
|
||||
int ret = OB_SUCCESS;
|
||||
UNUSED(expr_cg_ctx);
|
||||
UNUSED(raw_expr);
|
||||
if (1 == rt_expr.arg_cnt_) {
|
||||
ObObjType type = rt_expr.args_[0]->datum_meta_.type_;
|
||||
CK(ObNullType == type || ObDateTimeType == type);
|
||||
if (OB_SUCC(ret)) {
|
||||
rt_expr.eval_func_ = ObExprTimestamp::calc_timestamp1;
|
||||
}
|
||||
} else if (2 == rt_expr.arg_cnt_) {
|
||||
ObObjType type1 = rt_expr.args_[0]->datum_meta_.type_;
|
||||
ObObjType type2 = rt_expr.args_[1]->datum_meta_.type_;
|
||||
CK(ObNullType == type1 || ObDateTimeType == type1);
|
||||
CK(ObNullType == type2 || ObTimeType == type2);
|
||||
if (OB_SUCC(ret)) {
|
||||
rt_expr.eval_func_ = ObExprTimestamp::calc_timestamp2;
|
||||
}
|
||||
} else {
|
||||
ret = OB_ERR_PARAM_SIZE;
|
||||
LOG_WARN("invalid argument count of funtion timestmap", K(ret));
|
||||
}
|
||||
return ret;
|
||||
}
|
||||
|
||||
int ObExprTimestamp::calc_timestamp1(const ObExpr &expr, ObEvalCtx &ctx, ObDatum &result)
|
||||
{
|
||||
int ret = OB_SUCCESS;
|
||||
ObDatum *param = NULL;
|
||||
if (OB_FAIL(expr.eval_param_value(ctx, param))) {
|
||||
LOG_WARN("calc param failed", K(ret));
|
||||
} else if (param->is_null()) {
|
||||
result.set_null();
|
||||
} else {
|
||||
result.set_datetime(param->get_datetime());
|
||||
}
|
||||
return ret;
|
||||
}
|
||||
|
||||
int ObExprTimestamp::calc_timestamp2(const ObExpr &expr, ObEvalCtx &ctx, ObDatum &result)
|
||||
{
|
||||
int ret = OB_SUCCESS;
|
||||
ObDatum *datetime = NULL;
|
||||
ObDatum *time = NULL;
|
||||
if (OB_FAIL(expr.eval_param_value(ctx, datetime, time))) {
|
||||
LOG_WARN("calc param failed", K(ret));
|
||||
} else if (datetime->is_null() || time->is_null()) {
|
||||
result.set_null();
|
||||
} else {
|
||||
result.set_datetime(datetime->get_datetime() + time->get_time());
|
||||
}
|
||||
return ret;
|
||||
}
|
||||
|
||||
} // namespace sql
|
||||
} // namespace oceanbase
|
||||
|
@ -89,13 +89,19 @@ class ObExprTimestamp : public ObFuncExprOperator
|
||||
public:
|
||||
explicit ObExprTimestamp(common::ObIAllocator &alloc);
|
||||
virtual ~ObExprTimestamp();
|
||||
virtual int calc_result_type1(ObExprResType &type,
|
||||
ObExprResType &type1,
|
||||
virtual int calc_result_typeN(ObExprResType &type,
|
||||
ObExprResType *types_array,
|
||||
int64_t param_num,
|
||||
common::ObExprTypeCtx &type_ctx) const;
|
||||
virtual int calc_result1(common::ObObj &result,
|
||||
const common::ObObj &time,
|
||||
virtual int calc_resultN(common::ObObj &result,
|
||||
const common::ObObj *objs_array,
|
||||
int64_t param_num,
|
||||
common::ObExprCtx &expr_ctx) const;
|
||||
virtual common::ObCastMode get_cast_mode() const { return CM_NULL_ON_WARN;}
|
||||
static int calc_timestamp1(const ObExpr &expr, ObEvalCtx &ctx, ObDatum &result);
|
||||
static int calc_timestamp2(const ObExpr &expr, ObEvalCtx &ctx, ObDatum &result);
|
||||
virtual int cg_expr(ObExprCGCtx &expr_cg_ctx, const ObRawExpr &raw_expr,
|
||||
ObExpr &rt_expr) const override;
|
||||
private :
|
||||
//disallow copy
|
||||
DISALLOW_COPY_AND_ASSIGN(ObExprTimestamp);
|
||||
|
@ -73,6 +73,9 @@ int ObExprTimeStampAdd::calc_result3(
|
||||
LOG_WARN("unexpected error. calc buffer is null", K(ret));
|
||||
} else if (OB_UNLIKELY(unit.is_null() || interval.is_null() || timestamp.is_null())) {
|
||||
result.set_null();
|
||||
} else if (OB_ISNULL(expr_ctx.exec_ctx_)) {
|
||||
ret = OB_ERR_UNEXPECTED;
|
||||
LOG_WARN("exec ctx is null", K(ret));
|
||||
} else {
|
||||
int64_t ts = 0;
|
||||
int64_t interval_int = 0;
|
||||
@ -83,7 +86,8 @@ int ObExprTimeStampAdd::calc_result3(
|
||||
EXPR_GET_INT64_V2(interval, interval_int);
|
||||
ObTimeConvertCtx cvrt_ctx(get_timezone_info(expr_ctx.my_session_), true);
|
||||
if (OB_SUCC(ret)) {
|
||||
if (OB_FAIL(ob_obj_to_ob_time_with_date(timestamp, cvrt_ctx.tz_info_, ot))) {
|
||||
if (OB_FAIL(ob_obj_to_ob_time_with_date(
|
||||
timestamp, cvrt_ctx.tz_info_, ot, get_cur_time(expr_ctx.exec_ctx_->get_physical_plan_ctx())))) {
|
||||
LOG_WARN("cast to ob time failed", K(ret), K(timestamp), K(expr_ctx.cast_mode_));
|
||||
} else if (OB_FAIL(ObTimeConverter::ob_time_to_datetime(ot, cvrt_ctx, ts))) {
|
||||
LOG_WARN("ob time to datetime failed", K(ret));
|
||||
|
@ -36,9 +36,13 @@ int ObExprWeekOfYear::calc_result1(ObObj& result, const ObObj& obj, ObExprCtx& e
|
||||
int ret = OB_SUCCESS;
|
||||
int64_t week = 0;
|
||||
ObTime ot;
|
||||
if (OB_UNLIKELY(obj.is_null())) {
|
||||
if (OB_ISNULL(expr_ctx.my_session_) || OB_ISNULL(expr_ctx.exec_ctx_)) {
|
||||
ret = OB_NOT_INIT;
|
||||
LOG_WARN("session ptr or exec ctx is null", K(ret), K(expr_ctx.my_session_));
|
||||
} else if (OB_UNLIKELY(obj.is_null())) {
|
||||
result.set_null();
|
||||
} else if (OB_FAIL(ob_obj_to_ob_time_with_date(obj, get_timezone_info(expr_ctx.my_session_), ot, false))) {
|
||||
} else if (OB_FAIL(ob_obj_to_ob_time_with_date(obj, get_timezone_info(expr_ctx.my_session_), ot,
|
||||
get_cur_time(expr_ctx.exec_ctx_->get_physical_plan_ctx()), false))) {
|
||||
LOG_WARN("cast to ob time failed", K(ret), K(obj), K(expr_ctx.cast_mode_));
|
||||
if (CM_IS_WARN_ON_FAIL(expr_ctx.cast_mode_)) {
|
||||
ret = OB_SUCCESS;
|
||||
@ -116,9 +120,13 @@ int ObExprWeekDay::calc_result1(ObObj& result, const ObObj& obj, ObExprCtx& expr
|
||||
int ret = OB_SUCCESS;
|
||||
int64_t weekday = 0;
|
||||
ObTime ot;
|
||||
if (OB_UNLIKELY(obj.is_null())) {
|
||||
if (OB_ISNULL(expr_ctx.my_session_) || OB_ISNULL(expr_ctx.exec_ctx_)) {
|
||||
ret = OB_NOT_INIT;
|
||||
LOG_WARN("session ptr or exec ctx is null", K(ret), K(expr_ctx.my_session_));
|
||||
} else if (OB_UNLIKELY(obj.is_null())) {
|
||||
result.set_null();
|
||||
} else if (OB_FAIL(ob_obj_to_ob_time_with_date(obj, get_timezone_info(expr_ctx.my_session_), ot, false))) {
|
||||
} else if (OB_FAIL(ob_obj_to_ob_time_with_date(obj, get_timezone_info(expr_ctx.my_session_), ot,
|
||||
get_cur_time(expr_ctx.exec_ctx_->get_physical_plan_ctx()), false))) {
|
||||
LOG_WARN("cast to ob time failed", K(ret), K(obj), K(expr_ctx.cast_mode_));
|
||||
if (CM_IS_WARN_ON_FAIL(expr_ctx.cast_mode_)) {
|
||||
ret = OB_SUCCESS;
|
||||
@ -275,13 +283,17 @@ int ObExprYearWeek::calc_resultN(
|
||||
int64_t mode_value = 0;
|
||||
int64_t week = 0;
|
||||
ObTime ot;
|
||||
if (OB_ISNULL(objs_stack)) {
|
||||
if (OB_ISNULL(expr_ctx.my_session_) || OB_ISNULL(expr_ctx.exec_ctx_)) {
|
||||
ret = OB_NOT_INIT;
|
||||
LOG_WARN("session ptr or exec ctx is null", K(ret), K(expr_ctx.my_session_));
|
||||
} else if (OB_ISNULL(objs_stack)) {
|
||||
ret = OB_INVALID_ARGUMENT;
|
||||
LOG_WARN("null stack", KP(objs_stack), K(ret));
|
||||
} else if (OB_UNLIKELY(param_num > 2)) {
|
||||
ret = OB_INVALID_ARGUMENT;
|
||||
LOG_WARN("param num error", K(param_num));
|
||||
} else if (OB_FAIL(ob_obj_to_ob_time_with_date(objs_stack[0], get_timezone_info(expr_ctx.my_session_), ot, false))) {
|
||||
} else if (OB_FAIL(ob_obj_to_ob_time_with_date(objs_stack[0], get_timezone_info(expr_ctx.my_session_),
|
||||
ot, get_cur_time(expr_ctx.exec_ctx_->get_physical_plan_ctx()), false))) {
|
||||
LOG_WARN("cast to ob time failed", K(ret), K(objs_stack[0]), K(expr_ctx.cast_mode_));
|
||||
ret = OB_SUCCESS;
|
||||
result.set_null();
|
||||
@ -407,6 +419,9 @@ int ObExprWeek::calc_resultN(ObObj& result, const ObObj* params, int64_t params_
|
||||
} else if (OB_UNLIKELY(params_count > 2)) {
|
||||
ret = OB_INVALID_ARGUMENT;
|
||||
LOG_WARN("param num error", K(params_count));
|
||||
} else if (OB_ISNULL(expr_ctx.my_session_) || OB_ISNULL(expr_ctx.exec_ctx_)) {
|
||||
ret = OB_NOT_INIT;
|
||||
LOG_WARN("session ptr or exec ctx is null", K(ret), K(expr_ctx.my_session_));
|
||||
} else {
|
||||
const ObObj& date_arg = params[0];
|
||||
if (2 == params_count) {
|
||||
@ -414,7 +429,8 @@ int ObExprWeek::calc_resultN(ObObj& result, const ObObj* params, int64_t params_
|
||||
}
|
||||
if (OB_UNLIKELY(date_arg.is_null())) {
|
||||
result.set_null();
|
||||
} else if (OB_FAIL(ob_obj_to_ob_time_with_date(date_arg, get_timezone_info(expr_ctx.my_session_), ot, false))) {
|
||||
} else if (OB_FAIL(ob_obj_to_ob_time_with_date(date_arg, get_timezone_info(expr_ctx.my_session_),
|
||||
ot, get_cur_time(expr_ctx.exec_ctx_->get_physical_plan_ctx()), false))) {
|
||||
LOG_WARN("cast to ob time failed", K(ret), K(date_arg), K(expr_ctx.cast_mode_));
|
||||
if (CM_IS_WARN_ON_FAIL(expr_ctx.cast_mode_)) {
|
||||
LOG_WARN("cast to ob time failed", K(ret), K(expr_ctx.cast_mode_));
|
||||
|
@ -2221,6 +2221,13 @@ MOD '(' expr ',' expr ')'
|
||||
make_name_node($$, result->malloc_pool_, "timestamp");
|
||||
malloc_non_terminal_node($$, result->malloc_pool_, T_FUN_SYS, 2, $$, params);
|
||||
}
|
||||
| TIMESTAMP '(' expr ',' expr ')'
|
||||
{
|
||||
ParseNode *params = NULL;
|
||||
malloc_non_terminal_node(params, result->malloc_pool_, T_EXPR_LIST, 2, $3, $5);
|
||||
make_name_node($$, result->malloc_pool_, "timestamp");
|
||||
malloc_non_terminal_node($$, result->malloc_pool_, T_FUN_SYS, 2, $$, params);
|
||||
}
|
||||
| MONTH '(' expr ')'
|
||||
{
|
||||
ParseNode *params = NULL;
|
||||
@ -4299,6 +4306,11 @@ DATETIME
|
||||
malloc_terminal_node($$, result->malloc_pool_, T_INT);
|
||||
$$->value_ = GET_FORMAT_DATETIME;
|
||||
}
|
||||
| TIMESTAMP
|
||||
{
|
||||
malloc_terminal_node($$, result->malloc_pool_, T_INT);
|
||||
$$->value_ = GET_FORMAT_DATETIME;
|
||||
}
|
||||
| DATE
|
||||
{
|
||||
malloc_terminal_node($$, result->malloc_pool_, T_INT);
|
||||
|
File diff suppressed because it is too large
Load Diff
@ -2667,6 +2667,14 @@ bool ObSysFunRawExpr::same_as(const ObRawExpr& expr, ObExprEqualCheckContext* ch
|
||||
bool_ret = false;
|
||||
}
|
||||
}
|
||||
if (0 == get_param_count()
|
||||
&& (T_FUN_SYS_CUR_TIMESTAMP == get_expr_type()
|
||||
|| T_FUN_SYS_SYSDATE == get_expr_type()
|
||||
|| T_FUN_SYS_CUR_TIME == get_expr_type()
|
||||
|| T_FUN_SYS_UTC_TIMESTAMP == get_expr_type()
|
||||
|| T_FUN_SYS_UTC_TIME == get_expr_type())) {
|
||||
bool_ret = result_type_.get_scale() == s_expr->get_result_type().get_scale();
|
||||
}
|
||||
}
|
||||
}
|
||||
return bool_ret;
|
||||
|
@ -2230,8 +2230,16 @@ int ObRawExprPrinter::print_cast_type(ObRawExpr* expr)
|
||||
}
|
||||
case T_DATETIME: {
|
||||
// oracle mode treate date as datetime
|
||||
const char* type_str = lib::is_oracle_mode() ? "date" : "datetime";
|
||||
DATA_PRINTF(type_str);
|
||||
if (lib::is_oracle_mode()) {
|
||||
DATA_PRINTF("date");
|
||||
} else {
|
||||
int16_t scale = parse_node.int16_values_[OB_NODE_CAST_N_SCALE_IDX];
|
||||
if (scale >= 0) {
|
||||
DATA_PRINTF("datetime(%d)", scale);
|
||||
} else {
|
||||
DATA_PRINTF("datetime");
|
||||
}
|
||||
}
|
||||
break;
|
||||
}
|
||||
case T_DATE: {
|
||||
@ -2239,7 +2247,12 @@ int ObRawExprPrinter::print_cast_type(ObRawExpr* expr)
|
||||
break;
|
||||
}
|
||||
case T_TIME: {
|
||||
DATA_PRINTF("time");
|
||||
int16_t scale = parse_node.int16_values_[OB_NODE_CAST_N_SCALE_IDX];
|
||||
if (scale >= 0) {
|
||||
DATA_PRINTF("time(%d)", scale);
|
||||
} else {
|
||||
DATA_PRINTF("time");
|
||||
}
|
||||
break;
|
||||
}
|
||||
case T_NUMBER: {
|
||||
@ -2281,15 +2294,30 @@ int ObRawExprPrinter::print_cast_type(ObRawExpr* expr)
|
||||
break;
|
||||
}
|
||||
case T_TIMESTAMP_TZ: {
|
||||
DATA_PRINTF("timestamp with time zone");
|
||||
int16_t scale = parse_node.int16_values_[OB_NODE_CAST_N_SCALE_IDX];
|
||||
if (scale >= 0) {
|
||||
DATA_PRINTF("timestamp(%d) with time zone", scale);
|
||||
} else {
|
||||
DATA_PRINTF("timestamp with time zone");
|
||||
}
|
||||
break;
|
||||
}
|
||||
case T_TIMESTAMP_LTZ: {
|
||||
DATA_PRINTF("timestamp with local time zone");
|
||||
int16_t scale = parse_node.int16_values_[OB_NODE_CAST_N_SCALE_IDX];
|
||||
if (scale >= 0) {
|
||||
DATA_PRINTF("timestamp(%d) with local time zone", scale);
|
||||
} else {
|
||||
DATA_PRINTF("timestamp with local time zone");
|
||||
}
|
||||
break;
|
||||
}
|
||||
case T_TIMESTAMP_NANO: {
|
||||
DATA_PRINTF("timestamp");
|
||||
int16_t scale = parse_node.int16_values_[OB_NODE_CAST_N_SCALE_IDX];
|
||||
if (scale >= 0) {
|
||||
DATA_PRINTF("timestamp(%d)", scale);
|
||||
} else {
|
||||
DATA_PRINTF("timestamp");
|
||||
}
|
||||
break;
|
||||
}
|
||||
case T_RAW: {
|
||||
|
Loading…
x
Reference in New Issue
Block a user