1
0
Fork 0

Added empty dummy stubs for execute() in ExecutionBlock

This commit is contained in:
Michael Hackstein 2019-10-23 00:08:05 +02:00
parent 22d2977be5
commit 3ab448831c
11 changed files with 134 additions and 54 deletions

View File

@ -23,6 +23,7 @@
#include "BlocksWithClients.h"
#include "Aql/AqlCallStack.h"
#include "Aql/AqlItemBlock.h"
#include "Aql/AqlTransaction.h"
#include "Aql/AqlValue.h"
@ -137,3 +138,9 @@ std::pair<ExecutionState, size_t> BlocksWithClients::skipSome(size_t) {
TRI_ASSERT(false);
THROW_ARANGO_EXCEPTION(TRI_ERROR_NOT_IMPLEMENTED);
}
std::tuple<ExecutionState, size_t, SharedAqlItemBlockPtr> BlocksWithClients::execute(AqlCallStack stack) {
// This will not be implemented here!
TRI_ASSERT(false);
THROW_ARANGO_EXCEPTION(TRI_ERROR_NOT_IMPLEMENTED);
}

View File

@ -80,6 +80,8 @@ class BlocksWithClients : public ExecutionBlock {
virtual std::pair<ExecutionState, size_t> skipSomeForShard(size_t atMost,
std::string const& shardId) = 0;
std::tuple<ExecutionState, size_t, SharedAqlItemBlockPtr> execute(AqlCallStack stack) override;
protected:
/// @brief getClientId: get the number <clientId> (used internally)
/// corresponding to <shardId>

View File

@ -39,6 +39,7 @@ class Methods;
}
namespace aql {
class AqlCallStack;
class InputAqlItemRow;
class ExecutionEngine;
class ExecutionNode;
@ -96,8 +97,8 @@ class ExecutionBlock {
void traceGetSomeBegin(size_t atMost);
// Trace the end of a getSome call, potentially with result
std::pair<ExecutionState, SharedAqlItemBlockPtr> traceGetSomeEnd(
ExecutionState state, SharedAqlItemBlockPtr result);
std::pair<ExecutionState, SharedAqlItemBlockPtr> traceGetSomeEnd(ExecutionState state,
SharedAqlItemBlockPtr result);
void traceSkipSomeBegin(size_t atMost);
@ -122,6 +123,19 @@ class ExecutionBlock {
/// @brief add a dependency
void addDependency(ExecutionBlock* ep);
/// @brief main function to produce data in this ExecutionBlock.
/// It gets the AqlCallStack defining the operations required in every
/// subquery level. It will then perform the requested amount of offset, data and fullcount.
/// The AqlCallStack is copied on purpose, so this block can modify it.
/// Will return
/// 1. state:
/// * WAITING: We have async operation going on, nothing happend, please call again
/// * HASMORE: Here is some data in the request range, there is still more, if required call again
/// * DONE: Here is some data, and there will be no further data available.
/// 2. size_t: Amount of documents skipped.
/// 3. SharedAqlItemBlockPtr: The next data block.
virtual std::tuple<ExecutionState, size_t, SharedAqlItemBlockPtr> execute(AqlCallStack stack) = 0;
protected:
/// @brief the execution engine
ExecutionEngine* _engine;

View File

@ -26,6 +26,7 @@
#include "ExecutionBlockImpl.h"
#include "Aql/AllRowsFetcher.h"
#include "Aql/AqlCallStack.h"
#include "Aql/AqlItemBlock.h"
#include "Aql/CalculationExecutor.h"
#include "Aql/ConstFetcher.h"
@ -46,6 +47,7 @@
#include "Aql/InputAqlItemRow.h"
#include "Aql/KShortestPathsExecutor.h"
#include "Aql/LimitExecutor.h"
#include "Aql/MaterializeExecutor.h"
#include "Aql/ModificationExecutor.h"
#include "Aql/ModificationExecutorTraits.h"
#include "Aql/MultiDependencySingleRowFetcher.h"
@ -63,7 +65,6 @@
#include "Aql/SubqueryExecutor.h"
#include "Aql/SubqueryStartExecutor.h"
#include "Aql/TraversalExecutor.h"
#include "Aql/MaterializeExecutor.h"
#include <type_traits>
@ -79,18 +80,18 @@ using namespace arangodb::aql;
* constexpr bool someClassHasSomeMethod = hasSomeMethod<SomeClass>::value;
*/
#define CREATE_HAS_MEMBER_CHECK(methodName, checkName) \
template <typename T> \
class checkName { \
template <typename C> \
static std::true_type test(decltype(&C::methodName)); \
template <typename C> \
#define CREATE_HAS_MEMBER_CHECK(methodName, checkName) \
template <typename T> \
class checkName { \
template <typename C> \
static std::true_type test(decltype(&C::methodName)); \
template <typename C> \
static std::true_type test(decltype(&C::template methodName<>)); \
template <typename> \
static std::false_type test(...); \
\
public: \
static constexpr bool value = decltype(test<T>(0))::value; \
template <typename> \
static std::false_type test(...); \
\
public: \
static constexpr bool value = decltype(test<T>(0))::value; \
}
CREATE_HAS_MEMBER_CHECK(initializeCursor, hasInitializeCursor);
@ -301,23 +302,24 @@ static SkipVariants constexpr skipType() {
static_assert(!useFetcher || hasSkipRows<typename Executor::Fetcher>::value,
"Fetcher is chosen for skipping, but has not skipRows method!");
static_assert(useExecutor ==
(std::is_same<Executor, IndexExecutor>::value ||
std::is_same<Executor, IResearchViewExecutor<false, true>>::value ||
std::is_same<Executor, IResearchViewExecutor<true, true>>::value ||
std::is_same<Executor, IResearchViewMergeExecutor<false, true>>::value ||
std::is_same<Executor, IResearchViewMergeExecutor<true, true>>::value ||
std::is_same<Executor, IResearchViewExecutor<false, false>>::value ||
std::is_same<Executor, IResearchViewExecutor<true, false>>::value ||
std::is_same<Executor, IResearchViewMergeExecutor<false, false>>::value ||
std::is_same<Executor, IResearchViewMergeExecutor<true, false>>::value ||
std::is_same<Executor, EnumerateCollectionExecutor>::value ||
std::is_same<Executor, LimitExecutor>::value ||
std::is_same<Executor, IdExecutor<BlockPassthrough::Disable, SingleRowFetcher<BlockPassthrough::Disable>>>::value ||
std::is_same<Executor, ConstrainedSortExecutor>::value ||
std::is_same<Executor, SortingGatherExecutor>::value ||
std::is_same<Executor, MaterializeExecutor>::value),
"Unexpected executor for SkipVariants::EXECUTOR");
static_assert(
useExecutor ==
(std::is_same<Executor, IndexExecutor>::value ||
std::is_same<Executor, IResearchViewExecutor<false, true>>::value ||
std::is_same<Executor, IResearchViewExecutor<true, true>>::value ||
std::is_same<Executor, IResearchViewMergeExecutor<false, true>>::value ||
std::is_same<Executor, IResearchViewMergeExecutor<true, true>>::value ||
std::is_same<Executor, IResearchViewExecutor<false, false>>::value ||
std::is_same<Executor, IResearchViewExecutor<true, false>>::value ||
std::is_same<Executor, IResearchViewMergeExecutor<false, false>>::value ||
std::is_same<Executor, IResearchViewMergeExecutor<true, false>>::value ||
std::is_same<Executor, EnumerateCollectionExecutor>::value ||
std::is_same<Executor, LimitExecutor>::value ||
std::is_same<Executor, IdExecutor<BlockPassthrough::Disable, SingleRowFetcher<BlockPassthrough::Disable>>>::value ||
std::is_same<Executor, ConstrainedSortExecutor>::value ||
std::is_same<Executor, SortingGatherExecutor>::value ||
std::is_same<Executor, MaterializeExecutor>::value),
"Unexpected executor for SkipVariants::EXECUTOR");
// The LimitExecutor will not work correctly with SkipVariants::FETCHER!
static_assert(
@ -386,7 +388,6 @@ std::pair<ExecutionState, size_t> ExecutionBlockImpl<Executor>::skipSomeOnceWith
return {state, skipped};
}
template <bool customInit>
struct InitializeCursor {};
@ -453,6 +454,13 @@ std::pair<ExecutionState, Result> ExecutionBlockImpl<Executor>::shutdown(int err
return ExecutionBlock::shutdown(errorCode);
}
template <class Executor>
std::tuple<ExecutionState, size_t, SharedAqlItemBlockPtr> ExecutionBlockImpl<Executor>::execute(AqlCallStack stack) {
// TODO implement!
TRI_ASSERT(false);
THROW_ARANGO_EXCEPTION(TRI_ERROR_NOT_IMPLEMENTED);
}
// Work around GCC bug: https://gcc.gnu.org/bugzilla/show_bug.cgi?id=56480
// Without the namespaces it fails with
// error: specialization of 'template<class Executor> std::pair<arangodb::aql::ExecutionState, arangodb::Result> arangodb::aql::ExecutionBlockImpl<Executor>::initializeCursor(arangodb::aql::AqlItemBlock*, size_t)' in different namespace
@ -568,8 +576,8 @@ std::pair<ExecutionState, Result> ExecutionBlockImpl<SubqueryExecutor<false>>::s
}
template <>
std::pair<ExecutionState, Result>
ExecutionBlockImpl<IdExecutor<BlockPassthrough::Enable, SingleRowFetcher<BlockPassthrough::Enable>>>::shutdown(int errorCode) {
std::pair<ExecutionState, Result> ExecutionBlockImpl<
IdExecutor<BlockPassthrough::Enable, SingleRowFetcher<BlockPassthrough::Enable>>>::shutdown(int errorCode) {
if (this->infos().isResponsibleForInitializeCursor()) {
return ExecutionBlock::shutdown(errorCode);
}
@ -766,8 +774,10 @@ template class ::arangodb::aql::ExecutionBlockImpl<IResearchViewExecutor<true, f
template class ::arangodb::aql::ExecutionBlockImpl<IResearchViewMergeExecutor<false, false>>;
template class ::arangodb::aql::ExecutionBlockImpl<IResearchViewMergeExecutor<true, false>>;
template class ::arangodb::aql::ExecutionBlockImpl<IdExecutor<BlockPassthrough::Enable, ConstFetcher>>;
template class ::arangodb::aql::ExecutionBlockImpl<IdExecutor<BlockPassthrough::Enable, SingleRowFetcher<BlockPassthrough::Enable>>>;
template class ::arangodb::aql::ExecutionBlockImpl<IdExecutor<BlockPassthrough::Disable, SingleRowFetcher<BlockPassthrough::Disable>>>;
template class ::arangodb::aql::ExecutionBlockImpl<
IdExecutor<BlockPassthrough::Enable, SingleRowFetcher<BlockPassthrough::Enable>>>;
template class ::arangodb::aql::ExecutionBlockImpl<
IdExecutor<BlockPassthrough::Disable, SingleRowFetcher<BlockPassthrough::Disable>>>;
template class ::arangodb::aql::ExecutionBlockImpl<IndexExecutor>;
template class ::arangodb::aql::ExecutionBlockImpl<LimitExecutor>;
template class ::arangodb::aql::ExecutionBlockImpl<ModificationExecutor<Insert, SingleBlockFetcher<BlockPassthrough::Disable>>>;

View File

@ -98,7 +98,8 @@ class ExecutionBlockImpl final : public ExecutionBlock {
typename aql::DependencyProxy<Executor::Properties::allowsBlockPassthrough>;
static_assert(
Executor::Properties::allowsBlockPassthrough == BlockPassthrough::Disable || Executor::Properties::preservesOrder,
Executor::Properties::allowsBlockPassthrough == BlockPassthrough::Disable ||
Executor::Properties::preservesOrder,
"allowsBlockPassthrough must imply preservesOrder, but does not!");
public:
@ -174,6 +175,19 @@ class ExecutionBlockImpl final : public ExecutionBlock {
/// central place.
std::pair<ExecutionState, Result> shutdown(int) override;
/// @brief main function to produce data in this ExecutionBlock.
/// It gets the AqlCallStack defining the operations required in every
/// subquery level. It will then perform the requested amount of offset, data and fullcount.
/// The AqlCallStack is copied on purpose, so this block can modify it.
/// Will return
/// 1. state:
/// * WAITING: We have async operation going on, nothing happend, please call again
/// * HASMORE: Here is some data in the request range, there is still more, if required call again
/// * DONE: Here is some data, and there will be no further data available.
/// 2. size_t: Amount of documents skipped.
/// 3. SharedAqlItemBlockPtr: The next data block.
std::tuple<ExecutionState, size_t, SharedAqlItemBlockPtr> execute(AqlCallStack stack) override;
private:
/**
* @brief Inner getSome() part, without the tracing calls.

View File

@ -22,6 +22,7 @@
#include "IdExecutor.h"
#include "Aql/AqlCallStack.h"
#include "Aql/AqlValue.h"
#include "Aql/ConstFetcher.h"
#include "Aql/ExecutionEngine.h"
@ -43,9 +44,8 @@ constexpr BlockPassthrough IdExecutor<usePassThrough, T>::Properties::allowsBloc
template <BlockPassthrough usePassThrough, class T>
constexpr bool IdExecutor<usePassThrough, T>::Properties::inputSizeRestrictsOutputSize;
ExecutionBlockImpl<IdExecutor<BlockPassthrough::Enable, void>>::ExecutionBlockImpl(ExecutionEngine* engine,
ExecutionNode const* node,
RegisterId outputRegister, bool doCount)
ExecutionBlockImpl<IdExecutor<BlockPassthrough::Enable, void>>::ExecutionBlockImpl(
ExecutionEngine* engine, ExecutionNode const* node, RegisterId outputRegister, bool doCount)
: ExecutionBlock(engine, node),
_currentDependency(0),
_outputRegister(outputRegister),
@ -56,7 +56,8 @@ ExecutionBlockImpl<IdExecutor<BlockPassthrough::Enable, void>>::ExecutionBlockIm
}
}
std::pair<ExecutionState, size_t> ExecutionBlockImpl<IdExecutor<BlockPassthrough::Enable, void>>::skipSome(size_t atMost) {
std::pair<ExecutionState, size_t>
ExecutionBlockImpl<IdExecutor<BlockPassthrough::Enable, void>>::skipSome(size_t atMost) {
traceSkipSomeBegin(atMost);
if (isDone()) {
return traceSkipSomeEnd(ExecutionState::DONE, 0);
@ -73,7 +74,8 @@ std::pair<ExecutionState, size_t> ExecutionBlockImpl<IdExecutor<BlockPassthrough
return traceSkipSomeEnd(state, skipped);
}
std::pair<ExecutionState, SharedAqlItemBlockPtr> ExecutionBlockImpl<IdExecutor<BlockPassthrough::Enable, void>>::getSome(size_t atMost) {
std::pair<ExecutionState, SharedAqlItemBlockPtr>
ExecutionBlockImpl<IdExecutor<BlockPassthrough::Enable, void>>::getSome(size_t atMost) {
traceGetSomeBegin(atMost);
if (isDone()) {
return traceGetSomeEnd(ExecutionState::DONE, nullptr);
@ -99,10 +101,18 @@ bool aql::ExecutionBlockImpl<IdExecutor<BlockPassthrough::Enable, void>>::isDone
return _currentDependency >= _dependencies.size();
}
RegisterId ExecutionBlockImpl<IdExecutor<BlockPassthrough::Enable, void>>::getOutputRegisterId() const noexcept {
RegisterId ExecutionBlockImpl<IdExecutor<BlockPassthrough::Enable, void>>::getOutputRegisterId() const
noexcept {
return _outputRegister;
}
std::tuple<ExecutionState, size_t, SharedAqlItemBlockPtr>
ExecutionBlockImpl<IdExecutor<BlockPassthrough::Enable, void>>::execute(AqlCallStack stack) {
// TODO Implement me
TRI_ASSERT(false);
THROW_ARANGO_EXCEPTION(TRI_ERROR_NOT_IMPLEMENTED);
}
ExecutionBlock& ExecutionBlockImpl<IdExecutor<BlockPassthrough::Enable, void>>::currentDependency() const {
TRI_ASSERT(_currentDependency < _dependencies.size());
TRI_ASSERT(_dependencies[_currentDependency] != nullptr);
@ -209,10 +219,13 @@ template class ::arangodb::aql::IdExecutor<BlockPassthrough::Enable, SingleRowFe
template class ::arangodb::aql::IdExecutor<BlockPassthrough::Disable, SingleRowFetcher<BlockPassthrough::Disable>>;
template std::tuple<ExecutionState, typename IdExecutor<BlockPassthrough::Enable, ConstFetcher>::Stats, SharedAqlItemBlockPtr>
IdExecutor<BlockPassthrough::Enable, ConstFetcher>::fetchBlockForPassthrough<BlockPassthrough::Enable, void>(size_t atMost);
IdExecutor<BlockPassthrough::Enable, ConstFetcher>::fetchBlockForPassthrough<BlockPassthrough::Enable, void>(
size_t atMost);
template std::tuple<ExecutionState, typename IdExecutor<BlockPassthrough::Enable, SingleRowFetcher<BlockPassthrough::Enable>>::Stats, SharedAqlItemBlockPtr>
IdExecutor<BlockPassthrough::Enable, SingleRowFetcher<BlockPassthrough::Enable>>::fetchBlockForPassthrough<BlockPassthrough::Enable, void>(size_t atMost);
IdExecutor<BlockPassthrough::Enable, SingleRowFetcher<BlockPassthrough::Enable>>::fetchBlockForPassthrough<
BlockPassthrough::Enable, void>(size_t atMost);
template std::tuple<ExecutionState, NoStats, size_t>
IdExecutor<BlockPassthrough::Disable, SingleRowFetcher<BlockPassthrough::Disable>>::skipRows<BlockPassthrough::Disable, void>(size_t atMost);
IdExecutor<BlockPassthrough::Disable, SingleRowFetcher<BlockPassthrough::Disable>>::skipRows<
BlockPassthrough::Disable, void>(size_t atMost);

View File

@ -93,6 +93,8 @@ class ExecutionBlockImpl<IdExecutor<BlockPassthrough::Enable, void>> : public Ex
RegisterId getOutputRegisterId() const noexcept;
std::tuple<ExecutionState, size_t, SharedAqlItemBlockPtr> execute(AqlCallStack stack) override;
private:
bool isDone() const noexcept;

View File

@ -22,6 +22,7 @@
#include "RemoteExecutor.h"
#include "Aql/AqlCallStack.h"
#include "Aql/ClusterNodes.h"
#include "Aql/ExecutionEngine.h"
#include "Aql/ExecutorInfos.h"
@ -142,8 +143,6 @@ std::pair<ExecutionState, SharedAqlItemBlockPtr> ExecutionBlockImpl<RemoteExecut
auto res = sendAsyncRequest(fuerte::RestVerb::Put, "/_api/aql/getSome/",
std::move(buffer));
if (!res.ok()) {
THROW_ARANGO_EXCEPTION(res);
}
@ -373,6 +372,12 @@ std::pair<ExecutionState, Result> ExecutionBlockImpl<RemoteExecutor>::shutdown(i
return {ExecutionState::WAITING, TRI_ERROR_NO_ERROR};
}
std::tuple<ExecutionState, size_t, SharedAqlItemBlockPtr> ExecutionBlockImpl<RemoteExecutor>::execute(
AqlCallStack stack) {
TRI_ASSERT(false);
THROW_ARANGO_EXCEPTION(TRI_ERROR_NOT_IMPLEMENTED);
}
namespace {
Result handleErrorResponse(network::EndpointSpec const& spec, fuerte::Error err,
fuerte::Response* response) {
@ -390,7 +395,7 @@ Result handleErrorResponse(network::EndpointSpec const& spec, fuerte::Error err,
.append(spec.serverId)
.append("': ");
}
int res = TRI_ERROR_INTERNAL;
if (err != fuerte::Error::NoError) {
res = network::fuerteToArangoErrorCode(err);

View File

@ -24,8 +24,8 @@
#define ARANGOD_AQL_REMOTE_EXECUTOR_H
#include "Aql/ClusterNodes.h"
#include "Aql/ExecutorInfos.h"
#include "Aql/ExecutionBlockImpl.h"
#include "Aql/ExecutorInfos.h"
#include <mutex>
@ -62,6 +62,8 @@ class ExecutionBlockImpl<RemoteExecutor> : public ExecutionBlock {
std::pair<ExecutionState, Result> shutdown(int errorCode) override;
std::tuple<ExecutionState, size_t, SharedAqlItemBlockPtr> execute(AqlCallStack stack) override;
#ifdef ARANGODB_ENABLE_MAINTAINER_MODE
// only for asserts:
public:
@ -109,16 +111,16 @@ class ExecutionBlockImpl<RemoteExecutor> : public ExecutionBlock {
/// @brief the last remote response Result object, may contain an error.
arangodb::Result _lastError;
std::mutex _communicationMutex;
unsigned _lastTicket; /// used to check for canceled requests
bool _hasTriggeredShutdown;
// _communicationMutex *must* be locked for this!
unsigned generateNewTicket();
bool _didSendShutdownRequest = false;
void traceGetSomeRequest(velocypack::Slice slice, size_t atMost);

View File

@ -22,6 +22,7 @@
#include "WaitingExecutionBlockMock.h"
#include "Aql/AqlCallStack.h"
#include "Aql/AqlItemBlock.h"
#include "Aql/ExecutionEngine.h"
#include "Aql/ExecutionState.h"
@ -113,3 +114,9 @@ std::pair<arangodb::aql::ExecutionState, size_t> WaitingExecutionBlockMock::skip
return {ExecutionState::HASMORE, skipped};
}
}
std::tuple<ExecutionState, size_t, SharedAqlItemBlockPtr> WaitingExecutionBlockMock::execute(AqlCallStack stack) {
// TODO implement!
TRI_ASSERT(false);
THROW_ARANGO_EXCEPTION(TRI_ERROR_NOT_IMPLEMENTED);
}

View File

@ -95,6 +95,10 @@ class WaitingExecutionBlockMock final : public arangodb::aql::ExecutionBlock {
*/
std::pair<arangodb::aql::ExecutionState, size_t> skipSome(size_t atMost) override;
// TODO: Document and implement me!
std::tuple<arangodb::aql::ExecutionState, size_t, arangodb::aql::SharedAqlItemBlockPtr> execute(
arangodb::aql::AqlCallStack stack) override;
private:
std::deque<arangodb::aql::SharedAqlItemBlockPtr> _data;
arangodb::aql::ResourceMonitor _resourceMonitor;