From 19c84854fc3f7971deab3cca8a44ec26aad73f95 Mon Sep 17 00:00:00 2001 From: 2149 <260391947@qq.com> Date: Thu, 20 Jul 2023 13:18:47 +0000 Subject: [PATCH] Fix funcitonal index drop column bug --- src/share/mysql_errno.h | 1 + src/share/ob_errno.cpp | 2 +- src/share/ob_errno.def | 2 +- .../resolver/ddl/ob_alter_table_resolver.cpp | 18 ++++++++++-------- src/sql/resolver/ddl/ob_alter_table_resolver.h | 2 +- 5 files changed, 14 insertions(+), 11 deletions(-) diff --git a/src/share/mysql_errno.h b/src/share/mysql_errno.h index e93a83e2d..808ca5569 100644 --- a/src/share/mysql_errno.h +++ b/src/share/mysql_errno.h @@ -1060,6 +1060,7 @@ #define ER_MISSING_JSON_VALUE 3966 #define ER_MULTIPLE_JSON_VALUES 3967 #define ER_CHARACTER_SET_MISMATCH 3995 +#define ER_TABLE_MUST_HAVE_A_VISIBLE_COLUMN 4028 #define ER_INVALID_CAST_TO_GEOMETRY 4032 #define ER_INVALID_CAST_POLYGON_RING_DIRECTION 4033 #define ER_GIS_DIFFERENT_SRIDS_AGGREGATION 4034 diff --git a/src/share/ob_errno.cpp b/src/share/ob_errno.cpp index fcfd24fd6..c5df937dc 100755 --- a/src/share/ob_errno.cpp +++ b/src/share/ob_errno.cpp @@ -13885,7 +13885,7 @@ static const _error _error_OB_ERR_ONLY_HAVE_INVISIBLE_COL_IN_TABLE = { .error_name = "OB_ERR_ONLY_HAVE_INVISIBLE_COL_IN_TABLE", .error_cause = "Internal Error", .error_solution = "Contact OceanBase Support", - .mysql_errno = -1, + .mysql_errno = ER_TABLE_MUST_HAVE_A_VISIBLE_COLUMN, .sqlstate = "HY000", .str_error = "table must have at least one column that is not invisible", .str_user_error = "table must have at least one column that is not invisible", diff --git a/src/share/ob_errno.def b/src/share/ob_errno.def index 017195421..2ccaa218e 100755 --- a/src/share/ob_errno.def +++ b/src/share/ob_errno.def @@ -1270,7 +1270,7 @@ DEFINE_ORACLE_ERROR(OB_ERR_ORDER_BY_ITEM_NOT_IN_SELECT_LIST, -5675, -1, "HY000", DEFINE_ORACLE_ERROR_DEP(OB_ERR_INTERVAL_INVALID, -5676, -1, "HY000", "the interval is invalid", 1867, "the interval is invalid"); DEFINE_ORACLE_ERROR_EXT(OB_ERR_NUMERIC_OR_VALUE_ERROR, -5677, -1, "HY000", "PL/SQL: numeric or value error", "PL/SQL: numeric or value error: %.*s", 6502, "PL/SQL: numeric or value error", "PL/SQL: numeric or value error: %.*s"); DEFINE_ORACLE_ERROR_EXT(OB_ERR_CONSTRAINT_NAME_DUPLICATE, -5678, ER_CHECK_CONSTRAINT_DUP_NAME, "HY000", "Duplicate check constraint name","Duplicate check constraint name \'%.*s\'.", 2264, "name already used by an existing constraint", "name \'%.*s\' already used by an existing constraint"); -DEFINE_ORACLE_ERROR(OB_ERR_ONLY_HAVE_INVISIBLE_COL_IN_TABLE, -5679, -1, "HY000", "table must have at least one column that is not invisible", 54039, "table must have at least one column that is not invisible"); +DEFINE_ORACLE_ERROR(OB_ERR_ONLY_HAVE_INVISIBLE_COL_IN_TABLE, -5679, ER_TABLE_MUST_HAVE_A_VISIBLE_COLUMN, "HY000", "table must have at least one column that is not invisible", 54039, "table must have at least one column that is not invisible"); DEFINE_ORACLE_ERROR(OB_ERR_INVISIBLE_COL_ON_UNSUPPORTED_TABLE_TYPE, -5680, -1, "HY000", "Invisible column is not supported on this type of table.", 54042, "Invisible column is not supported on this type of table."); DEFINE_ORACLE_ERROR(OB_ERR_MODIFY_COL_VISIBILITY_COMBINED_WITH_OTHER_OPTION, -5681, -1, "HY000", "Column visibility modifications cannot be combined with any other modified column DDL option.", 54046, "Column visibility modifications cannot be combined with any other modified column DDL option."); DEFINE_ORACLE_ERROR(OB_ERR_MODIFY_COL_VISIBILITY_BY_SYS_USER, -5682, -1, "HY000", "The visibility of a column from a table owned by a SYS user cannot be changed.", 54053, "The visibility of a column from a table owned by a SYS user cannot be changed."); diff --git a/src/sql/resolver/ddl/ob_alter_table_resolver.cpp b/src/sql/resolver/ddl/ob_alter_table_resolver.cpp index fb826a61b..083214462 100644 --- a/src/sql/resolver/ddl/ob_alter_table_resolver.cpp +++ b/src/sql/resolver/ddl/ob_alter_table_resolver.cpp @@ -856,17 +856,18 @@ int ObAlterTableResolver::resolve_action_list(const ParseNode &node) //deal with drop column affer drop constraint (mysql mode) if (OB_SUCC(ret) && lib::is_mysql_mode() && drop_col_act_position_list.count() > 0) { for (uint64_t i = 0; i < drop_col_act_position_list.count(); ++i) { - if (OB_FAIL(resolve_drop_column_nodes_for_mysql(*node.children_[drop_col_act_position_list.at(i)]))) { + if (OB_FAIL(resolve_drop_column_nodes_for_mysql(*node.children_[drop_col_act_position_list.at(i)], reduced_visible_col_set))) { SQL_RESV_LOG(WARN, "Resolve drop column error!", K(ret)); } } } - if (OB_SUCC(ret) && lib::is_oracle_mode()) { - if (is_modify_column_visibility && (alter_column_times != alter_column_visibility_times)) { + if (OB_SUCC(ret)) { + if (lib::is_oracle_mode() && is_modify_column_visibility && (alter_column_times != alter_column_visibility_times)) { ret = OB_ERR_MODIFY_COL_VISIBILITY_COMBINED_WITH_OTHER_OPTION; SQL_RESV_LOG(WARN, "Column visibility modifications can not be combined with any other modified column DDL option.", K(ret)); } else { bool has_visible_col = false; + bool has_hidden_gencol = false; ObColumnIterByPrevNextID iter(*table_schema_); const ObColumnSchemaV2 *column_schema = NULL; while (OB_SUCC(ret) && OB_SUCC(iter.next(column_schema)) && !has_visible_col) { @@ -881,6 +882,7 @@ int ObAlterTableResolver::resolve_action_list(const ParseNode &node) continue; } else if (column_schema->is_hidden()) { // skip hidden column + has_hidden_gencol |= column_schema->is_virtual_generated_column(); continue; } else { // is visible column ObColumnNameHashWrapper col_key(column_schema->get_column_name_str()); @@ -902,9 +904,10 @@ int ObAlterTableResolver::resolve_action_list(const ParseNode &node) ret = OB_SUCCESS; } if (OB_SUCC(ret)) { - if (alter_column_visibility_times > reduced_visible_col_set.count()) { + if (lib::is_oracle_mode() && alter_column_visibility_times > reduced_visible_col_set.count()) { // 走到这里说明存在 alter table modify column visible,则至少有一个 visible column,不应该报错 - } else if (!has_visible_col) { + } else if (!has_visible_col && (is_oracle_mode() || has_hidden_gencol)) { + //If there's no hidden generated columns, OB will check if all fields are dropped on rootserver ret = OB_ERR_ONLY_HAVE_INVISIBLE_COL_IN_TABLE; SQL_RESV_LOG(WARN, "table must have at least one column that is not invisible", K(ret)); } @@ -1054,10 +1057,9 @@ int ObAlterTableResolver::resolve_column_options(const ParseNode &node, return ret; } -int ObAlterTableResolver::resolve_drop_column_nodes_for_mysql(const ParseNode& node) +int ObAlterTableResolver::resolve_drop_column_nodes_for_mysql(const ParseNode& node, ObReducedVisibleColSet &reduced_visible_col_set) { int ret = OB_SUCCESS; - ObReducedVisibleColSet reduced_visible_col_set; if (T_ALTER_COLUMN_OPTION != node.type_ || OB_ISNULL(node.children_)) { ret = OB_ERR_UNEXPECTED; SQL_RESV_LOG(WARN, "invalid parse tree!", K(ret)); @@ -5265,7 +5267,7 @@ int ObAlterTableResolver::resolve_drop_column(const ParseNode &node, ObReducedVi SQL_RESV_LOG(WARN, "Add alter column schema failed!", K(ret)); } } - if (OB_SUCC(ret) && lib::is_oracle_mode()) { + if (OB_SUCC(ret)) { const ObString &column_name = alter_column_schema.get_origin_column_name(); ObColumnSchemaHashWrapper col_key(column_name); if (OB_FAIL(reduced_visible_col_set.set_refactored(col_key))) { diff --git a/src/sql/resolver/ddl/ob_alter_table_resolver.h b/src/sql/resolver/ddl/ob_alter_table_resolver.h index c3c5a1660..0e6b1c7ce 100644 --- a/src/sql/resolver/ddl/ob_alter_table_resolver.h +++ b/src/sql/resolver/ddl/ob_alter_table_resolver.h @@ -70,7 +70,7 @@ public: ObReducedVisibleColSet &reduced_visible_col_set); int resolve_drop_column(const ParseNode &node, ObReducedVisibleColSet &reduced_visible_col_set); - int resolve_drop_column_nodes_for_mysql(const ParseNode& node); + int resolve_drop_column_nodes_for_mysql(const ParseNode& node, ObReducedVisibleColSet &reduced_visible_col_set); int resolve_rename_column(const ParseNode &node); int fill_table_option(const share::schema::ObTableSchema *table_schema); //save table option to AlterTableArg