diff --git a/mdbx.h++ b/mdbx.h++ index fd07c123..e8a58bfe 100644 --- a/mdbx.h++ +++ b/mdbx.h++ @@ -4353,6 +4353,37 @@ public: bool rename_map(const ::std::string &old_name, const ::std::string &new_name, bool throw_if_absent = false); +#if defined(DOXYGEN) || \ + (defined(__cpp_lib_string_view) && __cpp_lib_string_view >= 201606L) + + /// \brief Open existing key-value map. + inline map_handle open_map( + const ::std::string_view &name, + const ::mdbx::key_mode key_mode = ::mdbx::key_mode::usual, + const ::mdbx::value_mode value_mode = ::mdbx::value_mode::single) const; + /// \brief Create new or open existing key-value map. + inline map_handle + create_map(const ::std::string_view &name, + const ::mdbx::key_mode key_mode = ::mdbx::key_mode::usual, + const ::mdbx::value_mode value_mode = ::mdbx::value_mode::single); + /// \brief Drop key-value map. + /// \return `True` if the key-value map existed and was deleted, either + /// `false` if the key-value map did not exist and there is nothing to delete. + bool drop_map(const ::std::string_view &name, bool throw_if_absent = false); + /// \return `True` if the key-value map existed and was cleared, either + /// `false` if the key-value map did not exist and there is nothing to clear. + bool clear_map(const ::std::string_view &name, bool throw_if_absent = false); + /// \brief Переименовывает таблицу ключ-значение. + inline void rename_map(map_handle map, const ::std::string_view &new_name); + /// \brief Переименовывает таблицу ключ-значение. + /// \return `True` если таблица существует и была переименована, либо + /// `false` в случае отсутствия исходной таблицы. + bool rename_map(const ::std::string_view &old_name, + const ::std::string_view &new_name, + bool throw_if_absent = false); + +#endif /* __cpp_lib_string_view >= 201606L */ + using map_stat = ::MDBX_stat; /// \brief Returns statistics for a sub-database. inline map_stat get_map_stat(map_handle map) const; @@ -6294,12 +6325,6 @@ txn::open_map(const char *name, const ::mdbx::key_mode key_mode, return map; } -inline ::mdbx::map_handle -txn::open_map(const ::std::string &name, const ::mdbx::key_mode key_mode, - const ::mdbx::value_mode value_mode) const { - return open_map(name.c_str(), key_mode, value_mode); -} - inline ::mdbx::map_handle txn::create_map(const char *name, const ::mdbx::key_mode key_mode, const ::mdbx::value_mode value_mode) { @@ -6312,36 +6337,102 @@ inline ::mdbx::map_handle txn::create_map(const char *name, return map; } -inline ::mdbx::map_handle txn::create_map(const ::std::string &name, - const ::mdbx::key_mode key_mode, - const ::mdbx::value_mode value_mode) { - return create_map(name.c_str(), key_mode, value_mode); -} - inline void txn::drop_map(map_handle map) { error::success_or_throw(::mdbx_drop(handle_, map.dbi, true)); } -inline bool txn::drop_map(const ::std::string &name, bool throw_if_absent) { - return drop_map(name.c_str(), throw_if_absent); -} - inline void txn::clear_map(map_handle map) { error::success_or_throw(::mdbx_drop(handle_, map.dbi, false)); } -inline bool txn::clear_map(const ::std::string &name, bool throw_if_absent) { - return clear_map(name.c_str(), throw_if_absent); -} - inline void txn::rename_map(map_handle map, const char *new_name) { error::success_or_throw(::mdbx_dbi_rename(handle_, map, new_name)); } +#if defined(DOXYGEN) || \ + (defined(__cpp_lib_string_view) && __cpp_lib_string_view >= 201606L) + +inline ::mdbx::map_handle +txn::open_map(const ::std::string_view &name, const ::mdbx::key_mode key_mode, + const ::mdbx::value_mode value_mode) const { + ::mdbx::map_handle map; + error::success_or_throw(::mdbx_dbi_open2( + handle_, ::mdbx::slice(name), + MDBX_db_flags_t(key_mode) | MDBX_db_flags_t(value_mode), &map.dbi)); + assert(map.dbi != 0); + return map; +} + +inline ::mdbx::map_handle txn::create_map(const ::std::string_view &name, + const ::mdbx::key_mode key_mode, + const ::mdbx::value_mode value_mode) { + ::mdbx::map_handle map; + error::success_or_throw(::mdbx_dbi_open2( + handle_, ::mdbx::slice(name), + MDBX_CREATE | MDBX_db_flags_t(key_mode) | MDBX_db_flags_t(value_mode), + &map.dbi)); + assert(map.dbi != 0); + return map; +} + +inline void txn::rename_map(map_handle map, + const ::std::string_view &new_name) { + error::success_or_throw( + ::mdbx_dbi_rename2(handle_, map, ::mdbx::slice(new_name))); +} + +inline ::mdbx::map_handle +txn::open_map(const ::std::string &name, const ::mdbx::key_mode key_mode, + const ::mdbx::value_mode value_mode) const { + return open_map(::std::string_view(name), key_mode, value_mode); +} + +inline ::mdbx::map_handle txn::create_map(const ::std::string &name, + const ::mdbx::key_mode key_mode, + const ::mdbx::value_mode value_mode) { + return create_map(::std::string_view(name), key_mode, value_mode); +} + +inline bool txn::drop_map(const ::std::string &name, bool throw_if_absent) { + return drop_map(::std::string_view(name), throw_if_absent); +} + +inline bool txn::clear_map(const ::std::string &name, bool throw_if_absent) { + return clear_map(::std::string_view(name), throw_if_absent); +} + +inline void txn::rename_map(map_handle map, const ::std::string &new_name) { + return rename_map(map, ::std::string_view(new_name)); +} + +#else + +inline ::mdbx::map_handle +txn::open_map(const ::std::string &name, const ::mdbx::key_mode key_mode, + const ::mdbx::value_mode value_mode) const { + return open_map(name.c_str(), key_mode, value_mode); +} + +inline ::mdbx::map_handle txn::create_map(const ::std::string &name, + const ::mdbx::key_mode key_mode, + const ::mdbx::value_mode value_mode) { + return create_map(name.c_str(), key_mode, value_mode); +} + +inline bool txn::drop_map(const ::std::string &name, bool throw_if_absent) { + return drop_map(name.c_str(), throw_if_absent); +} + +inline bool txn::clear_map(const ::std::string &name, bool throw_if_absent) { + return clear_map(name.c_str(), throw_if_absent); +} + inline void txn::rename_map(map_handle map, const ::std::string &new_name) { return rename_map(map, new_name.c_str()); } +#endif /* __cpp_lib_string_view >= 201606L */ + inline txn::map_stat txn::get_map_stat(map_handle map) const { txn::map_stat r; error::success_or_throw(::mdbx_dbi_stat(handle_, map.dbi, &r, sizeof(r))); diff --git a/src/mdbx.c++ b/src/mdbx.c++ index 01334c5c..28977e42 100644 --- a/src/mdbx.c++ +++ b/src/mdbx.c++ @@ -1605,12 +1605,83 @@ __cold bool txn::rename_map(const char *old_name, const char *new_name, } } +#if defined(__cpp_lib_string_view) && __cpp_lib_string_view >= 201606L + +__cold bool txn::drop_map(const ::std::string_view &name, + bool throw_if_absent) { + map_handle map; + const int err = + ::mdbx_dbi_open2(handle_, mdbx::slice(name), MDBX_DB_ACCEDE, &map.dbi); + switch (err) { + case MDBX_SUCCESS: + drop_map(map); + return true; + case MDBX_NOTFOUND: + case MDBX_BAD_DBI: + if (!throw_if_absent) + return false; + MDBX_CXX17_FALLTHROUGH /* fallthrough */; + default: + MDBX_CXX20_UNLIKELY error::throw_exception(err); + } +} + +__cold bool txn::clear_map(const ::std::string_view &name, + bool throw_if_absent) { + map_handle map; + const int err = + ::mdbx_dbi_open2(handle_, mdbx::slice(name), MDBX_DB_ACCEDE, &map.dbi); + switch (err) { + case MDBX_SUCCESS: + clear_map(map); + return true; + case MDBX_NOTFOUND: + case MDBX_BAD_DBI: + if (!throw_if_absent) + return false; + MDBX_CXX17_FALLTHROUGH /* fallthrough */; + default: + MDBX_CXX20_UNLIKELY error::throw_exception(err); + } +} + +__cold bool txn::rename_map(const ::std::string_view &old_name, + const ::std::string_view &new_name, + bool throw_if_absent) { + map_handle map; + const int err = ::mdbx_dbi_open2(handle_, mdbx::slice(old_name), + MDBX_DB_ACCEDE, &map.dbi); + switch (err) { + case MDBX_SUCCESS: + rename_map(map, new_name); + return true; + case MDBX_NOTFOUND: + case MDBX_BAD_DBI: + if (!throw_if_absent) + return false; + MDBX_CXX17_FALLTHROUGH /* fallthrough */; + default: + MDBX_CXX20_UNLIKELY error::throw_exception(err); + } +} + +__cold bool txn::rename_map(const ::std::string &old_name, + const ::std::string &new_name, + bool throw_if_absent) { + return rename_map(::std::string_view(old_name), ::std::string_view(new_name), + throw_if_absent); +} + +#else + __cold bool txn::rename_map(const ::std::string &old_name, const ::std::string &new_name, bool throw_if_absent) { return rename_map(old_name.c_str(), new_name.c_str(), throw_if_absent); } +#endif /* __cpp_lib_string_view >= 201606L */ + //------------------------------------------------------------------------------ void cursor_managed::close() {