diff --git a/frameworks/libs/distributeddb/common/include/db_errno.h b/frameworks/libs/distributeddb/common/include/db_errno.h index 2ff010a3b8d5bfa0bfdc1e811ab15eabf4035980..f0332243b4ab5eca9ac468472557e3db641fbcf1 100644 --- a/frameworks/libs/distributeddb/common/include/db_errno.h +++ b/frameworks/libs/distributeddb/common/include/db_errno.h @@ -127,6 +127,7 @@ constexpr int E_DENIED_SQL = (E_BASE + 105); // denied sql, not permit to execu constexpr int E_USER_CHANGE = (E_BASE + 106); // user change constexpr int E_CONSTRAINT = (E_BASE + 107); // sql failed with constraint constexpr int E_CLOUD_ERROR = (E_BASE + 108); // cloud error +constexpr int E_GAUSSDB_RD_ERROR = (E_BASE + 109); // gaussdb rd error constexpr int E_QUERY_END = (E_BASE + 110); // Indicates that query function has queried last data from cloud constexpr int E_DB_CLOSED = (E_BASE + 111); // db is closed constexpr int E_NOT_SET = (E_BASE + 112); // asset loader is not set diff --git a/frameworks/libs/distributeddb/interfaces/include/kv_store_nb_delegate.h b/frameworks/libs/distributeddb/interfaces/include/kv_store_nb_delegate.h index 453aea705e8d1ad7343b1e2f7091a03e2f1af7ba..8f2bc4a5555cc1f865374d68cad34f147c254c48 100644 --- a/frameworks/libs/distributeddb/interfaces/include/kv_store_nb_delegate.h +++ b/frameworks/libs/distributeddb/interfaces/include/kv_store_nb_delegate.h @@ -55,6 +55,7 @@ public: uint8_t compressionRate = 100; // Valid in [1, 100]. bool syncDualTupleMode = false; // communicator label use dualTuple hash or not bool localOnly = false; // active sync module + bool useGaussDb = false; // use gaussdb_rd as storage engine }; DB_API virtual ~KvStoreNbDelegate() {} diff --git a/frameworks/libs/distributeddb/interfaces/src/kv_store_delegate_manager.cpp b/frameworks/libs/distributeddb/interfaces/src/kv_store_delegate_manager.cpp index 9854e2bf2e355c042788b162949794ce4addb713..371f9cd58932d525a9f9276ae59d6eff20cdb081 100644 --- a/frameworks/libs/distributeddb/interfaces/src/kv_store_delegate_manager.cpp +++ b/frameworks/libs/distributeddb/interfaces/src/kv_store_delegate_manager.cpp @@ -51,10 +51,13 @@ namespace { IKvDBConnection *GetOneConnectionWithRetry(const KvDBProperties &properties, int &errCode) { for (int i = 0; i < GET_CONNECT_RETRY; i++) { + LOGW("here 1 with retry %d", i); auto conn = KvDBManager::GetDatabaseConnection(properties, errCode); if (conn != nullptr) { + LOGW("here"); return conn; } + LOGW("return nullptr"); if (errCode == -E_STALE) { std::this_thread::sleep_for(std::chrono::milliseconds(RETRY_GET_CONN_INTER)); } else { @@ -84,7 +87,8 @@ namespace { const SchemaObject &schema, const KvStoreNbDelegate::Option &option) { properties.SetBoolProp(KvDBProperties::CREATE_IF_NECESSARY, option.createIfNecessary); - properties.SetIntProp(KvDBProperties::DATABASE_TYPE, KvDBProperties::SINGLE_VER_TYPE); + properties.SetIntProp(KvDBProperties::DATABASE_TYPE, option.useGaussDb ? + KvDBProperties::SINGLE_VER_TYPE_RD_KERNAL : KvDBProperties::SINGLE_VER_TYPE); properties.SetBoolProp(KvDBProperties::MEMORY_MODE, option.isMemoryDb); properties.SetBoolProp(KvDBProperties::ENCRYPTED_MODE, option.isEncryptedDb); if (!option.isMemoryDb) { // memory db ignore store path diff --git a/frameworks/libs/distributeddb/storage/include/ikvdb_factory.h b/frameworks/libs/distributeddb/storage/include/ikvdb_factory.h index 66c2c619fde69bdd9e9b48b253521dc00e99e2c8..02cf7e06d744dd437f71c1ec604294812dbcb283 100644 --- a/frameworks/libs/distributeddb/storage/include/ikvdb_factory.h +++ b/frameworks/libs/distributeddb/storage/include/ikvdb_factory.h @@ -29,10 +29,11 @@ namespace DistributedDB { enum KvDBType { LOCAL_KVDB = 0, SINGER_VER_KVDB, + SINGLE_VER_KVDB_RD_KERNAL, #ifndef OMIT_MULTI_VER MULTI_VER_KVDB, #endif // OMIT_MULTI_VER - UNSUPPORT_KVDB_TYPE = 3, + UNSUPPORT_KVDB_TYPE = 4, }; class IKvDBFactory { diff --git a/frameworks/libs/distributeddb/storage/include/kvdb_properties.h b/frameworks/libs/distributeddb/storage/include/kvdb_properties.h index 1f8749eab590579d1cc492bcecfafa1330e1587e..513f8206744aeca0ac75673e47f2dbdcf02d6a91 100644 --- a/frameworks/libs/distributeddb/storage/include/kvdb_properties.h +++ b/frameworks/libs/distributeddb/storage/include/kvdb_properties.h @@ -71,6 +71,7 @@ public: static const int LOCAL_TYPE = 1; static const int MULTI_VER_TYPE = 2; static const int SINGLE_VER_TYPE = 3; + static const int SINGLE_VER_TYPE_RD_KERNAL = 4; private: CipherType cipherType_; diff --git a/frameworks/libs/distributeddb/storage/src/default_factory.cpp b/frameworks/libs/distributeddb/storage/src/default_factory.cpp index 8c57e89fb3cb68ab7b394b1468e825e62b88c576..8ca11118b85039b71e253e64b036440f9d3c6f6d 100644 --- a/frameworks/libs/distributeddb/storage/src/default_factory.cpp +++ b/frameworks/libs/distributeddb/storage/src/default_factory.cpp @@ -23,6 +23,7 @@ #include "multi_ver_natural_store.h" #include "multi_ver_natural_store_commit_storage.h" #endif +#include "rd_single_ver_natural_store.h" #include "sqlite_single_ver_natural_store.h" #ifndef OMIT_MULTI_VER #include "sqlite_multi_ver_data_storage.h" @@ -38,6 +39,8 @@ IKvDB *DefaultFactory::CreateKvDb(KvDBType kvDbType, int &errCode) #endif case SINGER_VER_KVDB: return CreateSingleVerNaturalStore(errCode); + case SINGLE_VER_KVDB_RD_KERNAL: + return CreateRdSingleVerNaturalStore(errCode); #ifndef OMIT_MULTI_VER case MULTI_VER_KVDB: return CreateMultiVerNaturalStore(errCode); @@ -73,6 +76,14 @@ IKvDB *DefaultFactory::CreateSingleVerNaturalStore(int &errCode) return kvDb; } +// Create the single version natural store with gaussdb_rd +IKvDB *DefaultFactory::CreateRdSingleVerNaturalStore(int &errCode) +{ + IKvDB *kvDb = new (std::nothrow) RdSingleVerNaturalStore(); + errCode = ((kvDb == nullptr) ? -E_OUT_OF_MEMORY : E_OK); + return kvDb; +} + #ifndef OMIT_MULTI_VER // Create a key-value database for commit storage module. IKvDB *DefaultFactory::CreateCommitStorageDB(int &errCode) diff --git a/frameworks/libs/distributeddb/storage/src/default_factory.h b/frameworks/libs/distributeddb/storage/src/default_factory.h index 86a0b7482ede9bbe6d5ed155f0bb5b0b83336c74..26bb7d713c8d0f49f09197fd2fab766a1fae8ad1 100644 --- a/frameworks/libs/distributeddb/storage/src/default_factory.h +++ b/frameworks/libs/distributeddb/storage/src/default_factory.h @@ -48,6 +48,8 @@ private: #endif IKvDB *CreateSingleVerNaturalStore(int &errCode); + + IKvDB *CreateRdSingleVerNaturalStore(int &errCode); }; } // namespace DistributedDB #endif // DEFAULT_FACTORY_H diff --git a/frameworks/libs/distributeddb/storage/src/gaussdb_rd/rd_single_ver_natural_store.cpp b/frameworks/libs/distributeddb/storage/src/gaussdb_rd/rd_single_ver_natural_store.cpp new file mode 100644 index 0000000000000000000000000000000000000000..933d6f8f96cf6b10244456a89f19af30f423b8a9 --- /dev/null +++ b/frameworks/libs/distributeddb/storage/src/gaussdb_rd/rd_single_ver_natural_store.cpp @@ -0,0 +1,52 @@ +/* + * Copyright (c) 2021 Huawei Device Co., Ltd. + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#include "rd_single_ver_natural_store.h" + +#include "rd_single_ver_natural_store_connection.h" +#include "storage_engine_manager.h" + +namespace DistributedDB { + +RdSingleVerNaturalStore::RdSingleVerNaturalStore() +{ + LOGD("==============RdSingleVerNaturalStore Created=================="); +} + +RdSingleVerNaturalStore::~RdSingleVerNaturalStore() +{ +} + +GenericKvDBConnection *RdSingleVerNaturalStore::NewConnection(int &errCode) +{ + RdSingleVerNaturalStoreConnection *connection = new (std::nothrow) RdSingleVerNaturalStoreConnection(this); + if (connection == nullptr) { + errCode = -E_OUT_OF_MEMORY; + return nullptr; + } + errCode = E_OK; + return connection; +} + +int RdSingleVerNaturalStore::GetAndInitStorageEngine(const KvDBProperties &kvDBProp) +{ + int errCode = E_OK; + std::unique_lock lock(engineMutex_); + storageEngine_ = + static_cast(StorageEngineManager::GetStorageEngine(kvDBProp, errCode)); + return errCode; +} + +} // namespace DistributedDB diff --git a/frameworks/libs/distributeddb/storage/src/gaussdb_rd/rd_single_ver_natural_store.h b/frameworks/libs/distributeddb/storage/src/gaussdb_rd/rd_single_ver_natural_store.h new file mode 100644 index 0000000000000000000000000000000000000000..7f4d592185c666f741ec2e213fa5f3b0f7266430 --- /dev/null +++ b/frameworks/libs/distributeddb/storage/src/gaussdb_rd/rd_single_ver_natural_store.h @@ -0,0 +1,448 @@ +/* + * Copyright (c) 2021 Huawei Device Co., Ltd. + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +#ifndef RD_SINGLE_VER_NATURAL_STORE_H +#define RD_SINGLE_VER_NATURAL_STORE_H +#include +#include + +#include "sqlite_single_ver_natural_store.h" +#include "rd_single_ver_storage_engine.h" +#include "rd_single_ver_storage_executor.h" + +namespace DistributedDB { +class RdSingleVerNaturalStore : public SyncAbleKvDB, public SingleVerKvDBSyncInterface { +public: + RdSingleVerNaturalStore(); + ~RdSingleVerNaturalStore() override; + + // Delete the copy and assign constructors + DISABLE_COPY_ASSIGN_MOVE(RdSingleVerNaturalStore); + + // Open the database + int Open(const KvDBProperties &kvDBProp) override + { + LOGD("[RdSingleVerNaturalStore] Open RdSingleVerNaturalStore"); + int errCode = GetAndInitStorageEngine(kvDBProp); + if (errCode != E_OK) { + return errCode; + } + MyProp() = kvDBProp; + return E_OK; + } + + // Invoked automatically when connection count is zero + void Close() override + { + return; + } + + // Create a connection object. + GenericKvDBConnection *NewConnection(int &errCode) override; + + // Get interface type of this kvdb. + int GetInterfaceType() const override + { + return -E_NOT_SUPPORT; + } + + // Get the interface ref-count, in order to access asynchronously. + void IncRefCount() override + { + return; + } + + // Drop the interface ref-count. + void DecRefCount() override + { + return; + } + + // Get the identifier of this kvdb. + std::vector GetIdentifier() const override + { + return {}; + } + + // Get the dual tuple identifier of this kvdb. + std::vector GetDualTupleIdentifier() const override + { + return {}; + } + + // Get interface for syncer. + IKvDBSyncInterface *GetSyncInterface() override + { + return nullptr; + } + + int GetMetaData(const Key &key, Value &value) const override + { + return -E_NOT_SUPPORT; + } + + int PutMetaData(const Key &key, const Value &value) override + { + return -E_NOT_SUPPORT; + } + + // Delete multiple meta data records in a transaction. + int DeleteMetaData(const std::vector &keys) override + { + return -E_NOT_SUPPORT; + } + + // Delete multiple meta data records with key prefix in a transaction. + int DeleteMetaDataByPrefixKey(const Key &keyPrefix) const override + { + return -E_NOT_SUPPORT; + } + + int GetAllMetaKeys(std::vector &keys) const override + { + return -E_NOT_SUPPORT; + } + + int GetSyncData(Timestamp begin, Timestamp end, std::vector &dataItems, ContinueToken &continueStmtToken, + const DataSizeSpecInfo &dataSizeInfo) const override + { + return -E_NOT_SUPPORT; + } + + int GetSyncData(Timestamp begin, Timestamp end, std::vector &entries, + ContinueToken &continueStmtToken, const DataSizeSpecInfo &dataSizeInfo) const override + { + return -E_NOT_SUPPORT; + } + + int GetSyncData(QueryObject &query, const SyncTimeRange &timeRange, const DataSizeSpecInfo &dataSizeInfo, + ContinueToken &continueStmtToken, std::vector &entries) const override + { + return -E_NOT_SUPPORT; + } + + int GetSyncDataNext(std::vector &dataItems, ContinueToken &continueStmtToken, + const DataSizeSpecInfo &dataSizeInfo) const override + { + return -E_NOT_SUPPORT; + } + + int GetSyncDataNext(std::vector &entries, ContinueToken &continueStmtToken, + const DataSizeSpecInfo &dataSizeInfo) const override + { + return -E_NOT_SUPPORT; + } + + void ReleaseContinueToken(ContinueToken &continueStmtToken) const override + { + return; + } + + int PutSyncDataWithQuery(const QueryObject &query, const std::vector &entries, + const std::string &deviceName) override + { + return -E_NOT_SUPPORT; + } + + void GetMaxTimestamp(Timestamp &stamp) const override + { + return; + } + + void SetMaxTimestamp(Timestamp timestamp) + { + return; + } + + int Rekey(const CipherPassword &passwd) override + { + return -E_NOT_SUPPORT; + } + + int Export(const std::string &filePath, const CipherPassword &passwd) override + { + return -E_NOT_SUPPORT; + } + + int Import(const std::string &filePath, const CipherPassword &passwd) override + { + return -E_NOT_SUPPORT; + } + + // In sync procedure, call this function + int RemoveDeviceData(const std::string &deviceName, bool isNeedNotify) override + { + return -E_NOT_SUPPORT; + } + + // In local procedure, call this function + int RemoveDeviceData(const std::string &deviceName, bool isNeedNotify, bool isInSync) + { + return -E_NOT_SUPPORT; + } + + RdSingleVerStorageExecutor *GetHandle(bool isWrite, int &errCode, + OperatePerm perm = OperatePerm::NORMAL_PERM) const + { + return nullptr; + } + + void ReleaseHandle(RdSingleVerStorageExecutor *&handle) const + { + return; + } + + int TransObserverTypeToRegisterFunctionType(int observerType, RegisterFuncType &type) const override + { + return -E_NOT_SUPPORT;; + } + + int TransConflictTypeToRegisterFunctionType(int conflictType, RegisterFuncType &type) const override + { + return -E_NOT_SUPPORT;; + } + + bool CheckWritePermission() const override + { + return true; + } + + SchemaObject GetSchemaInfo() const override + { + return MyProp().GetSchema(); + } + + bool CheckCompatible(const std::string &schema, uint8_t type) const override + { + return true; + } + + Timestamp GetCurrentTimestamp() + { + return 0; + } + + SchemaObject GetSchemaObject() const + { + return MyProp().GetSchema(); + } + + const SchemaObject &GetSchemaObjectConstRef() const + { + return MyProp().GetSchemaConstRef(); + } + + const KvDBProperties &GetDbProperties() const override + { + return GetMyProperties(); + } + + int RemoveKvDB(const KvDBProperties &properties) override + { + return -E_NOT_SUPPORT; + } + + int GetKvDBSize(const KvDBProperties &properties, uint64_t &size) const override + { + return -E_NOT_SUPPORT; + } + + KvDBProperties &GetDbPropertyForUpdate() + { + return MyProp(); + } + + int InitDatabaseContext(const KvDBProperties &kvDBProp, bool isNeedUpdateSecOpt = false) + { + return -E_NOT_SUPPORT; + } + + int RegisterLifeCycleCallback(const DatabaseLifeCycleNotifier ¬ifier) + { + return -E_NOT_SUPPORT; + } + + int SetAutoLifeCycleTime(uint32_t time) + { + return -E_NOT_SUPPORT; + } + + int GetSecurityOption(SecurityOption &option) const override + { + return -E_NOT_SUPPORT; + } + + bool IsDataMigrating() const override + { + return true; + } + + void SetConnectionFlag(bool isExisted) const override + { + return; + } + + int TriggerToMigrateData() const + { + return -E_NOT_SUPPORT; + } + + // NOTE: 在sqlite_xxx_store里,这个函数负责校验数据符不符合schema。但是可以公用。 + // 他从conn透传到store, 是因为store有schema + // 但是他这里有一个备注: Not a schema database, do not need to check more; 也就是说没有schema也是符合预期的。 + // 但是在这之前,他判断了一下这个value有没有超过大小。 + // 先校验是不是必须要,不是的话 + // 如果有默认值的项,就自动补齐 + int CheckValueAndAmendIfNeed(ValueSource sourceType, const Value &oriValue, Value &amendValue, + bool &useAmendValue) const + { + // oriValue size may already be checked previously, but check here for safety + // TODO: 这个MAX_VALUE_SIZE需要和内核对齐 + if (oriValue.size() > DBConstant::MAX_VALUE_SIZE) { + return -E_INVALID_ARGS; + } + return E_OK; + } + + int CheckReadDataControlled() const + { + return -E_NOT_SUPPORT; + } + + bool IsCacheDBMode() const + { + return true; + } + + bool IsExtendedCacheDBMode() const + { + return true; + } + + void IncreaseCacheRecordVersion() const + { + return; + } + + uint64_t GetCacheRecordVersion() const + { + return 0; + } + + uint64_t GetAndIncreaseCacheRecordVersion() const + { + return 0; + } + + void NotifyRemotePushFinished(const std::string &targetId) const override + { + return; + } + + int GetDatabaseCreateTimestamp(Timestamp &outTime) const override + { + return -E_NOT_SUPPORT; + } + + int CheckIntegrity() const override + { + return -E_NOT_SUPPORT; + } + + int GetCompressionOption(bool &needCompressOnSync, uint8_t &compressionRate) const override + { + return -E_NOT_SUPPORT; + } + + int GetCompressionAlgo(std::set &algorithmSet) const override + { + return -E_NOT_SUPPORT; + } + + // Check and init query object for query sync and subscribe, flatbuffer schema will always return E_NOT_SUPPORT. + // return E_OK if subscribe is legal, ERROR on exception. + int CheckAndInitQueryCondition(QueryObject &query) const override + { + return -E_NOT_SUPPORT; + } + + int InterceptData(std::vector &entries, const std::string &sourceID, + const std::string &targetID) const override + { + return -E_NOT_SUPPORT; + } + + void SetDataInterceptor(const PushDataInterceptor &interceptor) override + { + return; + } + + int AddSubscribe(const std::string &subscribeId, const QueryObject &query, bool needCacheSubscribe) override + { + return -E_NOT_SUPPORT; + } + + int RemoveSubscribe(const std::string &subscribeId) override + { + return -E_NOT_SUPPORT; + } + + int RemoveSubscribe(const std::vector &subscribeIds) override + { + return -E_NOT_SUPPORT; + } + + int SetMaxLogSize(uint64_t limit) + { + return -E_NOT_SUPPORT; + } + + uint64_t GetMaxLogSize() const + { + return 0; + } + + void Dump(int fd) override + { + return; + } + + int IsSupportSubscribe() const override + { + return -E_NOT_SUPPORT; + } + + void AbortHandle() + { + return; + } + + void EnableHandle() + { + return; + } + + int TryHandle() const override + { + return -E_NOT_SUPPORT; + } + +private: + int GetAndInitStorageEngine(const KvDBProperties &kvDBProp); + + mutable std::shared_mutex engineMutex_; + RdSingleVerStorageEngine *storageEngine_; +}; +} // namespace DistributedDB +#endif // RD_SINGLE_VER_NATURAL_STORE_H diff --git a/frameworks/libs/distributeddb/storage/src/gaussdb_rd/rd_single_ver_natural_store_connection.cpp b/frameworks/libs/distributeddb/storage/src/gaussdb_rd/rd_single_ver_natural_store_connection.cpp new file mode 100644 index 0000000000000000000000000000000000000000..0beffc49e626ade08fad0571c7507fdc0b9cddc8 --- /dev/null +++ b/frameworks/libs/distributeddb/storage/src/gaussdb_rd/rd_single_ver_natural_store_connection.cpp @@ -0,0 +1,43 @@ +/* + * Copyright (c) 2023 Huawei Device Co., Ltd. + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#include "rd_single_ver_natural_store_connection.h" + +#include + +#include "db_common.h" +#include "db_constant.h" +#include "db_dfx_adapter.h" +#include "db_errno.h" +#include "kvdb_observer_handle.h" +#include "kvdb_pragma.h" +#include "log_print.h" +#include "sqlite_single_ver_natural_store.h" +#include "sqlite_single_ver_result_set.h" +#include "store_types.h" + +namespace DistributedDB { + +RdSingleVerNaturalStoreConnection::RdSingleVerNaturalStoreConnection(RdSingleVerNaturalStore *kvDB) +: SyncAbleKvDBConnection(kvDB) +{ + LOGD("==============RdSingleVerNaturalStoreConnection Created=================="); +} + +RdSingleVerNaturalStoreConnection::~RdSingleVerNaturalStoreConnection() +{ +} + +} // namespace DistributedDB \ No newline at end of file diff --git a/frameworks/libs/distributeddb/storage/src/gaussdb_rd/rd_single_ver_natural_store_connection.h b/frameworks/libs/distributeddb/storage/src/gaussdb_rd/rd_single_ver_natural_store_connection.h new file mode 100644 index 0000000000000000000000000000000000000000..e33f1016385d0e87c9ef36da2da107db058d7911 --- /dev/null +++ b/frameworks/libs/distributeddb/storage/src/gaussdb_rd/rd_single_ver_natural_store_connection.h @@ -0,0 +1,477 @@ +/* + * Copyright (c) 2023 Huawei Device Co., Ltd. + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#ifndef RD_SINGLE_VER_NATURAL_STORE_CONNECTION_H +#define RD_SINGLE_VER_NATURAL_STORE_CONNECTION_H +#include + +#include "rd_single_ver_natural_store.h" +#include "rd_single_ver_storage_executor.h" +#include "sync_able_kvdb_connection.h" +#include "sqlite_single_ver_natural_store_connection.h" +#include "db_types.h" +#include "runtime_context.h" + +namespace DistributedDB { +class SQLiteSingleVerNaturalStore; + +class RdSingleVerNaturalStoreConnection : public SyncAbleKvDBConnection { +public: + explicit RdSingleVerNaturalStoreConnection(RdSingleVerNaturalStore *kvDB); + virtual ~RdSingleVerNaturalStoreConnection() override; + + // Delete the copy and assign constructors + DISABLE_COPY_ASSIGN_MOVE(RdSingleVerNaturalStoreConnection); + + // Get the value from the database + int Get(const IOption &option, const Key &key, Value &value) const override + { + return -E_NOT_SUPPORT; + } + + // Put the value to the database + int Put(const IOption &option, const Key &key, const Value &value) override + { + std::vector entries; + Entry entry{key, value}; + entries.emplace_back(std::move(entry)); + + return PutBatch(option, entries); + } + + // Delete the value from the database + int Delete(const IOption &option, const Key &key) override + { + return -E_NOT_SUPPORT; + } + + // Clear all the data from the database + int Clear(const IOption &option) override + { + return -E_NOT_SUPPORT; + } + + // Get all the data from the database + int GetEntries(const IOption &option, const Key &keyPrefix, std::vector &entries) const override + { + return -E_NOT_SUPPORT; + } + + int GetEntries(const IOption &option, const Query &query, std::vector &entries) const override + { + return -E_NOT_SUPPORT; + } + + int GetCount(const IOption &option, const Query &query, int &count) const override + { + return -E_NOT_SUPPORT; + } + + // Put the batch values to the database. + int PutBatch(const IOption &option, const std::vector &entries) override + { + LOGD("[PutBatch] entries size is : %zu, dataType : %d", entries.size(), option.dataType); + if (option.dataType == IOption::SYNC_DATA) { + int errCode = CheckSyncEntriesValid(entries); + if (errCode != E_OK) { + return errCode; + } + return PutBatchInner(option, entries); + } + + return -E_NOT_SUPPORT; + } + + // Delete the batch values from the database. + int DeleteBatch(const IOption &option, const std::vector &keys) override + { + return -E_NOT_SUPPORT; + } + + // Get the snapshot + int GetSnapshot(IKvDBSnapshot *&snapshot) const override + { + return -E_NOT_SUPPORT; + } + + // Release the created snapshot + void ReleaseSnapshot(IKvDBSnapshot *&snapshot) override + { + return; + } + + // Start the transaction + int StartTransaction() override + { + return -E_NOT_SUPPORT; + } + + // Commit the transaction + int Commit() override + { + return -E_NOT_SUPPORT; + } + + // Roll back the transaction + int RollBack() override + { + return -E_NOT_SUPPORT; + } + + // Check if the transaction already started manually + bool IsTransactionStarted() const override + { + return -E_NOT_SUPPORT; + } + + // Pragma interface. + int Pragma(int cmd, void *parameter) override + { + return -E_NOT_SUPPORT; + } + + // Parse event types(from observer mode). + int TranslateObserverModeToEventTypes(unsigned mode, std::list &eventTypes) const override + { + return -E_NOT_SUPPORT; + } + + // Register a conflict notifier. + int SetConflictNotifier(int conflictType, const KvDBConflictAction &action) override + { + return -E_NOT_SUPPORT; + } + + int Rekey(const CipherPassword &passwd) override + { + return -E_NOT_SUPPORT; + } + + int Export(const std::string &filePath, const CipherPassword &passwd) override + { + return -E_NOT_SUPPORT; + } + + int Import(const std::string &filePath, const CipherPassword &passwd) override + { + return -E_NOT_SUPPORT; + } + + // Get the result set + int GetResultSet(const IOption &option, const Key &keyPrefix, IKvDBResultSet *&resultSet) const override + { + return -E_NOT_SUPPORT; + } + + int GetResultSet(const IOption &option, const Query &query, IKvDBResultSet *&resultSet) const override + { + return -E_NOT_SUPPORT; + } + + // Release the result set + void ReleaseResultSet(IKvDBResultSet *&resultSet) override + { + return; + } + + int RegisterLifeCycleCallback(const DatabaseLifeCycleNotifier ¬ifier) override + { + return -E_NOT_SUPPORT; + } + + // Called when Close and delete the connection. + int PreClose() override + { + return -E_NOT_SUPPORT; + } + + int CheckIntegrity() const override + { + return -E_NOT_SUPPORT; + } + + int GetKeys(const IOption &option, const Key &keyPrefix, std::vector &keys) const override + { + return -E_NOT_SUPPORT; + } + + int UpdateKey(const UpdateKeyCallback &callback) override + { + return -E_NOT_SUPPORT; + } + +private: + int CheckSyncEntriesValid(const std::vector &entries) const + { + if (entries.size() > DBConstant::MAX_BATCH_SIZE) { + return -E_INVALID_ARGS; + } + + RdSingleVerNaturalStore *naturalStore = GetDB(); + if (naturalStore == nullptr) { + return -E_INVALID_DB; + } + + // TODO: 确认是否需要 + if (!naturalStore->CheckWritePermission()) { + return -E_READ_ONLY; + } + + for (const auto &entry : entries) { + int errCode = naturalStore->CheckDataStatus(entry.key, entry.value, false); + if (errCode != E_OK) { + return errCode; + } + } + return E_OK; + } + + int PutBatchInner(const IOption &option, const std::vector &entries) + { + // std::lock_guard lock(transactionMutex_); TODO: 这个锁有必要加吗 + bool isAuto = false; + int errCode = E_OK; + if (writeHandle_ == nullptr) { + isAuto = true; + errCode = StartTransactionInner(TransactType::IMMEDIATE); + if (errCode != E_OK) { + return errCode; + } + } + + // TODO: OH5.0.才支持事务,不过这个限制先保留 + if ((transactionEntrySize_ + entries.size()) > DBConstant::MAX_TRANSACTION_ENTRY_SIZE) { + return -E_MAX_LIMITS; + } + + if (option.dataType == IOption::SYNC_DATA) { + errCode = SaveSyncEntries(entries); + } else { + return -E_NOT_SUPPORT; + } + if (errCode == E_OK) { + transactionEntrySize_ += entries.size(); + } + + if (isAuto) { + if (errCode == E_OK) { + errCode = CommitInner(); + } else { + int innerCode = RollbackInner(); + errCode = (innerCode != E_OK) ? innerCode : errCode; + } + } + return errCode; + } + + // NOTE: 这个函数和sqlite_conn的一样,公共方法 + int SaveSyncEntries(const std::vector &entries) + { + int errCode = E_OK; + for (const auto &entry : entries) { + errCode = SaveEntry(entry, false); + if (errCode != E_OK) { + break; + } + } + return errCode; + } + + // NOTE: 这个函数主要是校验数据,维护一个最大时间戳,判断是否是cache模式而选择调用不同的函数; 大部分可以共用。公共函数。 + // NOTE: 以下注释来自sqlite_xxx_conn + // This function currently only be called in local procedure to change sync_data table, do not use in sync procedure. + // It will check and amend value when need if it is a schema database. return error if some value disagree with the + // schema. But in sync procedure, we just neglect the value that disagree with schema. + int SaveEntry(const Entry &entry, bool isDelete, Timestamp timestamp = 0) + { + RdSingleVerNaturalStore *naturalStore = GetDB(); + if (naturalStore == nullptr) { + LOGE("[RdSingleVerNaturalStoreConnection][SaveEntry] the store is null"); + return -E_INVALID_DB; + } + + DataItem dataItem; + dataItem.key = entry.key; + dataItem.value = entry.value; + dataItem.flag = DataItem::LOCAL_FLAG; + if (isDelete) { + dataItem.flag |= DataItem::DELETE_FLAG; + } else { + // TODO: 在RD_XXX_CONN里,这个函数主要校验value有没有超过MAX_VALUE_SIZE + int errCode = CheckAmendValueContentForLocalProcedure(dataItem.value, dataItem.value); + if (errCode != E_OK) { + LOGE("[RdSinCon][SaveEntry] CheckAmendValue fail, errCode=%d.", errCode); + return errCode; + } + } + + dataItem.timestamp = naturalStore->GetCurrentTimestamp(); + if (currentMaxTimestamp_ > dataItem.timestamp) { + dataItem.timestamp = currentMaxTimestamp_; + } + + if (timestamp != 0) { + dataItem.writeTimestamp = timestamp; + } else { + dataItem.writeTimestamp = dataItem.timestamp; + } + + if (IsExtendedCacheDBMode()) { + return -E_NOT_SUPPORT; + } else { + return SaveEntryNormally(dataItem); + } + } + + int CheckAmendValueContentForLocalProcedure(const Value &oriValue, Value &amendValue) const + { + RdSingleVerNaturalStore *naturalStore = GetDB(); + if (naturalStore == nullptr) { // Not Likely + return -E_INVALID_DB; + } + bool useAmendValue = false; + return naturalStore->CheckValueAndAmendIfNeed(ValueSource::FROM_LOCAL, oriValue, amendValue, useAmendValue); + } + + int SaveEntryNormally(DataItem &dataItem) + { + Timestamp maxTimestamp = 0; + DeviceInfo deviceInfo = {true, ""}; + int errCode = writeHandle_->SaveSyncDataItem(dataItem, deviceInfo, maxTimestamp, committedData_); + if (errCode == E_OK) { + if (maxTimestamp > currentMaxTimestamp_) { + currentMaxTimestamp_ = maxTimestamp; + } + } else { + LOGE("Save entry failed, err:%d", errCode); + } + return errCode; + } + + RdSingleVerStorageExecutor *GetExecutor(bool isWrite, int &errCode) const + { + RdSingleVerNaturalStore *naturalStore = GetDB(); + if (naturalStore == nullptr) { + errCode = -E_NOT_INIT; + LOGE("[SingleVerConnection] the store is null"); + return nullptr; + } + errCode = naturalStore->TryHandle(); + if (errCode != E_OK) { + return nullptr; + } + return naturalStore->GetHandle(isWrite, errCode); + } + + void ReleaseExecutor(RdSingleVerStorageExecutor *&executor) const + { + kvDB_->ReEnableConnection(OperatePerm::NORMAL_WRITE); + RdSingleVerNaturalStore *naturalStore = GetDB(); + if (naturalStore != nullptr) { + naturalStore->ReleaseHandle(executor); + } + } + + // TODO: 目前内核缺少显示事务能力,计划OH5.0支持; 因此保留接口 + // 这个private方法同时负责创建Executor(为了尽量和原来的保持一致,这里保留这个方法) + int StartTransactionInner(TransactType transType = TransactType::DEFERRED) + { + if (IsExtendedCacheDBMode()) { + return -E_NOT_SUPPORT; + } else { + return StartTransactionNormally(transType); + } + } + + int StartTransactionNormally(TransactType transType = TransactType::DEFERRED) + { + int errCode = E_OK; + RdSingleVerStorageExecutor *handle = GetExecutor(true, errCode); + if (handle == nullptr) { + return errCode; + } + + errCode = kvDB_->TryToDisableConnection(OperatePerm::NORMAL_WRITE); + if (errCode != E_OK) { + ReleaseExecutor(handle); + LOGE("Start transaction failed, %d", errCode); + return errCode; + } + + // if (CheckLogOverLimit(handle)) { + // LOGW("Over the log limit"); + // ReleaseExecutor(handle); + // return -E_LOG_OVER_LIMITS; + // } + + // if (committedData_ == nullptr) { + // committedData_ = new (std::nothrow) SingleVerNaturalStoreCommitNotifyData; + // if (committedData_ == nullptr) { + // ReleaseExecutor(handle); + // return -E_OUT_OF_MEMORY; + // } + // InitConflictNotifiedFlag(); + // } + if (localCommittedData_ == nullptr) { + localCommittedData_ = new (std::nothrow) SingleVerNaturalStoreCommitNotifyData; + if (localCommittedData_ == nullptr) { + ReleaseExecutor(handle); + // ReleaseCommitData(committedData_); + return -E_OUT_OF_MEMORY; + } + } + errCode = handle->StartTransaction(transType); + if (errCode != E_OK) { + ReleaseExecutor(handle); + // ReleaseCommitData(committedData_); + // ReleaseCommitData(localCommittedData_); + return errCode; + } + + writeHandle_ = handle; + transactionEntrySize_ = 0; + return E_OK; + } + + int CommitInner() + { + return -E_NOT_SUPPORT; + } + + int RollbackInner() + { + return -E_NOT_SUPPORT; + } + + bool IsExtendedCacheDBMode() const + { + RdSingleVerNaturalStore *naturalStore = GetDB(); + if (naturalStore == nullptr) { + LOGE("[RdSingleVerNaturalStoreConnection][SaveEntry] the store is null"); + return false; + } + return naturalStore->IsExtendedCacheDBMode(); + } + + uint32_t transactionEntrySize_; // used for transaction + Timestamp currentMaxTimestamp_; // used for transaction + SingleVerNaturalStoreCommitNotifyData *committedData_; // used for transaction + SingleVerNaturalStoreCommitNotifyData *localCommittedData_; + + RdSingleVerStorageExecutor *writeHandle_; // only existed while in transaction. +}; +} + +#endif \ No newline at end of file diff --git a/frameworks/libs/distributeddb/storage/src/gaussdb_rd/rd_single_ver_storage_engine.cpp b/frameworks/libs/distributeddb/storage/src/gaussdb_rd/rd_single_ver_storage_engine.cpp new file mode 100644 index 0000000000000000000000000000000000000000..38952248f184b3b14313cfbebf4ed934ba55034b --- /dev/null +++ b/frameworks/libs/distributeddb/storage/src/gaussdb_rd/rd_single_ver_storage_engine.cpp @@ -0,0 +1,57 @@ +/* + * Copyright (c) 2023 Huawei Device Co., Ltd. + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#include "rd_single_ver_storage_engine.h" + +#include "grd_db_api.h" +#include "grd_error.h" +#include "grd_type_export.h" +#include "rd_single_ver_storage_executor.h" +#include "sqlite_single_ver_storage_executor_sql.h" + +namespace DistributedDB { + +RdSingleVerStorageEngine::RdSingleVerStorageEngine() +{ + LOGD("==============RdSingleVerStorageEngine Created=================="); +} + +RdSingleVerStorageEngine::~RdSingleVerStorageEngine() +{ +} + +int RdSingleVerStorageEngine::CreateNewExecutor(bool isWrite, StorageExecutor *&handle) +{ + GRD_DB *db = nullptr; + int ret = GRD_DBOpen("./testRdDB/testdb", "{}", GRD_DB_OPEN_CREATE, &db); + if (ret != GRD_OK) { + LOGE("============ GRD_DBOPEN FAILED================== %d", ret); + } + ret = GRD_CreateCollection(db, LOCAL_COLLECTION_NAME.c_str(), {}, 0); + if (ret != GRD_OK) { + LOGE("============ GRD_CreateCollection LOCAL_COLLECTION_NAME FAILED================== %d", ret); + } + ret = GRD_CreateCollection(db, META_COLLECTION_NAME.c_str(), {}, 0); + if (ret != GRD_OK) { + LOGE("============ GRD_CreateCollection META_COLLECTION_NAME FAILED================== %d", ret); + } + handle = new (std::nothrow) RdSingleVerStorageExecutor(db); + if (handle == nullptr) { + return -E_OUT_OF_MEMORY; + } + return E_OK; +} + +} // namespace DistributedDB diff --git a/frameworks/libs/distributeddb/storage/src/gaussdb_rd/rd_single_ver_storage_engine.h b/frameworks/libs/distributeddb/storage/src/gaussdb_rd/rd_single_ver_storage_engine.h new file mode 100644 index 0000000000000000000000000000000000000000..e56f435fd8892325f86d7ea4c669d93388c2c541 --- /dev/null +++ b/frameworks/libs/distributeddb/storage/src/gaussdb_rd/rd_single_ver_storage_engine.h @@ -0,0 +1,32 @@ +/* + * Copyright (c) 2023 Huawei Device Co., Ltd. + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#ifndef RD_SINGLE_VER_STORAGE_ENGINE_H +#define RD_SINGLE_VER_STORAGE_ENGINE_H + +#include "sqlite_single_ver_storage_engine.h" + +namespace DistributedDB { +class RdSingleVerStorageEngine : public StorageEngine { +public: + RdSingleVerStorageEngine(); + ~RdSingleVerStorageEngine() override; + +protected: + int CreateNewExecutor(bool isWrite, StorageExecutor *&handle); +}; +} // namespace DistributedDB + +#endif // RD_SINGLE_VER_STORAGE_ENGINE_H diff --git a/frameworks/libs/distributeddb/storage/src/gaussdb_rd/rd_single_ver_storage_executor.cpp b/frameworks/libs/distributeddb/storage/src/gaussdb_rd/rd_single_ver_storage_executor.cpp new file mode 100644 index 0000000000000000000000000000000000000000..c3373cbd14d7f9cebf467936e05bdd1eaa32ec08 --- /dev/null +++ b/frameworks/libs/distributeddb/storage/src/gaussdb_rd/rd_single_ver_storage_executor.cpp @@ -0,0 +1,210 @@ +/* + * Copyright (c) 2023 Huawei Device Co., Ltd. + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#include "rd_single_ver_storage_executor.h" + +#include + +#include "grd_db_api.h" +#include "grd_error.h" +#include "sqlite_single_ver_storage_executor_sql.h" + +namespace { + using namespace DistributedDB; + + GRD_KVItemT BlobToKvItem(const std::vector &blob) + { + return { .data = (void *)&blob[0], .dataLen = blob.size() }; + } + + std::vector KvItemToBlob(GRD_KVItemT &item) + { + return std::vector((uint8_t *)item.data, (uint8_t *)item.data + item.dataLen); + } + + int GetCollNameFromType(SingleVerDataType type, std::string &collName) + { + switch (type) { + case SingleVerDataType::LOCAL_TYPE: + collName = LOCAL_COLLECTION_NAME; + break; + case SingleVerDataType::META_TYPE: + collName = LOCAL_COLLECTION_NAME; + break; + default: + LOGE("data type not support"); + return -E_INVALID_ARGS; + } + return E_OK; + } + + struct GrdErrnoPair { + int32_t grdCode; + int kvDbCode; + }; + + const GrdErrnoPair GrdErrnoMap[] = { + { GRD_OK, E_OK }, + { GRD_INNER_ERR, -E_GAUSSDB_RD_ERROR }, + { GRD_OVER_LIMIT, -E_MAX_LIMITS }, + { GRD_INVALID_JSON_FORMAT, -E_INVALID_FORMAT }, + { GRD_INVALID_CONFIG_VALUE, -E_INVALID_FORMAT }, + { GRD_DATA_CONFLICT, -E_INVALID_DATA }, + { GRD_COLLECTION_CONFLICT, -E_INVALID_DATA }, + { GRD_NO_DATA, -E_NOT_FOUND }, + { GRD_INVALID_COLLECTION_NAME, -E_INVALID_DATA }, + { GRD_RESOURCE_BUSY, -E_BUSY }, + { GRD_INVALID_FILE_FORMAT, -E_INVALID_ARGS }, + }; + + int TransferGrdErrno(int err) + { + if (err > 0) { + return err; + } + for (const auto &item : GrdErrnoMap) { + if (item.grdCode == err) { + return item.kvDbCode; + } + } + return -E_GAUSSDB_RD_ERROR; + } + + int RdKvPut(GRD_DB *db, const char *collectionName, const GRD_KVItemT *key, const GRD_KVItemT *value) + { + return TransferGrdErrno(GRD_KVPut(db, collectionName, key, value)); + } + + int RdKvGet(GRD_DB *db, const char *collectionName, const GRD_KVItemT *key, GRD_KVItemT *value) + { + return TransferGrdErrno(GRD_KVGet(db, collectionName, key, value)); + } + + int RdKvDel(GRD_DB *db, const char *collectionName, const GRD_KVItemT *key) + { + return TransferGrdErrno(GRD_KVDel(db, collectionName, key)); + } + + int RdKVScan(GRD_DB *db, const char *collectionName, const GRD_KVItemT *key, KvScanModeE mode, + GRD_ResultSet **resultSet) + { + return TransferGrdErrno(GRD_KVScan(db, collectionName, key, resultSet)); + } +} + +namespace DistributedDB { + +RdSingleVerStorageExecutor::RdSingleVerStorageExecutor(GRD_DB *db) : RDStorageExecutor(db) +{ + LOGD("==============RdSingleVerStorageExecutor Created=================="); +} + +RdSingleVerStorageExecutor::~RdSingleVerStorageExecutor() +{ + int ret = GRD_OK; + if (db_ != nullptr) { + ret = GRD_DBClose(db_, 0); + LOGD("=====================rd has been closed==============================="); + } + if (ret != GRD_OK) { + LOGE("Can not close db %d", ret); + } + db_ = nullptr; + LOGD("=====================RdSingleVerStorageExecutor has been deconstructed==============================="); +} + +int RdSingleVerStorageExecutor::GetKvData(SingleVerDataType type, const Key &key, Value &value, + Timestamp ×tamp) const +{ + std::string collectionName; + int ret = GetCollNameFromType(type, collectionName); + if (ret != E_OK) { + LOGE("Can not GetCollNameFromType"); + return ret; + } + GRD_ResultSet *resultSet = nullptr; + GRD_KVItemT innerKey = BlobToKvItem(key); + GRD_KVItemT innerVal; + ret = RdKvGet(db_, LOCAL_COLLECTION_NAME.c_str(), &innerKey, &innerVal); + if (ret != E_OK) { + LOGE("================[RdSingleVerStorageExecutor][GetKvData]ERROR=========== %d", ret); + return ret; + } + value = KvItemToBlob(innerVal); + return ret; +} + +int RdSingleVerStorageExecutor::Reset() +{ + LOGW("=================Reset rd single ver storage executor================="); + return -E_NOT_SUPPORT; +} + +int RdSingleVerStorageExecutor::GetEntries(bool isGetValue, SingleVerDataType type, const Key &keyPrefix, + std::vector &entries) const +{ + std::string collectionName; + int ret = GetCollNameFromType(type, collectionName); + if (ret != E_OK) { + LOGE("Can not GetCollNameFromType"); + return ret; + } + GRD_KVItemT innerKey = BlobToKvItem(keyPrefix); + GRD_ResultSet *resultSet = nullptr; + ret = RdKVScan(db_, collectionName.c_str(), &innerKey, KV_SCAN_PREFIX, &resultSet); + if (ret != E_OK) { + LOGE("================[RdSingleVerStorageExecutor][GetEntries]ERROR=========== %d", ret); + return ret; + } + return ret; +} + +int RdSingleVerStorageExecutor::SaveKvData(SingleVerDataType type, const Key &key, const Value &value, + Timestamp timestamp) +{ + std::string collectionName; + int ret = GetCollNameFromType(type, collectionName); + if (ret != E_OK) { + LOGE("Can not GetCollNameFromType"); + return ret; + } + GRD_KVItemT innerKey = BlobToKvItem(key); + GRD_KVItemT innerVal = BlobToKvItem(value); + ret = RdKvPut(db_, collectionName.c_str(), &innerKey, &innerVal); + if (ret < 0) { + LOGE("================[RdSingleVerStorageExecutor][SaveKvData]ERROR=========== %d", ret); + } + return E_OK; +} + +int RdSingleVerStorageExecutor::DeleteLocalDataInner(SingleVerNaturalStoreCommitNotifyData *committedData, + const Key &key, const Value &value) +{ + GRD_KVItemT innerKey = BlobToKvItem(key); + int ret = RdKvDel(db_, LOCAL_COLLECTION_NAME.c_str(), &innerKey); + if (ret < 0) { + LOGE("================[RdSingleVerStorageExecutor][DeleteLocalDataInner]ERROR=========== %d", ret); + } + LOGW("Delete %d document", ret); + return ret; +} + +int RdSingleVerStorageExecutor::DeleteLocalKvData(const Key &key, SingleVerNaturalStoreCommitNotifyData *committedData, + Value &value, Timestamp ×tamp) +{ + return -E_NOT_SUPPORT; +} + +} // namespace DistributedDB diff --git a/frameworks/libs/distributeddb/storage/src/gaussdb_rd/rd_single_ver_storage_executor.h b/frameworks/libs/distributeddb/storage/src/gaussdb_rd/rd_single_ver_storage_executor.h new file mode 100644 index 0000000000000000000000000000000000000000..75bdcb0cec7686f287fff91fc56dc1b0708107ba --- /dev/null +++ b/frameworks/libs/distributeddb/storage/src/gaussdb_rd/rd_single_ver_storage_executor.h @@ -0,0 +1,484 @@ +/* + * Copyright (c) 2021 Huawei Device Co., Ltd. + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the spRdSingleVerStorageExecutorecific language governing permissions and + * limitations under the License. + */ + +#ifndef RD_SINGLE_VER_STORAGE_EXECUTOR_H +#define RD_SINGLE_VER_STORAGE_EXECUTOR_H + +#include "macro_utils.h" +#include "db_types.h" +#include "query_object.h" +#include "sqlite_utils.h" +#include "sqlite_single_ver_storage_executor.h" +#include "single_ver_natural_store_commit_notify_data.h" + +#include "grd_document_api.h" + +namespace DistributedDB { + +class RDStorageExecutor : public StorageExecutor { +public: + RDStorageExecutor(GRD_DB *db) : StorageExecutor(true), + db_(db) + { + } + + ~RDStorageExecutor() override + { + } + + // Delete the copy and assign constructors + DISABLE_COPY_ASSIGN_MOVE(RDStorageExecutor); + virtual int Reset() override + { + return 0; + } + + int GetDbHandle(GRD_DB *&dbHandle) const + { + return 0; + } + +protected: + GRD_DB *db_; +}; + +class RdSingleVerStorageExecutor : public RDStorageExecutor { +public: + RdSingleVerStorageExecutor(GRD_DB *db); + ~RdSingleVerStorageExecutor() override; + + // Delete the copy and assign constructors + DISABLE_COPY_ASSIGN_MOVE(RdSingleVerStorageExecutor); + + // Get the Kv data according the type(sync, meta, local data). + int GetKvData(SingleVerDataType type, const Key &key, Value &value, Timestamp ×tamp) const; + + // Get the sync data record by hash key. + int GetKvDataByHashKey(const Key &hashKey, SingleVerRecord &result) const + { + return -E_NOT_SUPPORT; + } + + // Put the Kv data according the type(meta and the local data). + virtual int PutKvData(SingleVerDataType type, const Key &key, const Value &value, + Timestamp timestamp, SingleVerNaturalStoreCommitNotifyData *committedData) + { + return -E_NOT_SUPPORT; + } + + virtual int GetEntries(bool isGetValue, SingleVerDataType type, const Key &keyPrefix, + std::vector &entries) const; + + int GetEntries(QueryObject &queryObj, std::vector &entries) const + { + return -E_NOT_SUPPORT; + } + + int GetCount(QueryObject &queryObj, int &count) const + { + return -E_NOT_SUPPORT; + } + + // Get all the meta keys. + int GetAllMetaKeys(std::vector &keys) const + { + return -E_NOT_SUPPORT; + } + + int GetAllSyncedEntries(const std::string &hashDev, std::vector &entries) const + { + return -E_NOT_SUPPORT; + } + + int SaveSyncDataItem(DataItem &dataItem, const DeviceInfo &deviceInfo, + Timestamp &maxStamp, SingleVerNaturalStoreCommitNotifyData *committedData, bool isPermitForceWrite = true) + { + NotifyConflictAndObserverData notify = { + .committedData = committedData + }; + + int errCode = PrepareForNotifyConflictAndObserver(dataItem, deviceInfo, notify, isPermitForceWrite); + if (errCode != E_OK) { + if (errCode == -E_IGNORE_DATA) { + errCode = E_OK; + } + return errCode; + } + + // TODO: 把冲突的数据放到数据通告的结构体里, 这次不需要冲突策略,因此先注释掉 + // PutConflictData(dataItem, notify.getData, deviceInfo, notify.dataStatus, committedData); + // if (notify.dataStatus.isDefeated) { + // LOGD("Data status is defeated:%d", errCode); + // return ResetSaveSyncStatements(errCode); + // } + + bool isUpdate = (notify.dataStatus.preStatus != DataStatus::NOEXISTED); + std::string origDev = GetOriginDevName(dataItem, notify.getData.origDev); + errCode = SaveSyncDataToDatabase(dataItem, notify.hashKey, origDev, deviceInfo.deviceName, isUpdate); + if (errCode == E_OK) { + PutIntoCommittedData(dataItem, notify.getData, notify.dataStatus, committedData); + maxStamp = std::max(dataItem.timestamp, maxStamp); + } else { + LOGE("Save sync data to db failed:%d", errCode); + } + return errCode; + } + + int DeleteLocalKvData(const Key &key, SingleVerNaturalStoreCommitNotifyData *committedData, Value &value, + Timestamp ×tamp); + + // delete a row data by hashKey, with no tombstone left. + int EraseSyncData(const Key &hashKey) + { + return -E_NOT_SUPPORT; + } + + int RemoveDeviceData(const std::string &deviceName) + { + return -E_NOT_SUPPORT; + } + + int RemoveDeviceDataInCacheMode(const std::string &hashDev, bool isNeedNotify, uint64_t recordVersion) const + { + return -E_NOT_SUPPORT; + } + + void InitCurrentMaxStamp(Timestamp &maxStamp) + { + return; + } + + void ReleaseContinueStatement() + { + return; + } + + int GetSyncDataByTimestamp(std::vector &dataItems, size_t appendLength, Timestamp begin, + Timestamp end, const DataSizeSpecInfo &dataSizeInfo) const + { + return -E_NOT_SUPPORT; + } + + int GetDeletedSyncDataByTimestamp(std::vector &dataItems, size_t appendLength, Timestamp begin, + Timestamp end, const DataSizeSpecInfo &dataSizeInfo) const + { + return -E_NOT_SUPPORT; + } + + int GetDeviceIdentifier(PragmaEntryDeviceIdentifier *identifier) + { + return -E_NOT_SUPPORT; + } + + int OpenResultSet(const Key &keyPrefix, int &count) + { + return -E_NOT_SUPPORT; + } + + int OpenResultSet(QueryObject &queryObj, int &count) + { + return -E_NOT_SUPPORT; + } + + int OpenResultSetForCacheRowIdMode(const Key &keyPrefix, std::vector &rowIdCache, + uint32_t cacheLimit, int &count) + { + return -E_NOT_SUPPORT; + } + + int OpenResultSetForCacheRowIdMode(QueryObject &queryObj, std::vector &rowIdCache, + uint32_t cacheLimit, int &count) + { + return -E_NOT_SUPPORT; + } + + int ReloadResultSet(const Key &keyPrefix) + { + return -E_NOT_SUPPORT; + } + + int ReloadResultSet(QueryObject &queryObj) + { + return -E_NOT_SUPPORT; + } + + int ReloadResultSetForCacheRowIdMode(const Key &keyPrefix, std::vector &rowIdCache, + uint32_t cacheLimit, uint32_t cacheStartPos) + { + return -E_NOT_SUPPORT; + } + + int ReloadResultSetForCacheRowIdMode(QueryObject &queryObj, std::vector &rowIdCache, + uint32_t cacheLimit, uint32_t cacheStartPos) + { + return -E_NOT_SUPPORT; + } + + int GetNextEntryFromResultSet(Key &key, Value &value, bool isCopy) + { + return -E_NOT_SUPPORT; + } + + int GetEntryByRowId(int64_t rowId, Entry &entry) + { + return -E_NOT_SUPPORT; + } + + void CloseResultSet() + { + return; + } + + int StartTransaction(TransactType type) + { + return -E_NOT_SUPPORT; + } + + int Commit() + { + return -E_NOT_SUPPORT; + } + + int Rollback() + { + return -E_NOT_SUPPORT; + } + + bool CheckIfKeyExisted(const Key &key, bool isLocal, Value &value, Timestamp ×tamp) const + { + return -E_NOT_SUPPORT; + } + + // TODO: 这个函数是用来拼装SQL的, rd不需要。 可删除。 + int PrepareForSavingData(SingleVerDataType type) + { + return -E_NOT_SUPPORT; + } + + int ResetForSavingData(SingleVerDataType type) + { + return -E_NOT_SUPPORT; + } + + int Reset() override; + + int UpdateLocalDataTimestamp(Timestamp timestamp) + { + return -E_NOT_SUPPORT; + } + + void SetAttachMetaMode(bool attachMetaMode) + { + return; + } + + int PutLocalDataToCacheDB(const LocalDataItem &dataItem) const + { + return -E_NOT_SUPPORT; + } + + int SaveSyncDataItemInCacheMode(DataItem &dataItem, const DeviceInfo &deviceInfo, Timestamp &maxStamp, + uint64_t recordVersion, const QueryObject &query) + { + return -E_NOT_SUPPORT; + } + + int PrepareForSavingCacheData(SingleVerDataType type) + { + return -E_NOT_SUPPORT; + } + + int ResetForSavingCacheData(SingleVerDataType type) + { + return -E_NOT_SUPPORT; + } + + int MigrateLocalData() + { + return -E_NOT_SUPPORT; + } + + int MigrateSyncDataByVersion(uint64_t recordVer, NotifyMigrateSyncData &syncData, + std::vector &dataItems) + { + return -E_NOT_SUPPORT; + } + + int GetMinVersionCacheData(std::vector &dataItems, uint64_t &minVerIncurCacheDb) const + { + return -E_NOT_SUPPORT; + } + + int GetMaxVersionInCacheDb(uint64_t &maxVersion) const + { + return -E_NOT_SUPPORT; + } + + int AttachMainDbAndCacheDb(CipherType type, const CipherPassword &passwd, + const std::string &attachDbAbsPath, EngineState engineState) + { + return -E_NOT_SUPPORT; + } + + // Clear migrating data. + void ClearMigrateData() + { + return; + } + + // Get current max timestamp. + int GetMaxTimestampDuringMigrating(Timestamp &maxTimestamp) const + { + return -E_NOT_SUPPORT; + } + + void SetConflictResolvePolicy(int policy) + { + return; + } + + // Delete multiple meta data records in a transaction. + int DeleteMetaData(const std::vector &keys) + { + return -E_NOT_SUPPORT; + } + + // Delete multiple meta data records with key prefix in a transaction. + int DeleteMetaDataByPrefixKey(const Key &keyPrefix) + { + return -E_NOT_SUPPORT; + } + + int CheckIntegrity() const + { + return -E_NOT_SUPPORT; + } + + int CheckQueryObjectLegal(QueryObject &queryObj) const + { + return -E_NOT_SUPPORT; + } + + int CheckDataWithQuery(QueryObject query, std::vector &dataItems, const DeviceInfo &deviceInfo) + { + return -E_NOT_SUPPORT; + } + + static size_t GetDataItemSerialSize(const DataItem &item, size_t appendLen) + { + return -E_NOT_SUPPORT; + } + + int AddSubscribeTrigger(QueryObject &query, const std::string &subscribeId) + { + return -E_NOT_SUPPORT; + } + + int RemoveSubscribeTrigger(const std::vector &subscribeIds) + { + return -E_NOT_SUPPORT; + } + + int RemoveSubscribeTriggerWaterMark(const std::vector &subscribeIds) + { + return -E_NOT_SUPPORT; + } + + int GetTriggers(const std::string &namePreFix, std::vector &triggerNames) + { + return -E_NOT_SUPPORT; + } + + int RemoveTrigger(const std::vector &triggers) + { + return -E_NOT_SUPPORT; + } + + int GetSyncDataWithQuery(const QueryObject &query, size_t appendLength, const DataSizeSpecInfo &dataSizeInfo, + const std::pair &timeRange, std::vector &dataItems) const + { + return -E_NOT_SUPPORT; + } + + int ForceCheckPoint() const + { + return -E_NOT_SUPPORT; + } + + uint64_t GetLogFileSize() const + { + return -E_NOT_SUPPORT; + } + + int GetExistsDevicesFromMeta(std::set &devices) + { + return -E_NOT_SUPPORT; + } + + int UpdateKey(const UpdateKeyCallback &callback) + { + return -E_NOT_SUPPORT; + } + +protected: + int SaveKvData(SingleVerDataType type, const Key &key, const Value &value, Timestamp timestamp); + + int DeleteLocalDataInner(SingleVerNaturalStoreCommitNotifyData *committedData, const Key &key, const Value &value); + +private: + void PutIntoCommittedData(const DataItem &itemPut, const DataItem &itemGet, const DataOperStatus &status, + SingleVerNaturalStoreCommitNotifyData *committedData) + { + return; + } + + // NOTE: 公共函数 + static std::string GetOriginDevName(const DataItem &dataItem, const std::string &origDevGet) + { + (void)dataItem; + (void)origDevGet; + return ""; + } + + // NOTE: 这个函数获得dataItem的hash,然后在数据库里找这条数据。 + // 然后把要插入的这条数据,和本地数据库中已经存在的数据进行比对,判断是否要忽略这条数据 + // 若不需要忽略这条数据,判断DataOperStatus, 类似于端云协同里的strategy. + // 最后从数据库里读出这条数据的kv值,送到notify里。 + // TODO: 这个函数是在准备一些数据通告相关的东西。 + int PrepareForNotifyConflictAndObserver(DataItem &dataItem, const DeviceInfo &deviceInfo, + NotifyConflictAndObserverData ¬ify, bool isPermitForceWrite = true) + { + (void)dataItem; + (void)deviceInfo; + (void)notify; + (void)isPermitForceWrite; + return E_OK; + } + + int SaveSyncDataToDatabase(const DataItem &dataItem, const Key &hashKey, const std::string &origDev, + const std::string &deviceName, bool isUpdate) + { + if ((dataItem.flag & DataItem::REMOTE_DEVICE_DATA_MISS_QUERY) == DataItem::REMOTE_DEVICE_DATA_MISS_QUERY) { + LOGD("Find query data missing, erase local data."); + // return EraseSyncData(hashKey); + return -E_NOT_SUPPORT; + } + // TODO: timeStamp or wTimestamp? 另外,我们这次不支持时间戳。 + return SaveKvData(SingleVerDataType::SYNC_TYPE, dataItem.key, dataItem.value, dataItem.timestamp); + } +}; +} // namespace DistributedDB + +#endif // RD_SINGLE_VER_STORAGE_EXECUTOR_H diff --git a/frameworks/libs/distributeddb/storage/src/kvdb_manager.cpp b/frameworks/libs/distributeddb/storage/src/kvdb_manager.cpp index 95bbc0d2674b0bb18742931a74dbf74fabc284fe..8b9bb068767e7e78831b6b17f54e58cc289c6552 100644 --- a/frameworks/libs/distributeddb/storage/src/kvdb_manager.cpp +++ b/frameworks/libs/distributeddb/storage/src/kvdb_manager.cpp @@ -63,6 +63,8 @@ namespace { #endif // OMIT_MULTI_VER } else if (databaseType == KvDBProperties::SINGLE_VER_TYPE) { kvDB = factory->CreateKvDb(SINGER_VER_KVDB, errCode); + } else if (databaseType == KvDBProperties::SINGLE_VER_TYPE_RD_KERNAL) { + kvDB = factory->CreateKvDb(SINGLE_VER_KVDB_RD_KERNAL, errCode); } else { #ifndef OMIT_MULTI_VER kvDB = factory->CreateKvDb(MULTI_VER_KVDB, errCode); diff --git a/frameworks/libs/distributeddb/storage/src/sqlite/sqlite_single_ver_natural_store.h b/frameworks/libs/distributeddb/storage/src/sqlite/sqlite_single_ver_natural_store.h index 5b4223f45b50242b2bda4aa70974a91b7cc1f160..5f5ac1020b811f80915b947776bbbcaecee5c575 100644 --- a/frameworks/libs/distributeddb/storage/src/sqlite/sqlite_single_ver_natural_store.h +++ b/frameworks/libs/distributeddb/storage/src/sqlite/sqlite_single_ver_natural_store.h @@ -31,7 +31,7 @@ namespace DistributedDB { class SQLiteSingleVerNaturalStore : public SyncAbleKvDB, public SingleVerKvDBSyncInterface { public: SQLiteSingleVerNaturalStore(); - ~SQLiteSingleVerNaturalStore() override; + virtual ~SQLiteSingleVerNaturalStore() override; // Delete the copy and assign constructors DISABLE_COPY_ASSIGN_MOVE(SQLiteSingleVerNaturalStore); @@ -278,7 +278,7 @@ private: int SaveCreateDBTime(); int SaveCreateDBTimeIfNotExisted(); - int GetAndInitStorageEngine(const KvDBProperties &kvDBProp); + virtual int GetAndInitStorageEngine(const KvDBProperties &kvDBProp); int RemoveAllSubscribe(); diff --git a/frameworks/libs/distributeddb/storage/src/sqlite/sqlite_single_ver_natural_store_connection.h b/frameworks/libs/distributeddb/storage/src/sqlite/sqlite_single_ver_natural_store_connection.h index 330876c6a9d706a6e678a516b0858c31da9a7a85..ddd08b2e5a01cdcf2da3cf8624da469d6d4380bf 100644 --- a/frameworks/libs/distributeddb/storage/src/sqlite/sqlite_single_ver_natural_store_connection.h +++ b/frameworks/libs/distributeddb/storage/src/sqlite/sqlite_single_ver_natural_store_connection.h @@ -27,7 +27,7 @@ class SQLiteSingleVerNaturalStore; class SQLiteSingleVerNaturalStoreConnection : public SyncAbleKvDBConnection { public: explicit SQLiteSingleVerNaturalStoreConnection(SQLiteSingleVerNaturalStore *kvDB); - ~SQLiteSingleVerNaturalStoreConnection() override; + virtual ~SQLiteSingleVerNaturalStoreConnection() override; // Delete the copy and assign constructors DISABLE_COPY_ASSIGN_MOVE(SQLiteSingleVerNaturalStoreConnection); diff --git a/frameworks/libs/distributeddb/storage/src/sqlite/sqlite_single_ver_storage_engine.cpp b/frameworks/libs/distributeddb/storage/src/sqlite/sqlite_single_ver_storage_engine.cpp index 5a2227d65e8a4d97e155ec08906c654f56414ed0..65c6d2eb04fd688d6e3168daabb2391aa53065ac 100644 --- a/frameworks/libs/distributeddb/storage/src/sqlite/sqlite_single_ver_storage_engine.cpp +++ b/frameworks/libs/distributeddb/storage/src/sqlite/sqlite_single_ver_storage_engine.cpp @@ -244,7 +244,7 @@ int SQLiteSingleVerStorageEngine::ReleaseHandleTransiently(SQLiteSingleVerStorag int SQLiteSingleVerStorageEngine::AddSubscribeToMainDBInMigrate() { - LOGD("Add subscribe to mainDB from cache. %d", engineState_); + LOGD("Add subscribe to mainDB from cache. %d", GetEngineState()); std::lock_guard lock(subscribeMutex_); if (subscribeQuery_.empty()) { return E_OK; diff --git a/frameworks/libs/distributeddb/storage/src/sqlite/sqlite_single_ver_storage_engine.h b/frameworks/libs/distributeddb/storage/src/sqlite/sqlite_single_ver_storage_engine.h index 89529138378406f5251c41a1ced7901e7f91048d..860d0a34090ab1d902607f05f67e2bc007aaf560 100644 --- a/frameworks/libs/distributeddb/storage/src/sqlite/sqlite_single_ver_storage_engine.h +++ b/frameworks/libs/distributeddb/storage/src/sqlite/sqlite_single_ver_storage_engine.h @@ -61,12 +61,14 @@ public: void CacheSubscribe(const std::string &subscribeId, const QueryObject &query); protected: - StorageExecutor *NewSQLiteStorageExecutor(sqlite3 *dbHandle, bool isWrite, bool isMemDb) override; + virtual StorageExecutor *NewSQLiteStorageExecutor(sqlite3 *dbHandle, bool isWrite, bool isMemDb) override; int Upgrade(sqlite3 *db) override; int CreateNewExecutor(bool isWrite, StorageExecutor *&handle) override; + ExecutorState executorState_; + private: // For executor. int PreCreateExecutor(bool isWrite); @@ -119,7 +121,6 @@ private: mutable std::mutex migrateLock_; std::atomic cacheRecordVersion_; - ExecutorState executorState_; bool isCorrupted_; bool isNeedUpdateSecOpt_; // update the option_ diff --git a/frameworks/libs/distributeddb/storage/src/sqlite/sqlite_single_ver_storage_executor.h b/frameworks/libs/distributeddb/storage/src/sqlite/sqlite_single_ver_storage_executor.h index 39139441d20fbe0e1560a814b4b6cc6410a768b5..dec04c1c9c1496b2a23d488b81f88b133cb1499f 100644 --- a/frameworks/libs/distributeddb/storage/src/sqlite/sqlite_single_ver_storage_executor.h +++ b/frameworks/libs/distributeddb/storage/src/sqlite/sqlite_single_ver_storage_executor.h @@ -104,16 +104,17 @@ public: DISABLE_COPY_ASSIGN_MOVE(SQLiteSingleVerStorageExecutor); // Get the Kv data according the type(sync, meta, local data). - int GetKvData(SingleVerDataType type, const Key &key, Value &value, Timestamp ×tamp) const; + virtual int GetKvData(SingleVerDataType type, const Key &key, Value &value, Timestamp ×tamp) const; // Get the sync data record by hash key. int GetKvDataByHashKey(const Key &hashKey, SingleVerRecord &result) const; // Put the Kv data according the type(meta and the local data). - int PutKvData(SingleVerDataType type, const Key &key, const Value &value, + virtual int PutKvData(SingleVerDataType type, const Key &key, const Value &value, Timestamp timestamp, SingleVerNaturalStoreCommitNotifyData *committedData); - int GetEntries(bool isGetValue, SingleVerDataType type, const Key &keyPrefix, std::vector &entries) const; + virtual int GetEntries(bool isGetValue, SingleVerDataType type, const Key &keyPrefix, + std::vector &entries) const; int GetEntries(QueryObject &queryObj, std::vector &entries) const; @@ -127,7 +128,7 @@ public: int SaveSyncDataItem(DataItem &dataItem, const DeviceInfo &deviceInfo, Timestamp &maxStamp, SingleVerNaturalStoreCommitNotifyData *committedData, bool isPermitForceWrite = true); - int DeleteLocalKvData(const Key &key, SingleVerNaturalStoreCommitNotifyData *committedData, Value &value, + virtual int DeleteLocalKvData(const Key &key, SingleVerNaturalStoreCommitNotifyData *committedData, Value &value, Timestamp ×tamp); // delete a row data by hashKey, with no tombstone left. @@ -252,6 +253,12 @@ public: int UpdateKey(const UpdateKeyCallback &callback); +protected: + virtual int SaveKvData(SingleVerDataType type, const Key &key, const Value &value, Timestamp timestamp); + + virtual int DeleteLocalDataInner(SingleVerNaturalStoreCommitNotifyData *committedData, + const Key &key, const Value &value); + private: struct SaveRecordStatements { sqlite3_stmt *queryStatement = nullptr; @@ -316,11 +323,6 @@ private: int SaveSyncDataToDatabase(const DataItem &dataItem, const Key &hashKey, const std::string &origDev, const std::string &deviceName, bool isUpdate); - int SaveKvData(SingleVerDataType type, const Key &key, const Value &value, Timestamp timestamp); - - int DeleteLocalDataInner(SingleVerNaturalStoreCommitNotifyData *committedData, - const Key &key, const Value &value); - int PrepareForSavingData(const std::string &readSql, const std::string &insertSql, const std::string &updateSql, SaveRecordStatements &statements) const; diff --git a/frameworks/libs/distributeddb/storage/src/sqlite/sqlite_single_ver_storage_executor_sql.h b/frameworks/libs/distributeddb/storage/src/sqlite/sqlite_single_ver_storage_executor_sql.h index 17ad51839d86f031a4685599c0d77de19e4a5289..9518e883f923b8e76ca9d6141760e2789e72d147 100644 --- a/frameworks/libs/distributeddb/storage/src/sqlite/sqlite_single_ver_storage_executor_sql.h +++ b/frameworks/libs/distributeddb/storage/src/sqlite/sqlite_single_ver_storage_executor_sql.h @@ -22,6 +22,10 @@ namespace DistributedDB { // cache.sync_data is design for migrating action after process restart + const std::string LOCAL_COLLECTION_NAME = + "LOCAL"; + const std::string META_COLLECTION_NAME = + "META"; const std::string INSERT_LOCAL_SQL = "INSERT OR REPLACE INTO local_data VALUES(?,?,?,?);"; const std::string INSERT_LOCAL_SQL_FROM_CACHEHANDLE = diff --git a/frameworks/libs/distributeddb/storage/src/sqlite/sqlite_storage_engine.cpp b/frameworks/libs/distributeddb/storage/src/sqlite/sqlite_storage_engine.cpp index f82b68009486a494afb1324dcd539153814ece14..c86701a020cbd6c4e45d39a8ebc4ab09030a26cd 100644 --- a/frameworks/libs/distributeddb/storage/src/sqlite/sqlite_storage_engine.cpp +++ b/frameworks/libs/distributeddb/storage/src/sqlite/sqlite_storage_engine.cpp @@ -96,53 +96,6 @@ int SQLiteStorageEngine::CreateNewExecutor(bool isWrite, StorageExecutor *&handl return E_OK; } -int SQLiteStorageEngine::ReInit() -{ - return E_OK; -} - -bool SQLiteStorageEngine::IsNeedTobeReleased() const -{ - EngineState engineState = GetEngineState(); - return ((engineState == EngineState::MAINDB) || (engineState == EngineState::INVALID)); -} - -const std::string &SQLiteStorageEngine::GetIdentifier() const -{ - return identifier_; -} - -EngineState SQLiteStorageEngine::GetEngineState() const -{ - return engineState_; -} - -void SQLiteStorageEngine::SetEngineState(EngineState state) -{ - LOGD("[SQLiteStorageEngine::SetEngineState] Engine State : [%d]", state); - engineState_ = state; // Current usage logically can guarantee no concurrency -} - -int SQLiteStorageEngine::ExecuteMigrate() -{ - return -E_NOT_SUPPORT; -} - -void SQLiteStorageEngine::IncreaseCacheRecordVersion() -{ - return; -} - -uint64_t SQLiteStorageEngine::GetCacheRecordVersion() const -{ - return 0; -} - -uint64_t SQLiteStorageEngine::GetAndIncreaseCacheRecordVersion() -{ - return 0; -} - bool SQLiteStorageEngine::IsEngineCorrupted() const { return false; diff --git a/frameworks/libs/distributeddb/storage/src/sqlite/sqlite_storage_engine.h b/frameworks/libs/distributeddb/storage/src/sqlite/sqlite_storage_engine.h index 3468cb4fa442f081057b632cd51252bfbc3afefd..2904a001ecbf0ea79118e287fa20fcc4815e7829 100644 --- a/frameworks/libs/distributeddb/storage/src/sqlite/sqlite_storage_engine.h +++ b/frameworks/libs/distributeddb/storage/src/sqlite/sqlite_storage_engine.h @@ -34,25 +34,11 @@ public: int InitSQLiteStorageEngine(const StorageEngineAttr &poolSize, const OpenDbProperties &option, const std::string &identifier = std::string()); - bool IsNeedTobeReleased() const override; - - const std::string &GetIdentifier() const override; - - EngineState GetEngineState() const override; - - int ExecuteMigrate() override; - - void SetEngineState(EngineState state) override; - - virtual void IncreaseCacheRecordVersion(); - virtual uint64_t GetCacheRecordVersion() const; - virtual uint64_t GetAndIncreaseCacheRecordVersion(); - virtual bool IsEngineCorrupted() const; - void ClearEnginePasswd() override; + void ClearEnginePasswd(); - int CheckEngineOption(const KvDBProperties &kvDBProp) const override; + int CheckEngineOption(const KvDBProperties &kvDBProp) const; protected: @@ -60,9 +46,7 @@ protected: virtual StorageExecutor *NewSQLiteStorageExecutor(sqlite3 *dbHandle, bool isWrite, bool isMemDb) = 0; - int CreateNewExecutor(bool isWrite, StorageExecutor *&handle) override; - - virtual int ReInit(); + int CreateNewExecutor(bool isWrite, StorageExecutor *&handle); OpenDbProperties option_; }; diff --git a/frameworks/libs/distributeddb/storage/src/sqlite/sqlite_storage_executor.h b/frameworks/libs/distributeddb/storage/src/sqlite/sqlite_storage_executor.h index 1730cfe86e48ebfa2aebdc2d954aedcf2881c256..729a6c9bb921fc66d14fa00a8d66362d6a02f2ef 100644 --- a/frameworks/libs/distributeddb/storage/src/sqlite/sqlite_storage_executor.h +++ b/frameworks/libs/distributeddb/storage/src/sqlite/sqlite_storage_executor.h @@ -29,7 +29,7 @@ public: // Delete the copy and assign constructors DISABLE_COPY_ASSIGN_MOVE(SQLiteStorageExecutor); - int Reset() override; + virtual int Reset() override; int GetDbHandle(sqlite3 *&dbHandle) const; protected: diff --git a/frameworks/libs/distributeddb/storage/src/storage_engine.cpp b/frameworks/libs/distributeddb/storage/src/storage_engine.cpp index 98f3a79d335e0a0f5670cea7add1d586d6c62247..d6e71c2b0fd50ebb84c0b3901414c1a2fb475c04 100644 --- a/frameworks/libs/distributeddb/storage/src/storage_engine.cpp +++ b/frameworks/libs/distributeddb/storage/src/storage_engine.cpp @@ -107,6 +107,11 @@ int StorageEngine::Init() return errCode; } +int StorageEngine::ReInit() +{ + return E_OK; +} + StorageExecutor *StorageEngine::FindExecutor(bool writable, OperatePerm perm, int &errCode, int waitTime) { if (GetEngineState() == EngineState::ENGINE_BUSY) { @@ -320,7 +325,8 @@ void StorageEngine::Abort(OperatePerm enableType) bool StorageEngine::IsNeedTobeReleased() const { - return true; + EngineState engineState = GetEngineState(); + return ((engineState == EngineState::MAINDB) || (engineState == EngineState::INVALID)); } const std::string &StorageEngine::GetIdentifier() const @@ -361,11 +367,6 @@ bool StorageEngine::IsExistConnection() const return isExistConnection_.load(); } -void StorageEngine::ClearEnginePasswd() -{ - return; -} - int StorageEngine::CheckEngineOption(const KvDBProperties &kvdbOption) const { return E_OK; @@ -463,4 +464,19 @@ void StorageEngine::WaitWriteHandleIdle() DBCommon::TransferStringToHex(identifier_).c_str(), writeIdleList_.size(), writeUsingList_.size(), engineAttr_.maxWriteNum); } + +void StorageEngine::IncreaseCacheRecordVersion() +{ + return; +} + +uint64_t StorageEngine::GetCacheRecordVersion() const +{ + return 0; +} + +uint64_t StorageEngine::GetAndIncreaseCacheRecordVersion() +{ + return 0; +} } diff --git a/frameworks/libs/distributeddb/storage/src/storage_engine.h b/frameworks/libs/distributeddb/storage/src/storage_engine.h index 36953171333a0bf549bcfb8f00e5b73b864b5161..ade48adbc4de3f3aefcfea3724b759ec140be863 100644 --- a/frameworks/libs/distributeddb/storage/src/storage_engine.h +++ b/frameworks/libs/distributeddb/storage/src/storage_engine.h @@ -44,6 +44,8 @@ public: int Init(); + virtual int ReInit(); + StorageExecutor *FindExecutor(bool writable, OperatePerm perm, int &errCode, int waitTime = MAX_WAIT_TIME); void Recycle(StorageExecutor *&handle); @@ -60,9 +62,9 @@ public: virtual const std::string &GetIdentifier() const; - virtual EngineState GetEngineState() const; + EngineState GetEngineState() const; - virtual void SetEngineState(EngineState state); + void SetEngineState(EngineState state); virtual int ExecuteMigrate(); @@ -72,14 +74,16 @@ public: bool IsExistConnection() const; - virtual void ClearEnginePasswd(); - virtual int CheckEngineOption(const KvDBProperties &kvdbOption) const; virtual bool IsMigrating() const; void WaitWriteHandleIdle(); + virtual void IncreaseCacheRecordVersion(); + virtual uint64_t GetCacheRecordVersion() const; + virtual uint64_t GetAndIncreaseCacheRecordVersion(); + protected: virtual int CreateNewExecutor(bool isWrite, StorageExecutor *&handle) = 0; @@ -95,7 +99,6 @@ protected: bool isUpdated_; std::atomic isMigrating_; std::string identifier_; - EngineState engineState_; // Mutex for commitNotifyFunc_. mutable std::shared_mutex notifyMutex_; @@ -134,6 +137,8 @@ private: std::mutex idleMutex_; std::condition_variable idleCondition_; + + EngineState engineState_; }; } // namespace DistributedDB #endif // STORAGE_ENGINE_H diff --git a/frameworks/libs/distributeddb/storage/src/storage_engine_manager.cpp b/frameworks/libs/distributeddb/storage/src/storage_engine_manager.cpp index 64d4d2fea192494fe527bad7da110a4ad12ff2a4..23a82ed1aeb9c250c45f9c7973a7694d23470073 100644 --- a/frameworks/libs/distributeddb/storage/src/storage_engine_manager.cpp +++ b/frameworks/libs/distributeddb/storage/src/storage_engine_manager.cpp @@ -17,6 +17,7 @@ #include "log_print.h" #include "db_errno.h" #include "runtime_context.h" +#include "rd_single_ver_storage_engine.h" #include "sqlite_single_ver_storage_engine.h" namespace DistributedDB { @@ -35,6 +36,12 @@ namespace { { return property.GetIntProp(KvDBProperties::DATABASE_TYPE, KvDBProperties::LOCAL_TYPE); } + + int IsSingleVerType(int databaseType) + { + return databaseType == KvDBProperties::SINGLE_VER_TYPE || + databaseType == KvDBProperties::SINGLE_VER_TYPE_RD_KERNAL; + } } StorageEngineManager::StorageEngineManager() : lockStatusListener_(nullptr) @@ -190,16 +197,26 @@ void StorageEngineManager::LockStatusNotifier(bool isAccessControlled) } } +StorageEngine *CreateSingleVerStorageEngine(int databaseType) +{ + if (databaseType == KvDBProperties::SINGLE_VER_TYPE) { + return new (std::nothrow) SQLiteSingleVerStorageEngine(); + } else { + return new (std::nothrow) RdSingleVerStorageEngine(); + } + return nullptr; +} + StorageEngine *StorageEngineManager::CreateStorageEngine(const KvDBProperties &property, int &errCode) { int databaseType = GetDatabaseType(property); - if (databaseType != KvDBProperties::SINGLE_VER_TYPE) { + if (!IsSingleVerType(databaseType)) { LOGE("[StorageEngineManager] Database type error : %d", databaseType); errCode = -E_NOT_SUPPORT; return nullptr; } - auto storageEngine = new (std::nothrow) SQLiteSingleVerStorageEngine(); + auto storageEngine = CreateSingleVerStorageEngine(databaseType); if (storageEngine == nullptr) { LOGE("[StorageEngineManager] Create storage engine failed"); errCode = -E_OUT_OF_MEMORY; diff --git a/frameworks/libs/distributeddb/test/unittest/common/interfaces/distributeddb_interfaces_nb_delegate_test_rd_kernal.cpp b/frameworks/libs/distributeddb/test/unittest/common/interfaces/distributeddb_interfaces_nb_delegate_test_rd_kernal.cpp new file mode 100644 index 0000000000000000000000000000000000000000..f8ca328c55395c36cadae683ea9dd9c5548a8df0 --- /dev/null +++ b/frameworks/libs/distributeddb/test/unittest/common/interfaces/distributeddb_interfaces_nb_delegate_test_rd_kernal.cpp @@ -0,0 +1,284 @@ +/* + * Copyright (c) 2021 Huawei Device Co., Ltd. + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#include +#include + +#include "db_common.h" +#include "db_constant.h" +#include "db_errno.h" +#include "distributeddb_data_generate_unit_test.h" +#include "distributeddb_tools_unit_test.h" +#include "log_print.h" +#include "platform_specific.h" +#include "process_system_api_adapter_impl.h" +#include "runtime_context.h" +#include "sqlite_single_ver_natural_store.h" +#include "storage_engine_manager.h" +#include "system_timer.h" +#include "kv_virtual_device.h" +#include "virtual_communicator_aggregator.h" + +using namespace testing::ext; +using namespace DistributedDB; +using namespace DistributedDBUnitTest; +using namespace std; + +namespace { + // define some variables to init a KvStoreDelegateManager object. + KvStoreDelegateManager g_mgr(APP_ID, USER_ID); + string g_testDir; + KvStoreConfig g_config; + std::string KeyStr("{\"_id\": \"12\"}"); + Key g_keyPrefix(KeyStr.begin(), KeyStr.end()); + const int RESULT_SET_COUNT = 9; + const int RESULT_SET_INIT_POS = -1; + uint8_t g_testDict[RESULT_SET_COUNT] = {'1', '2', '3', '4', '5', '6', '7', '8', '9'}; + + // define the g_kvNbDelegateCallback, used to get some information when open a kv store. + DBStatus g_kvDelegateStatus = INVALID_ARGS; + KvStoreNbDelegate *g_kvNbDelegatePtr = nullptr; +#ifndef OMIT_MULTI_VER + KvStoreDelegate *g_kvDelegatePtr = nullptr; + + // the type of g_kvDelegateCallback is function + auto g_kvDelegateCallback = bind(&DistributedDBToolsUnitTest::KvStoreDelegateCallback, placeholders::_1, + placeholders::_2, std::ref(g_kvDelegateStatus), std::ref(g_kvDelegatePtr)); +#endif // OMIT_MULTI_VER + const int OBSERVER_SLEEP_TIME = 100; + const int BATCH_PRESET_SIZE_TEST = 10; + const int DIVIDE_BATCH_PRESET_SIZE = 5; + const int VALUE_OFFSET = 5; + + const int DEFAULT_KEY_VALUE_SIZE = 10; + + const int CON_PUT_THREAD_NUM = 4; + const int PER_THREAD_PUT_NUM = 100; + + const std::string DEVICE_B = "deviceB"; + const std::string DEVICE_C = "deviceC"; + const std::string DEVICE_D = "deviceD"; + VirtualCommunicatorAggregator* g_communicatorAggregator = nullptr; + KvVirtualDevice *g_deviceB = nullptr; + KvVirtualDevice *g_deviceC = nullptr; + KvVirtualDevice *g_deviceD = nullptr; + VirtualSingleVerSyncDBInterface *g_syncInterfaceB = nullptr; + VirtualSingleVerSyncDBInterface *g_syncInterfaceC = nullptr; + VirtualSingleVerSyncDBInterface *g_syncInterfaceD = nullptr; + + // the type of g_kvNbDelegateCallback is function + auto g_kvNbDelegateCallback = bind(&DistributedDBToolsUnitTest::KvStoreNbDelegateCallback, placeholders::_1, + placeholders::_2, std::ref(g_kvDelegateStatus), std::ref(g_kvNbDelegatePtr)); + + enum LockState { + UNLOCKED = 0, + LOCKED + }; + +class DistributedDBInterfacesNBDelegateRdTest : public testing::Test { +public: + static void SetUpTestCase(void); + static void TearDownTestCase(void); + void SetUp(); + void TearDown(); +}; + +void DistributedDBInterfacesNBDelegateRdTest::SetUpTestCase(void) +{ + DistributedDBToolsUnitTest::TestDirInit(g_testDir); + g_config.dataDir = g_testDir; + g_mgr.SetKvStoreConfig(g_config); + if (DistributedDBToolsUnitTest::RemoveTestDbFiles(g_testDir) != 0) { + LOGE("rm test db files error!"); + } + + g_communicatorAggregator = new (std::nothrow) VirtualCommunicatorAggregator(); + ASSERT_TRUE(g_communicatorAggregator != nullptr); + RuntimeContext::GetInstance()->SetCommunicatorAggregator(g_communicatorAggregator); + + std::shared_ptr g_adapter = std::make_shared(); + RuntimeContext::GetInstance()->SetProcessSystemApiAdapter(g_adapter); +} + +void DistributedDBInterfacesNBDelegateRdTest::TearDownTestCase(void) +{ + RuntimeContext::GetInstance()->SetProcessSystemApiAdapter(nullptr); + + RuntimeContext::GetInstance()->SetCommunicatorAggregator(nullptr); +} + +void DistributedDBInterfacesNBDelegateRdTest::SetUp(void) +{ + DistributedDBToolsUnitTest::PrintTestCaseInfo(); + g_kvDelegateStatus = INVALID_ARGS; + g_kvNbDelegatePtr = nullptr; +#ifndef OMIT_MULTI_VER + g_kvDelegatePtr = nullptr; +#endif // OMIT_MULTI_VER +} + +void DistributedDBInterfacesNBDelegateRdTest::TearDown(void) +{ + if (g_kvNbDelegatePtr != nullptr) { + g_mgr.CloseKvStore(g_kvNbDelegatePtr); + g_kvNbDelegatePtr = nullptr; + } + RuntimeContext::GetInstance()->SetProcessSystemApiAdapter(nullptr); +} + +/** + * @tc.name: + * @tc.desc: + * @tc.type: FUNC + * @tc.require: + * @tc.author: + */ +HWTEST_F(DistributedDBInterfacesNBDelegateRdTest, CombineTest001, TestSize.Level1) +{ + /** + * @tc.steps:step1. Get the nb delegate. + * @tc.expected: step1. Get results OK and non-null delegate. + */ + KvStoreNbDelegate::Option option; + option.useGaussDb = true; + g_mgr.GetKvStore("distributed_nb_delegate_test", option, g_kvNbDelegateCallback); + ASSERT_TRUE(g_kvNbDelegatePtr != nullptr); + EXPECT_TRUE(g_kvDelegateStatus == OK); + // std::string keyStr("{\"name\": \"12\"}"); + std::string keyStr("acd"); + Key key(keyStr.begin(), keyStr.end()); + std::string valueStr("acd"); + Value value(valueStr.begin(), valueStr.end()); + Value valueRead; + KvStoreObserverUnitTest *observer = new (std::nothrow) KvStoreObserverUnitTest; + ASSERT_TRUE(observer != nullptr); + /** + * @tc.steps:step2. Register the non-null observer for the special key. + * @tc.expected: step2. Register results OK. + */ + EXPECT_EQ(g_kvNbDelegatePtr->RegisterObserver(key, OBSERVER_CHANGES_LOCAL_ONLY, observer), OK); + /** + * @tc.steps:step3. Put the local data. + * @tc.expected: step3. Put returns OK. + */ + EXPECT_EQ(g_kvNbDelegatePtr->Put(key, value), OK); + std::this_thread::sleep_for(std::chrono::milliseconds(OBSERVER_SLEEP_TIME)); + /** + * @tc.steps:step4. Check the local data. + * @tc.expected: step4. The get data is equal to the put data. + */ + EXPECT_EQ(g_kvNbDelegatePtr->Get(key, valueRead), OK); + /** + * @tc.steps:step5. Delete the local data. + * @tc.expected: step5. Delete returns OK. + */ + EXPECT_EQ(g_kvNbDelegatePtr->Delete(key), OK); + std::this_thread::sleep_for(std::chrono::milliseconds(OBSERVER_SLEEP_TIME)); + /** + * @tc.steps:step6. Check the local data. + * @tc.expected: step6. Couldn't find the deleted data. + */ + LOGD("step6 =========== Get local data again"); + EXPECT_EQ(g_kvNbDelegatePtr->Get(key, valueRead), NOT_FOUND); + /** + * @tc.steps:step7. UnRegister the observer. + * @tc.expected: step7. Returns OK. + */ + EXPECT_EQ(g_kvNbDelegatePtr->UnRegisterObserver(observer), OK); + delete observer; + observer = nullptr; + + /** + * @tc.steps:step8. Close the kv store. + * @tc.expected: step8. Results OK and delete successfully. + */ + LOGD("step8 =========== Close store"); + EXPECT_EQ(g_mgr.CloseKvStore(g_kvNbDelegatePtr), OK); + EXPECT_EQ(g_mgr.DeleteKvStore("distributed_nb_delegate_test"), OK); + g_kvNbDelegatePtr = nullptr; +} + +/** + * @tc.name: SingleVerGetLocalEntries001 + * @tc.desc: Test GetEntries interface for the single ver database. + * @tc.type: FUNC + * @tc.require: AR000DPTTA + * @tc.author: wangbingquan + */ +HWTEST_F(DistributedDBInterfacesNBDelegateRdTest, SingleVerGetLocalEntries001, TestSize.Level1) +{ + /** + * @tc.steps:step1. Get the nb delegate. + * @tc.expected: step1. Get results OK and non-null delegate. + */ + KvStoreNbDelegate::Option option; + option.useGaussDb = true; + g_mgr.GetKvStore("concurrentPutTest", option, g_kvNbDelegateCallback); + ASSERT_TRUE(g_kvNbDelegatePtr != nullptr); + EXPECT_TRUE(g_kvDelegateStatus == OK); + + /** + * @tc.steps:step2. Put one data whose key has prefix 'p' into the local zone. + */ + Entry entry1 = {{'p'}, {'q'}}; + EXPECT_EQ(g_kvNbDelegatePtr->Put(entry1.key, entry1.value), OK); + + /** + * @tc.steps:step3. Get batch data whose key has prefix 'k' from the local zone. + * @tc.expected: step3. Get results NOT_FOUND. + */ + std::vector entries; + EXPECT_EQ(g_kvNbDelegatePtr->GetEntries({'k'}, entries), NOT_FOUND); + + /** + * @tc.steps:step4. Put two data whose key have prefix 'k' into the local zone. + */ + Entry entry2 = {{'k', '1'}, {'d'}}; + Entry entry3 = {{'k', '2'}, {'d'}}; + EXPECT_EQ(g_kvNbDelegatePtr->Put(entry2.key, entry2.value), OK); + EXPECT_EQ(g_kvNbDelegatePtr->Put(entry3.key, entry3.value), OK); + + /** + * @tc.steps:step5. Get batch data whose key has prefix 'k' from the local zone. + * @tc.expected: step5. Get results OK, and the entries size is 2. + */ + EXPECT_EQ(g_kvNbDelegatePtr->GetEntries({'k'}, entries), OK); + EXPECT_EQ(entries.size(), 2UL); + + /** + * @tc.steps:step6. Get batch data whose key has empty prefix from the local zone. + * @tc.expected: step6. Get results OK, and the entries size is 3. + */ + EXPECT_EQ(g_kvNbDelegatePtr->GetEntries((Key){}, entries), OK); + EXPECT_EQ(entries.size(), 3UL); + + /** + * @tc.steps:step7. Delete one data whose key has prefix 'k' from the local zone. + */ + EXPECT_EQ(g_kvNbDelegatePtr->Delete(entry3.key), OK); + + /** + * @tc.steps:step8. Get batch data whose key has prefix 'k' from the local zone. + * @tc.expected: step8. Get results OK, and the entries size is 1. + */ + EXPECT_EQ(g_kvNbDelegatePtr->GetEntries({'k'}, entries), OK); + EXPECT_EQ(entries.size(), 1UL); + + EXPECT_EQ(g_mgr.CloseKvStore(g_kvNbDelegatePtr), OK); + EXPECT_EQ(g_mgr.DeleteKvStore("concurrentPutTest"), OK); + g_kvNbDelegatePtr = nullptr; +} + +} \ No newline at end of file diff --git a/frameworks/libs/distributeddb/test/unittest/common/syncer/cloud/distributeddb_cloud_syncer_upload_test.cpp b/frameworks/libs/distributeddb/test/unittest/common/syncer/cloud/distributeddb_cloud_syncer_upload_test.cpp index 0170c760251b2082277e40c5fd57acb276078970..1aa5b59f77ea84a01a206a1b03699571a7335b84 100644 --- a/frameworks/libs/distributeddb/test/unittest/common/syncer/cloud/distributeddb_cloud_syncer_upload_test.cpp +++ b/frameworks/libs/distributeddb/test/unittest/common/syncer/cloud/distributeddb_cloud_syncer_upload_test.cpp @@ -623,7 +623,7 @@ HWTEST_F(DistributedDBCloudSyncerUploadTest, UploadModeCheck010, TestSize.Level1 count = 3000; return E_OK; }); - EXPECT_CALL(*iCloud, Commit()).WillRepeatedly(Return(E_OK)); + EXPECT_CALL(*iCloud, Commit()).WillRepeatedly(Return(E_OK)); EXPECT_CALL(*iCloud, Rollback()).WillRepeatedly(Return(E_OK)); EXPECT_CALL(*iCloud, PutMetaData(_, _)).WillRepeatedly(Return(E_OK)); EXPECT_CALL(*idb, BatchInsert(_, _, _)).WillRepeatedly(Return(OK));