mirror of https://gitee.com/bigwinds/arangodb
unshapified VocBase/auth. Also replaced TRI_AssociativeList with an unordered_map.
This commit is contained in:
parent
d2febf9a58
commit
56f0e927cf
|
@ -25,14 +25,11 @@
|
||||||
#include "Basics/Logger.h"
|
#include "Basics/Logger.h"
|
||||||
#include "Basics/tri-strings.h"
|
#include "Basics/tri-strings.h"
|
||||||
#include "Basics/WriteLocker.h"
|
#include "Basics/WriteLocker.h"
|
||||||
#include "Indexes/PrimaryIndex.h"
|
|
||||||
#include "Rest/SslInterface.h"
|
#include "Rest/SslInterface.h"
|
||||||
#include "Utils/transactions.h"
|
#include "Utils/transactions.h"
|
||||||
#include "VocBase/collection.h"
|
#include "VocBase/collection.h"
|
||||||
#include "VocBase/document-collection.h"
|
#include "VocBase/document-collection.h"
|
||||||
#include "VocBase/shape-accessor.h"
|
|
||||||
#include "VocBase/vocbase.h"
|
#include "VocBase/vocbase.h"
|
||||||
#include "VocBase/VocShaper.h"
|
|
||||||
|
|
||||||
#include <velocypack/Iterator.h>
|
#include <velocypack/Iterator.h>
|
||||||
#include <velocypack/velocypack-aliases.h>
|
#include <velocypack/velocypack-aliases.h>
|
||||||
|
@ -49,27 +46,6 @@ static uint64_t HashKey(TRI_associative_pointer_t* array, void const* key) {
|
||||||
return TRI_FnvHashString(k);
|
return TRI_FnvHashString(k);
|
||||||
}
|
}
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @brief hashes the auth info
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
static uint64_t HashElementAuthInfo(TRI_associative_pointer_t* array,
|
|
||||||
void const* element) {
|
|
||||||
VocbaseAuthInfo const* e = static_cast<VocbaseAuthInfo const*>(element);
|
|
||||||
return e->hash();
|
|
||||||
}
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @brief compares an auth info and a username
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
static bool EqualKeyAuthInfo(TRI_associative_pointer_t* array, void const* key,
|
|
||||||
void const* element) {
|
|
||||||
char const* k = (char const*)key;
|
|
||||||
VocbaseAuthInfo const* e = static_cast<VocbaseAuthInfo const*>(element);
|
|
||||||
return e->isEqualName(k);
|
|
||||||
}
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////////////////////////
|
||||||
/// @brief hashes the cache entry
|
/// @brief hashes the cache entry
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////////////////////////
|
||||||
|
@ -181,33 +157,13 @@ static VocbaseAuthInfo* AuthFromVelocyPack(VPackSlice const& slice) {
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
static VocbaseAuthInfo* ConvertAuthInfo(TRI_vocbase_t* vocbase,
|
static VocbaseAuthInfo* ConvertAuthInfo(TRI_vocbase_t* vocbase,
|
||||||
TRI_document_collection_t* document,
|
|
||||||
TRI_doc_mptr_t const* mptr) {
|
TRI_doc_mptr_t const* mptr) {
|
||||||
auto shaper =
|
|
||||||
document->getShaper(); // PROTECTED by trx in caller, checked by RUNTIME
|
|
||||||
|
|
||||||
TRI_shaped_json_t shapedJson;
|
VPackSlice slice(mptr->vpack());
|
||||||
TRI_EXTRACT_SHAPED_JSON_MARKER(
|
if (slice.isNone()) {
|
||||||
shapedJson, mptr->getDataPtr()); // ONLY IN INDEX, PROTECTED by RUNTIME
|
|
||||||
|
|
||||||
if (shapedJson._sid == TRI_SHAPE_ILLEGAL) {
|
|
||||||
return nullptr;
|
return nullptr;
|
||||||
}
|
}
|
||||||
|
std::unique_ptr<VocbaseAuthInfo> auth(AuthFromVelocyPack(slice));
|
||||||
std::unique_ptr<TRI_json_t> json(TRI_JsonShapedJson(shaper, &shapedJson));
|
|
||||||
|
|
||||||
if (json == nullptr) {
|
|
||||||
return nullptr;
|
|
||||||
}
|
|
||||||
|
|
||||||
std::shared_ptr<VPackBuilder> parsed =
|
|
||||||
arangodb::basics::JsonHelper::toVelocyPack(json.get());
|
|
||||||
|
|
||||||
if (parsed == nullptr) {
|
|
||||||
return nullptr;
|
|
||||||
}
|
|
||||||
|
|
||||||
std::unique_ptr<VocbaseAuthInfo> auth(AuthFromVelocyPack(parsed->slice()));
|
|
||||||
return auth.release(); // maybe a nullptr
|
return auth.release(); // maybe a nullptr
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -219,24 +175,18 @@ static VocbaseAuthInfo* ConvertAuthInfo(TRI_vocbase_t* vocbase,
|
||||||
|
|
||||||
static void ClearAuthInfo(TRI_vocbase_t* vocbase) {
|
static void ClearAuthInfo(TRI_vocbase_t* vocbase) {
|
||||||
// clear auth info table
|
// clear auth info table
|
||||||
void** beg = vocbase->_authInfo._table;
|
for (auto& it : vocbase->_authInfo) {
|
||||||
void** end = vocbase->_authInfo._table + vocbase->_authInfo._nrAlloc;
|
if (it.second != nullptr) {
|
||||||
void** ptr = beg;
|
delete it.second;
|
||||||
|
it.second = nullptr;
|
||||||
for (; ptr < end; ++ptr) {
|
|
||||||
if (*ptr) {
|
|
||||||
VocbaseAuthInfo* auth = static_cast<VocbaseAuthInfo*>(*ptr);
|
|
||||||
delete auth;
|
|
||||||
*ptr = nullptr;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
vocbase->_authInfo.clear();
|
||||||
vocbase->_authInfo._nrUsed = 0;
|
|
||||||
|
|
||||||
// clear cache
|
// clear cache
|
||||||
beg = vocbase->_authCache._table;
|
void** beg = vocbase->_authCache._table;
|
||||||
end = vocbase->_authCache._table + vocbase->_authCache._nrAlloc;
|
void** end = vocbase->_authCache._table + vocbase->_authCache._nrAlloc;
|
||||||
ptr = beg;
|
void** ptr = beg;
|
||||||
|
|
||||||
for (; ptr < end; ++ptr) {
|
for (; ptr < end; ++ptr) {
|
||||||
if (*ptr) {
|
if (*ptr) {
|
||||||
|
@ -282,9 +232,6 @@ bool VocbaseAuthInfo::mustChange() const { return _mustChange; }
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
int TRI_InitAuthInfo(TRI_vocbase_t* vocbase) {
|
int TRI_InitAuthInfo(TRI_vocbase_t* vocbase) {
|
||||||
TRI_InitAssociativePointer(&vocbase->_authInfo, TRI_CORE_MEM_ZONE, HashKey,
|
|
||||||
HashElementAuthInfo, EqualKeyAuthInfo, nullptr);
|
|
||||||
|
|
||||||
TRI_InitAssociativePointer(&vocbase->_authCache, TRI_CORE_MEM_ZONE, HashKey,
|
TRI_InitAssociativePointer(&vocbase->_authCache, TRI_CORE_MEM_ZONE, HashKey,
|
||||||
HashElementAuthCache, EqualKeyAuthCache, nullptr);
|
HashElementAuthCache, EqualKeyAuthCache, nullptr);
|
||||||
|
|
||||||
|
@ -299,7 +246,6 @@ void TRI_DestroyAuthInfo(TRI_vocbase_t* vocbase) {
|
||||||
TRI_ClearAuthInfo(vocbase);
|
TRI_ClearAuthInfo(vocbase);
|
||||||
|
|
||||||
TRI_DestroyAssociativePointer(&vocbase->_authCache);
|
TRI_DestroyAssociativePointer(&vocbase->_authCache);
|
||||||
TRI_DestroyAssociativePointer(&vocbase->_authInfo);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////////////////////////
|
||||||
|
@ -362,29 +308,23 @@ bool TRI_LoadAuthInfo(TRI_vocbase_t* vocbase) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
TRI_document_collection_t* document = trx.documentCollection();
|
|
||||||
|
|
||||||
{
|
ClearAuthInfo(vocbase);
|
||||||
WRITE_LOCKER(writeLocker, vocbase->_authInfoLock);
|
auto work = [&](TRI_doc_mptr_t const* ptr) -> void {
|
||||||
|
std::unique_ptr<VocbaseAuthInfo> auth(
|
||||||
|
ConvertAuthInfo(vocbase, ptr));
|
||||||
|
if (auth != nullptr) {
|
||||||
|
VocbaseAuthInfo* old = vocbase->_authInfo.at(auth->username());
|
||||||
|
|
||||||
ClearAuthInfo(vocbase);
|
if (old != nullptr) {
|
||||||
auto work = [&](TRI_doc_mptr_t const* ptr) -> void {
|
delete old;
|
||||||
std::unique_ptr<VocbaseAuthInfo> auth(
|
|
||||||
ConvertAuthInfo(vocbase, document, ptr));
|
|
||||||
if (auth != nullptr) {
|
|
||||||
VocbaseAuthInfo* old =
|
|
||||||
static_cast<VocbaseAuthInfo*>(TRI_InsertKeyAssociativePointer(
|
|
||||||
&vocbase->_authInfo, auth->username(), auth.get(), true));
|
|
||||||
auth.release();
|
|
||||||
|
|
||||||
if (old != nullptr) {
|
|
||||||
delete old;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
};
|
vocbase->_authInfo.erase(auth->username());
|
||||||
|
auth.release();
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
document->primaryIndex()->invokeOnAllElements(work);
|
trx.invokeOnAllElements(collection->_name, work);
|
||||||
}
|
|
||||||
|
|
||||||
trx.finish(TRI_ERROR_NO_ERROR);
|
trx.finish(TRI_ERROR_NO_ERROR);
|
||||||
|
|
||||||
|
@ -406,8 +346,10 @@ bool TRI_PopulateAuthInfo(TRI_vocbase_t* vocbase, VPackSlice const& slice) {
|
||||||
std::unique_ptr<VocbaseAuthInfo> auth(AuthFromVelocyPack(authSlice));
|
std::unique_ptr<VocbaseAuthInfo> auth(AuthFromVelocyPack(authSlice));
|
||||||
|
|
||||||
if (auth != nullptr) {
|
if (auth != nullptr) {
|
||||||
TRI_InsertKeyAssociativePointer(&vocbase->_authInfo, auth->username(),
|
auto it = vocbase->_authInfo.find(auth->username());
|
||||||
auth.get(), false);
|
if (it == vocbase->_authInfo.end()) {
|
||||||
|
vocbase->_authInfo.emplace(auth->username(), auth.get());
|
||||||
|
}
|
||||||
auth.release();
|
auth.release();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -469,10 +411,13 @@ bool TRI_ExistsAuthenticationAuthInfo(TRI_vocbase_t* vocbase,
|
||||||
// look up username
|
// look up username
|
||||||
READ_LOCKER(readLocker, vocbase->_authInfoLock);
|
READ_LOCKER(readLocker, vocbase->_authInfoLock);
|
||||||
|
|
||||||
// We do not take responsiblity for the data
|
auto it = vocbase->_authInfo.find(username);
|
||||||
VocbaseAuthInfo* auth = static_cast<VocbaseAuthInfo*>(
|
if (it == vocbase->_authInfo.end()) {
|
||||||
TRI_LookupByKeyAssociativePointer(&vocbase->_authInfo, username));
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
// We do not take responsiblity for the data
|
||||||
|
VocbaseAuthInfo* auth = it->second;
|
||||||
return (auth != nullptr && auth->isActive());
|
return (auth != nullptr && auth->isActive());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -491,9 +436,13 @@ bool TRI_CheckAuthenticationAuthInfo(TRI_vocbase_t* vocbase, char const* hash,
|
||||||
// look up username
|
// look up username
|
||||||
READ_LOCKER(readLocker, vocbase->_authInfoLock);
|
READ_LOCKER(readLocker, vocbase->_authInfoLock);
|
||||||
|
|
||||||
// We do not take responsibilty for the data
|
auto it = vocbase->_authInfo.find(username);
|
||||||
auth = static_cast<VocbaseAuthInfo*>(
|
if (it == vocbase->_authInfo.end()) {
|
||||||
TRI_LookupByKeyAssociativePointer(&vocbase->_authInfo, username));
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
// We do not take responsiblity for the data
|
||||||
|
auth = it->second;
|
||||||
|
|
||||||
if (auth == nullptr || !auth->isActive()) {
|
if (auth == nullptr || !auth->isActive()) {
|
||||||
return false;
|
return false;
|
||||||
|
|
|
@ -32,7 +32,6 @@ namespace arangodb {
|
||||||
namespace velocypack {
|
namespace velocypack {
|
||||||
class Slice;
|
class Slice;
|
||||||
}
|
}
|
||||||
}
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////////////////////////
|
||||||
/// @brief authentication and authorization
|
/// @brief authentication and authorization
|
||||||
|
@ -86,6 +85,7 @@ class VocbaseAuthInfo {
|
||||||
bool mustChange() const;
|
bool mustChange() const;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
}
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////////////////////////
|
||||||
/// @brief header to username cache
|
/// @brief header to username cache
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
|
@ -48,6 +48,7 @@ class Builder;
|
||||||
namespace aql {
|
namespace aql {
|
||||||
class QueryList;
|
class QueryList;
|
||||||
}
|
}
|
||||||
|
class VocbaseAuthInfo;
|
||||||
class VocbaseCollectionInfo;
|
class VocbaseCollectionInfo;
|
||||||
class CollectionKeysRepository;
|
class CollectionKeysRepository;
|
||||||
class CursorRepository;
|
class CursorRepository;
|
||||||
|
@ -267,7 +268,7 @@ struct TRI_vocbase_t {
|
||||||
arangodb::CursorRepository* _cursorRepository;
|
arangodb::CursorRepository* _cursorRepository;
|
||||||
arangodb::CollectionKeysRepository* _collectionKeys;
|
arangodb::CollectionKeysRepository* _collectionKeys;
|
||||||
|
|
||||||
TRI_associative_pointer_t _authInfo;
|
std::unordered_map<std::string, arangodb::VocbaseAuthInfo*> _authInfo;
|
||||||
TRI_associative_pointer_t _authCache;
|
TRI_associative_pointer_t _authCache;
|
||||||
arangodb::basics::ReadWriteLock _authInfoLock;
|
arangodb::basics::ReadWriteLock _authInfoLock;
|
||||||
bool _authInfoLoaded; // flag indicating whether the authentication info was
|
bool _authInfoLoaded; // flag indicating whether the authentication info was
|
||||||
|
|
Loading…
Reference in New Issue