From 70e025872ff50576a7f21ce850b72cdb2c1ad483 Mon Sep 17 00:00:00 2001 From: "hs.zhang" <22708345+cangfengzhs@users.noreply.github.com> Date: Mon, 21 Aug 2023 14:09:38 +0800 Subject: [PATCH] copy local id when clone space (#3005) * copy local id when clone space * add test * fix bug * fix bug --------- Co-authored-by: Sophie <84560950+Sophie-Xie@users.noreply.github.com> --- .../parts/CreateSpaceAsProcessor.cpp | 35 +++++++++++++++++++ .../processors/parts/CreateSpaceAsProcessor.h | 3 ++ .../tck/features/schema/CreateSpaceAs.feature | 18 ++++++++++ 3 files changed, 56 insertions(+) diff --git a/src/meta/processors/parts/CreateSpaceAsProcessor.cpp b/src/meta/processors/parts/CreateSpaceAsProcessor.cpp index b2f87c9ac78..dd3a77a1c35 100644 --- a/src/meta/processors/parts/CreateSpaceAsProcessor.cpp +++ b/src/meta/processors/parts/CreateSpaceAsProcessor.cpp @@ -92,6 +92,15 @@ void CreateSpaceAsProcessor::process(const cpp2::CreateSpaceAsReq &req) { return; } + auto newLocalIdKey = makeLocalIDKey(nebula::value(oldSpaceId), nebula::value(newSpaceId)); + if (nebula::ok(newLocalIdKey)) { + data.push_back(nebula::value(newLocalIdKey)); + } else { + rc_ = nebula::error(newLocalIdKey); + LOG(INFO) << "Make new local id failed, " << apache::thrift::util::enumNameSafe(rc_); + return; + } + resp_.id_ref() = to(nebula::value(newSpaceId), EntryType::SPACE); auto timeInMilliSec = time::WallClock::fastNowInMilliSec(); LastUpdateTimeMan::update(data, timeInMilliSec); @@ -231,5 +240,31 @@ ErrorOr> CreateSpaceAsProcesso return data; } +ErrorOr CreateSpaceAsProcessor::makeLocalIDKey( + GraphSpaceID oldSpaceId, GraphSpaceID newSpaceId) { + auto localIdkey = MetaKeyUtils::localIdKey(oldSpaceId); + int32_t id; + std::string val; + auto ret = kvstore_->get(kDefaultSpaceId, kDefaultPartId, localIdkey, &val); + if (ret != nebula::cpp2::ErrorCode::SUCCEEDED) { + if (ret != nebula::cpp2::ErrorCode::E_KEY_NOT_FOUND) { + return ret; + } + + // In order to be compatible with the existing old schema, and simple to implement, + // when the local_id record does not exist in space, directly use the smallest + // id available globally. + auto globalIdRet = getAvailableGlobalId(); + if (!nebula::ok(globalIdRet)) { + return nebula::error(globalIdRet); + } + id = nebula::value(globalIdRet); + } else { + id = *reinterpret_cast(val.c_str()); + } + auto newLocalIdKey = MetaKeyUtils::localIdKey(newSpaceId); + return {newLocalIdKey, std::string(reinterpret_cast(&id), sizeof(id))}; +} + } // namespace meta } // namespace nebula diff --git a/src/meta/processors/parts/CreateSpaceAsProcessor.h b/src/meta/processors/parts/CreateSpaceAsProcessor.h index 84f7536371a..5d9f5d4270a 100644 --- a/src/meta/processors/parts/CreateSpaceAsProcessor.h +++ b/src/meta/processors/parts/CreateSpaceAsProcessor.h @@ -43,6 +43,9 @@ class CreateSpaceAsProcessor : public BaseProcessor { ErrorOr> makeNewIndexes( GraphSpaceID oldSpaceId, GraphSpaceID newSpaceId); + ErrorOr makeLocalIDKey(GraphSpaceID oldSpaceId, + GraphSpaceID newSpaceId); + nebula::cpp2::ErrorCode rc_{nebula::cpp2::ErrorCode::SUCCEEDED}; private: diff --git a/tests/tck/features/schema/CreateSpaceAs.feature b/tests/tck/features/schema/CreateSpaceAs.feature index 9963d24a274..a7e345fe444 100644 --- a/tests/tck/features/schema/CreateSpaceAs.feature +++ b/tests/tck/features/schema/CreateSpaceAs.feature @@ -164,6 +164,24 @@ Feature: Create space as another space Then the result should be, in any order: | src | dst | rank | | "1" | "2" | 0 | + When executing query: + """ + create tag t2 (col1 int); + """ + Then the execution should be successful + When executing query: + """ + create tag index i3 on t2(col1); + """ + Then the execution should be successful + When executing query: + """ + show tag indexes; + """ + Then the result should be, in any order: + | Index Name | By Tag | Columns | + | "i1" | "t1" | ["col1"] | + | "i3" | "t2" | ["col1"] | Then drop the used space Scenario: clone space if not exist