mirror of https://gitee.com/bigwinds/arangodb
cleanup action queues
This commit is contained in:
parent
888436b95d
commit
b2d521ee35
|
@ -3154,6 +3154,8 @@ unittests-shell-client:
|
|||
kill `cat $(PIDFILE)`
|
||||
while test -f $(PIDFILE); do sleep 1; done
|
||||
|
||||
@if [ "$(VALGRIND)" != "" ]; then sleep 60; fi
|
||||
|
||||
@rm -rf "$(VOCDIR)"
|
||||
|
||||
@echo
|
||||
|
|
|
@ -239,6 +239,8 @@ unittests-shell-client:
|
|||
kill `cat $(PIDFILE)`
|
||||
while test -f $(PIDFILE); do sleep 1; done
|
||||
|
||||
@if [ "$(VALGRIND)" != "" ]; then sleep 60; fi
|
||||
|
||||
@rm -rf "$(VOCDIR)"
|
||||
|
||||
@echo
|
||||
|
|
|
@ -50,10 +50,10 @@ using namespace triagens::arango;
|
|||
/// @brief constructor
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
RestActionHandler::RestActionHandler (HttpRequest* request, pair<TRI_vocbase_t*, set<string>*>* data)
|
||||
: RestVocbaseBaseHandler(request, data->first),
|
||||
RestActionHandler::RestActionHandler (HttpRequest* request, action_options_t* data)
|
||||
: RestVocbaseBaseHandler(request, data->_vocbase),
|
||||
_action(0),
|
||||
_allowedQueues(*data->second) {
|
||||
_queue(data->_queue) {
|
||||
_action = TRI_LookupActionVocBase(request);
|
||||
}
|
||||
|
||||
|
@ -83,9 +83,7 @@ bool RestActionHandler::isDirect () {
|
|||
////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
string const& RestActionHandler::queue () {
|
||||
static string const standard = "STANDARD";
|
||||
|
||||
return _action == 0 ? standard : _action->_queue;
|
||||
return _queue;
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
|
@ -110,50 +108,34 @@ HttpHandler::status_e RestActionHandler::execute () {
|
|||
}
|
||||
else {
|
||||
|
||||
// check the permission base on queue name
|
||||
bool allowed = false;
|
||||
|
||||
for (set<string>::iterator i = _allowedQueues.begin(); i != _allowedQueues.end(); ++i) {
|
||||
if (_action->_queue == *i) {
|
||||
allowed = true;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (! allowed) {
|
||||
generateForbidden();
|
||||
}
|
||||
else {
|
||||
|
||||
// extract the sub-request type
|
||||
HttpRequest::HttpRequestType type = request->requestType();
|
||||
// extract the sub-request type
|
||||
HttpRequest::HttpRequestType type = request->requestType();
|
||||
|
||||
// prepare logging
|
||||
switch (type) {
|
||||
case HttpRequest::HTTP_REQUEST_DELETE: task = &logExecute; break;
|
||||
case HttpRequest::HTTP_REQUEST_GET: task = &logExecute; break;
|
||||
case HttpRequest::HTTP_REQUEST_POST: task = &logExecute; break;
|
||||
case HttpRequest::HTTP_REQUEST_PUT: task = &logExecute; break;
|
||||
case HttpRequest::HTTP_REQUEST_HEAD: task = &logHead; break;
|
||||
case HttpRequest::HTTP_REQUEST_ILLEGAL: task = &logIllegal; break;
|
||||
}
|
||||
// prepare logging
|
||||
switch (type) {
|
||||
case HttpRequest::HTTP_REQUEST_DELETE: task = &logExecute; break;
|
||||
case HttpRequest::HTTP_REQUEST_GET: task = &logExecute; break;
|
||||
case HttpRequest::HTTP_REQUEST_POST: task = &logExecute; break;
|
||||
case HttpRequest::HTTP_REQUEST_PUT: task = &logExecute; break;
|
||||
case HttpRequest::HTTP_REQUEST_HEAD: task = &logHead; break;
|
||||
case HttpRequest::HTTP_REQUEST_ILLEGAL: task = &logIllegal; break;
|
||||
}
|
||||
|
||||
_timing << *task;
|
||||
LOGGER_REQUEST_IN_START_I(_timing);
|
||||
_timing << *task;
|
||||
LOGGER_REQUEST_IN_START_I(_timing);
|
||||
|
||||
// execute one of the CRUD methods
|
||||
switch (type) {
|
||||
case HttpRequest::HTTP_REQUEST_GET: res = executeAction(); break;
|
||||
case HttpRequest::HTTP_REQUEST_POST: res = executeAction(); break;
|
||||
case HttpRequest::HTTP_REQUEST_PUT: res = executeAction(); break;
|
||||
case HttpRequest::HTTP_REQUEST_DELETE: res = executeAction(); break;
|
||||
case HttpRequest::HTTP_REQUEST_HEAD: res = executeAction(); break;
|
||||
// execute one of the CRUD methods
|
||||
switch (type) {
|
||||
case HttpRequest::HTTP_REQUEST_GET: res = executeAction(); break;
|
||||
case HttpRequest::HTTP_REQUEST_POST: res = executeAction(); break;
|
||||
case HttpRequest::HTTP_REQUEST_PUT: res = executeAction(); break;
|
||||
case HttpRequest::HTTP_REQUEST_DELETE: res = executeAction(); break;
|
||||
case HttpRequest::HTTP_REQUEST_HEAD: res = executeAction(); break;
|
||||
|
||||
default:
|
||||
res = false;
|
||||
generateNotImplemented("METHOD");
|
||||
break;
|
||||
}
|
||||
default:
|
||||
res = false;
|
||||
generateNotImplemented("METHOD");
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -54,6 +54,30 @@ namespace triagens {
|
|||
/// @}
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
// -----------------------------------------------------------------------------
|
||||
// --SECTION-- public types
|
||||
// -----------------------------------------------------------------------------
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
/// @addtogroup ArangoDB
|
||||
/// @{
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
public:
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
/// @brief constructor options
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
struct action_options_t {
|
||||
TRI_vocbase_t* _vocbase;
|
||||
string _queue;
|
||||
};
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
/// @}
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
// -----------------------------------------------------------------------------
|
||||
// --SECTION-- constructors and destructors
|
||||
// -----------------------------------------------------------------------------
|
||||
|
@ -69,7 +93,7 @@ namespace triagens {
|
|||
/// @brief constructor
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
RestActionHandler (rest::HttpRequest*, std::pair<TRI_vocbase_t*, set<string>*>*);
|
||||
RestActionHandler (rest::HttpRequest*, action_options_t*);
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
/// @}
|
||||
|
@ -148,10 +172,10 @@ RestActionHandler (rest::HttpRequest*, std::pair<TRI_vocbase_t*, set<string>*>*)
|
|||
TRI_action_t const* _action;
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
/// @brief allowed queues
|
||||
/// @brief queue to use
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
set<string> const& _allowedQueues;
|
||||
string _queue;
|
||||
};
|
||||
}
|
||||
}
|
||||
|
|
|
@ -100,11 +100,13 @@ uint64_t ActionDispatcherThread::_gcInterval = 1000;
|
|||
|
||||
ActionDispatcherThread::ActionDispatcherThread (rest::DispatcherQueue* queue,
|
||||
string const& actionQueue,
|
||||
set<string> const& allowedContexts,
|
||||
JSLoader* actionLoader)
|
||||
: DispatcherThread(queue),
|
||||
_isolate(0),
|
||||
_context(),
|
||||
_actionQueue(actionQueue),
|
||||
_allowedContexts(allowedContexts),
|
||||
_actionLoader(actionLoader),
|
||||
_gc(0),
|
||||
_v8g(0) {
|
||||
|
@ -258,7 +260,7 @@ void ActionDispatcherThread::initialise () {
|
|||
|
||||
_v8g = TRI_InitV8VocBridge(_context, _vocbase);
|
||||
TRI_InitV8Queries(_context);
|
||||
TRI_InitV8Actions(_context, _actionQueue.c_str());
|
||||
TRI_InitV8Actions(_context, _actionQueue, _allowedContexts);
|
||||
TRI_InitV8Conversions(_context);
|
||||
TRI_InitV8Utils(_context, _startupModules);
|
||||
TRI_InitV8Shell(_context);
|
||||
|
|
|
@ -116,7 +116,10 @@ namespace triagens {
|
|||
/// @brief constructs a new dispatcher thread
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
ActionDispatcherThread (rest::DispatcherQueue*, string const& actionQueue, JSLoader*);
|
||||
ActionDispatcherThread (rest::DispatcherQueue*,
|
||||
string const& actionQueue,
|
||||
set<string> const& allowedContexts,
|
||||
JSLoader*);
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
/// @brief destructs a dispatcher thread
|
||||
|
@ -236,7 +239,7 @@ namespace triagens {
|
|||
v8::Isolate* _isolate;
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
/// @brief context
|
||||
/// @brief V8 context
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
v8::Persistent<v8::Context> _context;
|
||||
|
@ -247,6 +250,12 @@ namespace triagens {
|
|||
|
||||
std::string _actionQueue;
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
/// @brief allowed action contexts
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
std::set<std::string> _allowedContexts;
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
/// @brief action path
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
|
|
|
@ -113,10 +113,16 @@ static JSLoader StartupLoader;
|
|||
static JSLoader ActionLoader;
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
/// @brief system action loader
|
||||
/// @brief allowed client actions
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
static JSLoader SystemActionLoader;
|
||||
static set<string> AllowedClientActions;
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
/// @brief allowed admin actions
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
static set<string> AllowedAdminActions;
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
/// @}
|
||||
|
@ -136,7 +142,7 @@ static JSLoader SystemActionLoader;
|
|||
////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
static DispatcherThread* ClientActionDispatcherThreadCreator (DispatcherQueue* queue) {
|
||||
return new ActionDispatcherThread(queue, "CLIENT", &ActionLoader);
|
||||
return new ActionDispatcherThread(queue, "CLIENT", AllowedClientActions, &ActionLoader);
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
|
@ -144,7 +150,52 @@ static DispatcherThread* ClientActionDispatcherThreadCreator (DispatcherQueue* q
|
|||
////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
static DispatcherThread* SystemActionDispatcherThreadCreator (DispatcherQueue* queue) {
|
||||
return new ActionDispatcherThread(queue, "SYSTEM", &SystemActionLoader);
|
||||
return new ActionDispatcherThread(queue, "SYSTEM", AllowedAdminActions, &ActionLoader);
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
/// @brief define "_api" handlers
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
static void DefineApiHandlers (HttpHandlerFactory* factory,
|
||||
ApplicationAdminServer* admin,
|
||||
TRI_vocbase_t* vocbase) {
|
||||
|
||||
// add "/version" handler
|
||||
admin->addBasicHandlers(factory, "/_api");
|
||||
|
||||
// add "/document" handler
|
||||
factory->addPrefixHandler(RestVocbaseBaseHandler::DOCUMENT_PATH,
|
||||
RestHandlerCreator<RestDocumentHandler>::createData<TRI_vocbase_t*>,
|
||||
vocbase);
|
||||
|
||||
// add "/edge" handler
|
||||
factory->addPrefixHandler(RestVocbaseBaseHandler::EDGE_PATH,
|
||||
RestHandlerCreator<RestEdgeHandler>::createData<TRI_vocbase_t*>,
|
||||
vocbase);
|
||||
|
||||
// add import handler
|
||||
factory->addPrefixHandler(RestVocbaseBaseHandler::DOCUMENT_IMPORT_PATH,
|
||||
RestHandlerCreator<RestImportHandler>::createData<TRI_vocbase_t*>,
|
||||
vocbase);
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
/// @brief define "admin" handlers
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
static void DefineAdminHandlers (HttpHandlerFactory* factory,
|
||||
ApplicationAdminServer* admin,
|
||||
ApplicationUserManager* user,
|
||||
TRI_vocbase_t* vocbase) {
|
||||
|
||||
// add "/version" handler
|
||||
admin->addBasicHandlers(factory, "/_admin");
|
||||
|
||||
// add admin handlers
|
||||
admin->addHandlers(factory, "/_admin");
|
||||
user->addHandlers(factory, "/_admin");
|
||||
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
|
@ -181,7 +232,6 @@ ArangoServer::ArangoServer (int argc, char** argv)
|
|||
_dispatcherThreads(1),
|
||||
_startupPath(),
|
||||
_startupModules("js/modules"),
|
||||
_actionPath(),
|
||||
_systemActionPath(),
|
||||
_actionThreads(1),
|
||||
_gcInterval(1000),
|
||||
|
@ -424,7 +474,6 @@ void ArangoServer::buildApplicationServer () {
|
|||
additional["JAVASCRIPT Options:help-admin"]
|
||||
("startup.directory", &_startupPath, "path to the directory containing alternate startup scripts")
|
||||
("startup.modules-path", &_startupModules, "one or more directories separated by cola")
|
||||
("action.directory", &_actionPath, "path to the action directory, defaults to <database.directory>/_ACTIONS")
|
||||
("gc.interval", &_gcInterval, "garbage collection interval (each x requests)")
|
||||
;
|
||||
|
||||
|
@ -477,51 +526,12 @@ void ArangoServer::buildApplicationServer () {
|
|||
StartupLoader.setDirectory(_startupPath);
|
||||
}
|
||||
|
||||
if (_actionPath.empty()) {
|
||||
char* path = TRI_Concatenate2File(_databasePath.c_str(), "_ACTIONS");
|
||||
|
||||
if (path == 0) {
|
||||
LOGGER_FATAL << "out-of-memory";
|
||||
exit(EXIT_FAILURE);
|
||||
}
|
||||
|
||||
string pathString(path);
|
||||
TRI_FreeString(TRI_CORE_MEM_ZONE, path);
|
||||
|
||||
if (! TRI_IsDirectory(pathString.c_str())) {
|
||||
bool ok = TRI_ExistsFile(pathString.c_str());
|
||||
|
||||
if (ok) {
|
||||
LOGGER_FATAL << "action directory '" << pathString << "' must be a directory";
|
||||
cerr << "action directory '" << pathString << "' must be a directory\n";
|
||||
LOGGER_INFO << "please use the '--database.directory' option";
|
||||
exit(EXIT_FAILURE);
|
||||
}
|
||||
|
||||
ok = TRI_CreateDirectory(pathString.c_str());
|
||||
|
||||
if (! ok) {
|
||||
LOGGER_FATAL << "cannot create action directory '" << pathString << "': " << TRI_last_error();
|
||||
LOGGER_INFO << "please use the '--database.directory' option";
|
||||
exit(EXIT_FAILURE);
|
||||
}
|
||||
}
|
||||
|
||||
ActionLoader.setDirectory(pathString);
|
||||
|
||||
LOGGER_INFO << "using database action files at '" << pathString << "'";
|
||||
}
|
||||
else {
|
||||
ActionLoader.setDirectory(_actionPath);
|
||||
LOGGER_INFO << "using alternate action files at '" << _actionPath << "'";
|
||||
}
|
||||
|
||||
if (! _systemActionPath.empty()) {
|
||||
SystemActionLoader.setDirectory(_systemActionPath);
|
||||
LOGGER_INFO << "using system action files at '" << _systemActionPath << "'";
|
||||
ActionLoader.setDirectory(_systemActionPath);
|
||||
LOGGER_INFO << "using action files at '" << _systemActionPath << "'";
|
||||
}
|
||||
else {
|
||||
LOGGER_INFO << "system actions are disabled, empty system action path";
|
||||
LOGGER_INFO << "actions are disabled, empty system action path";
|
||||
}
|
||||
|
||||
// .............................................................................
|
||||
|
@ -581,6 +591,10 @@ void ArangoServer::buildApplicationServer () {
|
|||
int ArangoServer::startupServer () {
|
||||
v8::HandleScope handle_scope;
|
||||
|
||||
bool useHttpPort = ! _httpPort.empty();
|
||||
bool useAdminPort = ! _adminPort.empty() && _adminPort != "-";
|
||||
bool shareAdminPort = useHttpPort && _adminPort.empty();
|
||||
|
||||
// .............................................................................
|
||||
// open the database
|
||||
// .............................................................................
|
||||
|
@ -616,51 +630,50 @@ int ArangoServer::startupServer () {
|
|||
_actionThreads = 1;
|
||||
}
|
||||
|
||||
safe_cast<DispatcherImpl*>(dispatcher)->addQueue("CLIENT", ClientActionDispatcherThreadCreator, _actionThreads);
|
||||
safe_cast<DispatcherImpl*>(dispatcher)->addQueue("SYSTEM", SystemActionDispatcherThreadCreator, 2);
|
||||
// if we share a the server port for admin and client, only create a SYSTEM queue
|
||||
if (shareAdminPort) {
|
||||
safe_cast<DispatcherImpl*>(dispatcher)->addQueue("CLIENT", ClientActionDispatcherThreadCreator, _actionThreads);
|
||||
}
|
||||
|
||||
// use a separate queue for administrator requests
|
||||
else {
|
||||
safe_cast<DispatcherImpl*>(dispatcher)->addQueue("CLIENT", ClientActionDispatcherThreadCreator, _actionThreads);
|
||||
|
||||
if (useAdminPort) {
|
||||
safe_cast<DispatcherImpl*>(dispatcher)->addQueue("SYSTEM", SystemActionDispatcherThreadCreator, 2);
|
||||
}
|
||||
}
|
||||
|
||||
// .............................................................................
|
||||
// create a http server and http handler factory
|
||||
// .............................................................................
|
||||
|
||||
bool useHttpPort = ! _httpPort.empty();
|
||||
bool useAdminPort = ! _adminPort.empty() && _adminPort != "-";
|
||||
bool shareAdminPort = useHttpPort && _adminPort.empty();
|
||||
|
||||
Scheduler* scheduler = _applicationServer->scheduler();
|
||||
|
||||
set<string> allowedQueuesHttp;
|
||||
pair< TRI_vocbase_t*, set<string>* > handlerDataHttp = make_pair(_vocbase, &allowedQueuesHttp);
|
||||
RestActionHandler::action_options_t httpOptions;
|
||||
httpOptions._vocbase = _vocbase;
|
||||
httpOptions._queue = "CLIENT";
|
||||
|
||||
if (useHttpPort) {
|
||||
HttpHandlerFactory* factory = new HttpHandlerFactory();
|
||||
|
||||
allowedQueuesHttp.insert("STANDARD");
|
||||
allowedQueuesHttp.insert("CLIENT");
|
||||
AllowedClientActions.insert("user");
|
||||
AllowedClientActions.insert("api");
|
||||
|
||||
vector<AddressPort> ports;
|
||||
ports.push_back(AddressPort(_httpPort));
|
||||
|
||||
// add /version URL
|
||||
_applicationAdminServer->addBasicHandlers(factory, "/_api");
|
||||
|
||||
factory->addPrefixHandler(RestVocbaseBaseHandler::DOCUMENT_PATH, RestHandlerCreator<RestDocumentHandler>::createData<TRI_vocbase_t*>, _vocbase);
|
||||
factory->addPrefixHandler(RestVocbaseBaseHandler::EDGE_PATH, RestHandlerCreator<RestEdgeHandler>::createData<TRI_vocbase_t*>, _vocbase);
|
||||
|
||||
factory->addPrefixHandler(RestVocbaseBaseHandler::DOCUMENT_IMPORT_PATH, RestHandlerCreator<RestImportHandler>::createData<TRI_vocbase_t*>, _vocbase);
|
||||
DefineApiHandlers(factory, _applicationAdminServer, _vocbase);
|
||||
|
||||
if (shareAdminPort) {
|
||||
// add /version URL
|
||||
_applicationAdminServer->addBasicHandlers(factory, "/_admin");
|
||||
|
||||
_applicationAdminServer->addHandlers(factory, "/_admin");
|
||||
_applicationUserManager->addHandlers(factory, "/_admin");
|
||||
allowedQueuesHttp.insert("SYSTEM");
|
||||
DefineAdminHandlers(factory, _applicationAdminServer, _applicationUserManager, _vocbase);
|
||||
AllowedClientActions.insert("admin");
|
||||
}
|
||||
|
||||
// add action handler
|
||||
factory->addPrefixHandler("/",
|
||||
RestHandlerCreator<RestActionHandler>::createData< pair< TRI_vocbase_t*, set<string>* >* >,
|
||||
(void*) &handlerDataHttp);
|
||||
RestHandlerCreator<RestActionHandler>::createData<RestActionHandler::action_options_t*>,
|
||||
(void*) &httpOptions);
|
||||
|
||||
_httpServer = _applicationHttpServer->buildServer(new ArangoHttpServer(scheduler, dispatcher), factory, ports);
|
||||
}
|
||||
|
@ -669,36 +682,28 @@ int ArangoServer::startupServer () {
|
|||
// create a http server and http handler factory
|
||||
// .............................................................................
|
||||
|
||||
set<string> allowedQueuesAdmin;
|
||||
pair< TRI_vocbase_t*, set<string>* > handlerDataAdmin = make_pair(_vocbase, &allowedQueuesAdmin);
|
||||
RestActionHandler::action_options_t adminOptions;
|
||||
adminOptions._vocbase = _vocbase;
|
||||
adminOptions._queue = "SYSTEM";
|
||||
|
||||
if (useAdminPort) {
|
||||
HttpHandlerFactory* adminFactory = new HttpHandlerFactory();
|
||||
HttpHandlerFactory* factory = new HttpHandlerFactory();
|
||||
|
||||
allowedQueuesAdmin.insert("STANDARD");
|
||||
allowedQueuesAdmin.insert("CLIENT");
|
||||
allowedQueuesAdmin.insert("SYSTEM");
|
||||
AllowedAdminActions.insert("api");
|
||||
AllowedAdminActions.insert("admin");
|
||||
|
||||
vector<AddressPort> adminPorts;
|
||||
adminPorts.push_back(AddressPort(_adminPort));
|
||||
|
||||
// add /version URL
|
||||
_applicationAdminServer->addBasicHandlers(adminFactory, "/_admin");
|
||||
_applicationAdminServer->addBasicHandlers(adminFactory, "/_api");
|
||||
DefineApiHandlers(factory, _applicationAdminServer, _vocbase);
|
||||
DefineAdminHandlers(factory, _applicationAdminServer, _applicationUserManager, _vocbase);
|
||||
|
||||
_applicationAdminServer->addHandlers(adminFactory, "/_admin");
|
||||
_applicationUserManager->addHandlers(adminFactory, "/_admin");
|
||||
// add action handler
|
||||
factory->addPrefixHandler("/",
|
||||
RestHandlerCreator<RestActionHandler>::createData<RestActionHandler::action_options_t*>,
|
||||
(void*) &adminOptions);
|
||||
|
||||
adminFactory->addPrefixHandler(RestVocbaseBaseHandler::DOCUMENT_PATH, RestHandlerCreator<RestDocumentHandler>::createData<TRI_vocbase_t*>, _vocbase);
|
||||
adminFactory->addPrefixHandler(RestVocbaseBaseHandler::EDGE_PATH, RestHandlerCreator<RestEdgeHandler>::createData<TRI_vocbase_t*>, _vocbase);
|
||||
|
||||
adminFactory->addPrefixHandler("/",
|
||||
RestHandlerCreator<RestActionHandler>::createData< pair< TRI_vocbase_t*, set<string>* >* >,
|
||||
(void*) &handlerDataAdmin);
|
||||
|
||||
adminFactory->addPrefixHandler(RestVocbaseBaseHandler::DOCUMENT_IMPORT_PATH, RestHandlerCreator<RestImportHandler>::createData<TRI_vocbase_t*>, _vocbase);
|
||||
|
||||
_adminHttpServer = _applicationHttpServer->buildServer(new ArangoHttpServer(scheduler, dispatcher), adminFactory, adminPorts);
|
||||
_adminHttpServer = _applicationHttpServer->buildServer(new ArangoHttpServer(scheduler, dispatcher), factory, adminPorts);
|
||||
}
|
||||
|
||||
// .............................................................................
|
||||
|
|
|
@ -288,17 +288,6 @@ namespace triagens {
|
|||
|
||||
string _startupModules;
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
/// @brief path to the action directory
|
||||
///
|
||||
/// @CMDOPT{--action.directory @CA{directory}}
|
||||
///
|
||||
/// Specifies the @CA{directory} path to user defined Javascript files that
|
||||
/// can be invoked as actions.
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
string _actionPath;
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
/// @brief path to the system action directory
|
||||
///
|
||||
|
|
|
@ -187,12 +187,7 @@ static TRI_action_options_t ParseActionOptions (TRI_v8_global_t* v8g,
|
|||
////////////////////////////////////////////////////////////////////////////////
|
||||
/// @brief defines a new action
|
||||
///
|
||||
/// @FUN{defineAction(@FA{name}, @FA{queue}, @FA{callback}, @FA{parameter})}
|
||||
///
|
||||
/// Possible queues are:
|
||||
/// - "CLIENT"
|
||||
/// - "SYSTEM"
|
||||
/// - "MONITORING"
|
||||
/// @FUN{defineAction(@FA{name}, @FA{callback}, @FA{parameter})}
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
static v8::Handle<v8::Value> JS_DefineAction (v8::Arguments const& argv) {
|
||||
|
@ -201,8 +196,8 @@ static v8::Handle<v8::Value> JS_DefineAction (v8::Arguments const& argv) {
|
|||
|
||||
v8g = (TRI_v8_global_t*) v8::Isolate::GetCurrent()->GetData();
|
||||
|
||||
if (argv.Length() != 4) {
|
||||
return scope.Close(v8::ThrowException(v8::String::New("usage: SYS_DEFINE_ACTION(<name>, <queue>, <callback>, <parameter>)")));
|
||||
if (argv.Length() != 3) {
|
||||
return scope.Close(v8::ThrowException(v8::String::New("usage: SYS_DEFINE_ACTION(<name>, <callback>, <parameter>)")));
|
||||
}
|
||||
|
||||
// extract the action name
|
||||
|
@ -214,31 +209,18 @@ static v8::Handle<v8::Value> JS_DefineAction (v8::Arguments const& argv) {
|
|||
|
||||
string name = *utf8name;
|
||||
|
||||
// extract the action queue
|
||||
v8::String::Utf8Value utf8queue(argv[1]);
|
||||
|
||||
if (*utf8queue == 0) {
|
||||
return scope.Close(v8::ThrowException(v8::String::New("<queue> must be an UTF8 name")));
|
||||
}
|
||||
|
||||
string queue = *utf8queue;
|
||||
|
||||
if (queue != "CLIENT" && queue != "SYSTEM" && queue != "MONITORING") {
|
||||
return scope.Close(v8::ThrowException(v8::String::New("<queue> must CLIENT, SYSTEM, MONITORING")));
|
||||
}
|
||||
|
||||
// extract the action callback
|
||||
if (! argv[2]->IsFunction()) {
|
||||
if (! argv[1]->IsFunction()) {
|
||||
return scope.Close(v8::ThrowException(v8::String::New("<callback> must be a function")));
|
||||
}
|
||||
|
||||
v8::Handle<v8::Function> callback = v8::Handle<v8::Function>::Cast(argv[2]);
|
||||
v8::Handle<v8::Function> callback = v8::Handle<v8::Function>::Cast(argv[1]);
|
||||
|
||||
// extract the options
|
||||
v8::Handle<v8::Object> options;
|
||||
|
||||
if (argv[3]->IsObject()) {
|
||||
options = argv[3]->ToObject();
|
||||
if (argv[2]->IsObject()) {
|
||||
options = argv[2]->ToObject();
|
||||
}
|
||||
else {
|
||||
options = v8::Object::New();
|
||||
|
@ -247,7 +229,7 @@ static v8::Handle<v8::Value> JS_DefineAction (v8::Arguments const& argv) {
|
|||
TRI_action_options_t ao = ParseActionOptions(v8g, options);
|
||||
|
||||
// store an action with the given name
|
||||
TRI_CreateActionVocBase(name, queue, ao, callback);
|
||||
TRI_CreateActionVocBase(name, ao, callback);
|
||||
|
||||
return scope.Close(v8::Undefined());
|
||||
}
|
||||
|
@ -270,7 +252,6 @@ static v8::Handle<v8::Value> JS_DefineAction (v8::Arguments const& argv) {
|
|||
////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
void TRI_CreateActionVocBase (string const& name,
|
||||
string const& queue,
|
||||
TRI_action_options_t ao,
|
||||
v8::Handle<v8::Function> callback) {
|
||||
|
||||
|
@ -293,7 +274,6 @@ void TRI_CreateActionVocBase (string const& name,
|
|||
|
||||
action->_url = url;
|
||||
action->_urlParts = StringUtils::split(url, "/").size();
|
||||
action->_queue = queue;
|
||||
action->_options = ao;
|
||||
|
||||
Actions[url] = action;
|
||||
|
@ -311,7 +291,7 @@ void TRI_CreateActionVocBase (string const& name,
|
|||
v8g->Actions[url] = v8::Persistent<v8::Function>::New(callback);
|
||||
|
||||
// some debug output
|
||||
LOG_DEBUG("created action '%s' for queue %s", url.c_str(), queue.c_str());
|
||||
LOG_DEBUG("created action '%s'", url.c_str());
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
|
@ -600,7 +580,9 @@ HttpResponse* TRI_ExecuteActionVocBase (TRI_vocbase_t* vocbase,
|
|||
/// @brief stores the V8 actions function inside the global variable
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
void TRI_InitV8Actions (v8::Handle<v8::Context> context, char const* actionQueue) {
|
||||
void TRI_InitV8Actions (v8::Handle<v8::Context> context,
|
||||
string const& actionQueue,
|
||||
set<string> const& allowedContexts) {
|
||||
v8::HandleScope scope;
|
||||
|
||||
// check the isolate
|
||||
|
@ -617,7 +599,18 @@ void TRI_InitV8Actions (v8::Handle<v8::Context> context, char const* actionQueue
|
|||
// .............................................................................
|
||||
|
||||
context->Global()->Set(v8::String::New("SYS_ACTION_QUEUE"),
|
||||
v8::String::New(actionQueue),
|
||||
v8::String::New(actionQueue.c_str()),
|
||||
v8::ReadOnly);
|
||||
|
||||
v8::Handle<v8::Array> contexts = v8::Array::New();
|
||||
size_t pos = 0;
|
||||
|
||||
for (set<string>::iterator i = allowedContexts.begin(); i != allowedContexts.end(); ++i, ++pos) {
|
||||
contexts->Set(pos, v8::String::New((*i).c_str()));
|
||||
}
|
||||
|
||||
context->Global()->Set(v8::String::New("SYS_ACTION_CONTEXTS"),
|
||||
contexts,
|
||||
v8::ReadOnly);
|
||||
|
||||
// .............................................................................
|
||||
|
|
|
@ -199,7 +199,6 @@ TRI_action_options_t;
|
|||
typedef struct TRI_action_s {
|
||||
std::string _url;
|
||||
size_t _urlParts;
|
||||
std::string _queue;
|
||||
TRI_action_options_t _options;
|
||||
}
|
||||
TRI_action_t;
|
||||
|
@ -222,7 +221,6 @@ TRI_action_t;
|
|||
////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
void TRI_CreateActionVocBase (std::string const& name,
|
||||
std::string const& queue,
|
||||
TRI_action_options_t ao,
|
||||
v8::Handle<v8::Function> callback);
|
||||
|
||||
|
@ -250,7 +248,9 @@ triagens::rest::HttpResponse* TRI_ExecuteActionVocBase (TRI_vocbase_t* vocbase,
|
|||
/// @brief stores the V8 actions function inside the global variable
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
void TRI_InitV8Actions (v8::Handle<v8::Context> context, char const* actionQueue);
|
||||
void TRI_InitV8Actions (v8::Handle<v8::Context> context,
|
||||
std::string const& actionQueue,
|
||||
std::set<std::string> const& allowedContexts);
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
/// @}
|
||||
|
|
|
@ -52,6 +52,13 @@ actions.defineHttp({
|
|||
callback : GET_time
|
||||
});
|
||||
|
||||
actions.defineHttp({
|
||||
url : "_admin/time",
|
||||
context : "admin",
|
||||
prefix : false,
|
||||
callback : GET_time
|
||||
});
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
/// @brief returns system status information for the server
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
|
|
|
@ -59,14 +59,22 @@ static string JS_server_server =
|
|||
" internal.edges = edges;\n"
|
||||
" internal.ArangoCollection = ArangoCollection;\n"
|
||||
" internal.ArangoEdgesCollection = ArangoEdgesCollection;\n"
|
||||
" internal.allowedActionContexts = {}\n"
|
||||
"\n"
|
||||
" if (typeof SYS_DEFINE_ACTION === \"undefined\") {\n"
|
||||
" ModuleCache[\"/internal\"].exports.defineAction = function() {\n"
|
||||
" internal.defineAction = function() {\n"
|
||||
" console.error(\"SYS_DEFINE_ACTION not available\");\n"
|
||||
" };\n"
|
||||
" }\n"
|
||||
" else {\n"
|
||||
" ModuleCache[\"/internal\"].exports.defineAction = SYS_DEFINE_ACTION;\n"
|
||||
" var i;\n"
|
||||
" console.error(SYS_ACTION_CONTEXTS + \", \" + SYS_ACTION_QUEUE);\n"
|
||||
"\n"
|
||||
" for (i = 0; i < SYS_ACTION_CONTEXTS.length; ++i) {\n"
|
||||
" internal.allowedActionContexts[SYS_ACTION_CONTEXTS[i]] = true;\n"
|
||||
" }\n"
|
||||
"\n"
|
||||
" internal.defineAction = SYS_DEFINE_ACTION;\n"
|
||||
" }\n"
|
||||
"\n"
|
||||
"////////////////////////////////////////////////////////////////////////////////\n"
|
||||
|
|
|
@ -150,32 +150,11 @@ function DefineHttp (options) {
|
|||
|
||||
for (var i = 0; i < contexts.length; ++i) {
|
||||
var context = contexts[i];
|
||||
var use = false;
|
||||
|
||||
if (context == "admin") {
|
||||
if (SYS_ACTION_QUEUE == "SYSTEM") {
|
||||
use = true;
|
||||
}
|
||||
}
|
||||
else if (context == "api") {
|
||||
if (SYS_ACTION_QUEUE == "SYSTEM" || SYS_ACTION_QUEUE == "CLIENT") {
|
||||
use = true;
|
||||
}
|
||||
}
|
||||
else if (context == "user") {
|
||||
if (SYS_ACTION_QUEUE == "SYSTEM" || SYS_ACTION_QUEUE == "CLIENT") {
|
||||
use = true;
|
||||
}
|
||||
}
|
||||
else if (context == "monitoring") {
|
||||
if (SYS_ACTION_QUEUE == "MONITORING") {
|
||||
use = true;
|
||||
}
|
||||
}
|
||||
var use = (internal.allowedActionContexts[context] === true)
|
||||
|
||||
if (use) {
|
||||
try {
|
||||
internal.defineAction(url, SYS_ACTION_QUEUE, callback, parameter);
|
||||
internal.defineAction(url, callback, parameter);
|
||||
console.debug("defining action '%s' in context '%s' using queue '%s'", url, context, SYS_ACTION_QUEUE);
|
||||
}
|
||||
catch (err) {
|
||||
|
|
|
@ -58,14 +58,22 @@
|
|||
internal.edges = edges;
|
||||
internal.ArangoCollection = ArangoCollection;
|
||||
internal.ArangoEdgesCollection = ArangoEdgesCollection;
|
||||
internal.allowedActionContexts = {}
|
||||
|
||||
if (typeof SYS_DEFINE_ACTION === "undefined") {
|
||||
ModuleCache["/internal"].exports.defineAction = function() {
|
||||
internal.defineAction = function() {
|
||||
console.error("SYS_DEFINE_ACTION not available");
|
||||
};
|
||||
}
|
||||
else {
|
||||
ModuleCache["/internal"].exports.defineAction = SYS_DEFINE_ACTION;
|
||||
var i;
|
||||
console.error(SYS_ACTION_CONTEXTS + ", " + SYS_ACTION_QUEUE);
|
||||
|
||||
for (i = 0; i < SYS_ACTION_CONTEXTS.length; ++i) {
|
||||
internal.allowedActionContexts[SYS_ACTION_CONTEXTS[i]] = true;
|
||||
}
|
||||
|
||||
internal.defineAction = SYS_DEFINE_ACTION;
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////
|
||||
|
|
Loading…
Reference in New Issue