TDengine/source/libs/tdb/test/tdbTest.cpp

748 lines
16 KiB
C++
Raw Normal View History

#include <gtest/gtest.h>
2022-01-13 06:13:10 +00:00
2022-05-19 07:15:00 +00:00
#define ALLOW_FORBID_FUNC
2022-04-25 08:39:10 +00:00
#include "os.h"
2022-04-28 07:02:49 +00:00
#include "tdb.h"
2022-01-13 08:04:43 +00:00
2022-05-19 11:14:14 +00:00
#include <shared_mutex>
2022-03-26 02:53:38 +00:00
#include <string>
2022-05-19 07:15:00 +00:00
#include <thread>
#include <vector>
2022-12-07 14:24:47 +00:00
#include "tlog.h"
2022-03-26 02:53:38 +00:00
2022-03-26 09:29:49 +00:00
typedef struct SPoolMem {
int64_t size;
struct SPoolMem *prev;
struct SPoolMem *next;
} SPoolMem;
static SPoolMem *openPool() {
2022-04-28 07:02:49 +00:00
SPoolMem *pPool = (SPoolMem *)taosMemoryMalloc(sizeof(*pPool));
2022-03-26 09:29:49 +00:00
pPool->prev = pPool->next = pPool;
pPool->size = 0;
return pPool;
}
2022-04-02 11:20:56 +00:00
static void clearPool(SPoolMem *pPool) {
2022-03-26 09:29:49 +00:00
SPoolMem *pMem;
do {
pMem = pPool->next;
if (pMem == pPool) break;
pMem->next->prev = pMem->prev;
pMem->prev->next = pMem->next;
pPool->size -= pMem->size;
2022-04-28 07:02:49 +00:00
taosMemoryFree(pMem);
2022-03-26 09:29:49 +00:00
} while (1);
TD_ALWAYS_ASSERT(pPool->size == 0);
2022-04-02 11:20:56 +00:00
}
2022-03-26 09:29:49 +00:00
2022-04-02 11:20:56 +00:00
static void closePool(SPoolMem *pPool) {
clearPool(pPool);
2022-04-28 07:02:49 +00:00
taosMemoryFree(pPool);
2022-03-26 09:29:49 +00:00
}
2022-04-02 11:20:56 +00:00
static void *poolMalloc(void *arg, size_t size) {
2022-03-26 09:29:49 +00:00
void *ptr = NULL;
SPoolMem *pPool = (SPoolMem *)arg;
SPoolMem *pMem;
2022-04-28 07:02:49 +00:00
pMem = (SPoolMem *)taosMemoryMalloc(sizeof(*pMem) + size);
2022-03-26 09:29:49 +00:00
if (pMem == NULL) {
TD_ALWAYS_ASSERT(0);
2022-03-26 09:29:49 +00:00
}
pMem->size = sizeof(*pMem) + size;
pMem->next = pPool->next;
pMem->prev = pPool;
pPool->next->prev = pMem;
pPool->next = pMem;
pPool->size += pMem->size;
ptr = (void *)(&pMem[1]);
return ptr;
}
static void poolFree(void *arg, void *ptr) {
SPoolMem *pPool = (SPoolMem *)arg;
SPoolMem *pMem;
pMem = &(((SPoolMem *)ptr)[-1]);
pMem->next->prev = pMem->prev;
pMem->prev->next = pMem->next;
pPool->size -= pMem->size;
2022-04-28 07:02:49 +00:00
taosMemoryFree(pMem);
2022-03-26 09:29:49 +00:00
}
static int tKeyCmpr(const void *pKey1, int kLen1, const void *pKey2, int kLen2) {
int k1, k2;
std::string s1((char *)pKey1 + 3, kLen1 - 3);
std::string s2((char *)pKey2 + 3, kLen2 - 3);
k1 = stoi(s1);
k2 = stoi(s2);
if (k1 < k2) {
return -1;
} else if (k1 > k2) {
return 1;
} else {
return 0;
}
}
static int tDefaultKeyCmpr(const void *pKey1, int keyLen1, const void *pKey2, int keyLen2) {
int mlen;
int cret;
ASSERT(keyLen1 > 0 && keyLen2 > 0 && pKey1 != NULL && pKey2 != NULL);
2022-03-26 09:29:49 +00:00
mlen = keyLen1 < keyLen2 ? keyLen1 : keyLen2;
cret = memcmp(pKey1, pKey2, mlen);
if (cret == 0) {
if (keyLen1 < keyLen2) {
cret = -1;
} else if (keyLen1 > keyLen2) {
cret = 1;
} else {
cret = 0;
}
}
return cret;
}
2022-03-25 09:01:09 +00:00
2022-05-19 11:14:14 +00:00
TEST(tdb_test, DISABLED_simple_insert1) {
2022-04-28 07:02:49 +00:00
int ret;
2022-05-18 07:57:29 +00:00
TDB *pEnv;
TTB *pDb;
2022-04-28 07:02:49 +00:00
tdb_cmpr_fn_t compFunc;
2022-05-03 11:24:52 +00:00
int nData = 1000000;
TXN *txn;
2022-01-13 08:04:43 +00:00
2022-04-25 08:39:10 +00:00
taosRemoveDir("tdb");
2022-02-28 05:34:27 +00:00
// Open Env
2024-03-29 02:48:49 +00:00
ret = tdbOpen("tdb", 4096, 64, &pEnv, 0, 0, NULL);
2022-02-28 05:34:27 +00:00
GTEST_ASSERT_EQ(ret, 0);
2022-02-15 05:50:30 +00:00
2022-02-28 05:34:27 +00:00
// Create a database
2022-03-25 10:54:54 +00:00
compFunc = tKeyCmpr;
ret = tdbTbOpen("db.db", -1, -1, compFunc, pEnv, &pDb, 0);
2022-02-28 05:34:27 +00:00
GTEST_ASSERT_EQ(ret, 0);
2022-02-15 05:50:30 +00:00
2022-03-23 10:30:52 +00:00
{
2022-04-02 11:20:56 +00:00
char key[64];
char val[64];
int64_t poolLimit = 4096; // 1M pool limit
SPoolMem *pPool;
// open the pool
pPool = openPool();
// start a transaction
tdbBegin(pEnv, &txn, poolMalloc, poolFree, pPool, TDB_TXN_WRITE | TDB_TXN_READ_UNCOMMITTED);
2022-04-02 11:20:56 +00:00
for (int iData = 1; iData <= nData; iData++) {
sprintf(key, "key%d", iData);
sprintf(val, "value%d", iData);
ret = tdbTbInsert(pDb, key, strlen(key), val, strlen(val), txn);
2022-04-02 11:20:56 +00:00
GTEST_ASSERT_EQ(ret, 0);
// if pool is full, commit the transaction and start a new one
if (pPool->size >= poolLimit) {
// commit current transaction
tdbCommit(pEnv, txn);
tdbPostCommit(pEnv, txn);
2022-04-02 11:20:56 +00:00
// start a new transaction
clearPool(pPool);
tdbBegin(pEnv, &txn, poolMalloc, poolFree, pPool, TDB_TXN_WRITE | TDB_TXN_READ_UNCOMMITTED);
2022-03-23 10:30:52 +00:00
}
}
2022-04-02 11:20:56 +00:00
// commit the transaction
tdbCommit(pEnv, txn);
tdbPostCommit(pEnv, txn);
2022-04-02 11:20:56 +00:00
2022-03-23 10:30:52 +00:00
{ // Query the data
2022-03-25 04:59:20 +00:00
void *pVal = NULL;
int vLen;
2022-03-23 10:30:52 +00:00
for (int i = 1; i <= nData; i++) {
sprintf(key, "key%d", i);
sprintf(val, "value%d", i);
2022-05-18 07:57:29 +00:00
ret = tdbTbGet(pDb, key, strlen(key), &pVal, &vLen);
ASSERT(ret == 0);
2022-03-23 10:30:52 +00:00
GTEST_ASSERT_EQ(ret, 0);
GTEST_ASSERT_EQ(vLen, strlen(val));
GTEST_ASSERT_EQ(memcmp(val, pVal, vLen), 0);
}
2022-03-25 06:02:38 +00:00
2022-04-28 07:02:49 +00:00
tdbFree(pVal);
2022-03-16 07:15:39 +00:00
}
2022-03-24 08:40:37 +00:00
2022-03-25 06:15:21 +00:00
{ // Iterate to query the DB data
2022-05-18 07:57:29 +00:00
TBC *pDBC;
2022-03-28 06:06:34 +00:00
void *pKey = NULL;
void *pVal = NULL;
int vLen, kLen;
int count = 0;
2022-03-25 06:15:21 +00:00
2022-05-18 07:57:29 +00:00
ret = tdbTbcOpen(pDb, &pDBC, NULL);
2022-03-25 06:15:21 +00:00
GTEST_ASSERT_EQ(ret, 0);
2022-05-18 07:57:29 +00:00
tdbTbcMoveToFirst(pDBC);
2022-05-03 09:59:58 +00:00
2022-03-25 06:15:21 +00:00
for (;;) {
2022-05-18 07:57:29 +00:00
ret = tdbTbcNext(pDBC, &pKey, &kLen, &pVal, &vLen);
2022-03-25 06:15:21 +00:00
if (ret < 0) break;
2022-03-25 09:01:09 +00:00
// std::cout.write((char *)pKey, kLen) /* << " " << kLen */ << " ";
// std::cout.write((char *)pVal, vLen) /* << " " << vLen */;
// std::cout << std::endl;
2022-03-25 06:15:21 +00:00
count++;
}
GTEST_ASSERT_EQ(count, nData);
2022-05-18 07:57:29 +00:00
tdbTbcClose(pDBC);
2022-03-25 06:15:21 +00:00
2022-04-28 07:02:49 +00:00
tdbFree(pKey);
tdbFree(pVal);
2022-03-24 08:40:37 +00:00
}
2022-03-15 09:58:50 +00:00
}
2022-03-01 03:46:40 +00:00
2022-05-18 07:57:29 +00:00
ret = tdbTbDrop(pDb);
2022-03-01 05:25:42 +00:00
GTEST_ASSERT_EQ(ret, 0);
2022-02-15 05:50:30 +00:00
2022-02-28 05:34:27 +00:00
// Close a database
2022-05-18 07:57:29 +00:00
tdbTbClose(pDb);
2022-02-15 05:50:30 +00:00
2022-04-25 07:32:41 +00:00
// Close Env
2024-09-24 01:56:42 +00:00
tdbClose(pEnv);
2022-04-25 07:32:41 +00:00
}
2022-05-19 11:14:14 +00:00
TEST(tdb_test, DISABLED_simple_insert2) {
2022-04-28 07:02:49 +00:00
int ret;
2022-05-18 07:57:29 +00:00
TDB *pEnv;
TTB *pDb;
2022-04-28 07:02:49 +00:00
tdb_cmpr_fn_t compFunc;
int nData = 1000000;
TXN *txn;
2022-04-25 07:32:41 +00:00
2022-04-25 08:39:10 +00:00
taosRemoveDir("tdb");
2022-04-25 07:32:41 +00:00
// Open Env
2024-03-29 02:48:49 +00:00
ret = tdbOpen("tdb", 1024, 10, &pEnv, 0, 0, NULL);
2022-04-25 07:32:41 +00:00
GTEST_ASSERT_EQ(ret, 0);
// Create a database
2022-04-25 08:39:10 +00:00
compFunc = tDefaultKeyCmpr;
ret = tdbTbOpen("db.db", -1, -1, compFunc, pEnv, &pDb, 0);
2022-04-25 07:32:41 +00:00
GTEST_ASSERT_EQ(ret, 0);
{
char key[64];
char val[64];
SPoolMem *pPool;
// open the pool
pPool = openPool();
// start a transaction
tdbBegin(pEnv, &txn, poolMalloc, poolFree, pPool, TDB_TXN_WRITE | TDB_TXN_READ_UNCOMMITTED);
2022-04-25 07:32:41 +00:00
for (int iData = 1; iData <= nData; iData++) {
sprintf(key, "key%d", iData);
sprintf(val, "value%d", iData);
ret = tdbTbInsert(pDb, key, strlen(key), val, strlen(val), txn);
2022-04-25 07:32:41 +00:00
GTEST_ASSERT_EQ(ret, 0);
}
{ // Iterate to query the DB data
2022-05-18 07:57:29 +00:00
TBC *pDBC;
2022-04-25 07:32:41 +00:00
void *pKey = NULL;
void *pVal = NULL;
int vLen, kLen;
int count = 0;
2022-05-18 07:57:29 +00:00
ret = tdbTbcOpen(pDb, &pDBC, NULL);
2022-04-25 07:32:41 +00:00
GTEST_ASSERT_EQ(ret, 0);
2022-05-18 07:57:29 +00:00
tdbTbcMoveToFirst(pDBC);
2022-05-03 09:59:58 +00:00
2022-04-25 07:32:41 +00:00
for (;;) {
2022-05-18 07:57:29 +00:00
ret = tdbTbcNext(pDBC, &pKey, &kLen, &pVal, &vLen);
2022-04-25 07:32:41 +00:00
if (ret < 0) break;
2022-05-03 11:24:52 +00:00
// std::cout.write((char *)pKey, kLen) /* << " " << kLen */ << " ";
// std::cout.write((char *)pVal, vLen) /* << " " << vLen */;
// std::cout << std::endl;
2022-04-25 07:32:41 +00:00
count++;
}
GTEST_ASSERT_EQ(count, nData);
2022-05-18 07:57:29 +00:00
tdbTbcClose(pDBC);
2022-04-25 07:32:41 +00:00
2022-04-28 07:02:49 +00:00
tdbFree(pKey);
tdbFree(pVal);
2022-04-25 07:32:41 +00:00
}
}
// commit the transaction
tdbCommit(pEnv, txn);
tdbPostCommit(pEnv, txn);
2022-04-25 07:32:41 +00:00
2022-05-18 07:57:29 +00:00
ret = tdbTbDrop(pDb);
2022-04-25 07:32:41 +00:00
GTEST_ASSERT_EQ(ret, 0);
// Close a database
2022-05-18 07:57:29 +00:00
tdbTbClose(pDb);
2022-04-25 07:32:41 +00:00
2022-02-28 05:34:27 +00:00
// Close Env
2024-09-24 01:56:42 +00:00
tdbClose(pEnv);
2022-05-02 15:17:43 +00:00
}
2022-05-19 11:14:14 +00:00
TEST(tdb_test, DISABLED_simple_delete1) {
2022-05-03 08:09:58 +00:00
int ret;
2022-05-18 07:57:29 +00:00
TTB *pDb;
2022-05-03 08:09:58 +00:00
char key[128];
char data[128];
TXN *txn;
2022-05-18 07:57:29 +00:00
TDB *pEnv;
2022-05-03 08:09:58 +00:00
SPoolMem *pPool;
void *pKey = NULL;
void *pData = NULL;
int nKey;
2022-05-18 07:57:29 +00:00
TBC *pDbc;
2022-05-03 08:09:58 +00:00
int nData;
2022-05-03 11:24:52 +00:00
int nKV = 69;
2022-05-03 08:09:58 +00:00
taosRemoveDir("tdb");
pPool = openPool();
// open env
2024-03-29 02:48:49 +00:00
ret = tdbOpen("tdb", 1024, 256, &pEnv, 0, 0, NULL);
2022-05-03 08:09:58 +00:00
GTEST_ASSERT_EQ(ret, 0);
// open database
ret = tdbTbOpen("db.db", -1, -1, tKeyCmpr, pEnv, &pDb, 0);
2022-05-03 08:09:58 +00:00
GTEST_ASSERT_EQ(ret, 0);
tdbBegin(pEnv, &txn, poolMalloc, poolFree, pPool, TDB_TXN_WRITE | TDB_TXN_READ_UNCOMMITTED);
2022-05-03 08:09:58 +00:00
// loop to insert batch data
for (int iData = 0; iData < nKV; iData++) {
sprintf(key, "key%d", iData);
sprintf(data, "data%d", iData);
ret = tdbTbInsert(pDb, key, strlen(key), data, strlen(data), txn);
2022-05-03 08:09:58 +00:00
GTEST_ASSERT_EQ(ret, 0);
}
// query the data
for (int iData = 0; iData < nKV; iData++) {
sprintf(key, "key%d", iData);
sprintf(data, "data%d", iData);
2022-05-18 07:57:29 +00:00
ret = tdbTbGet(pDb, key, strlen(key), &pData, &nData);
2022-05-03 08:09:58 +00:00
GTEST_ASSERT_EQ(ret, 0);
GTEST_ASSERT_EQ(memcmp(data, pData, nData), 0);
}
// loop to delete some data
2022-05-03 11:24:52 +00:00
for (int iData = nKV - 1; iData > 30; iData--) {
2022-05-03 08:09:58 +00:00
sprintf(key, "key%d", iData);
ret = tdbTbDelete(pDb, key, strlen(key), txn);
2022-05-03 08:09:58 +00:00
GTEST_ASSERT_EQ(ret, 0);
}
// query the data
2022-05-03 11:24:52 +00:00
for (int iData = 0; iData < nKV; iData++) {
sprintf(key, "key%d", iData);
2022-05-18 07:57:29 +00:00
ret = tdbTbGet(pDb, key, strlen(key), &pData, &nData);
2022-05-03 11:24:52 +00:00
if (iData <= 30) {
GTEST_ASSERT_EQ(ret, 0);
} else {
GTEST_ASSERT_EQ(ret, -1);
}
}
// loop to iterate the data
2022-05-18 07:57:29 +00:00
tdbTbcOpen(pDb, &pDbc, NULL);
2022-05-03 11:24:52 +00:00
2022-05-18 07:57:29 +00:00
ret = tdbTbcMoveToFirst(pDbc);
2022-05-03 11:24:52 +00:00
GTEST_ASSERT_EQ(ret, 0);
pKey = NULL;
pData = NULL;
for (;;) {
2022-05-18 07:57:29 +00:00
ret = tdbTbcNext(pDbc, &pKey, &nKey, &pData, &nData);
2022-05-03 11:24:52 +00:00
if (ret < 0) break;
std::cout.write((char *)pKey, nKey) /* << " " << kLen */ << " ";
std::cout.write((char *)pData, nData) /* << " " << vLen */;
std::cout << std::endl;
}
2022-05-18 07:57:29 +00:00
tdbTbcClose(pDbc);
2022-05-03 08:09:58 +00:00
tdbCommit(pEnv, txn);
tdbPostCommit(pEnv, txn);
2022-05-03 08:09:58 +00:00
closePool(pPool);
2022-05-18 07:57:29 +00:00
tdbTbClose(pDb);
tdbClose(pEnv);
2022-05-05 03:17:34 +00:00
}
2022-05-19 11:14:14 +00:00
TEST(tdb_test, DISABLED_simple_upsert1) {
2022-05-05 03:17:34 +00:00
int ret;
2022-05-18 07:57:29 +00:00
TDB *pEnv;
TTB *pDb;
2022-05-05 03:17:34 +00:00
int nData = 100000;
char key[64];
char data[64];
void *pData = NULL;
SPoolMem *pPool;
TXN *txn;
2022-05-05 03:17:34 +00:00
taosRemoveDir("tdb");
// open env
2024-03-29 02:48:49 +00:00
ret = tdbOpen("tdb", 4096, 64, &pEnv, 0, 0, NULL);
2022-05-05 03:17:34 +00:00
GTEST_ASSERT_EQ(ret, 0);
// open database
ret = tdbTbOpen("db.db", -1, -1, NULL, pEnv, &pDb, 0);
2022-05-05 03:17:34 +00:00
GTEST_ASSERT_EQ(ret, 0);
pPool = openPool();
// insert some data
tdbBegin(pEnv, &txn, poolMalloc, poolFree, pPool, TDB_TXN_WRITE | TDB_TXN_READ_UNCOMMITTED);
2022-05-05 03:17:34 +00:00
for (int iData = 0; iData < nData; iData++) {
sprintf(key, "key%d", iData);
sprintf(data, "data%d", iData);
ret = tdbTbInsert(pDb, key, strlen(key), data, strlen(data), txn);
2022-05-05 03:17:34 +00:00
GTEST_ASSERT_EQ(ret, 0);
}
// query the data
for (int iData = 0; iData < nData; iData++) {
sprintf(key, "key%d", iData);
sprintf(data, "data%d", iData);
2022-05-18 07:57:29 +00:00
ret = tdbTbGet(pDb, key, strlen(key), &pData, &nData);
2022-05-05 03:17:34 +00:00
GTEST_ASSERT_EQ(ret, 0);
GTEST_ASSERT_EQ(memcmp(pData, data, nData), 0);
}
// upsert some data
for (int iData = 0; iData < nData; iData++) {
sprintf(key, "key%d", iData);
sprintf(data, "data%d-u", iData);
ret = tdbTbUpsert(pDb, key, strlen(key), data, strlen(data), txn);
2022-05-05 03:17:34 +00:00
GTEST_ASSERT_EQ(ret, 0);
}
tdbCommit(pEnv, txn);
tdbPostCommit(pEnv, txn);
2022-05-05 03:17:34 +00:00
// query the data
for (int iData = 0; iData < nData; iData++) {
sprintf(key, "key%d", iData);
sprintf(data, "data%d-u", iData);
2022-05-18 07:57:29 +00:00
ret = tdbTbGet(pDb, key, strlen(key), &pData, &nData);
2022-05-05 03:17:34 +00:00
GTEST_ASSERT_EQ(ret, 0);
GTEST_ASSERT_EQ(memcmp(pData, data, nData), 0);
}
2022-05-18 07:57:29 +00:00
tdbTbClose(pDb);
tdbClose(pEnv);
2022-05-19 07:15:00 +00:00
}
2024-04-29 05:43:31 +00:00
TEST(tdb_test, simple_upsert2) {
int ret;
TDB *pEnv;
TTB *pDb;
int nData = 10000;
const char *key = "key";
int32_t dataSize = 256 * 1024;
void *data = taosMemoryMalloc(dataSize);
void *pData = NULL;
SPoolMem *pPool;
TXN *txn;
taosRemoveDir("tdb");
memset(data, 'a', dataSize);
// open env
ret = tdbOpen("tdb", 4096, 64, &pEnv, 0, 0, 0);
GTEST_ASSERT_EQ(ret, 0);
// open database
ret = tdbTbOpen("db.db", -1, -1, NULL, pEnv, &pDb, 0);
GTEST_ASSERT_EQ(ret, 0);
pPool = openPool();
for (int iData = 0; iData < nData; iData++) {
tdbBegin(pEnv, &txn, poolMalloc, poolFree, pPool, TDB_TXN_WRITE | TDB_TXN_READ_UNCOMMITTED);
ret = tdbTbUpsert(pDb, key, strlen(key), data, dataSize, txn);
GTEST_ASSERT_EQ(ret, 0);
tdbCommit(pEnv, txn);
tdbPostCommit(pEnv, txn);
}
tdbTbClose(pDb);
tdbClose(pEnv);
}
2022-05-20 07:07:51 +00:00
TEST(tdb_test, multi_thread_query) {
2022-05-19 07:15:00 +00:00
int ret;
TDB *pEnv;
TTB *pDb;
tdb_cmpr_fn_t compFunc;
2022-05-20 07:07:51 +00:00
int nData = 1000000;
TXN *txn;
2022-05-19 07:15:00 +00:00
taosRemoveDir("tdb");
// Open Env
2024-03-29 02:48:49 +00:00
ret = tdbOpen("tdb", 4096, 10, &pEnv, 0, 0, NULL);
2022-05-19 07:15:00 +00:00
GTEST_ASSERT_EQ(ret, 0);
// Create a database
compFunc = tKeyCmpr;
ret = tdbTbOpen("db.db", -1, -1, compFunc, pEnv, &pDb, 0);
2022-05-19 07:15:00 +00:00
GTEST_ASSERT_EQ(ret, 0);
char key[64];
char val[64];
2022-05-20 07:07:51 +00:00
int64_t poolLimit = 4096 * 20; // 1M pool limit
2022-05-19 07:15:00 +00:00
SPoolMem *pPool;
// open the pool
pPool = openPool();
// start a transaction
tdbBegin(pEnv, &txn, poolMalloc, poolFree, pPool, TDB_TXN_WRITE | TDB_TXN_READ_UNCOMMITTED);
2022-05-19 07:15:00 +00:00
for (int iData = 1; iData <= nData; iData++) {
sprintf(key, "key%d", iData);
sprintf(val, "value%d", iData);
ret = tdbTbInsert(pDb, key, strlen(key), val, strlen(val), txn);
2022-05-19 07:15:00 +00:00
GTEST_ASSERT_EQ(ret, 0);
}
auto f = [](TTB *pDb, int nData) {
TBC *pDBC;
void *pKey = NULL;
void *pVal = NULL;
int vLen, kLen;
int count = 0;
int ret;
TXN txn;
SPoolMem *pPool = openPool();
2022-05-19 08:16:06 +00:00
txn.flags = 0;
txn.txnId = 0;
txn.xMalloc = poolMalloc;
txn.xFree = poolFree;
txn.xArg = pPool;
2022-05-19 07:15:00 +00:00
ret = tdbTbcOpen(pDb, &pDBC, &txn);
GTEST_ASSERT_EQ(ret, 0);
tdbTbcMoveToFirst(pDBC);
for (;;) {
ret = tdbTbcNext(pDBC, &pKey, &kLen, &pVal, &vLen);
if (ret < 0) break;
// std::cout.write((char *)pKey, kLen) /* << " " << kLen */ << " ";
// std::cout.write((char *)pVal, vLen) /* << " " << vLen */;
// std::cout << std::endl;
count++;
}
GTEST_ASSERT_EQ(count, nData);
tdbTbcClose(pDBC);
tdbFree(pKey);
tdbFree(pVal);
};
// tdbCommit(pEnv, &txn);
// multi-thread query
int nThreads = 20;
std::vector<std::thread> threads;
for (int i = 0; i < nThreads; i++) {
if (i == 0) {
threads.push_back(std::thread(tdbCommit, pEnv, txn));
2022-05-19 07:15:00 +00:00
} else {
threads.push_back(std::thread(f, pDb, nData));
}
}
for (auto &th : threads) {
th.join();
}
// commit the transaction
tdbCommit(pEnv, txn);
tdbPostCommit(pEnv, txn);
2022-05-19 07:15:00 +00:00
// Close a database
tdbTbClose(pDb);
// Close Env
2024-09-24 01:56:42 +00:00
tdbClose(pEnv);
2022-05-19 11:14:14 +00:00
}
2022-05-20 07:07:51 +00:00
TEST(tdb_test, DISABLED_multi_thread1) {
2022-05-20 05:28:24 +00:00
#if 0
2022-05-19 11:14:14 +00:00
int ret;
TDB *pDb;
TTB *pTb;
tdb_cmpr_fn_t compFunc;
int nData = 10000000;
TXN txn;
std::shared_timed_mutex mutex;
taosRemoveDir("tdb");
// Open Env
2024-03-29 02:48:49 +00:00
ret = tdbOpen("tdb", 512, 1, &pDb, 0, 0, NULL);
2022-05-19 11:14:14 +00:00
GTEST_ASSERT_EQ(ret, 0);
ret = tdbTbOpen("db.db", -1, -1, NULL, pDb, &pTb, 0);
2022-05-19 11:14:14 +00:00
GTEST_ASSERT_EQ(ret, 0);
auto insert = [](TDB *pDb, TTB *pTb, int nData, int *stop, std::shared_timed_mutex *mu) {
TXN *txn = NULL;
2022-05-19 11:14:14 +00:00
char key[128];
char val[128];
SPoolMem *pPool = openPool();
tdbBegin(pDb, &txn, poolMalloc, poolFree, pPool, TDB_TXN_WRITE | TDB_TXN_READ_UNCOMMITTED);
2022-05-19 11:14:14 +00:00
for (int iData = 1; iData <= nData; iData++) {
sprintf(key, "key%d", iData);
sprintf(val, "value%d", iData);
{
std::lock_guard<std::shared_timed_mutex> wmutex(*mu);
int ret = tdbTbInsert(pTb, key, strlen(key), val, strlen(val), &txn);
GTEST_ASSERT_EQ(ret, 0);
}
if (pPool->size > 1024 * 1024) {
tdbCommit(pDb, txn);
tdbPostCommit(pDb, txn);
2022-05-19 11:14:14 +00:00
clearPool(pPool);
tdbBegin(pDb, &txn, poolMalloc, poolFree, pPool, TDB_TXN_WRITE | TDB_TXN_READ_UNCOMMITTED);
2022-05-19 11:14:14 +00:00
}
}
tdbCommit(pDb, txn);
tdbPostCommit(pDb, txn);
2022-05-19 11:14:14 +00:00
closePool(pPool);
*stop = 1;
};
auto query = [](TTB *pTb, int *stop, std::shared_timed_mutex *mu) {
TBC *pDBC;
void *pKey = NULL;
void *pVal = NULL;
int vLen, kLen;
int ret;
TXN txn;
SPoolMem *pPool = openPool();
txn.flags = 0;
txn.txnId = 0;
txn.xMalloc = poolMalloc;
txn.xFree = poolFree;
txn.xArg = pPool;
for (;;) {
if (*stop) break;
clearPool(pPool);
int count = 0;
{
std::shared_lock<std::shared_timed_mutex> rMutex(*mu);
ret = tdbTbcOpen(pTb, &pDBC, &txn);
GTEST_ASSERT_EQ(ret, 0);
tdbTbcMoveToFirst(pDBC);
for (;;) {
ret = tdbTbcNext(pDBC, &pKey, &kLen, &pVal, &vLen);
if (ret < 0) break;
count++;
}
std::cout << count << std::endl;
tdbTbcClose(pDBC);
}
usleep(500000);
}
closePool(pPool);
tdbFree(pKey);
tdbFree(pVal);
};
std::vector<std::thread> threads;
int nThreads = 10;
int stop = 0;
for (int i = 0; i < nThreads; i++) {
if (i == 0) {
threads.push_back(std::thread(insert, pDb, pTb, nData, &stop, &mutex));
} else {
threads.push_back(std::thread(query, pTb, &stop, &mutex));
}
}
for (auto &th : threads) {
th.join();
}
// Close a database
tdbTbClose(pTb);
// Close Env
2024-09-24 01:56:42 +00:00
tdbClose(pEnv);
2022-05-20 05:28:24 +00:00
#endif
}