MXS-1475 Remove all traces of RocsDB cache storage
Some API changes are needed and it's not time well spent to update the RocksDB storage implementation.
This commit is contained in:
@ -1,3 +1 @@
|
||||
#Storage RocksDB not built by default.
|
||||
#add_subdirectory(storage_rocksdb)
|
||||
add_subdirectory(storage_inmemory)
|
||||
|
@ -1,49 +0,0 @@
|
||||
# Build RocksDB
|
||||
|
||||
if ((CMAKE_CXX_COMPILER_ID STREQUAL "GNU") AND (NOT (CMAKE_CXX_COMPILER_VERSION VERSION_LESS 4.8)))
|
||||
message(STATUS "GCC >= 4.8, RocksDB is built.")
|
||||
|
||||
set(ROCKSDB_REPO "https://github.com/facebook/rocksdb.git"
|
||||
CACHE STRING "RocksDB Git repository")
|
||||
|
||||
# Release 4.9 of RocksDB
|
||||
set(ROCKSDB_TAG "v4.9"
|
||||
CACHE STRING "RocksDB Git tag")
|
||||
|
||||
set(ROCKSDB_SUBPATH "/server/modules/filter/cache/storage/storage_rocksdb/RocksDB-prefix/src/RocksDB")
|
||||
set(ROCKSDB_ROOT ${CMAKE_BINARY_DIR}${ROCKSDB_SUBPATH})
|
||||
|
||||
ExternalProject_Add(RocksDB
|
||||
GIT_REPOSITORY ${ROCKSDB_REPO}
|
||||
GIT_TAG ${ROCKSDB_TAG}
|
||||
CONFIGURE_COMMAND ""
|
||||
BINARY_DIR ${ROCKSDB_ROOT}
|
||||
CONFIGURE_COMMAND ""
|
||||
BUILD_COMMAND make DISABLE_JEMALLOC=1 EXTRA_CXXFLAGS=-fPIC static_lib
|
||||
INSTALL_COMMAND "")
|
||||
|
||||
set(ROCKSDB_BUILT TRUE CACHE INTERNAL "")
|
||||
set(ROCKSDB_INCLUDE_DIRS ${ROCKSDB_ROOT}/include ${ROCKSDB_ROOT})
|
||||
set(ROCKSDB_LIB_DIR ${ROCKSDB_ROOT})
|
||||
set(ROCKSDB_LIB librocksdb.a)
|
||||
|
||||
# RocksDB supports several compression libraries and automatically
|
||||
# uses them if it finds the headers in the environment. Consequently,
|
||||
# we must ensure that a user of RocksDB can link to the needed
|
||||
# libraries.
|
||||
#
|
||||
# ROCKSDB_LINK_LIBS specifies that libraries a module using ROCKSDB_LIB
|
||||
# must link with.
|
||||
|
||||
find_package(BZip2)
|
||||
if (BZIP2_FOUND)
|
||||
set(ROCKSDB_LINK_LIBS ${ROCKSDB_LINK_LIBS} ${BZIP2_LIBRARIES})
|
||||
endif()
|
||||
|
||||
find_package(ZLIB)
|
||||
if (ZLIB_FOUND)
|
||||
set(ROCKSDB_LINK_LIBS ${ROCKSDB_LINK_LIBS} ${ZLIB_LIBRARIES})
|
||||
endif()
|
||||
else()
|
||||
message(STATUS "RocksDB requires GCC >= 4.7, only ${CMAKE_CXX_COMPILER_VERSION} available.")
|
||||
endif()
|
@ -1,26 +0,0 @@
|
||||
include(BuildRocksDB.cmake)
|
||||
|
||||
if (ROCKSDB_BUILT)
|
||||
message(STATUS "RocksDB is built, storage_rocksdb will be built.")
|
||||
|
||||
set(CMAKE_CXX_FLAGS "-std=c++11 ${CMAKE_CXX_FLAGS} -DROCKSDB_PLATFORM_POSIX")
|
||||
set(CMAKE_CXX_FLAGS_DEBUG "-std=c++11 ${CMAKE_CXX_FLAGS_DEBUG} -DROCKSDB_PLATFORM_POSIX")
|
||||
set(CMAKE_CXX_FLAGS_RELEASE "-std=c++11 ${CMAKE_CXX_FLAGS_RELEASE} -DROCKSDB_PLATFORM_POSIX")
|
||||
set(CMAKE_CXX_FLAGS_RELWITHDEBINFO "-std=c++11 ${CMAKE_CXX_FLAGS_RELWITHDEBINFO} -DROCKSDB_PLATFORM_POSIX")
|
||||
|
||||
include_directories(${ROCKSDB_INCLUDE_DIRS})
|
||||
link_directories(${ROCKSDB_LIB_DIR})
|
||||
|
||||
add_library(storage_rocksdb SHARED
|
||||
rocksdbinternals.cc
|
||||
rocksdbstorage.cc
|
||||
storage_rocksdb.cc
|
||||
)
|
||||
add_dependencies(storage_rocksdb RocksDB)
|
||||
target_link_libraries(storage_rocksdb maxscale-common ${JANSSON_LIBRARIES} ${ROCKSDB_LIB} ${ROCKSDB_LINK_LIBS} lz4)
|
||||
set_target_properties(storage_rocksdb PROPERTIES VERSION "1.0.0")
|
||||
set_target_properties(storage_rocksdb PROPERTIES LINK_FLAGS -Wl,-z,defs)
|
||||
install_module(storage_rocksdb core)
|
||||
else()
|
||||
message("RocksDB not built, storage_rocksdb cannot be built.")
|
||||
endif()
|
@ -1,47 +0,0 @@
|
||||
/*
|
||||
* Copyright (c) 2016 MariaDB Corporation Ab
|
||||
*
|
||||
* Use of this software is governed by the Business Source License included
|
||||
* in the LICENSE.TXT file and at www.mariadb.com/bsl11.
|
||||
*
|
||||
* Change Date: 2020-01-01
|
||||
*
|
||||
* On the date above, in accordance with the Business Source License, use
|
||||
* of this software will be governed by version 2 or later of the General
|
||||
* Public License.
|
||||
*/
|
||||
|
||||
#define MXS_MODULE_NAME "storage_rocksdb"
|
||||
#include "rocksdbinternals.hh"
|
||||
#include <rocksdb/env.h>
|
||||
#include <util/coding.h>
|
||||
#include <maxscale/debug.h>
|
||||
|
||||
/**
|
||||
* The following is basically a copy from RocksDB/utilities/ttl/db_ttl_impl.cc:160
|
||||
* but note that the here we claim the data is stale if we fail to get the time
|
||||
* while the original code claims it is fresh.
|
||||
*/
|
||||
bool RocksDBInternals::is_stale(const rocksdb::Slice& value, int32_t ttl, rocksdb::Env* pEnv)
|
||||
{
|
||||
if (ttl <= 0)
|
||||
{
|
||||
// Data is fresh if TTL is non-positive
|
||||
return false;
|
||||
}
|
||||
|
||||
int64_t curtime;
|
||||
if (!pEnv->GetCurrentTime(&curtime).ok())
|
||||
{
|
||||
return true; // Treat the data as stale if could not get current time
|
||||
}
|
||||
|
||||
int32_t timestamp = rocksdb::DecodeFixed32(value.data() + value.size() - TS_LENGTH);
|
||||
return (timestamp + ttl) < curtime;
|
||||
}
|
||||
|
||||
int32_t RocksDBInternals::extract_timestamp(const rocksdb::Slice& value)
|
||||
{
|
||||
ss_dassert(value.size() >= TS_LENGTH);
|
||||
return rocksdb::DecodeFixed32(value.data() + value.size() - TS_LENGTH);
|
||||
}
|
@ -1,55 +0,0 @@
|
||||
#pragma once
|
||||
/*
|
||||
* Copyright (c) 2016 MariaDB Corporation Ab
|
||||
*
|
||||
* Use of this software is governed by the Business Source License included
|
||||
* in the LICENSE.TXT file and at www.mariadb.com/bsl11.
|
||||
*
|
||||
* Change Date: 2020-01-01
|
||||
*
|
||||
* On the date above, in accordance with the Business Source License, use
|
||||
* of this software will be governed by version 2 or later of the General
|
||||
* Public License.
|
||||
*/
|
||||
|
||||
#include <maxscale/cppdefs.hh>
|
||||
#include <rocksdb/env.h>
|
||||
#include <rocksdb/version.h>
|
||||
#include <rocksdb/slice.h>
|
||||
|
||||
#if (ROCKSDB_MAJOR != 4) || (ROCKSDB_MINOR != 9)
|
||||
#error RocksDBStorage was created with knowledge of RocksDB 4.9 internals.\
|
||||
The version used is something else. Ensure the knowledge is still applicable.
|
||||
#endif
|
||||
|
||||
namespace RocksDBInternals
|
||||
{
|
||||
|
||||
/**
|
||||
* The length of the timestamp when stashed after the actual value.
|
||||
*
|
||||
* See RocksDB/utilities/ttl/db_ttl_impl.h
|
||||
*/
|
||||
static const uint32_t TS_LENGTH = sizeof(int32_t);
|
||||
|
||||
/**
|
||||
* Check whether a value is stale or not.
|
||||
*
|
||||
* @param value A value with the timestamp at the end.
|
||||
* @param ttl The time-to-live in seconds.
|
||||
* @param pEnv The used RocksDB environment instance.
|
||||
*
|
||||
* @return True of the value is stale.
|
||||
*/
|
||||
bool is_stale(const rocksdb::Slice& slice, int32_t ttl, rocksdb::Env* pEnv);
|
||||
|
||||
/**
|
||||
* Extract the timestamp from a slice coming from a rocksdb::DBWithTTL.
|
||||
*
|
||||
* @param value The slice whose timestamp should be extracted.
|
||||
*
|
||||
* @return The timestamp
|
||||
*/
|
||||
int32_t extract_timestamp(const rocksdb::Slice& value);
|
||||
|
||||
}
|
@ -1,465 +0,0 @@
|
||||
/*
|
||||
* Copyright (c) 2016 MariaDB Corporation Ab
|
||||
*
|
||||
* Use of this software is governed by the Business Source License included
|
||||
* in the LICENSE.TXT file and at www.mariadb.com/bsl11.
|
||||
*
|
||||
* Change Date: 2020-01-01
|
||||
*
|
||||
* On the date above, in accordance with the Business Source License, use
|
||||
* of this software will be governed by version 2 or later of the General
|
||||
* Public License.
|
||||
*/
|
||||
|
||||
#define MXS_MODULE_NAME "storage_rocksdb"
|
||||
#include "rocksdbstorage.hh"
|
||||
#include <sys/stat.h>
|
||||
#include <sys/types.h>
|
||||
#include <fts.h>
|
||||
#include <algorithm>
|
||||
#include <rocksdb/env.h>
|
||||
#include <rocksdb/statistics.h>
|
||||
#include <maxscale/alloc.h>
|
||||
#include <maxscale/paths.h>
|
||||
#include <maxscale/modutil.h>
|
||||
#include <maxscale/query_classifier.h>
|
||||
#include "rocksdbinternals.hh"
|
||||
|
||||
using std::for_each;
|
||||
using std::string;
|
||||
using std::unique_ptr;
|
||||
|
||||
|
||||
namespace
|
||||
{
|
||||
|
||||
// See https://github.com/facebook/rocksdb/wiki/Basic-Operations#thread-pools
|
||||
// These figures should perhaps depend upon the number of cache instances.
|
||||
const size_t ROCKSDB_N_LOW_THREADS = 2;
|
||||
const size_t ROCKSDB_N_HIGH_THREADS = 1;
|
||||
|
||||
/**
|
||||
* Deletes a path, irrespective of whether it represents a file, a directory
|
||||
* or a directory hierarchy. If the path does not exist, then the path is
|
||||
* considered to have been removed.
|
||||
*
|
||||
* @param path A path (file or directory).
|
||||
*
|
||||
* @return True if the path could be deleted, false otherwise.
|
||||
*/
|
||||
bool deletePath(const string& path)
|
||||
{
|
||||
int rv = false;
|
||||
|
||||
struct stat st;
|
||||
|
||||
if (stat(path.c_str(), &st) == -1)
|
||||
{
|
||||
if (errno == ENOENT)
|
||||
{
|
||||
rv = true;
|
||||
}
|
||||
else
|
||||
{
|
||||
MXS_ERROR("Could not stat: %s", mxs_strerror(errno));
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
MXS_NOTICE("Deleting cache storage at '%s'.", path.c_str());
|
||||
|
||||
rv = true;
|
||||
|
||||
char* files[] = { (char *) path.c_str(), NULL };
|
||||
|
||||
// FTS_NOCHDIR - Do not change CWD while traversing.
|
||||
// FTS_PHYSICAL - Don't follow symlinks.
|
||||
// FTS_XDEV - Don't cross filesystem boundaries
|
||||
FTS *pFts = fts_open(files, FTS_NOCHDIR | FTS_PHYSICAL | FTS_XDEV, NULL);
|
||||
|
||||
if (pFts)
|
||||
{
|
||||
FTSENT* pCurrent;
|
||||
while ((pCurrent = fts_read(pFts)))
|
||||
{
|
||||
switch (pCurrent->fts_info)
|
||||
{
|
||||
case FTS_NS:
|
||||
case FTS_DNR:
|
||||
case FTS_ERR:
|
||||
{
|
||||
MXS_ERROR("Error while traversing %s: %s",
|
||||
pCurrent->fts_accpath,
|
||||
mxs_strerror(pCurrent->fts_errno));
|
||||
rv = false;
|
||||
}
|
||||
break;
|
||||
|
||||
case FTS_DC:
|
||||
case FTS_DOT:
|
||||
case FTS_NSOK:
|
||||
// Not reached unless FTS_LOGICAL, FTS_SEEDOT, or FTS_NOSTAT were
|
||||
// passed to fts_open()
|
||||
break;
|
||||
|
||||
case FTS_D:
|
||||
// Do nothing. Need depth-first search, so directories are deleted
|
||||
// in FTS_DP
|
||||
break;
|
||||
|
||||
case FTS_DP:
|
||||
case FTS_F:
|
||||
case FTS_SL:
|
||||
case FTS_SLNONE:
|
||||
case FTS_DEFAULT:
|
||||
if (remove(pCurrent->fts_accpath) < 0)
|
||||
{
|
||||
MXS_ERROR("Could not remove '%s', the cache directory may need to "
|
||||
"be deleted manually: %s",
|
||||
pCurrent->fts_accpath,
|
||||
mxs_strerror(errno));
|
||||
rv = false;
|
||||
}
|
||||
break;
|
||||
|
||||
default:
|
||||
ss_dassert(!true);
|
||||
}
|
||||
}
|
||||
|
||||
if (rv)
|
||||
{
|
||||
MXS_NOTICE("Deleted cache storage at '%s'.", path.c_str());
|
||||
}
|
||||
|
||||
if (pFts)
|
||||
{
|
||||
fts_close(pFts);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return rv;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
//private
|
||||
rocksdb::WriteOptions RocksDBStorage::s_write_options;
|
||||
|
||||
//private
|
||||
RocksDBStorage::RocksDBStorage(const string& name,
|
||||
const CACHE_STORAGE_CONFIG& config,
|
||||
const string& path,
|
||||
unique_ptr<rocksdb::DBWithTTL>& sDb)
|
||||
: m_name(name)
|
||||
, m_config(config)
|
||||
, m_path(path)
|
||||
, m_sDb(std::move(sDb))
|
||||
{
|
||||
}
|
||||
|
||||
RocksDBStorage::~RocksDBStorage()
|
||||
{
|
||||
}
|
||||
|
||||
bool RocksDBStorage::Initialize(uint32_t* pCapabilities)
|
||||
{
|
||||
*pCapabilities = CACHE_STORAGE_CAP_MT;
|
||||
|
||||
auto pEnv = rocksdb::Env::Default();
|
||||
pEnv->SetBackgroundThreads(ROCKSDB_N_LOW_THREADS, rocksdb::Env::LOW);
|
||||
pEnv->SetBackgroundThreads(ROCKSDB_N_HIGH_THREADS, rocksdb::Env::HIGH);
|
||||
|
||||
// No logging; the database will always be deleted at startup, so there's
|
||||
// no reason for usinf space and processing for writing the write ahead log.
|
||||
s_write_options.disableWAL = true;
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
RocksDBStorage* RocksDBStorage::Create_instance(const char* zName,
|
||||
const CACHE_STORAGE_CONFIG& config,
|
||||
int argc, char* argv[])
|
||||
{
|
||||
ss_dassert(zName);
|
||||
|
||||
string storageDirectory = get_cachedir();
|
||||
bool collectStatistics = false;
|
||||
|
||||
for (int i = 0; i < argc; ++i)
|
||||
{
|
||||
size_t len = strlen(argv[i]);
|
||||
char arg[len + 1];
|
||||
strcpy(arg, argv[i]);
|
||||
|
||||
const char* zValue = NULL;
|
||||
char *zEq = strchr(arg, '=');
|
||||
|
||||
if (zEq)
|
||||
{
|
||||
*zEq = 0;
|
||||
zValue = trim(zEq + 1);
|
||||
}
|
||||
|
||||
const char* zKey = trim(arg);
|
||||
|
||||
if (strcmp(zKey, "cache_directory") == 0)
|
||||
{
|
||||
if (zValue)
|
||||
{
|
||||
storageDirectory = zValue;
|
||||
}
|
||||
else
|
||||
{
|
||||
MXS_WARNING("No value specified for '%s', using default '%s' instead.",
|
||||
zKey, get_cachedir());
|
||||
}
|
||||
}
|
||||
else if (strcmp(zKey, "collect_statistics") == 0)
|
||||
{
|
||||
if (zValue)
|
||||
{
|
||||
collectStatistics = config_truth_value(zValue);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
MXS_WARNING("Unknown argument '%s'.", zKey);
|
||||
}
|
||||
}
|
||||
|
||||
storageDirectory += "/storage_rocksdb";
|
||||
|
||||
return Create(zName, config, storageDirectory, collectStatistics);
|
||||
}
|
||||
|
||||
RocksDBStorage* RocksDBStorage::Create(const char* zName,
|
||||
const CACHE_STORAGE_CONFIG& config,
|
||||
const string& storageDirectory,
|
||||
bool collectStatistics)
|
||||
{
|
||||
unique_ptr<RocksDBStorage> sStorage;
|
||||
|
||||
bool ok = true;
|
||||
|
||||
if (mkdir(storageDirectory.c_str(), S_IRWXU) == 0)
|
||||
{
|
||||
MXS_NOTICE("Created storage directory %s.", storageDirectory.c_str());
|
||||
}
|
||||
else if (errno != EEXIST)
|
||||
{
|
||||
MXS_ERROR("Failed to create storage directory %s: %s",
|
||||
storageDirectory.c_str(),
|
||||
mxs_strerror(errno));
|
||||
ok = false;
|
||||
}
|
||||
|
||||
if (ok)
|
||||
{
|
||||
string path(storageDirectory + "/" + zName);
|
||||
|
||||
if (deletePath(path))
|
||||
{
|
||||
rocksdb::Options options;
|
||||
options.env = rocksdb::Env::Default();
|
||||
options.max_background_compactions = ROCKSDB_N_LOW_THREADS;
|
||||
options.max_background_flushes = ROCKSDB_N_HIGH_THREADS;
|
||||
|
||||
options.create_if_missing = true;
|
||||
options.error_if_exists = true;
|
||||
|
||||
if (collectStatistics)
|
||||
{
|
||||
options.statistics = rocksdb::CreateDBStatistics();
|
||||
}
|
||||
|
||||
rocksdb::DBWithTTL* pDb;
|
||||
rocksdb::Status status;
|
||||
|
||||
status = rocksdb::DBWithTTL::Open(options, path, &pDb, config.hard_ttl);
|
||||
|
||||
if (status.ok())
|
||||
{
|
||||
unique_ptr<rocksdb::DBWithTTL> sDb(pDb);
|
||||
|
||||
sStorage = unique_ptr<RocksDBStorage>(new RocksDBStorage(zName, config, path, sDb));
|
||||
}
|
||||
else
|
||||
{
|
||||
MXS_ERROR("Could not create RocksDB database %s. RocksDB error: \"%s\"",
|
||||
path.c_str(), status.ToString().c_str());
|
||||
|
||||
if (status.IsIOError())
|
||||
{
|
||||
MXS_ERROR("Is an other MaxScale process running?");
|
||||
}
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
MXS_ERROR("Could not delete old storage at %s.", path.c_str());
|
||||
}
|
||||
}
|
||||
|
||||
return sStorage.release();
|
||||
}
|
||||
|
||||
void RocksDBStorage::get_config(CACHE_STORAGE_CONFIG* pConfig)
|
||||
{
|
||||
*pConfig = m_config;
|
||||
}
|
||||
|
||||
cache_result_t RocksDBStorage::get_info(uint32_t what, json_t** ppInfo) const
|
||||
{
|
||||
json_t* pInfo = json_object();
|
||||
|
||||
if (pInfo)
|
||||
{
|
||||
auto sStatistics = m_sDb->GetOptions().statistics;
|
||||
|
||||
for_each(rocksdb::TickersNameMap.begin(), rocksdb::TickersNameMap.end(),
|
||||
[pInfo, sStatistics](const std::pair<rocksdb::Tickers, string>& tickerName)
|
||||
{
|
||||
json_t* pValue = json_integer(sStatistics->getTickerCount(tickerName.first));
|
||||
|
||||
if (pValue)
|
||||
{
|
||||
json_object_set(pInfo, tickerName.second.c_str(), pValue);
|
||||
json_decref(pValue);
|
||||
}
|
||||
});
|
||||
|
||||
*ppInfo = pInfo;
|
||||
}
|
||||
|
||||
return pInfo ? CACHE_RESULT_OK : CACHE_RESULT_OUT_OF_RESOURCES;
|
||||
}
|
||||
|
||||
cache_result_t RocksDBStorage::get_value(const CACHE_KEY& key, uint32_t flags, GWBUF** ppResult)
|
||||
{
|
||||
// Use the root DB so that we get the value *with* the timestamp at the end.
|
||||
rocksdb::DB* pDb = m_sDb->GetRootDB();
|
||||
rocksdb::Slice rocksdb_key(reinterpret_cast<const char*>(&key.data), sizeof(key.data));
|
||||
string value;
|
||||
|
||||
rocksdb::Status status = pDb->Get(rocksdb::ReadOptions(), rocksdb_key, &value);
|
||||
|
||||
cache_result_t result = CACHE_RESULT_ERROR;
|
||||
|
||||
switch (status.code())
|
||||
{
|
||||
case rocksdb::Status::kOk:
|
||||
if (value.length() >= RocksDBInternals::TS_LENGTH)
|
||||
{
|
||||
rocksdb::Env* pEnv = rocksdb::Env::Default();
|
||||
int64_t now;
|
||||
|
||||
if (!pEnv->GetCurrentTime(&now).ok())
|
||||
{
|
||||
ss_dassert(!true);
|
||||
now = INT64_MAX;
|
||||
}
|
||||
|
||||
int32_t timestamp = RocksDBInternals::extract_timestamp(value);
|
||||
|
||||
bool is_hard_stale = m_config.hard_ttl == 0 ? false : (now - timestamp > m_config.hard_ttl);
|
||||
bool is_soft_stale = m_config.soft_ttl == 0 ? false : (now - timestamp > m_config.soft_ttl);
|
||||
bool include_stale = ((flags & CACHE_FLAGS_INCLUDE_STALE) != 0);
|
||||
|
||||
if (is_hard_stale)
|
||||
{
|
||||
status = m_sDb->Delete(Write_options(), rocksdb_key);
|
||||
|
||||
if (!status.ok())
|
||||
{
|
||||
MXS_WARNING("Failed when deleting stale item from RocksDB.");
|
||||
}
|
||||
result = CACHE_RESULT_NOT_FOUND;
|
||||
}
|
||||
else if (!is_soft_stale || include_stale)
|
||||
{
|
||||
size_t length = value.length() - RocksDBInternals::TS_LENGTH;
|
||||
|
||||
*ppResult = gwbuf_alloc(length);
|
||||
|
||||
if (*ppResult)
|
||||
{
|
||||
memcpy(GWBUF_DATA(*ppResult), value.data(), length);
|
||||
|
||||
result = CACHE_RESULT_OK;
|
||||
|
||||
if (is_soft_stale)
|
||||
{
|
||||
result |= CACHE_RESULT_STALE;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
result = CACHE_RESULT_OUT_OF_RESOURCES;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
ss_dassert(is_soft_stale);
|
||||
result = (CACHE_RESULT_NOT_FOUND | CACHE_RESULT_STALE);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
MXS_ERROR("RocksDB value too short. Database corrupted?");
|
||||
result = CACHE_RESULT_ERROR;
|
||||
}
|
||||
break;
|
||||
|
||||
case rocksdb::Status::kNotFound:
|
||||
result = CACHE_RESULT_NOT_FOUND;
|
||||
break;
|
||||
|
||||
default:
|
||||
MXS_ERROR("Failed to look up value: %s", status.ToString().c_str());
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
cache_result_t RocksDBStorage::put_value(const CACHE_KEY& key, const GWBUF& value)
|
||||
{
|
||||
ss_dassert(GWBUF_IS_CONTIGUOUS(&value));
|
||||
|
||||
rocksdb::Slice rocksdb_key(reinterpret_cast<const char*>(&key.data), sizeof(key.data));
|
||||
rocksdb::Slice rocksdb_value((char*)GWBUF_DATA(&value), GWBUF_LENGTH(&value));
|
||||
|
||||
rocksdb::Status status = m_sDb->Put(Write_options(), rocksdb_key, rocksdb_value);
|
||||
|
||||
return status.ok() ? CACHE_RESULT_OK : CACHE_RESULT_ERROR;
|
||||
}
|
||||
|
||||
cache_result_t RocksDBStorage::del_value(const CACHE_KEY& key)
|
||||
{
|
||||
rocksdb::Slice rocksdb_key(reinterpret_cast<const char*>(&key.data), sizeof(key.data));
|
||||
|
||||
rocksdb::Status status = m_sDb->Delete(Write_options(), rocksdb_key);
|
||||
|
||||
return status.ok() ? CACHE_RESULT_OK : CACHE_RESULT_ERROR;
|
||||
}
|
||||
|
||||
cache_result_t RocksDBStorage::get_head(CACHE_KEY* pKey, GWBUF** ppHead) const
|
||||
{
|
||||
return CACHE_RESULT_OUT_OF_RESOURCES;
|
||||
}
|
||||
|
||||
cache_result_t RocksDBStorage::get_tail(CACHE_KEY* pKey, GWBUF** ppHead) const
|
||||
{
|
||||
return CACHE_RESULT_OUT_OF_RESOURCES;
|
||||
}
|
||||
|
||||
cache_result_t RocksDBStorage::get_size(uint64_t* pSize) const
|
||||
{
|
||||
return CACHE_RESULT_OUT_OF_RESOURCES;
|
||||
}
|
||||
|
||||
cache_result_t RocksDBStorage::get_items(uint64_t* pItems) const
|
||||
{
|
||||
return CACHE_RESULT_OUT_OF_RESOURCES;
|
||||
}
|
@ -1,70 +0,0 @@
|
||||
#pragma once
|
||||
/*
|
||||
* Copyright (c) 2016 MariaDB Corporation Ab
|
||||
*
|
||||
* Use of this software is governed by the Business Source License included
|
||||
* in the LICENSE.TXT file and at www.mariadb.com/bsl11.
|
||||
*
|
||||
* Change Date: 2020-01-01
|
||||
*
|
||||
* On the date above, in accordance with the Business Source License, use
|
||||
* of this software will be governed by version 2 or later of the General
|
||||
* Public License.
|
||||
*/
|
||||
|
||||
#include <maxscale/cppdefs.hh>
|
||||
#include <memory>
|
||||
#include <string>
|
||||
#include <rocksdb/utilities/db_ttl.h>
|
||||
#include "../../cache_storage_api.h"
|
||||
|
||||
class RocksDBStorage
|
||||
{
|
||||
public:
|
||||
typedef std::unique_ptr<RocksDBStorage> SRocksDBStorage;
|
||||
|
||||
static bool Initialize(uint32_t* pCapabilities);
|
||||
|
||||
static RocksDBStorage* Create_instance(const char* zName,
|
||||
const CACHE_STORAGE_CONFIG& config,
|
||||
int argc, char* argv[]);
|
||||
~RocksDBStorage();
|
||||
|
||||
void get_config(CACHE_STORAGE_CONFIG* pConfig);
|
||||
cache_result_t get_info(uint32_t flags, json_t** ppInfo) const;
|
||||
cache_result_t get_value(const CACHE_KEY& key, uint32_t flags, GWBUF** ppResult);
|
||||
cache_result_t put_value(const CACHE_KEY& key, const GWBUF& value);
|
||||
cache_result_t del_value(const CACHE_KEY& key);
|
||||
|
||||
cache_result_t get_head(CACHE_KEY* pKey, GWBUF** ppHead) const;
|
||||
cache_result_t get_tail(CACHE_KEY* pKey, GWBUF** ppHead) const;
|
||||
cache_result_t get_size(uint64_t* pSize) const;
|
||||
cache_result_t get_items(uint64_t* pItems) const;
|
||||
|
||||
private:
|
||||
RocksDBStorage(const std::string& name,
|
||||
const CACHE_STORAGE_CONFIG& config,
|
||||
const std::string& path,
|
||||
std::unique_ptr<rocksdb::DBWithTTL>& sDb);
|
||||
|
||||
RocksDBStorage(const RocksDBStorage&) = delete;
|
||||
RocksDBStorage& operator = (const RocksDBStorage&) = delete;
|
||||
|
||||
static RocksDBStorage* Create(const char* zName,
|
||||
const CACHE_STORAGE_CONFIG& config,
|
||||
const std::string& storage_directory,
|
||||
bool collect_statistics);
|
||||
|
||||
static const rocksdb::WriteOptions& Write_options()
|
||||
{
|
||||
return s_write_options;
|
||||
}
|
||||
|
||||
private:
|
||||
std::string m_name;
|
||||
const CACHE_STORAGE_CONFIG m_config;
|
||||
std::string m_path;
|
||||
std::unique_ptr<rocksdb::DBWithTTL> m_sDb;
|
||||
|
||||
static rocksdb::WriteOptions s_write_options;
|
||||
};
|
@ -1,29 +0,0 @@
|
||||
/*
|
||||
* Copyright (c) 2016 MariaDB Corporation Ab
|
||||
*
|
||||
* Use of this software is governed by the Business Source License included
|
||||
* in the LICENSE.TXT file and at www.mariadb.com/bsl11.
|
||||
*
|
||||
* Change Date: 2020-01-01
|
||||
*
|
||||
* On the date above, in accordance with the Business Source License, use
|
||||
* of this software will be governed by version 2 or later of the General
|
||||
* Public License.
|
||||
*/
|
||||
|
||||
#define MXS_MODULE_NAME "storage_rocksdb"
|
||||
#include <maxscale/cppdefs.hh>
|
||||
#include "../../cache_storage_api.h"
|
||||
#include "../storagemodule.hh"
|
||||
#include "rocksdbstorage.hh"
|
||||
|
||||
|
||||
extern "C"
|
||||
{
|
||||
|
||||
CACHE_STORAGE_API* CacheGetStorageAPI()
|
||||
{
|
||||
return &StorageModule<RocksDBStorage>::s_api;
|
||||
}
|
||||
|
||||
}
|
@ -46,14 +46,11 @@ target_link_libraries(test_cacheoptions maxscale-common)
|
||||
add_test(TestCache_rules testrules)
|
||||
|
||||
add_test(TestCache_inmemory_keygeneration testkeygeneration storage_inmemory ${CMAKE_CURRENT_SOURCE_DIR}/input.test)
|
||||
#add_test(TestCache_rocksdb_keygeneration testkeygeneration storage_rocksdb ${CMAKE_CURRENT_SOURCE_DIR}/input.test)
|
||||
|
||||
#usage: testrawstorage storage-module [threads [time [items [min-size [max-size]]]]]\n"
|
||||
add_test(TestCache_storage_inmemory testrawstorage storage_inmemory 0 10 1000 1024 1024000)
|
||||
#add_test(TestCache_storage_rocksdb testrawstorage storage_rocksdb 0 10 1000 1024 1024000)
|
||||
|
||||
#usage: testlrustorage storage-module [threads [time [items [min-size [max-size]]]]]\n"
|
||||
add_test(TestCache_lru_inmemory testlrustorage storage_inmemory 0 10 1000 1024 1024000)
|
||||
#add_test(TestCache_lru_rocksdb testlrustorage storage_rocksdb 0 10 1000 1024 1024000)
|
||||
|
||||
add_test(TestCache_options test_cacheoptions)
|
||||
|
Reference in New Issue
Block a user