mirror of https://gitee.com/bigwinds/arangodb
removed MRuby for arangod
This commit is contained in:
parent
5373f1cea0
commit
06a56a7d36
|
@ -30,18 +30,6 @@ set(CMAKE_RUNTIME_OUTPUT_DIRECTORY "${PROJECT_BINARY_DIR}/bin")
|
||||||
### @brief arangod
|
### @brief arangod
|
||||||
################################################################################
|
################################################################################
|
||||||
|
|
||||||
if (USE_MRUBY)
|
|
||||||
set(ARANGOD_MRUBY_SOURCE
|
|
||||||
MRServer/ApplicationMR.cpp
|
|
||||||
MRServer/mr-actions.cpp
|
|
||||||
)
|
|
||||||
|
|
||||||
set(ARANGOD_MRUBY_LIBS
|
|
||||||
${LIB_ARANGO_MRUBY}
|
|
||||||
${MRUBY_LIBS}
|
|
||||||
)
|
|
||||||
endif ()
|
|
||||||
|
|
||||||
add_executable(
|
add_executable(
|
||||||
${BIN_ARANGOD}
|
${BIN_ARANGOD}
|
||||||
Actions/actions.cpp
|
Actions/actions.cpp
|
||||||
|
@ -155,7 +143,6 @@ add_executable(
|
||||||
Wal/Slots.cpp
|
Wal/Slots.cpp
|
||||||
Wal/SynchroniserThread.cpp
|
Wal/SynchroniserThread.cpp
|
||||||
Wal/TestThread.cpp
|
Wal/TestThread.cpp
|
||||||
${ARANGOD_MRUBY_SOURCE}
|
|
||||||
)
|
)
|
||||||
|
|
||||||
target_link_libraries(
|
target_link_libraries(
|
||||||
|
@ -163,7 +150,6 @@ target_link_libraries(
|
||||||
${LIB_ARANGO_FE}
|
${LIB_ARANGO_FE}
|
||||||
${LIB_ARANGO_V8}
|
${LIB_ARANGO_V8}
|
||||||
${LIB_ARANGO}
|
${LIB_ARANGO}
|
||||||
${ARANGOD_MRUBY_LIBS}
|
|
||||||
${LIBEV_LIBS}
|
${LIBEV_LIBS}
|
||||||
${V8_LIBS} # need this for rest::Version
|
${V8_LIBS} # need this for rest::Version
|
||||||
${ICU_LIBS}
|
${ICU_LIBS}
|
||||||
|
|
|
@ -1,507 +0,0 @@
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @brief MR engine configuration
|
|
||||||
///
|
|
||||||
/// @file
|
|
||||||
///
|
|
||||||
/// DISCLAIMER
|
|
||||||
///
|
|
||||||
/// Copyright 2004-2013 triAGENS GmbH, Cologne, Germany
|
|
||||||
///
|
|
||||||
/// Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
/// you may not use this file except in compliance with the License.
|
|
||||||
/// You may obtain a copy of the License at
|
|
||||||
///
|
|
||||||
/// http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
///
|
|
||||||
/// Unless required by applicable law or agreed to in writing, software
|
|
||||||
/// distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
/// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
/// See the License for the specific language governing permissions and
|
|
||||||
/// limitations under the License.
|
|
||||||
///
|
|
||||||
/// Copyright holder is triAGENS GmbH, Cologne, Germany
|
|
||||||
///
|
|
||||||
/// @author Dr. Frank Celler
|
|
||||||
/// @author Copyright 2011-2013, triAGENS GmbH, Cologne, Germany
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
#include "ApplicationMR.h"
|
|
||||||
|
|
||||||
#include "Basics/ConditionLocker.h"
|
|
||||||
#include "Basics/ReadLocker.h"
|
|
||||||
#include "Basics/Thread.h"
|
|
||||||
#include "Basics/WriteLocker.h"
|
|
||||||
#include "BasicsC/logging.h"
|
|
||||||
#include "MRServer/mr-actions.h"
|
|
||||||
#include "VocBase/server.h"
|
|
||||||
#include "VocBase/vocbase.h"
|
|
||||||
|
|
||||||
using namespace triagens::basics;
|
|
||||||
using namespace triagens::arango;
|
|
||||||
using namespace std;
|
|
||||||
|
|
||||||
#include "mr/common/bootstrap/mr-error.h"
|
|
||||||
#include "mr/server/mr-server.h"
|
|
||||||
|
|
||||||
// -----------------------------------------------------------------------------
|
|
||||||
// --SECTION-- class MRGcThread
|
|
||||||
// -----------------------------------------------------------------------------
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @addtogroup ArangoDB
|
|
||||||
/// @{
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
namespace {
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @brief garbage collector
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
class MRGcThread : public Thread {
|
|
||||||
public:
|
|
||||||
MRGcThread (ApplicationMR* applicationMR)
|
|
||||||
: Thread("mr-gc"),
|
|
||||||
_applicationMR(applicationMR),
|
|
||||||
_lock(),
|
|
||||||
_lastGcStamp(TRI_microtime()) {
|
|
||||||
}
|
|
||||||
|
|
||||||
public:
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @brief collect garbage in an endless loop (main functon of GC thread)
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
void run () {
|
|
||||||
_applicationMR->collectGarbage();
|
|
||||||
}
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @brief get the timestamp of the last GC
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
double getLastGcStamp () {
|
|
||||||
READ_LOCKER(_lock);
|
|
||||||
return _lastGcStamp;
|
|
||||||
}
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @brief set the global GC timestamp
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
void updateGcStamp (double value) {
|
|
||||||
WRITE_LOCKER(_lock);
|
|
||||||
}
|
|
||||||
|
|
||||||
private:
|
|
||||||
ApplicationMR* _applicationMR;
|
|
||||||
ReadWriteLock _lock;
|
|
||||||
double _lastGcStamp;
|
|
||||||
};
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @}
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
// -----------------------------------------------------------------------------
|
|
||||||
// --SECTION-- class ApplicationMR
|
|
||||||
// -----------------------------------------------------------------------------
|
|
||||||
|
|
||||||
// -----------------------------------------------------------------------------
|
|
||||||
// --SECTION-- constructors and destructors
|
|
||||||
// -----------------------------------------------------------------------------
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @addtogroup ArangoDB
|
|
||||||
/// @{
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @brief constructor
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
ApplicationMR::ApplicationMR (TRI_server_t* server)
|
|
||||||
: ApplicationFeature("MRuby"),
|
|
||||||
_server(server),
|
|
||||||
_startupPath(),
|
|
||||||
_startupModules(),
|
|
||||||
_actionPath(),
|
|
||||||
_gcInterval(1000),
|
|
||||||
_gcFrequency(10.0),
|
|
||||||
_startupLoader(),
|
|
||||||
_actionLoader(),
|
|
||||||
_vocbase(0),
|
|
||||||
_nrInstances(0),
|
|
||||||
_contexts(0),
|
|
||||||
_contextCondition(),
|
|
||||||
_freeContexts(),
|
|
||||||
_dirtyContexts(),
|
|
||||||
_stopping(0) {
|
|
||||||
|
|
||||||
assert(_server != 0);
|
|
||||||
}
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @brief destructor
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
ApplicationMR::~ApplicationMR () {
|
|
||||||
}
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @}
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
// -----------------------------------------------------------------------------
|
|
||||||
// --SECTION-- public methods
|
|
||||||
// -----------------------------------------------------------------------------
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @addtogroup ArangoDB
|
|
||||||
/// @{
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @brief sets the concurrency
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
void ApplicationMR::setConcurrency (size_t n) {
|
|
||||||
_nrInstances = n;
|
|
||||||
}
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @brief sets the database
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
void ApplicationMR::setVocbase (TRI_vocbase_t* vocbase) {
|
|
||||||
_vocbase = vocbase;
|
|
||||||
}
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @brief enters an context
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
ApplicationMR::MRContext* ApplicationMR::enterContext () {
|
|
||||||
CONDITION_LOCKER(guard, _contextCondition);
|
|
||||||
|
|
||||||
while (_freeContexts.empty()) {
|
|
||||||
LOG_DEBUG("waiting for unused MRuby context");
|
|
||||||
guard.wait();
|
|
||||||
}
|
|
||||||
|
|
||||||
LOG_TRACE("found unused MRuby context");
|
|
||||||
|
|
||||||
MRContext* context = _freeContexts.back();
|
|
||||||
_freeContexts.pop_back();
|
|
||||||
|
|
||||||
return context;
|
|
||||||
}
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @brief exists an context
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
void ApplicationMR::exitContext (MRContext* context) {
|
|
||||||
MRGcThread* gc = dynamic_cast<MRGcThread*>(_gcThread);
|
|
||||||
assert(gc != 0);
|
|
||||||
double lastGc = gc->getLastGcStamp();
|
|
||||||
|
|
||||||
++context->_dirt;
|
|
||||||
|
|
||||||
{
|
|
||||||
CONDITION_LOCKER(guard, _contextCondition);
|
|
||||||
|
|
||||||
if (context->_lastGcStamp + _gcFrequency < lastGc) {
|
|
||||||
LOG_TRACE("periodic gc interval reached");
|
|
||||||
_dirtyContexts.push_back(context);
|
|
||||||
}
|
|
||||||
else if (context->_dirt >= _gcInterval) {
|
|
||||||
LOG_TRACE("maximum number of requests reached");
|
|
||||||
_dirtyContexts.push_back(context);
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
_freeContexts.push_back(context);
|
|
||||||
}
|
|
||||||
|
|
||||||
guard.broadcast();
|
|
||||||
}
|
|
||||||
|
|
||||||
LOG_TRACE("returned dirty MR context");
|
|
||||||
}
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @brief runs the garbage collection
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
void ApplicationMR::collectGarbage () {
|
|
||||||
MRGcThread* gc = dynamic_cast<MRGcThread*>(_gcThread);
|
|
||||||
assert(gc != 0);
|
|
||||||
uint64_t waitTime = (uint64_t) (_gcFrequency * 1000.0 * 1000.0);
|
|
||||||
|
|
||||||
while (_stopping == 0) {
|
|
||||||
MRContext* context = 0;
|
|
||||||
|
|
||||||
{
|
|
||||||
bool gotSignal = false;
|
|
||||||
CONDITION_LOCKER(guard, _contextCondition);
|
|
||||||
|
|
||||||
if (_dirtyContexts.empty()) {
|
|
||||||
// check whether we got a wait timeout or a signal
|
|
||||||
gotSignal = guard.wait(waitTime);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (! _dirtyContexts.empty()) {
|
|
||||||
context = _dirtyContexts.back();
|
|
||||||
_dirtyContexts.pop_back();
|
|
||||||
}
|
|
||||||
else if (! gotSignal && ! _freeContexts.empty()) {
|
|
||||||
// we timed out waiting for a signal
|
|
||||||
|
|
||||||
// do nothing for now
|
|
||||||
// TODO: fix this if MRuby needs some proactive GC
|
|
||||||
context = 0;
|
|
||||||
|
|
||||||
// TODO: pick one of the free contexts to clean up, based on its last GC stamp
|
|
||||||
// this is already implemented in ApplicationV8::pickContextForFc()
|
|
||||||
// if necessary for MRuby, the code in pickContextForGc() can be used as a prototype
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// update last gc time
|
|
||||||
double lastGc = TRI_microtime();
|
|
||||||
gc->updateGcStamp(lastGc);
|
|
||||||
|
|
||||||
if (context != 0) {
|
|
||||||
LOG_TRACE("collecting MR garbage");
|
|
||||||
|
|
||||||
mrb_garbage_collect(context->_mrb);
|
|
||||||
|
|
||||||
context->_dirt = 0;
|
|
||||||
context->_lastGcStamp = lastGc;
|
|
||||||
|
|
||||||
{
|
|
||||||
CONDITION_LOCKER(guard, _contextCondition);
|
|
||||||
|
|
||||||
_freeContexts.push_back(context);
|
|
||||||
guard.broadcast();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @brief disables actions
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
void ApplicationMR::disableActions () {
|
|
||||||
_actionPath.clear();
|
|
||||||
}
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @}
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
// -----------------------------------------------------------------------------
|
|
||||||
// --SECTION-- ApplicationFeature methods
|
|
||||||
// -----------------------------------------------------------------------------
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @addtogroup ApplicationServer
|
|
||||||
/// @{
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// {@inheritDoc}
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
void ApplicationMR::setupOptions (map<string, basics::ProgramOptionsDescription>& options) {
|
|
||||||
options["RUBY Options:help-admin"]
|
|
||||||
("ruby.gc-interval", &_gcInterval, "Ruby request-based garbage collection interval (each x requests)")
|
|
||||||
("ruby.gc-frequency", &_gcFrequency, "Ruby time-based garbage collection frequency (each x seconds)")
|
|
||||||
;
|
|
||||||
|
|
||||||
options["RUBY Options:help-admin"]
|
|
||||||
("ruby.action-directory", &_actionPath, "path to the Ruby action directory")
|
|
||||||
("ruby.modules-path", &_startupModules, "one or more directories separated by (semi-) colons")
|
|
||||||
("ruby.startup-directory", &_startupPath, "path to the directory containing alternate Ruby startup scripts")
|
|
||||||
;
|
|
||||||
}
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// {@inheritDoc}
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
bool ApplicationMR::prepare () {
|
|
||||||
// check the startup modules
|
|
||||||
if (_startupModules.empty()) {
|
|
||||||
LOG_FATAL_AND_EXIT("no 'ruby.modules-path' has been supplied, giving up");
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
LOG_INFO("using Ruby modules path '%s'", _startupModules.c_str());
|
|
||||||
}
|
|
||||||
|
|
||||||
// set up the startup loader
|
|
||||||
if (_startupPath.empty()) {
|
|
||||||
LOG_INFO("using built-in Ruby startup files");
|
|
||||||
|
|
||||||
_startupLoader.defineScript("common/bootstrap/error.rb", MR_common_bootstrap_error);
|
|
||||||
_startupLoader.defineScript("server/server.rb", MR_server_server);
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
LOG_INFO("using Ruby startup files at '%s'", _startupPath.c_str());
|
|
||||||
|
|
||||||
_startupLoader.setDirectory(_startupPath);
|
|
||||||
}
|
|
||||||
|
|
||||||
// set up action loader
|
|
||||||
if (_actionPath.empty()) {
|
|
||||||
LOG_FATAL_AND_EXIT("no 'ruby.action-directory' has been supplied, giving up");
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
LOG_INFO("using Ruby action files at '%s'", _actionPath.c_str());
|
|
||||||
|
|
||||||
_actionLoader.setDirectory(_actionPath);
|
|
||||||
}
|
|
||||||
|
|
||||||
// setup instances
|
|
||||||
_contexts = new MRContext*[_nrInstances];
|
|
||||||
|
|
||||||
for (size_t i = 0; i < _nrInstances; ++i) {
|
|
||||||
bool ok = prepareMRInstance(i);
|
|
||||||
|
|
||||||
if (! ok) {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// {@inheritDoc}
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
bool ApplicationMR::start () {
|
|
||||||
_gcThread = new MRGcThread(this);
|
|
||||||
_gcThread->start();
|
|
||||||
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// {@inheritDoc}
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
void ApplicationMR::close () {
|
|
||||||
_stopping = 1;
|
|
||||||
_contextCondition.broadcast();
|
|
||||||
}
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// {@inheritDoc}
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
void ApplicationMR::stop () {
|
|
||||||
_gcThread->shutdown();
|
|
||||||
delete _gcThread;
|
|
||||||
|
|
||||||
for (size_t i = 0; i < _nrInstances; ++i) {
|
|
||||||
shutdownMRInstance(i);
|
|
||||||
}
|
|
||||||
|
|
||||||
delete[] _contexts;
|
|
||||||
}
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @}
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
// -----------------------------------------------------------------------------
|
|
||||||
// --SECTION-- private methods
|
|
||||||
// -----------------------------------------------------------------------------
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @addtogroup ArangoDB
|
|
||||||
/// @{
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @brief prepares a MR instance
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
bool ApplicationMR::prepareMRInstance (size_t i) {
|
|
||||||
static char const* files[] = { "common/bootstrap/error.rb",
|
|
||||||
"server/server.rb"
|
|
||||||
};
|
|
||||||
|
|
||||||
LOG_TRACE("initialising MR context #%d", (int) i);
|
|
||||||
|
|
||||||
MRContext* context = _contexts[i] = new MRContext();
|
|
||||||
|
|
||||||
// create a new shell
|
|
||||||
context->_mrb = MR_OpenShell();
|
|
||||||
|
|
||||||
TRI_InitMRUtils(context->_mrb);
|
|
||||||
|
|
||||||
if (! _actionPath.empty()) {
|
|
||||||
TRI_InitMRActions(context->_mrb, this);
|
|
||||||
}
|
|
||||||
|
|
||||||
// load all init files
|
|
||||||
for (i = 0; i < sizeof(files) / sizeof(files[0]); ++i) {
|
|
||||||
bool ok = _startupLoader.loadScript(context->_mrb, files[i]);
|
|
||||||
|
|
||||||
if (! ok) {
|
|
||||||
LOG_FATAL_AND_EXIT("cannot load Ruby utilities from file '%s'", files[i]);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// load all actions
|
|
||||||
if (! _actionPath.empty()) {
|
|
||||||
bool ok = _actionLoader.executeAllScripts(context->_mrb);
|
|
||||||
|
|
||||||
if (! ok) {
|
|
||||||
LOG_FATAL_AND_EXIT("cannot load Ruby actions from directory '%s'", _actionLoader.getDirectory().c_str());
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
context->_lastGcStamp = TRI_microtime();
|
|
||||||
|
|
||||||
// and return from the context
|
|
||||||
LOG_TRACE("initialised MR context #%d", (int) i);
|
|
||||||
|
|
||||||
_freeContexts.push_back(context);
|
|
||||||
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @brief shut downs a MR instances
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
void ApplicationMR::shutdownMRInstance (size_t i) {
|
|
||||||
LOG_TRACE("shutting down MR context #%d", (int) i);
|
|
||||||
|
|
||||||
MRContext* context = _contexts[i];
|
|
||||||
mrb_state* mrb = context->_mrb;
|
|
||||||
|
|
||||||
mrb_garbage_collect(mrb);
|
|
||||||
|
|
||||||
MR_CloseShell(mrb);
|
|
||||||
|
|
||||||
LOG_TRACE("closed MR context #%d", (int) i);
|
|
||||||
|
|
||||||
delete context;
|
|
||||||
}
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @}
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
// Local Variables:
|
|
||||||
// mode: outline-minor
|
|
||||||
// outline-regexp: "/// @brief\\|/// {@inheritDoc}\\|/// @addtogroup\\|/// @page\\|// --SECTION--\\|/// @\\}"
|
|
||||||
// End:
|
|
|
@ -1,408 +0,0 @@
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @brief MR enigne configuration
|
|
||||||
///
|
|
||||||
/// @file
|
|
||||||
///
|
|
||||||
/// DISCLAIMER
|
|
||||||
///
|
|
||||||
/// Copyright 2004-2013 triAGENS GmbH, Cologne, Germany
|
|
||||||
///
|
|
||||||
/// Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
/// you may not use this file except in compliance with the License.
|
|
||||||
/// You may obtain a copy of the License at
|
|
||||||
///
|
|
||||||
/// http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
///
|
|
||||||
/// Unless required by applicable law or agreed to in writing, software
|
|
||||||
/// distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
/// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
/// See the License for the specific language governing permissions and
|
|
||||||
/// limitations under the License.
|
|
||||||
///
|
|
||||||
/// Copyright holder is triAGENS GmbH, Cologne, Germany
|
|
||||||
///
|
|
||||||
/// @author Dr. Frank Celler
|
|
||||||
/// @author Copyright 2011-2013, triAGENS GmbH, Cologne, Germany
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
#ifndef TRIAGENS_MRSERVER_APPLICATION_MR_H
|
|
||||||
#define TRIAGENS_MRSERVER_APPLICATION_MR_H 1
|
|
||||||
|
|
||||||
#include "Basics/Common.h"
|
|
||||||
|
|
||||||
#include "ApplicationServer/ApplicationFeature.h"
|
|
||||||
|
|
||||||
#include "MRuby/mr-utils.h"
|
|
||||||
|
|
||||||
#include "Basics/ConditionVariable.h"
|
|
||||||
#include "MRuby/MRLoader.h"
|
|
||||||
|
|
||||||
// -----------------------------------------------------------------------------
|
|
||||||
// --SECTION-- forward declarations
|
|
||||||
// -----------------------------------------------------------------------------
|
|
||||||
|
|
||||||
extern "C" {
|
|
||||||
struct TRI_server_s;
|
|
||||||
struct TRI_vocbase_s;
|
|
||||||
}
|
|
||||||
|
|
||||||
namespace triagens {
|
|
||||||
namespace basics {
|
|
||||||
class Thread;
|
|
||||||
}
|
|
||||||
|
|
||||||
// -----------------------------------------------------------------------------
|
|
||||||
// --SECTION-- class ApplicationMR
|
|
||||||
// -----------------------------------------------------------------------------
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @addtogroup ArangoDB
|
|
||||||
/// @{
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
namespace arango {
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @brief application simple user and session management feature
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
class ApplicationMR : public rest::ApplicationFeature {
|
|
||||||
private:
|
|
||||||
ApplicationMR (ApplicationMR const&);
|
|
||||||
ApplicationMR& operator= (ApplicationMR const&);
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @}
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
// -----------------------------------------------------------------------------
|
|
||||||
// --SECTION-- public types
|
|
||||||
// -----------------------------------------------------------------------------
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @addtogroup ArangoDB
|
|
||||||
/// @{
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
public:
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @brief MR isolate and context
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
struct MRContext {
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @brief ruby state
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
mrb_state* _mrb;
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @brief number of requests since last GC of the context
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
size_t _dirt;
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @brief timestamp of last GC for the context
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
double _lastGcStamp;
|
|
||||||
|
|
||||||
};
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @}
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
// -----------------------------------------------------------------------------
|
|
||||||
// --SECTION-- constructors and destructors
|
|
||||||
// -----------------------------------------------------------------------------
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @addtogroup ArangoDB
|
|
||||||
/// @{
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
public:
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @brief constructor
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
ApplicationMR (struct TRI_server_s*);
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @brief destructor
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
~ApplicationMR ();
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @}
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
// -----------------------------------------------------------------------------
|
|
||||||
// --SECTION-- public methods
|
|
||||||
// -----------------------------------------------------------------------------
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @addtogroup ArangoDB
|
|
||||||
/// @{
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @brief sets the concurrency
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
void setConcurrency (size_t);
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @brief sets the database
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
void setVocbase (struct TRI_vocbase_s*);
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @brief enters an context
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
MRContext* enterContext ();
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @brief exists an context
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
void exitContext (MRContext*);
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @brief runs the garbage collection
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
void collectGarbage ();
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @brief disables actions
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
void disableActions ();
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @}
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
// -----------------------------------------------------------------------------
|
|
||||||
// --SECTION-- ApplicationFeature methods
|
|
||||||
// -----------------------------------------------------------------------------
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @addtogroup ApplicationServer
|
|
||||||
/// @{
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
public:
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// {@inheritDoc}
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
void setupOptions (map<string, basics::ProgramOptionsDescription>&);
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// {@inheritDoc}
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
bool prepare ();
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// {@inheritDoc}
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
bool start ();
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// {@inheritDoc}
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
void close ();
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// {@inheritDoc}
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
void stop ();
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @}
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
// -----------------------------------------------------------------------------
|
|
||||||
// --SECTION-- private methods
|
|
||||||
// -----------------------------------------------------------------------------
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @addtogroup ArangoDB
|
|
||||||
/// @{
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @brief prepares a MR instance
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
bool prepareMRInstance (size_t i);
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @brief shut downs a MR instances
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
void shutdownMRInstance (size_t i);
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @}
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
// -----------------------------------------------------------------------------
|
|
||||||
// --SECTION-- private variables
|
|
||||||
// -----------------------------------------------------------------------------
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @addtogroup ArangoDB
|
|
||||||
/// @{
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @brief server object
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
struct TRI_server_s* _server;
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @brief path to the directory containing alternate startup scripts
|
|
||||||
///
|
|
||||||
/// @CMDOPT{\--ruby.directory @CA{directory}}
|
|
||||||
///
|
|
||||||
/// Specifies the @CA{directory} path to the MRuby files used for bootstraping.
|
|
||||||
/// Multiple paths can be specified separated with commas.
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
string _startupPath;
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @brief semicolon separated list of module directories
|
|
||||||
///
|
|
||||||
/// @CMDOPT{\--ruby.modules-path @CA{directory}}
|
|
||||||
///
|
|
||||||
/// Specifies the @CA{directory} paths where the MRuby modules are located.
|
|
||||||
/// Multiple paths can be specified separated with commas.
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
string _startupModules;
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @brief path to the system action directory
|
|
||||||
///
|
|
||||||
/// @CMDOPT{\--ruby.action-directory @CA{directory}}
|
|
||||||
///
|
|
||||||
/// Specifies the @CA{directory} containg the MRuby files describing the system
|
|
||||||
/// actions. Multiple paths can be specified separated with commas.
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
string _actionPath;
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @brief MRuby garbage collection interval (each x requests)
|
|
||||||
///
|
|
||||||
/// @CMDOPT{\--ruby.gc-interval @CA{interval}}
|
|
||||||
///
|
|
||||||
/// Specifies the interval (approximately in number of requests) that the
|
|
||||||
/// garbage collection for MRuby objects will be run in each thread.
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
uint64_t _gcInterval;
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @brief MRuby garbage collection frequency (each x seconds)
|
|
||||||
///
|
|
||||||
/// @CMDOPT{\--ruby.gc-frequency @CA{frequency}}
|
|
||||||
///
|
|
||||||
/// Specifies the frequency in seconds for the automatic garbage collection of
|
|
||||||
/// MRuby objects. This setting is useful to have the garbage collection
|
|
||||||
/// still work in periods with no or little numbers of requests.
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
double _gcFrequency;
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @brief MR startup loader
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
MRLoader _startupLoader;
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @brief MR action loader
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
MRLoader _actionLoader;
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @brief database
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
struct TRI_vocbase_s* _vocbase;
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @brief number of instances to create
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
size_t _nrInstances;
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @brief MR contexts
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
MRContext** _contexts;
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @brief MR contexts queue lock
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
basics::ConditionVariable _contextCondition;
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @brief MR free contexts
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
std::vector<MRContext*> _freeContexts;
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @brief MR free contexts
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
std::vector<MRContext*> _dirtyContexts;
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @brief shutdown in progress
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
volatile sig_atomic_t _stopping;
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @brief garbage collection thread
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
basics::Thread* _gcThread;
|
|
||||||
};
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @}
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
#endif
|
|
||||||
|
|
||||||
// Local Variables:
|
|
||||||
// mode: outline-minor
|
|
||||||
// outline-regexp: "/// @brief\\|/// {@inheritDoc}\\|/// @addtogroup\\|/// @page\\|// --SECTION--\\|/// @\\}"
|
|
||||||
// End:
|
|
|
@ -1,451 +0,0 @@
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @brief mruby actions
|
|
||||||
///
|
|
||||||
/// @file
|
|
||||||
///
|
|
||||||
/// DISCLAIMER
|
|
||||||
///
|
|
||||||
/// Copyright 2004-2014 triAGENS GmbH, Cologne, Germany
|
|
||||||
///
|
|
||||||
/// Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
/// you may not use this file except in compliance with the License.
|
|
||||||
/// You may obtain a copy of the License at
|
|
||||||
///
|
|
||||||
/// http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
///
|
|
||||||
/// Unless required by applicable law or agreed to in writing, software
|
|
||||||
/// distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
/// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
/// See the License for the specific language governing permissions and
|
|
||||||
/// limitations under the License.
|
|
||||||
///
|
|
||||||
/// Copyright holder is triAGENS GmbH, Cologne, Germany
|
|
||||||
///
|
|
||||||
/// @author Dr. Frank Celler
|
|
||||||
/// @author Copyright 2012-2014, triAGENS GmbH, Cologne, Germany
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
#include "mr-actions.h"
|
|
||||||
|
|
||||||
#include "Actions/actions.h"
|
|
||||||
#include "Basics/ReadLocker.h"
|
|
||||||
#include "Basics/WriteLocker.h"
|
|
||||||
#include "BasicsC/conversions.h"
|
|
||||||
#include "BasicsC/logging.h"
|
|
||||||
#include "BasicsC/tri-strings.h"
|
|
||||||
#include "MRServer/ApplicationMR.h"
|
|
||||||
#include "Rest/HttpRequest.h"
|
|
||||||
#include "Rest/HttpResponse.h"
|
|
||||||
#include "VocBase/vocbase.h"
|
|
||||||
|
|
||||||
#include "mruby/array.h"
|
|
||||||
#include "mruby/class.h"
|
|
||||||
#include "mruby/hash.h"
|
|
||||||
#include "mruby/string.h"
|
|
||||||
#include "mruby/variable.h"
|
|
||||||
|
|
||||||
using namespace std;
|
|
||||||
using namespace triagens::basics;
|
|
||||||
using namespace triagens::rest;
|
|
||||||
using namespace triagens::arango;
|
|
||||||
|
|
||||||
// -----------------------------------------------------------------------------
|
|
||||||
// --SECTION-- forward declarations
|
|
||||||
// -----------------------------------------------------------------------------
|
|
||||||
|
|
||||||
static HttpResponse* ExecuteActionVocbase (TRI_vocbase_t* vocbase,
|
|
||||||
mrb_state* mrb,
|
|
||||||
TRI_action_t const* action,
|
|
||||||
mrb_value callback,
|
|
||||||
HttpRequest* request);
|
|
||||||
|
|
||||||
// -----------------------------------------------------------------------------
|
|
||||||
// --SECTION-- private variables
|
|
||||||
// -----------------------------------------------------------------------------
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @brief global MRuby dealer
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
ApplicationMR* GlobalMRDealer = 0;
|
|
||||||
|
|
||||||
// -----------------------------------------------------------------------------
|
|
||||||
// --SECTION-- private types
|
|
||||||
// -----------------------------------------------------------------------------
|
|
||||||
|
|
||||||
// -----------------------------------------------------------------------------
|
|
||||||
// --SECTION-- class mr_action_t
|
|
||||||
// -----------------------------------------------------------------------------
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @brief action description for MRuby
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
class mr_action_t : public TRI_action_t {
|
|
||||||
public:
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @brief constructor
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
mr_action_t (set<string> const& contexts)
|
|
||||||
: TRI_action_t(contexts) {
|
|
||||||
_type = "RUBY";
|
|
||||||
}
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @brief destructor
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
~mr_action_t () {
|
|
||||||
// TODO cleanup
|
|
||||||
}
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @brief creates callback for a context
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
void createCallback (mrb_state* mrb, mrb_value callback) {
|
|
||||||
WRITE_LOCKER(_callbacksLock);
|
|
||||||
|
|
||||||
_callbacks[mrb] = callback;
|
|
||||||
}
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @brief creates callback for a context
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
TRI_action_result_t execute (TRI_vocbase_t* vocbase, HttpRequest* request, Mutex*, void**) {
|
|
||||||
TRI_action_result_t result;
|
|
||||||
ApplicationMR::MRContext* context = GlobalMRDealer->enterContext();
|
|
||||||
mrb_state* mrb = context->_mrb;
|
|
||||||
|
|
||||||
READ_LOCKER(_callbacksLock);
|
|
||||||
|
|
||||||
map< mrb_state*, mrb_value >::iterator i = _callbacks.find(mrb);
|
|
||||||
|
|
||||||
if (i == _callbacks.end()) {
|
|
||||||
LOG_WARNING("no callback function for Ruby action '%s'", _url.c_str());
|
|
||||||
|
|
||||||
result.isValid = true;
|
|
||||||
result.response = new HttpResponse(HttpResponse::NOT_FOUND, request->compatibility());
|
|
||||||
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
|
|
||||||
mrb_value callback = i->second;
|
|
||||||
|
|
||||||
HttpResponse* response = ExecuteActionVocbase(vocbase, mrb, this, callback, request);
|
|
||||||
|
|
||||||
GlobalMRDealer->exitContext(context);
|
|
||||||
|
|
||||||
result.isValid = true;
|
|
||||||
result.response = response;
|
|
||||||
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// {@inheritDoc}
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
bool cancel (Mutex* dataLock, void** data) {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
private:
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @brief callback dictionary
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
map< mrb_state*, mrb_value > _callbacks;
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @brief lock for the callback dictionary
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
ReadWriteLock _callbacksLock;
|
|
||||||
};
|
|
||||||
|
|
||||||
// -----------------------------------------------------------------------------
|
|
||||||
// --SECTION-- private functions
|
|
||||||
// -----------------------------------------------------------------------------
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @brief float value
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
double MR_float (mrb_state* mrb, mrb_value val) {
|
|
||||||
switch (mrb_type(val)) {
|
|
||||||
case MRB_TT_FIXNUM:
|
|
||||||
return (double) mrb_fixnum(val);
|
|
||||||
|
|
||||||
case MRB_TT_FLOAT:
|
|
||||||
return mrb_float(val);
|
|
||||||
break;
|
|
||||||
|
|
||||||
default:
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @brief string value
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
char const* MR_string (mrb_state* mrb, mrb_value val) {
|
|
||||||
return RSTRING_PTR(val);
|
|
||||||
}
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @brief executes an action
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
static HttpResponse* ExecuteActionVocbase (TRI_vocbase_t* vocbase,
|
|
||||||
mrb_state* mrb,
|
|
||||||
TRI_action_t const* action,
|
|
||||||
mrb_value callback,
|
|
||||||
HttpRequest* request) {
|
|
||||||
MR_state_t* mrs;
|
|
||||||
mrb_sym id;
|
|
||||||
mrb_sym bodyId;
|
|
||||||
mrb_value key;
|
|
||||||
mrb_value val;
|
|
||||||
|
|
||||||
mrs = (MR_state_t*) mrb->ud;
|
|
||||||
|
|
||||||
// setup the request
|
|
||||||
mrb_value req = mrb_class_new_instance(mrb, 0, 0, mrs->_arangoRequest);
|
|
||||||
|
|
||||||
// setup the response
|
|
||||||
mrb_value res = mrb_class_new_instance(mrb, 0, 0, mrs->_arangoResponse);
|
|
||||||
|
|
||||||
// copy suffixes
|
|
||||||
vector<string> const& suffix = request->suffix();
|
|
||||||
mrb_value suffixArray = mrb_ary_new_capa(mrb, suffix.size());
|
|
||||||
|
|
||||||
uint32_t index = 0;
|
|
||||||
|
|
||||||
for (size_t s = action->_urlParts; s < suffix.size(); ++s, ++index) {
|
|
||||||
string const& str = suffix[s];
|
|
||||||
val = mrb_str_new(mrb, str.c_str(), str.size());
|
|
||||||
|
|
||||||
mrb_ary_set(mrb, suffixArray, index, val);
|
|
||||||
}
|
|
||||||
|
|
||||||
id = mrb_intern(mrb, "@suffix");
|
|
||||||
mrb_iv_set(mrb, req, id, suffixArray);
|
|
||||||
|
|
||||||
// copy header fields
|
|
||||||
map<string, string> const& headers = request->headers();
|
|
||||||
map<string, string>::const_iterator iter = headers.begin();
|
|
||||||
|
|
||||||
mrb_value headerFields = mrb_hash_new_capa(mrb, headers.size());
|
|
||||||
|
|
||||||
for (; iter != headers.end(); ++iter) {
|
|
||||||
string const& f = iter->first;
|
|
||||||
string const& s = iter->second;
|
|
||||||
|
|
||||||
key = mrb_str_new(mrb, f.c_str(), f.size());
|
|
||||||
val = mrb_str_new(mrb, s.c_str(), s.size());
|
|
||||||
|
|
||||||
|
|
||||||
mrb_hash_set(mrb, headerFields, key, val);
|
|
||||||
}
|
|
||||||
|
|
||||||
id = mrb_intern(mrb, "@headers");
|
|
||||||
mrb_iv_set(mrb, req, id, headerFields);
|
|
||||||
|
|
||||||
// copy request type
|
|
||||||
id = mrb_intern(mrb, "@request_type");
|
|
||||||
bodyId = mrb_intern(mrb, "@body");
|
|
||||||
|
|
||||||
switch (request->requestType()) {
|
|
||||||
case HttpRequest::HTTP_REQUEST_POST:
|
|
||||||
mrb_iv_set(mrb, req, id, mrb_str_new_cstr(mrb, "POST"));
|
|
||||||
mrb_iv_set(mrb, req, bodyId, mrb_str_new(mrb, request->body(), request->bodySize()));
|
|
||||||
break;
|
|
||||||
|
|
||||||
case HttpRequest::HTTP_REQUEST_PUT:
|
|
||||||
mrb_iv_set(mrb, req, id, mrb_str_new_cstr(mrb, "PUT"));
|
|
||||||
mrb_iv_set(mrb, req, bodyId, mrb_str_new(mrb, request->body(), request->bodySize()));
|
|
||||||
break;
|
|
||||||
|
|
||||||
case HttpRequest::HTTP_REQUEST_DELETE:
|
|
||||||
mrb_iv_set(mrb, req, id, mrb_str_new_cstr(mrb, "DELETE"));
|
|
||||||
break;
|
|
||||||
|
|
||||||
case HttpRequest::HTTP_REQUEST_HEAD:
|
|
||||||
mrb_iv_set(mrb, req, id, mrb_str_new_cstr(mrb, "DELETE"));
|
|
||||||
break;
|
|
||||||
|
|
||||||
default:
|
|
||||||
mrb_iv_set(mrb, req, id, mrb_str_new_cstr(mrb, "GET"));
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
|
|
||||||
// copy request parameter
|
|
||||||
map<string, string> values = request->values();
|
|
||||||
mrb_value parametersArray = mrb_hash_new_capa(mrb, values.size());
|
|
||||||
|
|
||||||
for (map<string, string>::iterator i = values.begin(); i != values.end(); ++i) {
|
|
||||||
string const& k = i->first;
|
|
||||||
string const& v = i->second;
|
|
||||||
|
|
||||||
key = mrb_str_new(mrb, k.c_str(), k.size());
|
|
||||||
val = mrb_str_new(mrb, v.c_str(), v.size());
|
|
||||||
|
|
||||||
mrb_hash_set(mrb, parametersArray, key, val);
|
|
||||||
}
|
|
||||||
|
|
||||||
id = mrb_intern(mrb, "@parameters");
|
|
||||||
mrb_iv_set(mrb, req, id, parametersArray);
|
|
||||||
|
|
||||||
// execute the callback
|
|
||||||
mrb_value args[2];
|
|
||||||
args[0] = req;
|
|
||||||
args[1] = res;
|
|
||||||
|
|
||||||
id = mrb_intern(mrb, "service");
|
|
||||||
mrb_funcall_argv(mrb, callback, id, 2, args);
|
|
||||||
|
|
||||||
if (mrb->exc) {
|
|
||||||
TRI_LogRubyException(mrb, mrb->exc);
|
|
||||||
mrb->exc = 0;
|
|
||||||
return new HttpResponse(HttpResponse::SERVER_ERROR, request->compatibility());
|
|
||||||
}
|
|
||||||
|
|
||||||
// set status code
|
|
||||||
id = mrb_intern(mrb, "@status");
|
|
||||||
val = mrb_iv_get(mrb, res, id);
|
|
||||||
HttpResponse::HttpResponseCode code = HttpResponse::OK;
|
|
||||||
|
|
||||||
if (! mrb_nil_p(val)) {
|
|
||||||
code = (HttpResponse::HttpResponseCode) MR_float(mrb, val);
|
|
||||||
}
|
|
||||||
|
|
||||||
// generate response
|
|
||||||
HttpResponse* response = new HttpResponse(code, request->compatibility());
|
|
||||||
|
|
||||||
// set content type
|
|
||||||
id = mrb_intern(mrb, "@content_type");
|
|
||||||
val = mrb_iv_get(mrb, res, id);
|
|
||||||
|
|
||||||
if (! mrb_nil_p(val)) {
|
|
||||||
response->setContentType(MR_string(mrb, val));
|
|
||||||
}
|
|
||||||
|
|
||||||
id = mrb_intern(mrb, "@body");
|
|
||||||
val = mrb_iv_get(mrb, res, id);
|
|
||||||
|
|
||||||
if (! mrb_nil_p(val)) {
|
|
||||||
response->body().appendText(MR_string(mrb, val));
|
|
||||||
}
|
|
||||||
|
|
||||||
return response;
|
|
||||||
}
|
|
||||||
|
|
||||||
// -----------------------------------------------------------------------------
|
|
||||||
// --SECTION-- ruby functions
|
|
||||||
// -----------------------------------------------------------------------------
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @brief defines an action
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
static mrb_value MR_Mount (mrb_state* mrb, mrb_value self) {
|
|
||||||
char* s;
|
|
||||||
size_t l;
|
|
||||||
mrb_value cl;
|
|
||||||
struct RClass* rcl;
|
|
||||||
|
|
||||||
mrb_get_args(mrb, "so", &s, &l, &cl);
|
|
||||||
|
|
||||||
// extract the mount point
|
|
||||||
if (s == NULL) {
|
|
||||||
return mrb_false_value();
|
|
||||||
}
|
|
||||||
|
|
||||||
// extract the class template
|
|
||||||
rcl = mrb_class_ptr(cl);
|
|
||||||
|
|
||||||
if (rcl == 0) {
|
|
||||||
return mrb_false_value();
|
|
||||||
}
|
|
||||||
|
|
||||||
// create an action with the given options
|
|
||||||
set<string> contexts;
|
|
||||||
contexts.insert("api");
|
|
||||||
contexts.insert("admin");
|
|
||||||
|
|
||||||
mr_action_t* action = new mr_action_t(contexts);
|
|
||||||
|
|
||||||
// store an action with the given name
|
|
||||||
TRI_action_t* result = TRI_DefineActionVocBase(s, action);
|
|
||||||
|
|
||||||
// and define the callback
|
|
||||||
if (result != 0) {
|
|
||||||
action = dynamic_cast<mr_action_t*>(result);
|
|
||||||
|
|
||||||
if (action != 0) {
|
|
||||||
mrb_value callback = mrb_class_new_instance(mrb, 0, 0, rcl);
|
|
||||||
|
|
||||||
action->createCallback(mrb, callback);
|
|
||||||
return mrb_false_value();
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
LOG_ERROR("cannot create callback for MRuby action");
|
|
||||||
return mrb_true_value();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
LOG_ERROR("cannot define MRuby action");
|
|
||||||
return mrb_false_value();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// -----------------------------------------------------------------------------
|
|
||||||
// --SECTION-- module functions
|
|
||||||
// -----------------------------------------------------------------------------
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @brief init mruby utilities
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
void TRI_InitMRActions (mrb_state* mrb, triagens::arango::ApplicationMR* applicationMR) {
|
|
||||||
MR_state_t* mrs;
|
|
||||||
struct RClass *rcl;
|
|
||||||
struct RClass *arango;
|
|
||||||
|
|
||||||
mrs = (MR_state_t*) mrb->ud;
|
|
||||||
arango = mrb_define_module(mrb, "Arango");
|
|
||||||
|
|
||||||
GlobalMRDealer = applicationMR;
|
|
||||||
|
|
||||||
// .............................................................................
|
|
||||||
// HttpServer
|
|
||||||
// .............................................................................
|
|
||||||
|
|
||||||
rcl = mrb_define_class_under(mrb, arango, "HttpServer", mrb->object_class);
|
|
||||||
|
|
||||||
mrb_define_class_method(mrb, rcl, "mount", MR_Mount, ARGS_REQ(2));
|
|
||||||
|
|
||||||
// .............................................................................
|
|
||||||
// HttpRequest
|
|
||||||
// .............................................................................
|
|
||||||
|
|
||||||
// TODO: rcl is assigned and then re-assigned directly. Is this intentional?
|
|
||||||
rcl = mrs->_arangoRequest = mrb_define_class_under(mrb, arango, "HttpRequest", mrb->object_class);
|
|
||||||
|
|
||||||
// .............................................................................
|
|
||||||
// HttpResponse
|
|
||||||
// .............................................................................
|
|
||||||
|
|
||||||
rcl = mrs->_arangoResponse = mrb_define_class_under(mrb, arango, "HttpResponse", mrb->object_class);
|
|
||||||
}
|
|
||||||
|
|
||||||
// Local Variables:
|
|
||||||
// mode: outline-minor
|
|
||||||
// outline-regexp: "/// @brief\\|/// {@inheritDoc}\\|/// @addtogroup\\|/// @page\\|// --SECTION--\\|/// @\\}"
|
|
||||||
// End:
|
|
|
@ -1,64 +0,0 @@
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @brief mruby actions
|
|
||||||
///
|
|
||||||
/// @file
|
|
||||||
///
|
|
||||||
/// DISCLAIMER
|
|
||||||
///
|
|
||||||
/// Copyright 2004-2014 triAGENS GmbH, Cologne, Germany
|
|
||||||
///
|
|
||||||
/// Licensed under the Apache License, Version 2.0 (the "License");
|
|
||||||
/// you may not use this file except in compliance with the License.
|
|
||||||
/// You may obtain a copy of the License at
|
|
||||||
///
|
|
||||||
/// http://www.apache.org/licenses/LICENSE-2.0
|
|
||||||
///
|
|
||||||
/// Unless required by applicable law or agreed to in writing, software
|
|
||||||
/// distributed under the License is distributed on an "AS IS" BASIS,
|
|
||||||
/// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
||||||
/// See the License for the specific language governing permissions and
|
|
||||||
/// limitations under the License.
|
|
||||||
///
|
|
||||||
/// Copyright holder is triAGENS GmbH, Cologne, Germany
|
|
||||||
///
|
|
||||||
/// @author Dr. Frank Celler
|
|
||||||
/// @author Copyright 2011-2014, triAGENS GmbH, Cologne, Germany
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
#ifndef TRIAGENS_MRSERVER_MR_ACTIONS_H
|
|
||||||
#define TRIAGENS_MRSERVER_MR_ACTIONS_H 1
|
|
||||||
|
|
||||||
#include "Basics/Common.h"
|
|
||||||
|
|
||||||
#include "MRuby/mr-utils.h"
|
|
||||||
|
|
||||||
// -----------------------------------------------------------------------------
|
|
||||||
// --SECTION-- forward declarations
|
|
||||||
// -----------------------------------------------------------------------------
|
|
||||||
|
|
||||||
namespace triagens {
|
|
||||||
namespace arango {
|
|
||||||
class ApplicationMR;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// -----------------------------------------------------------------------------
|
|
||||||
// --SECTION-- ACTIONS
|
|
||||||
// -----------------------------------------------------------------------------
|
|
||||||
|
|
||||||
// -----------------------------------------------------------------------------
|
|
||||||
// --SECTION-- module functions
|
|
||||||
// -----------------------------------------------------------------------------
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @brief init utilities
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
void TRI_InitMRActions (mrb_state* mrb, triagens::arango::ApplicationMR*);
|
|
||||||
|
|
||||||
#endif
|
|
||||||
|
|
||||||
// Local Variables:
|
|
||||||
// mode: outline-minor
|
|
||||||
// outline-regexp: "/// @brief\\|/// {@inheritDoc}\\|/// @addtogroup\\|/// @page\\|// --SECTION--\\|/// @\\}"
|
|
||||||
// End:
|
|
|
@ -133,17 +133,6 @@ bin_arangod_SOURCES = \
|
||||||
arangod/Cluster/ClusterMethods.cpp
|
arangod/Cluster/ClusterMethods.cpp
|
||||||
|
|
||||||
|
|
||||||
if ENABLE_MRUBY
|
|
||||||
|
|
||||||
bin_arangod_LDADD += \
|
|
||||||
lib/libarango_mruby.a \
|
|
||||||
@MRUBY_LIBS@
|
|
||||||
|
|
||||||
bin_arangod_SOURCES += \
|
|
||||||
arangod/MRServer/ApplicationMR.cpp \
|
|
||||||
arangod/MRServer/mr-actions.cpp
|
|
||||||
endif
|
|
||||||
|
|
||||||
################################################################################
|
################################################################################
|
||||||
## --SECTION-- SCANNER & PARSER
|
## --SECTION-- SCANNER & PARSER
|
||||||
################################################################################
|
################################################################################
|
||||||
|
|
|
@ -29,14 +29,6 @@
|
||||||
|
|
||||||
#include <v8.h>
|
#include <v8.h>
|
||||||
|
|
||||||
#ifdef TRI_ENABLE_MRUBY
|
|
||||||
#include "mruby.h"
|
|
||||||
#include "mruby/compile.h"
|
|
||||||
#include "mruby/data.h"
|
|
||||||
#include "mruby/proc.h"
|
|
||||||
#include "mruby/variable.h"
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#include "Actions/RestActionHandler.h"
|
#include "Actions/RestActionHandler.h"
|
||||||
#include "Actions/actions.h"
|
#include "Actions/actions.h"
|
||||||
#include "Admin/ApplicationAdminServer.h"
|
#include "Admin/ApplicationAdminServer.h"
|
||||||
|
@ -83,13 +75,6 @@
|
||||||
#include "Cluster/RestShardHandler.h"
|
#include "Cluster/RestShardHandler.h"
|
||||||
#include "Cluster/ClusterComm.h"
|
#include "Cluster/ClusterComm.h"
|
||||||
|
|
||||||
#ifdef TRI_ENABLE_MRUBY
|
|
||||||
#include "MRServer/ApplicationMR.h"
|
|
||||||
#include "MRServer/mr-actions.h"
|
|
||||||
#include "MRuby/MRLineEditor.h"
|
|
||||||
#include "MRuby/MRLoader.h"
|
|
||||||
#endif
|
|
||||||
|
|
||||||
using namespace std;
|
using namespace std;
|
||||||
using namespace triagens::basics;
|
using namespace triagens::basics;
|
||||||
using namespace triagens::rest;
|
using namespace triagens::rest;
|
||||||
|
@ -287,9 +272,6 @@ ArangoServer::ArangoServer (int argc, char** argv)
|
||||||
_applicationAdminServer(0),
|
_applicationAdminServer(0),
|
||||||
_applicationCluster(0),
|
_applicationCluster(0),
|
||||||
_jobManager(0),
|
_jobManager(0),
|
||||||
#ifdef TRI_ENABLE_MRUBY
|
|
||||||
_applicationMR(0),
|
|
||||||
#endif
|
|
||||||
_applicationV8(0),
|
_applicationV8(0),
|
||||||
_authenticateSystemOnly(false),
|
_authenticateSystemOnly(false),
|
||||||
_disableAuthentication(false),
|
_disableAuthentication(false),
|
||||||
|
@ -421,21 +403,9 @@ void ArangoServer::buildApplicationServer () {
|
||||||
_applicationServer->addFeature(_applicationV8);
|
_applicationServer->addFeature(_applicationV8);
|
||||||
|
|
||||||
// .............................................................................
|
// .............................................................................
|
||||||
// MRuby engine
|
// MRuby engine (this has been removed from arangod in version 2.2)
|
||||||
// .............................................................................
|
// .............................................................................
|
||||||
|
|
||||||
#ifdef TRI_ENABLE_MRUBY
|
|
||||||
|
|
||||||
_applicationMR = new ApplicationMR(_server);
|
|
||||||
|
|
||||||
if (_applicationMR == 0) {
|
|
||||||
LOG_FATAL_AND_EXIT("out of memory");
|
|
||||||
}
|
|
||||||
|
|
||||||
_applicationServer->addFeature(_applicationMR);
|
|
||||||
|
|
||||||
#else
|
|
||||||
|
|
||||||
string ignoreOpt;
|
string ignoreOpt;
|
||||||
|
|
||||||
additional[ApplicationServer::OPTIONS_HIDDEN]
|
additional[ApplicationServer::OPTIONS_HIDDEN]
|
||||||
|
@ -445,8 +415,6 @@ void ArangoServer::buildApplicationServer () {
|
||||||
("ruby.startup-directory", &ignoreOpt, "path to the directory containing alternate Ruby startup scripts")
|
("ruby.startup-directory", &ignoreOpt, "path to the directory containing alternate Ruby startup scripts")
|
||||||
;
|
;
|
||||||
|
|
||||||
#endif
|
|
||||||
|
|
||||||
// .............................................................................
|
// .............................................................................
|
||||||
// and start a simple admin server
|
// and start a simple admin server
|
||||||
// .............................................................................
|
// .............................................................................
|
||||||
|
@ -782,11 +750,6 @@ int ArangoServer::startupServer () {
|
||||||
_applicationV8->skipUpgrade();
|
_applicationV8->skipUpgrade();
|
||||||
}
|
}
|
||||||
|
|
||||||
#ifdef TRI_ENABLE_MRUBY
|
|
||||||
_applicationMR->setVocbase(vocbase);
|
|
||||||
_applicationMR->setConcurrency(_dispatcherThreads);
|
|
||||||
#endif
|
|
||||||
|
|
||||||
_applicationServer->prepare();
|
_applicationServer->prepare();
|
||||||
|
|
||||||
// .............................................................................
|
// .............................................................................
|
||||||
|
|
|
@ -224,14 +224,6 @@ namespace triagens {
|
||||||
|
|
||||||
rest::AsyncJobManager* _jobManager;
|
rest::AsyncJobManager* _jobManager;
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
/// @brief application MR
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
#ifdef TRI_ENABLE_MRUBY
|
|
||||||
ApplicationMR* _applicationMR;
|
|
||||||
#endif
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////////////////////////
|
||||||
/// @brief application V8
|
/// @brief application V8
|
||||||
////////////////////////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
Loading…
Reference in New Issue