From 5c64c72df53d0b2488ed3749a2a2815e651b896d Mon Sep 17 00:00:00 2001 From: SanmuWangZJU Date: Thu, 9 Mar 2023 09:41:24 +0000 Subject: [PATCH] [OBCDC] Fix usage of incorrect tenant_id when using data_dict --- .../data_dictionary/ob_data_dict_struct.cpp | 12 --------- .../data_dictionary/ob_data_dict_struct.h | 18 +++++++++++++ .../src/ob_cdc_multi_data_source_info.cpp | 25 ++++++++++--------- .../src/ob_log_meta_data_baseline_loader.cpp | 1 + .../libobcdc/src/ob_log_meta_data_struct.cpp | 18 +++++++++++-- .../data_dictionary/test_data_dict_struct.cpp | 6 +++-- 6 files changed, 52 insertions(+), 28 deletions(-) diff --git a/src/logservice/data_dictionary/ob_data_dict_struct.cpp b/src/logservice/data_dictionary/ob_data_dict_struct.cpp index 65c652764..7ff1ea9a9 100644 --- a/src/logservice/data_dictionary/ob_data_dict_struct.cpp +++ b/src/logservice/data_dictionary/ob_data_dict_struct.cpp @@ -249,7 +249,6 @@ DEFINE_EQUAL(ObDictTenantMeta) { bool is_equal = true; LST_DO_CODE(IS_ARG_EQUAL, - tenant_id_, schema_version_, tenant_name_, compatibility_mode_, @@ -270,7 +269,6 @@ DEFINE_SERIALIZE(ObDictTenantMeta) if (OB_FAIL(ret)) { } else { LST_DO_CODE(OB_UNIS_ENCODE, - tenant_id_, schema_version_, tenant_name_, compatibility_mode_, @@ -293,7 +291,6 @@ DEFINE_DESERIALIZE(ObDictTenantMeta) } else { ObString tmp_tenant_name; LST_DO_CODE(OB_UNIS_DECODE, - tenant_id_, schema_version_, tmp_tenant_name, compatibility_mode_, @@ -317,7 +314,6 @@ DEFINE_GET_SERIALIZE_SIZE(ObDictTenantMeta) int64_t len = 0; LST_DO_CODE(OB_UNIS_ADD_LEN, - tenant_id_, schema_version_, tenant_name_, compatibility_mode_, @@ -437,7 +433,6 @@ DEFINE_EQUAL(ObDictDatabaseMeta) { bool is_equal = true; LST_DO_CODE(IS_ARG_EQUAL, - tenant_id_, database_id_, schema_version_, database_name_, @@ -456,7 +451,6 @@ DEFINE_SERIALIZE(ObDictDatabaseMeta) if (OB_FAIL(ret)) { } else { LST_DO_CODE(OB_UNIS_ENCODE, - tenant_id_, database_id_, schema_version_, database_name_, @@ -477,7 +471,6 @@ DEFINE_DESERIALIZE(ObDictDatabaseMeta) } else { ObString tmp_db_name; LST_DO_CODE(OB_UNIS_DECODE, - tenant_id_, database_id_, schema_version_, tmp_db_name, @@ -499,7 +492,6 @@ DEFINE_GET_SERIALIZE_SIZE(ObDictDatabaseMeta) int64_t len = 0; LST_DO_CODE(OB_UNIS_ADD_LEN, - tenant_id_, database_id_, schema_version_, database_name_, @@ -839,7 +831,6 @@ DEFINE_EQUAL(ObDictTableMeta) { bool is_equal = true; LST_DO_CODE(IS_ARG_EQUAL, - tenant_id_, database_id_, table_id_, schema_version_, @@ -872,7 +863,6 @@ DEFINE_SERIALIZE(ObDictTableMeta) if (OB_FAIL(ret)) { } else { LST_DO_CODE(OB_UNIS_ENCODE, - tenant_id_, database_id_, table_id_, schema_version_, @@ -908,7 +898,6 @@ DEFINE_DESERIALIZE(ObDictTableMeta) ObString tmp_table_name; LST_DO_CODE(OB_UNIS_DECODE, - tenant_id_, database_id_, table_id_, schema_version_, @@ -945,7 +934,6 @@ DEFINE_GET_SERIALIZE_SIZE(ObDictTableMeta) int64_t len = 0; LST_DO_CODE(OB_UNIS_ADD_LEN, - tenant_id_, database_id_, table_id_, schema_version_, diff --git a/src/logservice/data_dictionary/ob_data_dict_struct.h b/src/logservice/data_dictionary/ob_data_dict_struct.h index 16a834ffe..01c39554b 100644 --- a/src/logservice/data_dictionary/ob_data_dict_struct.h +++ b/src/logservice/data_dictionary/ob_data_dict_struct.h @@ -138,6 +138,7 @@ public: && ! tenant_name_.empty(); } OB_INLINE uint64_t get_tenant_id() const { return tenant_id_; } + OB_INLINE void set_tenant_id(const uint64_t tenant_id) { tenant_id_ = tenant_id; } OB_INLINE const char *get_tenant_name() const { return extract_str(tenant_name_); } OB_INLINE int64_t get_schema_version() const { return schema_version_; } OB_INLINE common::ObCompatibilityMode get_compatibility_mode() const { return compatibility_mode_; } @@ -162,6 +163,11 @@ public: private: ObIAllocator *allocator_; + // Won't serialize tenant_id in dict. + // DATADICT of StandBy is the same with Promary tenant. However tenant_id of standby tenant may not consist with primary tenant + // + // OBCDC will set tenant_id when consume and replay DATADICT + // Anyother consumer of DATADICT should also notice this feature. uint64_t tenant_id_; int64_t schema_version_; common::ObString tenant_name_; @@ -196,6 +202,7 @@ public: && ! database_name_.empty(); } OB_INLINE uint64_t get_tenant_id() const { return tenant_id_; } + OB_INLINE void set_tenant_id(const uint64_t tenant_id) { tenant_id_ = tenant_id; } OB_INLINE uint64_t get_database_id() const { return database_id_; } OB_INLINE int64_t get_schema_version() const { return schema_version_; } OB_INLINE const char *get_database_name() const { return extract_str(database_name_); } @@ -218,6 +225,11 @@ private: private: ObIAllocator *allocator_; + // Won't serialize tenant_id in dict. + // DATADICT of StandBy is the same with Promary tenant. However tenant_id of standby tenant may not consist with primary tenant + // + // OBCDC will set tenant_id when consume and replay DATADICT + // Anyother consumer of DATADICT should also notice this feature. uint64_t tenant_id_; uint64_t database_id_; int64_t schema_version_; @@ -341,6 +353,7 @@ public: public: // for user like OBCDC OB_INLINE uint64_t get_tenant_id() const { return tenant_id_; } + OB_INLINE void set_tenant_id(const uint64_t tenant_id) { tenant_id_ = tenant_id; } OB_INLINE uint64_t get_database_id() const { return database_id_; } OB_INLINE uint64_t get_table_id() const { return table_id_; } OB_INLINE const char *get_table_name() const { return extract_str(table_name_); } @@ -451,6 +464,11 @@ private: private: ObIAllocator *allocator_; + // Won't serialize tenant_id in dict. + // DATADICT of StandBy is the same with Promary tenant. However tenant_id of standby tenant may not consist with primary tenant + // + // OBCDC will set tenant_id when consume and replay DATADICT + // Anyother consumer of DATADICT should also notice this feature. uint64_t tenant_id_; uint64_t database_id_; uint64_t table_id_; diff --git a/src/logservice/libobcdc/src/ob_cdc_multi_data_source_info.cpp b/src/logservice/libobcdc/src/ob_cdc_multi_data_source_info.cpp index 4d2688276..5c0213b9d 100644 --- a/src/logservice/libobcdc/src/ob_cdc_multi_data_source_info.cpp +++ b/src/logservice/libobcdc/src/ob_cdc_multi_data_source_info.cpp @@ -132,26 +132,27 @@ int MultiDataSourceInfo::get_new_tenant_scehma_info( bool found = false; const int64_t tenant_meta_cnt = dict_tenant_metas_.count(); - for (int i = 0; OB_SUCC(ret) && ! found && i < tenant_meta_cnt; i++) { - const ObDictTenantMeta *tenant_meta = dict_tenant_metas_[i]; + if (OB_UNLIKELY(tenant_meta_cnt > 1)) { + ret = OB_ERR_UNEXPECTED; + LOG_ERROR("expect at most one tenant_dict in multi_data_source_info", KR(ret), + K(tenant_meta_cnt), K_(dict_tenant_metas)); + } else if (0 == tenant_meta_cnt) { + ret = OB_ENTRY_NOT_EXIST; + } else { + const ObDictTenantMeta *tenant_meta = dict_tenant_metas_[0]; if (OB_ISNULL(tenant_meta)) { ret = OB_ERR_UNEXPECTED; - LOG_ERROR("invalid tenant_meta", KR(ret), K(tenant_id)); - } else if (tenant_meta->get_tenant_id() == tenant_id) { + LOG_ERROR("invalid dict_tenant_meta", KR(ret), K(tenant_id)); + } else { tenant_schema_info.reset( - tenant_meta->get_tenant_id(), + tenant_id, tenant_meta->get_schema_version(), tenant_meta->get_tenant_name(), tenant_meta->is_restore()); - found = true; } } - if (OB_SUCC(ret) && ! found) { - ret = OB_ENTRY_NOT_EXIST; - } - return ret; } @@ -171,7 +172,7 @@ int MultiDataSourceInfo::get_new_database_scehma_info( if (OB_ISNULL(db_meta)) { ret = OB_ERR_UNEXPECTED; LOG_ERROR("invalid database_meta", KR(ret), K(tenant_id), K(database_id)); - } else if (db_meta->get_tenant_id() == tenant_id && db_meta->get_database_id() == database_id) { + } else if (db_meta->get_database_id() == database_id) { db_schema_info.reset( db_meta->get_database_id(), db_meta->get_schema_version(), @@ -203,7 +204,7 @@ int MultiDataSourceInfo::get_new_table_meta( if (OB_ISNULL(tb_meta)) { ret = OB_ERR_UNEXPECTED; LOG_ERROR("invalid table_meta", KR(ret), K(tenant_id), K(table_id)); - } else if (tb_meta->get_tenant_id() == tenant_id && tb_meta->get_table_id() == table_id) { + } else if (tb_meta->get_table_id() == table_id) { table_meta = tb_meta; found = true; } diff --git a/src/logservice/libobcdc/src/ob_log_meta_data_baseline_loader.cpp b/src/logservice/libobcdc/src/ob_log_meta_data_baseline_loader.cpp index 167ff4dcd..d8325e0d5 100644 --- a/src/logservice/libobcdc/src/ob_log_meta_data_baseline_loader.cpp +++ b/src/logservice/libobcdc/src/ob_log_meta_data_baseline_loader.cpp @@ -196,6 +196,7 @@ int ObLogMetaDataBaselineLoader::read( LOG_ERROR("data_dict_iterator next_dict_entry for tenant_meta failed", K(ret), K(tenant_id), K(tenant_meta)); } else { + tenant_meta.set_tenant_id(tenant_id); // TODO debug LOG_INFO("tenant_meta", K(tenant_id), K(tenant_meta)); } diff --git a/src/logservice/libobcdc/src/ob_log_meta_data_struct.cpp b/src/logservice/libobcdc/src/ob_log_meta_data_struct.cpp index df061325e..d45a6544c 100644 --- a/src/logservice/libobcdc/src/ob_log_meta_data_struct.cpp +++ b/src/logservice/libobcdc/src/ob_log_meta_data_struct.cpp @@ -149,11 +149,18 @@ int ObDictTenantInfo::insert_dict_db_meta(datadict::ObDictDatabaseMeta *dict_db_ ret = OB_NOT_INIT; LOG_ERROR("ObDictTenantInfo has not been initialized", KR(ret)); } else { + const uint64_t tenant_id = get_tenant_id(); const uint64_t db_id = dict_db_meta->get_database_id(); MetaDataKey meta_data_key(db_id); - if (OB_FAIL(db_map_.insert(meta_data_key, dict_db_meta))) { + if (OB_UNLIKELY(OB_INVALID_TENANT_ID == tenant_id)) { + ret = OB_STATE_NOT_MATCH; + LOG_ERROR("expect valid tenant_id", KR(ret), K(tenant_id)); + } else if (OB_FAIL(db_map_.insert(meta_data_key, dict_db_meta))) { LOG_ERROR("db_map_ insert failed", KR(ret), K(meta_data_key), KPC(dict_db_meta)); + } else { + // NOTICE: tenant_id should set while load baseline dict. + dict_db_meta->set_tenant_id(tenant_id); } } @@ -217,11 +224,18 @@ int ObDictTenantInfo::insert_dict_table_meta(datadict::ObDictTableMeta *dict_tab ret = OB_NOT_INIT; LOG_ERROR("ObDictTenantInfo has not been initialized", KR(ret)); } else { + const uint64_t tenant_id = get_tenant_id(); const uint64_t table_id = dict_table_meta->get_table_id(); MetaDataKey meta_data_key(table_id); - if (OB_FAIL(table_map_.insert(meta_data_key, dict_table_meta))) { + if (OB_UNLIKELY(OB_INVALID_TENANT_ID == tenant_id)) { + ret = OB_STATE_NOT_MATCH; + LOG_ERROR("expect valid tenant_id", KR(ret), K(tenant_id)); + } else if (OB_FAIL(table_map_.insert(meta_data_key, dict_table_meta))) { LOG_ERROR("table_map_ insert failed", KR(ret), K(meta_data_key), KPC(dict_table_meta)); + } else { + // NOTICE: tenant_id should set while load baseline dict. + dict_table_meta->set_tenant_id(tenant_id); } } diff --git a/unittest/data_dictionary/test_data_dict_struct.cpp b/unittest/data_dictionary/test_data_dict_struct.cpp index 300b7ba96..4fa5be4bb 100644 --- a/unittest/data_dictionary/test_data_dict_struct.cpp +++ b/unittest/data_dictionary/test_data_dict_struct.cpp @@ -87,7 +87,8 @@ TEST(ObDictTenantMeta, test_raw) ob_free(buf); EXPECT_EQ(serialize_size, deserialize_pos); - EXPECT_EQ(tenant_meta.tenant_id_, tenant_meta_after.tenant_id_); + EXPECT_EQ(OB_INVALID_TENANT_ID, tenant_meta_after.tenant_id_); + // EXPECT_EQ(tenant_meta.tenant_id_, tenant_meta_after.tenant_id_); EXPECT_EQ(tenant_meta.tenant_name_, tenant_meta_after.tenant_name_); EXPECT_EQ(ls_arr[1], tenant_meta_after.ls_arr_[1]); EXPECT_TRUE(tenant_meta == tenant_meta_after); @@ -124,7 +125,8 @@ TEST(ObDictDatabaseMeta, test_raw) EXPECT_EQ(serialize_size, deserialize_pos); EXPECT_EQ(db_meta.database_id_, db_meta_after.database_id_); - EXPECT_EQ(db_meta.tenant_id_, db_meta_after.tenant_id_); + EXPECT_EQ(OB_INVALID_TENANT_ID, db_meta_after.tenant_id_); + //EXPECT_EQ(db_meta.tenant_id_, db_meta_after.tenant_id_); EXPECT_EQ(db_meta.database_name_, db_meta_after.database_name_); EXPECT_EQ(db_meta.schema_version_, db_meta_after.schema_version_); EXPECT_EQ(db_meta.name_case_mode_, db_meta_after.name_case_mode_);