[FEAT MERGE] 4.3 online ddl column type change

This commit is contained in:
gaishun
2023-12-13 02:12:59 +00:00
committed by ob-robot
parent 509d45f3e6
commit 143a6f2f2e
8 changed files with 238 additions and 64 deletions

View File

@ -642,6 +642,62 @@ int ob_urowid_str(char *buff, int64_t buff_length, int64_t &pos, int64_t length,
return databuff_printf(buff, buff_length, pos, "urowid(%ld)", length);
}
bool is_match_alter_integer_column_online_ddl_rules(const common::ObObjMeta& src_meta,
const common::ObObjMeta& dst_meta)
{
bool is_online_ddl = false;
if ((((src_meta.is_signed_integer() && dst_meta.is_signed_integer())
|| (src_meta.is_unsigned_integer() && dst_meta.is_unsigned_integer())) // both are singed or unsigned integer
&& src_meta.get_type() <= dst_meta.get_type())) { // (unsigned) integer can be changed into larger by online ddl
is_online_ddl = true;
} else if (src_meta.is_unsigned_integer() && dst_meta.is_signed_integer()) {
if (src_meta.is_utinyint()) {
if (dst_meta.get_type() >= ObSmallIntType && dst_meta.get_type() <= ObIntType) { // unsigned tinyint -> smallint mediumint int bigint
is_online_ddl = true;
}
} else if (src_meta.is_usmallint()) {
if (dst_meta.get_type() >= ObMediumIntType && dst_meta.get_type() <= ObIntType) { // unsigned smallint -> mediumint int bigint
is_online_ddl = true;
}
} else if (src_meta.is_umediumint()) {
if (dst_meta.get_type() >= ObInt32Type && dst_meta.get_type() <= ObIntType) { // unsigned mediumint -> int bigint
is_online_ddl = true;
}
} else if (src_meta.is_uint32()) {
if (dst_meta.is_int()) { // unsigned int -> bigint
is_online_ddl = true;
}
}
}
return is_online_ddl;
}
bool is_match_alter_string_column_online_ddl_rules(const common::ObObjMeta& src_meta,
const common::ObObjMeta& dst_meta,
const int32_t src_len,
const int32_t dst_len)
{
bool is_online_ddl = false;
if (src_len > dst_len
|| src_meta.get_charset_type() != dst_meta.get_charset_type()
|| src_meta.get_collation_type() != dst_meta.get_collation_type()) {
// is_online_ddl = false;
} else if ((src_meta.is_varbinary() && dst_meta.is_blob() && ObTinyTextType == dst_meta.get_type()) // varbinary -> tinyblob; depended by generated column
|| (src_meta.is_varchar() && dst_meta.is_text() && ObTinyTextType == dst_meta.get_type()) // varchar -> tinytext; depended by generated column
|| (dst_meta.is_varbinary() && src_meta.is_blob() && ObTinyTextType == src_meta.get_type()) // tinyblob -> varbinary; depended by generated column
|| (dst_meta.is_varchar() && src_meta.is_text() && ObTinyTextType == src_meta.get_type())) { // tinytext -> varchar; depended by generated column
// support online ddl with generated column depended:
// varbinary -> tinyblob, varchar -> tinytext, tinyblob -> varbinary and tinytext -> varchar in version 4.3
is_online_ddl = true;
} else if (((src_meta.is_blob() && ObTinyTextType != src_meta.get_type() && dst_meta.is_blob() && ObTinyTextType != dst_meta.get_type()) // tinyblob -x-> blob ---> mediumblob ---> logblob
|| (src_meta.is_text() && ObTinyTextType != src_meta.get_type() && dst_meta.is_text() && ObTinyTextType != dst_meta.get_type()))) { // tinytext -x-> text ---> mediumtext ---> longtext
// support online ddl with generated column depended:
// smaller lob -> larger lob;
is_online_ddl = true;
}
return is_online_ddl;
}
int ob_sql_type_str(char *buff,
int64_t buff_length,
int64_t &pos,

View File

@ -1269,7 +1269,12 @@ inline bool ob_is_unsigned_type(ObObjType type)
|| ObUDoubleType == type
|| ObUNumberType == type;
}
bool is_match_alter_integer_column_online_ddl_rules(const common::ObObjMeta& src_meta,
const common::ObObjMeta& dst_meta);
bool is_match_alter_string_column_online_ddl_rules(const common::ObObjMeta& src_meta,
const common::ObObjMeta& dst_meta,
const int32_t src_len,
const int32_t dst_len);
inline void convert_unsigned_type_to_signed(ObObjType &type)
{
switch(type) {

View File

@ -7714,19 +7714,43 @@ int ObDDLService::rebuild_constraint_check_expr(
int ObDDLService::check_can_alter_column_type(
const share::schema::ObColumnSchemaV2 &src_column,
const share::schema::ObColumnSchemaV2 &dst_column,
const share::schema::ObTableSchema &table_schema)
const share::schema::ObTableSchema &table_schema,
const bool is_oracle_mode)
{
int ret = OB_SUCCESS;
bool is_change_column_type = false;
bool is_in_index = false;
bool has_generated_depend = src_column.has_generated_column_deps();
if (OB_FAIL(check_is_change_column_type(src_column, dst_column, is_change_column_type))) {
LOG_WARN("fail to check is change column type", K(ret), K(src_column), K(dst_column));
} else if (is_change_column_type) {
if (OB_FAIL(check_column_in_index(src_column.get_column_id(), table_schema, is_in_index))) {
LOG_WARN("fail to check column is in index table", K(ret));
} else if (is_in_index) {
ret = OB_NOT_SUPPORTED;
LOG_WARN("cannot modify column in index table", K(ret));
} else if (is_in_index || has_generated_depend) {
// is_in_index==true means : src_column is 'the index column' or 'index create by user'.
const common::ObObjMeta &src_meta = src_column.get_meta_type();
const common::ObObjMeta &dst_meta = dst_column.get_meta_type();
if (is_oracle_mode) {
// in oracle mode
ret = OB_NOT_SUPPORTED;
LOG_WARN("cannot modify column in index table", K(ret), K(src_column), K(dst_column), K(table_schema));
} else {
// in mysql mode
uint64_t data_version = 0;
if (OB_FAIL(GET_MIN_DATA_VERSION(table_schema.get_tenant_id(), data_version))) {
LOG_WARN("fail to get data version", KR(ret), K(table_schema.get_tenant_id()));
} else if (((has_generated_depend && !is_in_index) || data_version >= DATA_VERSION_4_2_2_0)
&& common::is_match_alter_integer_column_online_ddl_rules(src_meta, dst_meta)) {
// support online ddl with index, generated column depended:
// smaller integer -> big integer in mysql mode in version 4.2.2
} else if (((has_generated_depend && !is_in_index) || data_version >= DATA_VERSION_4_3_0_0)
&& common::is_match_alter_string_column_online_ddl_rules(src_meta, dst_meta, src_column.get_data_length(), dst_column.get_data_length())) {
// generated column type change of: varchar <-> tinytext; varbinary <-> tinyblob; smaller lob -> larger lob; (4.3.0.0)
} else {
ret = OB_NOT_SUPPORTED;
LOG_WARN("cannot modify column in index table", K(ret), K(src_column), K(dst_column), K(table_schema), K(data_version));
}
}
}
}
return ret;
@ -7785,29 +7809,25 @@ int ObDDLService::check_column_in_index(
LOG_WARN("fail to get column ids", K(ret));
}
for (int64_t j = 0; OB_SUCC(ret) && !is_in_index && j < column_ids.count(); ++j) {
const ObColumnSchemaV2 *column_schema = NULL;
if (column_id == column_ids.at(j).col_id_) {
is_in_index = true;
}
}
}
}
}
if (OB_SUCC(ret) && !is_in_index) {
column_ids.reuse();
if (OB_FAIL(table_schema.get_column_ids(column_ids))) {
LOG_WARN("fail to get column ids", K(ret));
} else {
for (int64_t j = 0; OB_SUCC(ret) && !is_in_index && j < column_ids.count(); ++j) {
const ObColumnSchemaV2 *column_schema = NULL;
if (OB_ISNULL(column_schema = table_schema.get_column_schema(column_ids.at(j).col_id_))) {
ret = OB_SCHEMA_ERROR;
LOG_WARN("column schema must not be NULL", K(ret), K(column_ids.at(j)));
} else if (column_schema->is_generated_column()) {
ObArray<uint64_t> ref_column_ids;
if (OB_FAIL(column_schema->get_cascaded_column_ids(ref_column_ids))) {
LOG_WARN("fail to get cascade column ids", K(ret));
} else {
is_in_index = has_exist_in_array(ref_column_ids, column_id);
} else if (column_ids.at(j).col_id_ > common::OB_MIN_SHADOW_COLUMN_ID) {
// table schema get column_schema by shadow_column_id, the result is nullptr;
} else if (OB_ISNULL(column_schema = table_schema.get_column_schema(column_ids.at(j).col_id_))) {
ret = OB_SCHEMA_ERROR;
LOG_WARN("column schema must not be NULL", K(ret), K(column_ids.at(j)));
} else if (column_schema->is_generated_column()) {
ObArray<uint64_t> ref_column_ids;
if (OB_FAIL(column_schema->get_cascaded_column_ids(ref_column_ids))) {
LOG_WARN("fail to get cascade column ids", K(ret));
} else {
/*
If the column (namely A) is depended by a generated column, and users build an index on the generated column.
We consider the column (A) is in index.
*/
is_in_index = has_exist_in_array(ref_column_ids, column_id);
}
}
}
}
@ -7883,6 +7903,58 @@ int ObDDLService::check_modify_column_when_upgrade(
}
return ret;
}
int ObDDLService::alter_shadow_column_for_index(
const ObArray<ObTableSchema> &idx_schema_array,
const AlterColumnSchema *alter_column_schema,
const ObColumnSchemaV2 &new_column_schema,
ObDDLOperator &ddl_operator,
common::ObMySQLTransaction &trans)
{
int ret = OB_SUCCESS;
if (OB_ISNULL(alter_column_schema)) {
ret = OB_INVALID_ARGUMENT;
LOG_WARN("invalid argument", K(ret), KP(alter_column_schema));
} else if (!new_column_schema.is_rowkey_column()) {
// column is not rowkey column, need not update
} else {
const ObColumnSchemaV2 *origin_shadow_column_schema = nullptr;
for (int64_t i = 0; OB_SUCC(ret) && i < idx_schema_array.count(); ++i) {
const ObTableSchema& idx_table_schema = idx_schema_array.at(i);
if (idx_table_schema.get_shadow_rowkey_column_num() > 0) {
const ObColumnSchemaV2 *origin_shadow_column_schema = nullptr;
if (OB_ISNULL(origin_shadow_column_schema = idx_table_schema.get_column_schema(alter_column_schema->get_column_id() + common::OB_MIN_SHADOW_COLUMN_ID))) {
ret = OB_ENTRY_NOT_EXIST;
LOG_WARN("origin_shadow_column not exist", K(ret), KPC(alter_column_schema), K(idx_table_schema));
} else if (!origin_shadow_column_schema->is_rowkey_column()) {
ret = OB_ERR_UNEXPECTED;
LOG_WARN("origin_shadow_column_schema is not rowkey column", K(ret), K(idx_table_schema), KPC(origin_shadow_column_schema));
} else {
SMART_VAR(ObColumnSchemaV2, new_aux_column_schema) {
new_aux_column_schema.reset();
if (OB_FAIL(new_aux_column_schema.assign(*origin_shadow_column_schema))){
LOG_WARN("fail to assgin new_aux_column_schema", K(ret), KPC(origin_shadow_column_schema));
} else if (OB_FAIL(fill_new_column_attributes(*alter_column_schema, new_aux_column_schema))) {
LOG_WARN("failed to fill new column attributes", K(ret), KPC(alter_column_schema), K(new_aux_column_schema));
} else if (OB_FAIL(ObIndexBuilderUtil::set_shadow_column_info(origin_shadow_column_schema->get_column_name(), origin_shadow_column_schema->get_column_id(), new_aux_column_schema))) {
LOG_WARN("fail to set shadow_column_info", K(ret), K(new_aux_column_schema), K(origin_shadow_column_schema->get_column_name()));
} else if (OB_FAIL(ddl_operator.update_single_column(trans,
idx_table_schema,
idx_table_schema,
new_aux_column_schema))) {
LOG_WARN("schema service update aux column failed", K(ret), K(idx_table_schema), K(new_aux_column_schema));
} else if (OB_FAIL(ddl_operator.sync_aux_schema_version_for_history(
trans,
idx_table_schema))) {
LOG_WARN("fail to update aux schema version for update column", K(ret), K(idx_table_schema));
}
} // end SMART_VAR
}
}
} // end for
}
return ret;
}
int ObDDLService::check_new_column_for_index(
ObIArray<ObTableSchema> &idx_schemas,
@ -9090,6 +9162,8 @@ int ObDDLService::alter_table_column(const ObTableSchema &origin_table_schema,
} else if (OB_FAIL(ddl_operator.update_single_column(
trans, origin_table_schema, new_table_schema, new_column_schema))) {
RS_LOG(WARN, "failed to alter column", K(alter_column_schema), K(ret));
} else if (OB_FAIL(alter_shadow_column_for_index(idx_schema_array, alter_column_schema, new_column_schema, ddl_operator, trans))) {
RS_LOG(WARN, "failed to alter shadow column for index", K(ret));
} else if (OB_FAIL(alter_table_update_index_and_view_column(
new_table_schema,
new_column_schema,
@ -9182,7 +9256,7 @@ int ObDDLService::alter_table_column(const ObTableSchema &origin_table_schema,
}
if (OB_SUCC(ret)) {
if (OB_FAIL(check_can_alter_column_type(*orig_column_schema, *alter_column_schema, origin_table_schema))) {
if (OB_FAIL(check_can_alter_column_type(*orig_column_schema, *alter_column_schema, origin_table_schema, is_oracle_mode))) {
LOG_WARN("fail to check can alter column type", K(ret));
}
}
@ -9220,6 +9294,8 @@ int ObDDLService::alter_table_column(const ObTableSchema &origin_table_schema,
new_table_schema,
new_column_schema))) {
RS_LOG(WARN, "failed to alter column", K(alter_column_schema), K(ret));
} else if (OB_FAIL(alter_shadow_column_for_index(idx_schema_array, alter_column_schema, new_column_schema, ddl_operator, trans))) {
RS_LOG(WARN, "failed to alter shadow column for index", K(ret));
} else if (OB_FAIL(alter_table_update_index_and_view_column(new_table_schema,
new_column_schema,
ddl_operator,
@ -35552,7 +35628,7 @@ int ObDDLService::prepare_change_modify_column_online(AlterColumnSchema &alter_c
}
if (OB_SUCC(ret)) {
if (OB_FAIL(check_can_alter_column_type(*orig_column_schema, alter_column_schema,
origin_table_schema))) {
origin_table_schema, is_oracle_mode))) {
LOG_WARN("fail to check can alter column type", K(ret));
}
}

View File

@ -1802,7 +1802,8 @@ private:
int check_can_alter_column_type(
const share::schema::ObColumnSchemaV2 &src_column,
const share::schema::ObColumnSchemaV2 &dst_column,
const share::schema::ObTableSchema &table_schema);
const share::schema::ObTableSchema &table_schema,
const bool is_oracle_mode);
int check_is_change_column_type(
const share::schema::ObColumnSchemaV2 &src_column,
const share::schema::ObColumnSchemaV2 &dst_column,
@ -1817,6 +1818,13 @@ private:
int check_modify_column_when_upgrade(
const share::schema::ObColumnSchemaV2 &new_column,
const share::schema::ObColumnSchemaV2 &orig_column);
int alter_shadow_column_for_index(
const ObArray<ObTableSchema> &idx_schema_array,
const AlterColumnSchema *alter_column_schema,
const ObColumnSchemaV2 &new_column_schema,
ObDDLOperator &ddl_operator,
common::ObMySQLTransaction &trans);
int check_new_column_for_index(
ObIArray<share::schema::ObTableSchema> &idx_schemas,
const share::schema::ObColumnSchemaV2 &new_column_schema);

View File

@ -138,7 +138,27 @@ int ObIndexBuilderUtil::add_column(
}
return ret;
}
int ObIndexBuilderUtil::set_shadow_column_info(
const ObString &src_column_name,
const uint64_t src_column_id,
ObColumnSchemaV2 &shadow_column_schema) {
int ret = OB_SUCCESS;
shadow_column_schema.set_nullable(true);
//the shadow pk is an independent column
//so it should not inherit the column flags of the original pk
shadow_column_schema.set_column_flags(0);
ObObj default_obj;
default_obj.set_null();
shadow_column_schema.set_cur_default_value(default_obj);
shadow_column_schema.set_orig_default_value(default_obj);
shadow_column_schema.set_tbl_part_key_pos(0);
shadow_column_schema.set_column_id(src_column_id);
shadow_column_schema.set_is_hidden(true);
if (OB_FAIL(shadow_column_schema.set_column_name(src_column_name))) {
LOG_WARN("set_column_name failed", K(src_column_name), K(ret));
}
return ret;
}
int ObIndexBuilderUtil::add_shadow_pks(
const ObTableSchema &data_schema,
ObRowDesc &row_desc,
@ -187,19 +207,8 @@ int ObIndexBuilderUtil::add_shadow_pks(
K(column_id), K(ret));
} else {
data_column = *const_data_column;
data_column.set_nullable(true);
//the shadow pk is an independent column
//so it should not inherit the column flags of the original pk
data_column.set_column_flags(0);
ObObj default_obj;
default_obj.set_null();
data_column.set_cur_default_value(default_obj);
data_column.set_orig_default_value(default_obj);
data_column.set_tbl_part_key_pos(0);
data_column.set_column_id(OB_MIN_SHADOW_COLUMN_ID + const_data_column->get_column_id());
data_column.set_is_hidden(true);
if (OB_FAIL(data_column.set_column_name(shadow_pk_name))) {
LOG_WARN("set_column_name failed", KCSTRING(shadow_pk_name), K(ret));
if (OB_FAIL(set_shadow_column_info(shadow_pk_name, common::OB_MIN_SHADOW_COLUMN_ID + const_data_column->get_column_id(), data_column))) {
LOG_WARN("fail to set shadow_column_info", K(ret), K(data_column), K(shadow_pk_name));
} else {
// primary key(uk2, uk1)
if (data_column.get_column_id() > schema.get_max_used_column_id()) {

View File

@ -73,6 +73,10 @@ public:
share::schema::ObTableSchema &table_schema,
const bool is_hidden,
const bool is_specified_storing_col);
static int set_shadow_column_info(
const ObString &src_column_name,
const uint64_t src_column_id,
ObColumnSchemaV2 &shadow_column_schema);
private:
static const int SPATIAL_MBR_COLUMN_MAX_LENGTH = 32;
typedef common::ObArray<std::pair<int64_t, common::ObString> > OrderFTColumns;

View File

@ -4475,10 +4475,8 @@ int ObTableSchema::check_alter_column_type(const ObColumnSchemaV2 &src_column,
} else {
// in mysql mode
if (!is_type_reduction &&
((src_meta.is_integer_type() && dst_meta.is_integer_type())
|| (src_meta.is_varbinary() && dst_meta.is_blob())
|| (src_meta.is_text() && (dst_meta.is_text() || dst_meta.is_varchar()))
|| (src_meta.is_blob() && (dst_meta.is_blob() || dst_meta.is_varbinary())))) {
(common::is_match_alter_integer_column_online_ddl_rules(src_meta, dst_meta) // smaller integer -> larger integer
|| common::is_match_alter_string_column_online_ddl_rules(src_meta, dst_meta, src_col_byte_len, dst_col_byte_len))) { // varchar, tinytext; varbinary, tinyblob; lob;
// online, do nothing
} else {
is_offline = true;
@ -4574,7 +4572,8 @@ int ObTableSchema::check_prohibition_rules(const ObColumnSchemaV2 &src_schema,
} else if (OB_FAIL(check_alter_column_in_foreign_key(src_schema, dst_schema, is_oracle_mode))) {
LOG_WARN("failed to check alter column in foreign key", K(ret));
} else if (!is_oracle_mode
&& is_column_in_check_constraint(src_schema.get_column_id())) {
&& (is_column_in_check_constraint(src_schema.get_column_id())
&& !common::is_match_alter_integer_column_online_ddl_rules(src_schema.get_meta_type(), dst_schema.get_meta_type()))) {
// The column contains the check constraint to prohibit modification of the type in mysql mode
ret = OB_NOT_SUPPORTED;
LOG_USER_ERROR(OB_NOT_SUPPORTED, "Alter column with check constraint");
@ -4616,6 +4615,7 @@ int ObTableSchema::check_ddl_type_change_rules(const ObColumnSchemaV2 &src_colum
bool is_rowkey = false;
bool is_index = false;
bool is_same = false;
uint64_t data_version = 0;
const ColumnType src_col_type = src_column.get_data_type();
const ColumnType dst_col_type = dst_column.get_data_type();
const ObObjMeta &src_meta = src_column.get_meta_type();
@ -4628,8 +4628,10 @@ int ObTableSchema::check_ddl_type_change_rules(const ObColumnSchemaV2 &src_colum
} else if (is_same) {
// do nothing
} else if (!is_offline) {
if (is_oracle_mode) {
if (!ob_is_number_tc(src_col_type) &&
if (OB_FAIL(GET_MIN_DATA_VERSION(tenant_id_, data_version))) {
LOG_WARN("failed to get min data version", K(ret), K(tenant_id_), K(data_version));
} else if (is_oracle_mode) {
if (!(ob_is_number_tc(src_col_type)) &&
((!src_meta.is_varying_len_char_type() &&
!src_meta.is_timestamp_tz() &&
!src_meta.is_timestamp_ltz() &&
@ -4651,8 +4653,8 @@ int ObTableSchema::check_ddl_type_change_rules(const ObColumnSchemaV2 &src_colum
is_offline = true;
}
} else {
// MYSQL mode
if (!ob_is_number_tc(src_col_type) &&
!ob_is_decimal_int_tc(src_col_type) &&
((!ob_is_text_tc(src_col_type) &&
!src_meta.is_bit() &&
!src_meta.is_varchar() &&
@ -4661,18 +4663,31 @@ int ObTableSchema::check_ddl_type_change_rules(const ObColumnSchemaV2 &src_colum
!src_meta.is_datetime()) ||
src_col_type != dst_col_type) &&
(!src_meta.is_timestamp() &&
(!dst_meta.is_datetime() ||
!dst_meta.is_datetime()))) {
!dst_meta.is_datetime()) &&
!((src_meta.is_char() && dst_meta.is_char()) && // char(x) -> char(y) (y>=x) && src_column has no generated column depended on (rowkey or index)
!src_column.has_generated_column_deps()) &&
!(src_meta.is_integer_type() && dst_meta.is_integer_type() && data_version >= DATA_VERSION_4_2_2_0)) {
/*
Note of the judge of data_version:
Determine data_version to avoid mixed deployment problems during the upgrade process.
During the upgrade process, the memtable_key.h of the old version of the observer will not have different types of defense rules (common::is_match_alter_integer_column_online_ddl_rules).
And, the type dismatch may cause 4016 problems;
1. This issue only needs to consider the primary key, index and part_key columns, so put the check here.
2. In the online ddl conversion released in 4.2.2 and 4.3, only the column type conversion of integer will involve this issue.
Therefore, we make a special case where the integer column is used as the primary key or index column.
*/
if (is_rowkey || src_column.is_tbl_part_key_column()) {
is_offline = true;
}
if (is_index && (!src_meta.is_char() || !dst_meta.is_char())) {
if (is_index) {
is_offline = true;
}
}
if (is_column_in_foreign_key(src_column.get_column_id()) ||
src_column.has_generated_column_deps() ||
src_column.is_stored_generated_column()) {
if (!is_offline &&
src_meta.is_char() &&
dst_meta.is_char() && // char(x) -> char(y) (y>=x) && src_column has no generated column depended on (common column)
src_column.has_generated_column_deps()) {
is_offline = true;
}
if (src_column.is_string_type() || src_column.is_enum_or_set()) {
@ -4680,8 +4695,6 @@ int ObTableSchema::check_ddl_type_change_rules(const ObColumnSchemaV2 &src_colum
src_column.get_charset_type() != dst_column.get_charset_type()) {
is_offline = true;
}
} else if (src_meta.is_unsigned() != dst_meta.is_unsigned()) {
is_offline = true;
}
}
}
@ -4945,6 +4958,7 @@ int ObTableSchema::check_column_can_be_altered_offline(
return ret;
}
int ObTableSchema::check_column_can_be_altered_online(
const ObColumnSchemaV2 *src_schema,
ObColumnSchemaV2 *dst_schema) const
@ -4991,8 +5005,7 @@ int ObTableSchema::check_column_can_be_altered_online(
// support number to float in oracle mode
} else if ((src_schema->get_data_type() == dst_schema->get_data_type()
&& src_schema->get_collation_type() == dst_schema->get_collation_type())
|| (ob_is_integer_type(src_schema->get_data_type()) && // can change int to large scale
src_schema->get_data_type_class() == dst_schema->get_data_type_class())
|| common::is_match_alter_integer_column_online_ddl_rules(src_schema->get_meta_type(), dst_schema->get_meta_type()) // has to check the changing is valid
|| (src_schema->is_string_type() && dst_schema->is_string_type()
&& src_schema->get_charset_type() == dst_schema->get_charset_type()
&& src_schema->get_collation_type() == dst_schema->get_collation_type())) {
@ -5034,8 +5047,8 @@ int ObTableSchema::check_column_can_be_altered_online(
ret = OB_NOT_SUPPORTED;
LOG_USER_ERROR(OB_NOT_SUPPORTED, "modify column to binary type");
LOG_WARN("can not modify data to binary type", K(ret), KPC(src_schema), KPC(dst_schema));
} else if (ob_is_integer_type(src_schema->get_data_type())
&& src_schema->get_data_type() > dst_schema->get_data_type()) {
} else if (ob_is_integer_type(src_schema->get_data_type()) && ob_is_integer_type(dst_schema->get_data_type())
&& !common::is_match_alter_integer_column_online_ddl_rules(src_schema->get_meta_type(), dst_schema->get_meta_type())) {
ret = OB_NOT_SUPPORTED;
LOG_USER_ERROR(OB_NOT_SUPPORTED, "Change int data type to small scale");
LOG_WARN("can't not change int data type to small scale",

View File

@ -173,7 +173,10 @@ public:
const common::ObObjMeta &schema_meta = columns.at(i).col_type_;
if (common::ObNullType != value.get_type()
&& common::ObExtendType != value.get_type()
&& schema_meta.get_type() != value.get_type()) {
&& schema_meta.get_type() != value.get_type()
&& !(lib::is_mysql_mode()
&& (common::is_match_alter_integer_column_online_ddl_rules(schema_meta, value.get_meta())
|| common::is_match_alter_integer_column_online_ddl_rules(value.get_meta(), schema_meta)))) { // small integer -> big integer; mysql mode;
TRANS_LOG(WARN, "data/schema type does not match",
"index", i,
"data_type", value.get_type(),