From 971e006d132813293689ac68c279ccacb723f274 Mon Sep 17 00:00:00 2001 From: florijan Date: Wed, 8 Mar 2017 14:11:05 +0100 Subject: [PATCH] Query stripping now uses a parse tree and differentiates between int literals in a range expression (not stripped) and outside of a range (stripped). Summary: See above Reviewers: buda, mislav.bradac Reviewed By: mislav.bradac Subscribers: pullbot Differential Revision: https://phabricator.memgraph.io/D98 --- CMakeLists.txt | 1 + src/query/parameters.hpp | 74 ++++++ src/query/plan_interface.hpp | 5 +- src/query/preprocessor.hpp | 6 +- src/query/stripped.hpp | 17 +- src/query/stripper.cpp | 221 ++++++++++++++++++ src/query/stripper.hpp | 101 +------- tests/benchmark/query/strip/stripper.cpp | 3 +- .../cypher_queries/stripper/query_dict.yaml | 2 +- tests/integration/hardcoded_query/clique.cpp | 3 +- tests/integration/hardcoded_query/clique.hpp | 17 +- .../hardcoded_query/clique_scored.cpp | 3 +- .../create_full_profile_conceals_return.cpp | 9 +- .../create_full_profile_return.cpp | 7 +- .../create_full_profile_reveals_return.cpp | 9 +- .../hardcoded_query/create_garment.cpp | 7 +- .../create_garment_conceals.cpp | 9 +- .../create_garment_reveals.cpp | 9 +- .../hardcoded_query/delete_all.cpp | 5 +- .../hardcoded_query/match_garment.cpp | 5 +- .../match_garment_default_outfit.cpp | 7 +- .../match_garment_set_label_AA_return.cpp | 3 +- .../match_garment_set_label_BB_return.cpp | 3 +- .../match_garment_set_label_CC_return.cpp | 3 +- .../match_garment_set_label_DD_return.cpp | 3 +- .../match_garment_set_label_EE_return.cpp | 3 +- ...match_garment_set_label_general_return.hpp | 5 +- .../hardcoded_query/match_profile.cpp | 7 +- .../match_profile_garment_score.cpp | 10 +- .../match_profile_garment_set_score.cpp | 11 +- .../match_profile_garment_update_score.cpp | 11 +- tests/integration/hardcoded_query/template | 2 +- tests/manual/query_hash.cpp | 5 +- tests/manual/query_stripper_timing.cpp | 28 +++ tests/unit/query_stripper.cpp | 90 +++++++ 35 files changed, 523 insertions(+), 181 deletions(-) create mode 100644 src/query/parameters.hpp create mode 100644 src/query/stripper.cpp create mode 100644 tests/manual/query_stripper_timing.cpp create mode 100644 tests/unit/query_stripper.cpp diff --git a/CMakeLists.txt b/CMakeLists.txt index 5c0b90d73..c41f7fc62 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -346,6 +346,7 @@ set(memgraph_src_files ${src_dir}/logging/log.cpp ${src_dir}/database/graph_db.cpp ${src_dir}/database/graph_db_accessor.cpp + ${src_dir}/query/stripper.cpp ${src_dir}/query/backend/cpp/cypher_main_visitor.cpp ${src_dir}/query/backend/cpp/typed_value.cpp ) diff --git a/src/query/parameters.hpp b/src/query/parameters.hpp new file mode 100644 index 000000000..fb9be2905 --- /dev/null +++ b/src/query/parameters.hpp @@ -0,0 +1,74 @@ +// +// Copyright 2017 Memgraph +// Created by Florijan Stamenkovic on 08.03.17. +// + +#ifndef MEMGRAPH_PARAMETERS_HPP +#define MEMGRAPH_PARAMETERS_HPP + +#include + +/** + * Encapsulates user provided parameters (and stripped literals) + * and provides ways of obtaining them by name or position. + */ +struct Parameters { + public: + /** + * Adds a value to the stripped arguments under a sequentially + * generated name and returns a reference to that name. + * + * @param value + * @return + */ + const std::string &Add(const TypedValue &value) { + return storage_.emplace(NextName(), value).first->first; + } + + /** + * Returns the value found for the given name. + * The name MUST be present in this container + * (this is asserted). + * + * @param name Param name. + * @return Value for the given param. + */ + const TypedValue &At(const std::string &name) const { + auto found = storage_.find(name); + permanent_assert(found != storage_.end(), + "Name must be present in stripped arg container"); + return found->second; + } + + /** + * Returns the position-th stripped value. Asserts that this + * container has at least (position + 1) elements. + * + * This is future proofing for when both query params and + * stripping will be supported and naming collisions will have to + * be avoided. + * + * @param position Which stripped param is sought. + * @return Stripped param. + */ + const TypedValue &At(const size_t position) const { + permanent_assert(position < storage_.size(), "Invalid position"); + return storage_.find(NameForPosition(position))->second; + } + + /** Returns the number of arguments in this container */ + const size_t Size() const { return storage_.size(); } + + private: + std::map storage_; + + /** Generates and returns a new name */ + std::string NextName() const { return NameForPosition(storage_.size()); } + + /** Returns a name for positon */ + std::string NameForPosition(unsigned long position) const { + return "stripped_arg_" + std::to_string(position); + } +}; + +#endif //MEMGRAPH_PARAMETERS_HPP diff --git a/src/query/plan_interface.hpp b/src/query/plan_interface.hpp index 1b77a036d..fc5ae2dff 100644 --- a/src/query/plan_interface.hpp +++ b/src/query/plan_interface.hpp @@ -1,6 +1,7 @@ #pragma once #include "database/graph_db_accessor.hpp" + #include "query/stripped.hpp" /** @@ -18,12 +19,12 @@ class PlanInterface { * concrete execution plan. * * @param db_accessor Accessor for ihe database. - * @param args plan argument (vector of literal values from the query) + * @param args Plan arguments (including literals stripped from the query). * @param stream stream for results writing * * @return bool status after execution (success OR fail) */ - virtual bool run(GraphDbAccessor &db_accessor, const PropertyValueStore<> &args, + virtual bool run(GraphDbAccessor &db_accessor, const Parameters &args, Stream &stream) = 0; /** diff --git a/src/query/preprocessor.hpp b/src/query/preprocessor.hpp index 5f80c48e8..d2b96eab3 100644 --- a/src/query/preprocessor.hpp +++ b/src/query/preprocessor.hpp @@ -31,14 +31,10 @@ class QueryPreprocessor : public Loggable { * @return QueryStripped object */ auto preprocess(const std::string &query) { - auto preprocessed = stripper.strip(query); - + auto preprocessed = query::Strip(query); logger.info("stripped_query = {}", preprocessed.query); logger.info("query_hash = {}", preprocessed.hash); return preprocessed; } - - private: - QueryStripper stripper; }; diff --git a/src/query/stripped.hpp b/src/query/stripped.hpp index 24f0d3b2c..885de721b 100644 --- a/src/query/stripped.hpp +++ b/src/query/stripped.hpp @@ -1,7 +1,13 @@ #pragma once +#include + +#include "query/backend/cpp/typed_value.hpp" #include "storage/property_value_store.hpp" + +#include "utils/assert.hpp" #include "utils/hashing/fnv.hpp" +#include "parameters.hpp" /* * StrippedQuery contains: @@ -10,14 +16,13 @@ * * hash of stripped query */ struct StrippedQuery { - StrippedQuery(const std::string &&query, PropertyValueStore<> &&arguments, + StrippedQuery(const std::string &&query, + const Parameters &arguments, HashType hash) - : query(std::forward(query)), - arguments(std::forward>(arguments)), - hash(hash) {} + : query(query), arguments(arguments), hash(hash) {} /** - * Copy constructor is deleted because we don't want to make unecessary + * Copy constructor is deleted because we don't want to make unnecessary * copies of this object (copying of string and vector could be expensive) */ StrippedQuery(const StrippedQuery &other) = delete; @@ -38,7 +43,7 @@ struct StrippedQuery { /** * Stripped arguments */ - const PropertyValueStore<> arguments; + const Parameters arguments; /** * Hash based on stripped query. diff --git a/src/query/stripper.cpp b/src/query/stripper.cpp new file mode 100644 index 000000000..07dfb83fe --- /dev/null +++ b/src/query/stripper.cpp @@ -0,0 +1,221 @@ +// +// Copyright 2017 Memgraph +// Created by Florijan Stamenkovic on 07.03.17. +// +#include +#include +#include + +#include "logging/loggable.hpp" +#include "query/stripper.hpp" +#include "utils/hashing/fnv.hpp" +#include "utils/assert.hpp" + +#include "query/frontend/opencypher/generated/CypherBaseVisitor.h" +#include "query/frontend/opencypher/generated/CypherLexer.h" +#include "query/frontend/opencypher/generated/CypherParser.h" + +using namespace antlr4; +using namespace antlropencypher; + +namespace query { + +/** + * A visitor that for each literal that is not enclosed + * by a range literal calls the given callback (which should + * then replace Tokens of literals with placeholders). + */ +class StripperVisitor : public antlropencypher::CypherBaseVisitor { +public: + /** + * @param callback Callback function (see class description) called + * with start and stop tokens of a literal. + */ + StripperVisitor(const std::function callback) + : callback_(callback) {} + + antlrcpp::Any visitRangeLiteral( + CypherParser::RangeLiteralContext *ctx) override { + is_in_range_ = true; + auto r_val = visitChildren(ctx); + is_in_range_ = false; + return r_val; + } + + antlrcpp::Any visitLiteral( + CypherParser::LiteralContext *ctx) override { + if (ctx->booleanLiteral() != nullptr || + ctx->StringLiteral() != nullptr || + ctx->numberLiteral() != nullptr) + callback_(ctx->getStart(), ctx->getStop()); + + is_in_literal_ = true; + auto r_val = visitChildren(ctx); + is_in_literal_ = false; + return r_val; + } + + antlrcpp::Any visitIntegerLiteral( + CypherParser::IntegerLiteralContext *ctx) override { + // convert integer literals into param placeholders only if not in range + // literal + if (!is_in_range_ && !is_in_literal_) callback_(ctx->getStart(), ctx->getStop()); + return visitChildren(ctx); + } + +private: + const std::function callback_; + bool is_in_range_{false}; + bool is_in_literal_{false}; +}; + +/** + * Strips the input query and returns stripped query, stripped arguments and + * stripped query hash. + * + * @param query input query + * @return stripped query, stripped arguments and stripped query hash as a + * single object of class StrippedQuery + */ +StrippedQuery Strip(const std::string &query) { + + // tokenize the query + ANTLRInputStream input(query); + CypherLexer lexer(&input); + CommonTokenStream token_stream(&lexer); + token_stream.fill(); + std::vector tokens = token_stream.getTokens(); + + // initialize data structures we return + Parameters stripped_arguments; + + // convert tokens to strings, perform lowercasing and filtering + std::vector token_strings; + token_strings.reserve(tokens.size()); + for (int i = 0; i < tokens.size(); ++i) + switch (tokens[i]->getType()) { + case CypherLexer::UNION: + case CypherLexer::ALL: + case CypherLexer::OPTIONAL: + case CypherLexer::MATCH: + case CypherLexer::UNWIND: + case CypherLexer::AS: + case CypherLexer::MERGE: + case CypherLexer::ON: + case CypherLexer::CREATE: + case CypherLexer::SET: + case CypherLexer::DETACH: + case CypherLexer::DELETE: + case CypherLexer::REMOVE: + case CypherLexer::WITH: + case CypherLexer::DISTINCT: + case CypherLexer::RETURN: + case CypherLexer::ORDER: + case CypherLexer::BY: + case CypherLexer::L_SKIP: + case CypherLexer::LIMIT: + case CypherLexer::ASCENDING: + case CypherLexer::ASC: + case CypherLexer::DESCENDING: + case CypherLexer::DESC: + case CypherLexer::WHERE: + case CypherLexer::OR: + case CypherLexer::XOR: + case CypherLexer::AND: + case CypherLexer::NOT: + case CypherLexer::IN: + case CypherLexer::STARTS: + case CypherLexer::ENDS: + case CypherLexer::CONTAINS: + case CypherLexer::IS: + case CypherLexer::CYPHERNULL: + case CypherLexer::COUNT: + case CypherLexer::FILTER: + case CypherLexer::EXTRACT: + case CypherLexer::ANY: + case CypherLexer::NONE: + case CypherLexer::SINGLE: + token_strings.push_back(tokens[i]->getText()); + std::transform(token_strings.back().begin(), + token_strings.back().end(), + token_strings.back().begin(), ::tolower); + break; + + case CypherLexer::SP: + case Token::EOF: + token_strings.push_back(""); + break; + + default: + token_strings.push_back(tokens[i]->getText()); + break; + } + + // a helper function that generates a new param name for the stripped + // literal, appends is to the the stripped_query and adds the passed + // value to stripped args + auto replace_stripped = [&stripped_arguments, &token_strings]( + const TypedValue &value, size_t token_position) { + const auto &stripped_name = stripped_arguments.Add(value); + token_strings[token_position] = "$" + stripped_name; + }; + + // callback for every literal that should be changed + // TODO consider literal parsing problems (like an int with 100 digits) + auto callback = [&replace_stripped](Token *start, Token *end) { + assert(start->getTokenIndex() == end->getTokenIndex()); + switch (start->getType()) { + case CypherLexer::DecimalInteger: + replace_stripped(std::stoi(start->getText()), + start->getTokenIndex()); + break; + case CypherLexer::HexInteger: + replace_stripped(std::stoi(start->getText(), 0, 16), + start->getTokenIndex()); + break; + case CypherLexer::OctalInteger: + replace_stripped(std::stoi(start->getText(), 0, 8), + start->getTokenIndex()); + break; + case CypherLexer::StringLiteral: + replace_stripped(start->getText(), + start->getTokenIndex()); + break; + case CypherLexer::RegularDecimalReal: + case CypherLexer::ExponentDecimalReal: + replace_stripped(std::stof(start->getText()), + start->getTokenIndex()); + break; + case CypherLexer::TRUE: + replace_stripped(true, start->getTokenIndex()); + break; + case CypherLexer::FALSE: + replace_stripped(false, start->getTokenIndex()); + break; + + default: + permanent_assert(true, "Unsupported literal type"); + } + }; + + // parse the query and visit the AST with a stripping visitor + CypherParser parser(&token_stream); + tree::ParseTree *tree = parser.cypher(); + StripperVisitor stripper_visitor(callback); + stripper_visitor.visit(tree); + + // concatenate the stripped query tokens + std::string stripped_query; + stripped_query.reserve(query.size()); + for (const std::string &token_string : token_strings) { + stripped_query += token_string; + if (token_string.size() > 0) + stripped_query += " "; + } + + // return stripped query, stripped arguments and stripped query hash + return StrippedQuery(std::move(stripped_query), + std::move(stripped_arguments), + fnv(stripped_query)); +} +}; diff --git a/src/query/stripper.hpp b/src/query/stripper.hpp index 464186ebf..e28a99546 100644 --- a/src/query/stripper.hpp +++ b/src/query/stripper.hpp @@ -1,104 +1,7 @@ #pragma once -#include -#include -#include -#include -#include -#include - -#include "logging/loggable.hpp" #include "query/stripped.hpp" -#include "storage/property_value_store.hpp" -#include "utils/hashing/fnv.hpp" -#include "utils/string/transform.hpp" -#include "utils/variadic/variadic.hpp" -#include "antlr4-runtime.h" -#include "query/frontend/opencypher/generated/CypherLexer.h" -#include "query/frontend/opencypher/generated/CypherParser.h" - -using namespace antlr4; -using namespace antlropencypher; - -/** - * @brief QueryStripper - * - * Strips the input query and returns stripped query, stripped arguments and - * stripped query hash. - */ -class QueryStripper : public Loggable { - public: - QueryStripper() : Loggable("QueryStripper") {} - - QueryStripper(const QueryStripper &) = delete; - QueryStripper(QueryStripper &&) = delete; - QueryStripper &operator=(const QueryStripper &) = delete; - QueryStripper &operator=(QueryStripper &&) = delete; - - /** - * Strips the input query (openCypher query). - * - * @param query input query - * @param separator char that is added between all literals in the stripped - * query because after stripping compiler frontend will use the stripped - * query to AST and literals have to be separated - * - * @return stripped query, stripped arguments and stripped query hash as a - * single object of class StrippedQuery - */ - auto strip(const std::string &query, const std::string &separator = " ") { - // generate tokens - ANTLRInputStream input(query); - CypherLexer lexer(&input); - CommonTokenStream tokens(&lexer); - - // initialize data structures that will be populated - PropertyValueStore<> stripped_arguments; - std::string stripped_query; - stripped_query.reserve(query.size()); - - // iterate through tokens -> take arguments and generate stripped query - tokens.fill(); - int counter = 0; - for (auto token : tokens.getTokens()) { - int type = token->getType(); - if (type == CypherLexer::DecimalInteger || - type == CypherLexer::StringLiteral || - type == CypherLexer::RegularDecimalReal) { // TODO: add others - switch (type) { - case CypherLexer::DecimalInteger: - stripped_arguments.set(counter, std::stoi(token->getText())); - break; - case CypherLexer::StringLiteral: - stripped_arguments.set(counter, token->getText()); - break; - case CypherLexer::RegularDecimalReal: - stripped_arguments.set(counter, std::stof(token->getText())); - break; - } - stripped_query += std::to_string(counter++) + separator; - - } else if (type == CypherLexer::MATCH || type == CypherLexer::CREATE || - type == CypherLexer::RETURN || type == CypherLexer::DELETE || - type == CypherLexer::SET || - type == CypherLexer::WHERE) { // TODO: add others - auto value = token->getText(); - std::transform(value.begin(), value.end(), value.begin(), ::tolower); - stripped_query += value + separator; - } else if (type == CypherLexer::SP || type < 0 || - type > 113) { // SP || EOF // TODO: add others if exist - // pass - } else { - stripped_query += token->getText() + separator; - } - } - - // calculate query hash - HashType hash = fnv(stripped_query); - - // return stripped query, stripped arguments and stripped query hash - return StrippedQuery(std::move(stripped_query), - std::move(stripped_arguments), hash); - } +namespace query { + StrippedQuery Strip(const std::string &query); }; diff --git a/tests/benchmark/query/strip/stripper.cpp b/tests/benchmark/query/strip/stripper.cpp index 00b34e2b8..bd0e077e3 100644 --- a/tests/benchmark/query/strip/stripper.cpp +++ b/tests/benchmark/query/strip/stripper.cpp @@ -31,8 +31,7 @@ int main(int argc, char **argv) { for (auto &test : tests) { auto *benchmark = benchmark::RegisterBenchmark(test.c_str(), BM_Strip, preprocess, test) - ->RangeMultiplier(2) - ->Range(1, 8 << 10) + ->Range(1, 1) ->Complexity(benchmark::oN); } diff --git a/tests/data/cypher_queries/stripper/query_dict.yaml b/tests/data/cypher_queries/stripper/query_dict.yaml index 549733ce4..8fbf3baf3 100644 --- a/tests/data/cypher_queries/stripper/query_dict.yaml +++ b/tests/data/cypher_queries/stripper/query_dict.yaml @@ -17,7 +17,7 @@ benchmark_queries: - "MATCH (u:User) WITH {key: u} AS nodes DELETE nodes.key" - - "CREATE ()-[:T {id: 42, alive: true, name: kifla, height=4.2}]->()" + - "CREATE ()-[:T {id: 42, alive: true, name: kifla, height: 4.2}]->()" - "MATCH p = ()-[r:T]-() WHERE r.id = 42 DELETE r" diff --git a/tests/integration/hardcoded_query/clique.cpp b/tests/integration/hardcoded_query/clique.cpp index 1fa891261..9f0b68de2 100644 --- a/tests/integration/hardcoded_query/clique.cpp +++ b/tests/integration/hardcoded_query/clique.cpp @@ -9,6 +9,7 @@ #include "storage/vertex_accessor.hpp" #include "using.hpp" #include "utils/assert.hpp" +#include "query/parameters.hpp" using std::cout; using std::endl; @@ -20,7 +21,7 @@ using std::endl; class CPUPlan : public PlanInterface { public: - bool run(GraphDbAccessor &db_accessor, const PropertyValueStore<> &args, + bool run(GraphDbAccessor &db_accessor, const Parameters &args, Stream &stream) { return run_general_query(db_accessor, args, stream, CliqueQuery::FIND_ALL); } diff --git a/tests/integration/hardcoded_query/clique.hpp b/tests/integration/hardcoded_query/clique.hpp index 91102cc1e..08e8c6107 100644 --- a/tests/integration/hardcoded_query/clique.hpp +++ b/tests/integration/hardcoded_query/clique.hpp @@ -9,6 +9,7 @@ #include "storage/vertex_accessor.hpp" #include "using.hpp" #include "utils/assert.hpp" +#include "query/parameters.hpp" using std::cout; using std::endl; @@ -116,7 +117,7 @@ class Bitset { enum CliqueQuery { SCORE_AND_LIMIT, FIND_ALL }; bool run_general_query(GraphDbAccessor &db_accessor, - const PropertyValueStore<> &args, Stream &stream, + const Parameters &args, Stream &stream, enum CliqueQuery query_type) { if (query_type == CliqueQuery::FIND_ALL) stream.write_fields( @@ -129,7 +130,8 @@ bool run_general_query(GraphDbAccessor &db_accessor, // happening in code review!!! auto vertices_iterator = db_accessor.vertices(); auto edge_iterator = db_accessor.edges(); - std::vector vertices(vertices_iterator.begin(), vertices_iterator.end()); + std::vector vertices(vertices_iterator.begin(), + vertices_iterator.end()); std::vector edges(edge_iterator.begin(), edge_iterator.end()); std::vector vertices_indexed; @@ -142,11 +144,11 @@ bool run_general_query(GraphDbAccessor &db_accessor, if (query_type == CliqueQuery::SCORE_AND_LIMIT && vertices[i].has_label(db_accessor.label("profile"))) { auto has_prop = - vertices[i].PropsAt(db_accessor.property("profile_id")) == args.at(0); + vertices[i].PropsAt(db_accessor.property("profile_id")) == args.At(0); if (has_prop.type() == TypedValue::Type::Null) continue; if (has_prop.Value() == false) continue; has_prop = - vertices[i].PropsAt(db_accessor.property("partner_id")) == args.at(1); + vertices[i].PropsAt(db_accessor.property("partner_id")) == args.At(1); if (has_prop.type() == TypedValue::Type::Null) continue; if (has_prop.Value() == false) continue; profile_index = i; @@ -184,8 +186,7 @@ bool run_general_query(GraphDbAccessor &db_accessor, * @param bitset bitset to update. * @param edges edges from which to update bitset. */ - auto update = [&db_accessor, &query](Bitset &bitset, - auto &&edges) { + auto update = [&db_accessor, &query](Bitset &bitset, auto &&edges) { for (auto e : edges) { if (e.edge_type() != db_accessor.edge_type("default_outfit")) continue; const int from = query(e.from()); @@ -208,7 +209,7 @@ bool run_general_query(GraphDbAccessor &db_accessor, for (int i = 0; i < n; ++i) { const VertexAccessor v = *vertices_indexed[i]; auto cmp_res = v.PropsAt(db_accessor.property("garment_id")) == - args.at(query_type == CliqueQuery::SCORE_AND_LIMIT ? 8 : 0); + args.At(query_type == CliqueQuery::SCORE_AND_LIMIT ? 8 : 0); if (cmp_res.type() != TypedValue::Type::Bool) continue; if (cmp_res.Value() != true) continue; auto neigh = connected[i].Ones(); @@ -288,7 +289,7 @@ bool run_general_query(GraphDbAccessor &db_accessor, reverse(results.begin(), results.end()); } const int limit = query_type == CliqueQuery::SCORE_AND_LIMIT - ? args.at((int)args.size() - 1).Value() + ? args.At((int)args.Size() - 1).Value() : (int)results.size(); for (int i = 0; i < std::min(limit, (int)results.size()); ++i) { stream.write_record(); diff --git a/tests/integration/hardcoded_query/clique_scored.cpp b/tests/integration/hardcoded_query/clique_scored.cpp index cb8367dff..61c414309 100644 --- a/tests/integration/hardcoded_query/clique_scored.cpp +++ b/tests/integration/hardcoded_query/clique_scored.cpp @@ -9,6 +9,7 @@ #include "storage/vertex_accessor.hpp" #include "using.hpp" #include "utils/assert.hpp" +#include "query/parameters.hpp" using std::cout; using std::endl; @@ -26,7 +27,7 @@ using std::endl; class CPUPlan : public PlanInterface { public: - bool run(GraphDbAccessor &db_accessor, const PropertyValueStore<> &args, + bool run(GraphDbAccessor &db_accessor, const Parameters &args, Stream &stream) { return run_general_query(db_accessor, args, stream, CliqueQuery::SCORE_AND_LIMIT); diff --git a/tests/integration/hardcoded_query/create_full_profile_conceals_return.cpp b/tests/integration/hardcoded_query/create_full_profile_conceals_return.cpp index 47290eee0..989a22a3a 100644 --- a/tests/integration/hardcoded_query/create_full_profile_conceals_return.cpp +++ b/tests/integration/hardcoded_query/create_full_profile_conceals_return.cpp @@ -5,6 +5,7 @@ #include "storage/edge_accessor.hpp" #include "storage/vertex_accessor.hpp" #include "using.hpp" +#include "query/parameters.hpp" using std::cout; using std::endl; @@ -14,12 +15,12 @@ using std::endl; class CPUPlan : public PlanInterface { public: - bool run(GraphDbAccessor &db_accessor, const PropertyValueStore<> &args, + bool run(GraphDbAccessor &db_accessor, const Parameters &args, Stream &stream) { auto v = db_accessor.insert_vertex(); - v.PropsSet(db_accessor.property("profile_id"), args.at(0)); - v.PropsSet(db_accessor.property("partner_id"), args.at(1)); - v.PropsSet(db_accessor.property("conceals"), args.at(2)); + v.PropsSet(db_accessor.property("profile_id"), args.At(0)); + v.PropsSet(db_accessor.property("partner_id"), args.At(1)); + v.PropsSet(db_accessor.property("conceals"), args.At(2)); v.add_label(db_accessor.label("profile")); stream.write_field("p"); stream.write_vertex_record(v); diff --git a/tests/integration/hardcoded_query/create_full_profile_return.cpp b/tests/integration/hardcoded_query/create_full_profile_return.cpp index d3f9da601..6413079b5 100644 --- a/tests/integration/hardcoded_query/create_full_profile_return.cpp +++ b/tests/integration/hardcoded_query/create_full_profile_return.cpp @@ -5,6 +5,7 @@ #include "storage/edge_accessor.hpp" #include "storage/vertex_accessor.hpp" #include "using.hpp" +#include "query/parameters.hpp" using std::cout; using std::endl; @@ -13,11 +14,11 @@ using std::endl; class CPUPlan : public PlanInterface { public: - bool run(GraphDbAccessor &db_accessor, const PropertyValueStore<> &args, + bool run(GraphDbAccessor &db_accessor, const Parameters &args, Stream &stream) { auto v = db_accessor.insert_vertex(); - v.PropsSet(db_accessor.property("profile_id"), args.at(0)); - v.PropsSet(db_accessor.property("partner_id"), args.at(1)); + v.PropsSet(db_accessor.property("profile_id"), args.At(0)); + v.PropsSet(db_accessor.property("partner_id"), args.At(1)); v.add_label(db_accessor.label("profile")); stream.write_field("p"); stream.write_vertex_record(v); diff --git a/tests/integration/hardcoded_query/create_full_profile_reveals_return.cpp b/tests/integration/hardcoded_query/create_full_profile_reveals_return.cpp index dccf12ddf..7262ac20a 100644 --- a/tests/integration/hardcoded_query/create_full_profile_reveals_return.cpp +++ b/tests/integration/hardcoded_query/create_full_profile_reveals_return.cpp @@ -5,6 +5,7 @@ #include "storage/edge_accessor.hpp" #include "storage/vertex_accessor.hpp" #include "using.hpp" +#include "query/parameters.hpp" using std::cout; using std::endl; @@ -14,12 +15,12 @@ using std::endl; class CPUPlan : public PlanInterface { public: - bool run(GraphDbAccessor &db_accessor, const PropertyValueStore<> &args, + bool run(GraphDbAccessor &db_accessor, const Parameters &args, Stream &stream) { auto v = db_accessor.insert_vertex(); - v.PropsSet(db_accessor.property("profile_id"), args.at(0)); - v.PropsSet(db_accessor.property("partner_id"), args.at(1)); - v.PropsSet(db_accessor.property("reveals"), args.at(2)); + v.PropsSet(db_accessor.property("profile_id"), args.At(0)); + v.PropsSet(db_accessor.property("partner_id"), args.At(1)); + v.PropsSet(db_accessor.property("reveals"), args.At(2)); v.add_label(db_accessor.label("profile")); stream.write_field("p"); stream.write_vertex_record(v); diff --git a/tests/integration/hardcoded_query/create_garment.cpp b/tests/integration/hardcoded_query/create_garment.cpp index 618381304..56cc7f9fb 100644 --- a/tests/integration/hardcoded_query/create_garment.cpp +++ b/tests/integration/hardcoded_query/create_garment.cpp @@ -5,6 +5,7 @@ #include "storage/edge_accessor.hpp" #include "storage/vertex_accessor.hpp" #include "using.hpp" +#include "query/parameters.hpp" using std::cout; using std::endl; @@ -13,12 +14,12 @@ using std::endl; class CPUPlan : public PlanInterface { public: - bool run(GraphDbAccessor &db_accessor, const PropertyValueStore<> &args, + bool run(GraphDbAccessor &db_accessor, const Parameters &args, Stream &stream) { auto v = db_accessor.insert_vertex(); v.add_label(db_accessor.label("garment")); - v.PropsSet(db_accessor.property("garment_id"), args.at(0)); - v.PropsSet(db_accessor.property("garment_category_id"), args.at(1)); + v.PropsSet(db_accessor.property("garment_id"), args.At(0)); + v.PropsSet(db_accessor.property("garment_category_id"), args.At(1)); stream.write_field("g"); stream.write_vertex_record(v); stream.write_meta("rw"); diff --git a/tests/integration/hardcoded_query/create_garment_conceals.cpp b/tests/integration/hardcoded_query/create_garment_conceals.cpp index c49a29f54..08808efff 100644 --- a/tests/integration/hardcoded_query/create_garment_conceals.cpp +++ b/tests/integration/hardcoded_query/create_garment_conceals.cpp @@ -5,6 +5,7 @@ #include "storage/edge_accessor.hpp" #include "storage/vertex_accessor.hpp" #include "using.hpp" +#include "query/parameters.hpp" using std::cout; using std::endl; @@ -14,13 +15,13 @@ using std::endl; class CPUPlan : public PlanInterface { public: - bool run(GraphDbAccessor &db_accessor, const PropertyValueStore<> &args, + bool run(GraphDbAccessor &db_accessor, const Parameters &args, Stream &stream) { auto v = db_accessor.insert_vertex(); v.add_label(db_accessor.label("garment")); - v.PropsSet(db_accessor.property("garment_id"), args.at(0)); - v.PropsSet(db_accessor.property("garment_category_id"), args.at(1)); - v.PropsSet(db_accessor.property("conceals"), args.at(2)); + v.PropsSet(db_accessor.property("garment_id"), args.At(0)); + v.PropsSet(db_accessor.property("garment_category_id"), args.At(1)); + v.PropsSet(db_accessor.property("conceals"), args.At(2)); stream.write_field("g"); stream.write_vertex_record(v); stream.write_meta("rw"); diff --git a/tests/integration/hardcoded_query/create_garment_reveals.cpp b/tests/integration/hardcoded_query/create_garment_reveals.cpp index 2f6e96beb..73ea1d205 100644 --- a/tests/integration/hardcoded_query/create_garment_reveals.cpp +++ b/tests/integration/hardcoded_query/create_garment_reveals.cpp @@ -5,6 +5,7 @@ #include "storage/edge_accessor.hpp" #include "storage/vertex_accessor.hpp" #include "using.hpp" +#include "query/parameters.hpp" using std::cout; using std::endl; @@ -14,13 +15,13 @@ using std::endl; class CPUPlan : public PlanInterface { public: - bool run(GraphDbAccessor &db_accessor, const PropertyValueStore<> &args, + bool run(GraphDbAccessor &db_accessor, const Parameters &args, Stream &stream) { auto v = db_accessor.insert_vertex(); v.add_label(db_accessor.label("garment")); - v.PropsSet(db_accessor.property("garment_id"), args.at(0)); - v.PropsSet(db_accessor.property("garment_category_id"), args.at(1)); - v.PropsSet(db_accessor.property("reveals"), args.at(2)); + v.PropsSet(db_accessor.property("garment_id"), args.At(0)); + v.PropsSet(db_accessor.property("garment_category_id"), args.At(1)); + v.PropsSet(db_accessor.property("reveals"), args.At(2)); stream.write_field("g"); stream.write_vertex_record(v); stream.write_meta("rw"); diff --git a/tests/integration/hardcoded_query/delete_all.cpp b/tests/integration/hardcoded_query/delete_all.cpp index 918231e71..80c23f74c 100644 --- a/tests/integration/hardcoded_query/delete_all.cpp +++ b/tests/integration/hardcoded_query/delete_all.cpp @@ -1,8 +1,11 @@ #include #include +#include "query/backend/cpp/typed_value.hpp" #include "query/plan_interface.hpp" +#include "query/stripped.hpp" #include "using.hpp" +#include "query/parameters.hpp" using std::cout; using std::endl; @@ -11,7 +14,7 @@ using std::endl; class CPUPlan : public PlanInterface { public: - bool run(GraphDbAccessor &db_accessor, const PropertyValueStore<> &args, + bool run(GraphDbAccessor &db_accessor, const Parameters &args, Stream &stream) { for (auto v : db_accessor.vertices()) db_accessor.detach_remove_vertex(v); stream.write_empty_fields(); diff --git a/tests/integration/hardcoded_query/match_garment.cpp b/tests/integration/hardcoded_query/match_garment.cpp index 528d1a4e8..a044713b0 100644 --- a/tests/integration/hardcoded_query/match_garment.cpp +++ b/tests/integration/hardcoded_query/match_garment.cpp @@ -6,6 +6,7 @@ #include "storage/edge_accessor.hpp" #include "storage/vertex_accessor.hpp" #include "using.hpp" +#include "query/parameters.hpp" using std::cout; using std::endl; @@ -14,14 +15,14 @@ using std::endl; class CPUPlan : public PlanInterface { public: - bool run(GraphDbAccessor &db_accessor, const PropertyValueStore<> &args, + bool run(GraphDbAccessor &db_accessor, const Parameters &args, Stream &stream) { stream.write_field("g"); for (auto vertex : db_accessor.vertices()) { if (vertex.has_label(db_accessor.label("garment"))) { TypedValue prop = vertex.PropsAt(db_accessor.property("garment_id")); if (prop.type() == TypedValue::Type::Null) continue; - auto cmp = prop == args.at(0); + auto cmp = prop == args.At(0); if (cmp.type() != TypedValue::Type::Bool) continue; if (cmp.Value() != true) continue; stream.write_vertex_record(vertex); diff --git a/tests/integration/hardcoded_query/match_garment_default_outfit.cpp b/tests/integration/hardcoded_query/match_garment_default_outfit.cpp index 0805bfccc..5fa8d96c7 100644 --- a/tests/integration/hardcoded_query/match_garment_default_outfit.cpp +++ b/tests/integration/hardcoded_query/match_garment_default_outfit.cpp @@ -6,6 +6,7 @@ #include "storage/edge_accessor.hpp" #include "storage/vertex_accessor.hpp" #include "using.hpp" +#include "query/parameters.hpp" using std::cout; using std::endl; @@ -15,7 +16,7 @@ using std::endl; class CPUPlan : public PlanInterface { public: - bool run(GraphDbAccessor &db_accessor, const PropertyValueStore<> &args, + bool run(GraphDbAccessor &db_accessor, const Parameters &args, Stream &stream) { stream.write_field("r"); std::vector g1_set, g2_set; @@ -23,7 +24,7 @@ class CPUPlan : public PlanInterface { if (g1.has_label(db_accessor.label("garment"))) { TypedValue prop = g1.PropsAt(db_accessor.property("garment_id")); if (prop.type() == TypedValue::Type::Null) continue; - auto cmp = prop == args.at(0); + auto cmp = prop == args.At(0); if (cmp.type() != TypedValue::Type::Bool) continue; if (cmp.Value() != true) continue; g1_set.push_back(g1); @@ -33,7 +34,7 @@ class CPUPlan : public PlanInterface { if (g2.has_label(db_accessor.label("garment"))) { auto prop = g2.PropsAt(db_accessor.property("garment_id")); if (prop.type() == PropertyValue::Type::Null) continue; - auto cmp = prop == args.at(1); + auto cmp = prop == args.At(1); if (cmp.type() != TypedValue::Type::Bool) continue; if (cmp.Value() != true) continue; g2_set.push_back(g2); diff --git a/tests/integration/hardcoded_query/match_garment_set_label_AA_return.cpp b/tests/integration/hardcoded_query/match_garment_set_label_AA_return.cpp index 01e3cc748..b0836179a 100644 --- a/tests/integration/hardcoded_query/match_garment_set_label_AA_return.cpp +++ b/tests/integration/hardcoded_query/match_garment_set_label_AA_return.cpp @@ -4,6 +4,7 @@ #include "match_garment_set_label_general_return.hpp" #include "query/plan_interface.hpp" #include "using.hpp" +#include "query/parameters.hpp" using std::cout; using std::endl; @@ -12,7 +13,7 @@ using std::endl; class CPUPlan : public PlanInterface { public: - bool run(GraphDbAccessor &db_accessor, const PropertyValueStore<> &args, + bool run(GraphDbAccessor &db_accessor, const Parameters &args, Stream &stream) { return run_general_query(db_accessor, args, stream, "AA"); } diff --git a/tests/integration/hardcoded_query/match_garment_set_label_BB_return.cpp b/tests/integration/hardcoded_query/match_garment_set_label_BB_return.cpp index 94505f5ec..98c710507 100644 --- a/tests/integration/hardcoded_query/match_garment_set_label_BB_return.cpp +++ b/tests/integration/hardcoded_query/match_garment_set_label_BB_return.cpp @@ -4,6 +4,7 @@ #include "match_garment_set_label_general_return.hpp" #include "query/plan_interface.hpp" #include "using.hpp" +#include "query/parameters.hpp" using std::cout; using std::endl; @@ -12,7 +13,7 @@ using std::endl; class CPUPlan : public PlanInterface { public: - bool run(GraphDbAccessor &db_accessor, const PropertyValueStore<> &args, + bool run(GraphDbAccessor &db_accessor, const Parameters &args, Stream &stream) { return run_general_query(db_accessor, args, stream, "BB"); } diff --git a/tests/integration/hardcoded_query/match_garment_set_label_CC_return.cpp b/tests/integration/hardcoded_query/match_garment_set_label_CC_return.cpp index 67f2c895f..4e2fd2776 100644 --- a/tests/integration/hardcoded_query/match_garment_set_label_CC_return.cpp +++ b/tests/integration/hardcoded_query/match_garment_set_label_CC_return.cpp @@ -4,6 +4,7 @@ #include "match_garment_set_label_general_return.hpp" #include "query/plan_interface.hpp" #include "using.hpp" +#include "query/parameters.hpp" using std::cout; using std::endl; @@ -12,7 +13,7 @@ using std::endl; class CPUPlan : public PlanInterface { public: - bool run(GraphDbAccessor &db_accessor, const PropertyValueStore<> &args, + bool run(GraphDbAccessor &db_accessor, const Parameters &args, Stream &stream) { return run_general_query(db_accessor, args, stream, "CC"); } diff --git a/tests/integration/hardcoded_query/match_garment_set_label_DD_return.cpp b/tests/integration/hardcoded_query/match_garment_set_label_DD_return.cpp index da9ee716e..822a2968f 100644 --- a/tests/integration/hardcoded_query/match_garment_set_label_DD_return.cpp +++ b/tests/integration/hardcoded_query/match_garment_set_label_DD_return.cpp @@ -4,6 +4,7 @@ #include "match_garment_set_label_general_return.hpp" #include "query/plan_interface.hpp" #include "using.hpp" +#include "query/parameters.hpp" using std::cout; using std::endl; @@ -12,7 +13,7 @@ using std::endl; class CPUPlan : public PlanInterface { public: - bool run(GraphDbAccessor &db_accessor, const PropertyValueStore<> &args, + bool run(GraphDbAccessor &db_accessor, const Parameters &args, Stream &stream) { return run_general_query(db_accessor, args, stream, "DD"); } diff --git a/tests/integration/hardcoded_query/match_garment_set_label_EE_return.cpp b/tests/integration/hardcoded_query/match_garment_set_label_EE_return.cpp index c394160c1..18416c3a8 100644 --- a/tests/integration/hardcoded_query/match_garment_set_label_EE_return.cpp +++ b/tests/integration/hardcoded_query/match_garment_set_label_EE_return.cpp @@ -4,6 +4,7 @@ #include "match_garment_set_label_general_return.hpp" #include "query/plan_interface.hpp" #include "using.hpp" +#include "query/parameters.hpp" using std::cout; using std::endl; @@ -12,7 +13,7 @@ using std::endl; class CPUPlan : public PlanInterface { public: - bool run(GraphDbAccessor &db_accessor, const PropertyValueStore<> &args, + bool run(GraphDbAccessor &db_accessor, const Parameters &args, Stream &stream) { return run_general_query(db_accessor, args, stream, "EE"); } diff --git a/tests/integration/hardcoded_query/match_garment_set_label_general_return.hpp b/tests/integration/hardcoded_query/match_garment_set_label_general_return.hpp index 25e211e9a..f74c609ce 100644 --- a/tests/integration/hardcoded_query/match_garment_set_label_general_return.hpp +++ b/tests/integration/hardcoded_query/match_garment_set_label_general_return.hpp @@ -3,6 +3,7 @@ #include "query/backend/cpp/typed_value.hpp" #include "query/plan_interface.hpp" +#include "query/parameters.hpp" #include "storage/edge_accessor.hpp" #include "storage/vertex_accessor.hpp" #include "using.hpp" @@ -14,14 +15,14 @@ using std::endl; // RETURN g bool run_general_query(GraphDbAccessor &db_accessor, - const PropertyValueStore<> &args, Stream &stream, + const Parameters &args, Stream &stream, const std::string &general_label) { stream.write_field("g"); for (auto vertex : db_accessor.vertices()) { if (vertex.has_label(db_accessor.label("garment"))) { TypedValue prop = vertex.PropsAt(db_accessor.property("garment_id")); if (prop.type() == TypedValue::Type::Null) continue; - TypedValue cmp = prop == args.at(0); + TypedValue cmp = prop == args.At(0); if (cmp.type() != TypedValue::Type::Bool) continue; if (cmp.Value() != true) continue; vertex.add_label(db_accessor.label(general_label)); diff --git a/tests/integration/hardcoded_query/match_profile.cpp b/tests/integration/hardcoded_query/match_profile.cpp index 076fe9dc4..092386d59 100644 --- a/tests/integration/hardcoded_query/match_profile.cpp +++ b/tests/integration/hardcoded_query/match_profile.cpp @@ -6,6 +6,7 @@ #include "storage/edge_accessor.hpp" #include "storage/vertex_accessor.hpp" #include "using.hpp" +#include "query/parameters.hpp" using std::cout; using std::endl; @@ -14,20 +15,20 @@ using std::endl; class CPUPlan : public PlanInterface { public: - bool run(GraphDbAccessor &db_accessor, const PropertyValueStore<> &args, + bool run(GraphDbAccessor &db_accessor, const Parameters &args, Stream &stream) { stream.write_field("p"); for (auto vertex : db_accessor.vertices()) { if (vertex.has_label(db_accessor.label("profile"))) { TypedValue prop = vertex.PropsAt(db_accessor.property("profile_id")); if (prop.type() == TypedValue::Type::Null) continue; - auto cmp = prop == args.at(0); + auto cmp = prop == args.At(0); if (cmp.type() != TypedValue::Type::Bool) continue; if (cmp.Value() != true) continue; TypedValue prop2 = vertex.PropsAt(db_accessor.property("partner_id")); if (prop2.type() == TypedValue::Type::Null) continue; - auto cmp2 = prop2 == args.at(1); + auto cmp2 = prop2 == args.At(1); if (cmp2.type() != TypedValue::Type::Bool) continue; if (cmp2.Value() != true) continue; stream.write_vertex_record(vertex); diff --git a/tests/integration/hardcoded_query/match_profile_garment_score.cpp b/tests/integration/hardcoded_query/match_profile_garment_score.cpp index 41e401e65..3fb69f97e 100644 --- a/tests/integration/hardcoded_query/match_profile_garment_score.cpp +++ b/tests/integration/hardcoded_query/match_profile_garment_score.cpp @@ -3,9 +3,11 @@ #include "query/backend/cpp/typed_value.hpp" #include "query/plan_interface.hpp" +#include "query/stripped.hpp" #include "storage/edge_accessor.hpp" #include "storage/vertex_accessor.hpp" #include "using.hpp" +#include "query/parameters.hpp" using std::cout; using std::endl; @@ -16,26 +18,26 @@ using std::endl; class CPUPlan : public PlanInterface { public: - bool run(GraphDbAccessor &db_accessor, const PropertyValueStore<> &args, + bool run(GraphDbAccessor &db_accessor, const Parameters &args, Stream &stream) { stream.write_field("s"); auto profile = [&db_accessor, &args](const VertexAccessor &v) -> bool { TypedValue prop = v.PropsAt(db_accessor.property("profile_id")); if (prop.type() == TypedValue::Type::Null) return false; - auto cmp = prop == args.at(0); + auto cmp = prop == args.At(0); if (cmp.type() != TypedValue::Type::Bool) return false; if (cmp.Value() != true) return false; TypedValue prop2 = v.PropsAt(db_accessor.property("partner_id")); if (prop2.type() == TypedValue::Type::Null) return false; - auto cmp2 = prop2 == args.at(1); + auto cmp2 = prop2 == args.At(1); if (cmp2.type() != TypedValue::Type::Bool) return false; return cmp2.Value(); }; auto garment = [&db_accessor, &args](const VertexAccessor &v) -> bool { TypedValue prop = v.PropsAt(db_accessor.property("garment_id")); if (prop.type() == TypedValue::Type::Null) return false; - auto cmp = prop == args.at(2); + auto cmp = prop == args.At(2); if (cmp.type() != TypedValue::Type::Bool) return false; return cmp.Value(); }; diff --git a/tests/integration/hardcoded_query/match_profile_garment_set_score.cpp b/tests/integration/hardcoded_query/match_profile_garment_set_score.cpp index b6dbe1004..c267ccb4f 100644 --- a/tests/integration/hardcoded_query/match_profile_garment_set_score.cpp +++ b/tests/integration/hardcoded_query/match_profile_garment_set_score.cpp @@ -6,6 +6,7 @@ #include "storage/edge_accessor.hpp" #include "storage/vertex_accessor.hpp" #include "using.hpp" +#include "query/parameters.hpp" using std::cout; using std::endl; @@ -15,7 +16,7 @@ using std::endl; class CPUPlan : public PlanInterface { public: - bool run(GraphDbAccessor &db_accessor, const PropertyValueStore<> &args, + bool run(GraphDbAccessor &db_accessor, const Parameters &args, Stream &stream) { stream.write_field("r"); std::vector g1_set, g2_set; @@ -23,13 +24,13 @@ class CPUPlan : public PlanInterface { if (g1.has_label(db_accessor.label("profile"))) { auto prop = TypedValue(g1.PropsAt(db_accessor.property("profile_id"))); if (prop.type() == TypedValue::Type::Null) continue; - auto cmp = prop == args.at(0); + auto cmp = prop == args.At(0); if (cmp.type() != TypedValue::Type::Bool) continue; if (cmp.Value() != true) continue; auto prop2 = TypedValue(g1.PropsAt(db_accessor.property("partner_id"))); if (prop2.type() == TypedValue::Type::Null) continue; - auto cmp2 = prop2 == args.at(1); + auto cmp2 = prop2 == args.At(1); if (cmp2.type() != TypedValue::Type::Bool) continue; if (cmp2.Value() != true) continue; g1_set.push_back(g1); @@ -39,7 +40,7 @@ class CPUPlan : public PlanInterface { if (g2.has_label(db_accessor.label("garment"))) { auto prop = TypedValue(g2.PropsAt(db_accessor.property("garment_id"))); if (prop.type() == TypedValue::Type::Null) continue; - auto cmp = prop == args.at(2); + auto cmp = prop == args.At(2); if (cmp.type() != TypedValue::Type::Bool) continue; if (cmp.Value() != true) continue; g2_set.push_back(g2); @@ -49,7 +50,7 @@ class CPUPlan : public PlanInterface { for (auto g2 : g2_set) { EdgeAccessor e = db_accessor.insert_edge(g1, g2, db_accessor.edge_type("score")); - e.PropsSet(db_accessor.property("score"), args.at(3)); + e.PropsSet(db_accessor.property("score"), args.At(3)); stream.write_edge_record(e); } stream.write_meta("rw"); diff --git a/tests/integration/hardcoded_query/match_profile_garment_update_score.cpp b/tests/integration/hardcoded_query/match_profile_garment_update_score.cpp index 1fdd3295f..7f5a64fd2 100644 --- a/tests/integration/hardcoded_query/match_profile_garment_update_score.cpp +++ b/tests/integration/hardcoded_query/match_profile_garment_update_score.cpp @@ -6,6 +6,7 @@ #include "storage/edge_accessor.hpp" #include "storage/vertex_accessor.hpp" #include "using.hpp" +#include "query/parameters.hpp" using std::cout; using std::endl; @@ -16,26 +17,26 @@ using std::endl; class CPUPlan : public PlanInterface { public: - bool run(GraphDbAccessor &db_accessor, const PropertyValueStore<> &args, + bool run(GraphDbAccessor &db_accessor, const Parameters &args, Stream &stream) { stream.write_field("s"); auto profile = [&db_accessor, &args](const VertexAccessor &v) -> bool { TypedValue prop = v.PropsAt(db_accessor.property("profile_id")); if (prop.type() == TypedValue::Type::Null) return false; - auto cmp = prop == args.at(0); + auto cmp = prop == args.At(0); if (cmp.type() != TypedValue::Type::Bool) return false; if (cmp.Value() != true) return false; TypedValue prop2 = v.PropsAt(db_accessor.property("partner_id")); if (prop2.type() == TypedValue::Type::Null) return false; - auto cmp2 = prop2 == args.at(1); + auto cmp2 = prop2 == args.At(1); if (cmp2.type() != TypedValue::Type::Bool) return false; return cmp2.Value(); }; auto garment = [&db_accessor, &args](const VertexAccessor &v) -> bool { TypedValue prop = v.PropsAt(db_accessor.property("garment_id")); if (prop.type() == TypedValue::Type::Null) return false; - auto cmp = prop == args.at(2); + auto cmp = prop == args.At(2); if (cmp.type() != TypedValue::Type::Bool) return false; return cmp.Value(); }; @@ -44,7 +45,7 @@ class CPUPlan : public PlanInterface { auto to = edge.to(); if (edge.edge_type() != db_accessor.edge_type("score")) continue; if ((profile(from) && garment(to)) || (profile(to) && garment(from))) { - edge.PropsSet(db_accessor.property("score"), args.at(3)); + edge.PropsSet(db_accessor.property("score"), args.At(3)); stream.write_edge_record(edge); } } diff --git a/tests/integration/hardcoded_query/template b/tests/integration/hardcoded_query/template index e64fe4120..abbf15697 100644 --- a/tests/integration/hardcoded_query/template +++ b/tests/integration/hardcoded_query/template @@ -12,7 +12,7 @@ using std::endl; class CPUPlan : public PlanInterface { public: - bool run(GraphDbAccessor &db_accessor, const PropertyValueStore<> &args, + bool run(GraphDbAccessor &db_accessor, const StrippedArguments &args, Stream &stream) { db_accessor.commit(); return true; diff --git a/tests/manual/query_hash.cpp b/tests/manual/query_hash.cpp index f5972eb0d..78715d8ed 100644 --- a/tests/manual/query_hash.cpp +++ b/tests/manual/query_hash.cpp @@ -36,9 +36,8 @@ int main(int argc, char **argv) { println("Stripped query: ", preprocessed.query); println("Query hash: ", preprocessed.hash); println("Property values:"); - for (auto property : preprocessed.arguments) { - println(" ", property.second); - } + for (int i = 0; i < preprocessed.arguments.Size(); ++i) + println(" ", preprocessed.arguments.At(i)); println(""); return 0; diff --git a/tests/manual/query_stripper_timing.cpp b/tests/manual/query_stripper_timing.cpp new file mode 100644 index 000000000..f60312998 --- /dev/null +++ b/tests/manual/query_stripper_timing.cpp @@ -0,0 +1,28 @@ +// +// Copyright 2017 Memgraph +// Created by Florijan Stamenkovic on 07.03.17. +// + +#include +#include + +#include "query/stripper.hpp" + +int main(int argc, const char **a) { + if (argc < 2) { + std::cout << "Provide a query string as input" << std::endl; + return 1; + } + + const char *query = a[1]; + const int REPEATS = 100; + + clock_t begin = clock(); + for (int i = 0; i < REPEATS; ++i) + query::Strip(query); + clock_t end = clock(); + + double elapsed_secs = double(end - begin) / CLOCKS_PER_SEC; + std::cout << "Performed " << REPEATS << " strip ops, each took " + << elapsed_secs / REPEATS * 1000 << "ms" << std::endl; +} diff --git a/tests/unit/query_stripper.cpp b/tests/unit/query_stripper.cpp new file mode 100644 index 000000000..4dc3287de --- /dev/null +++ b/tests/unit/query_stripper.cpp @@ -0,0 +1,90 @@ +// +// Copyright 2017 Memgraph +// Created by Florijan Stamenkovic on 07.03.17. +// + +#include "gtest/gtest.h" + +#include "query/stripper.hpp" + +void EXPECT_PROP_TRUE(const TypedValue& a) { + EXPECT_TRUE(a.type() == TypedValue::Type::Bool && a.Value()); +} + +void EXPECT_PROP_EQ(const TypedValue& a, const TypedValue& b) { + EXPECT_PROP_TRUE(a == b); +} + +TEST(QueryStripper, NoLiterals) { + StrippedQuery stripped = query::Strip("CREATE (n)"); + EXPECT_EQ(stripped.arguments.Size(), 0); + EXPECT_EQ(stripped.query, "create ( n ) "); +} + +TEST(QueryStripper, DecimalInteger) { + StrippedQuery stripped = query::Strip("RETURN 42"); + EXPECT_EQ(stripped.arguments.Size(), 1); + EXPECT_EQ(stripped.arguments.At(0).Value(), 42); + EXPECT_EQ(stripped.query, "return $stripped_arg_0 "); +} + +TEST(QueryStripper, OctalInteger) { + StrippedQuery stripped = query::Strip("RETURN 010"); + EXPECT_EQ(stripped.arguments.Size(), 1); + EXPECT_EQ(stripped.arguments.At(0).Value(), 8); + EXPECT_EQ(stripped.query, "return $stripped_arg_0 "); +} + +TEST(QueryStripper, HexInteger) { + StrippedQuery stripped = query::Strip("RETURN 0xa"); + EXPECT_EQ(stripped.arguments.Size(), 1); + EXPECT_EQ(stripped.arguments.At(0).Value(), 10); + EXPECT_EQ(stripped.query, "return $stripped_arg_0 "); +} + +TEST(QueryStripper, RegularDecimal) { + StrippedQuery stripped = query::Strip("RETURN 42.3"); + EXPECT_EQ(stripped.arguments.Size(), 1); + EXPECT_FLOAT_EQ(stripped.arguments.At(0).Value(), 42.3); + EXPECT_EQ(stripped.query, "return $stripped_arg_0 "); +} + +TEST(QueryStripper, ExponentDecimal) { + StrippedQuery stripped = query::Strip("RETURN 4e2"); + EXPECT_EQ(stripped.arguments.Size(), 1); + EXPECT_FLOAT_EQ(stripped.arguments.At(0).Value(), 4e2); + EXPECT_EQ(stripped.query, "return $stripped_arg_0 "); +} + +TEST(QueryStripper, StringLiteral) { + StrippedQuery stripped = query::Strip("RETURN 'something'"); + EXPECT_EQ(stripped.arguments.Size(), 1); + EXPECT_EQ(stripped.arguments.At(0).Value(), "'something'"); + EXPECT_EQ(stripped.query, "return $stripped_arg_0 "); +} + +TEST(QueryStripper, BoolLiteral) { + StrippedQuery stripped = query::Strip("RETURN true"); + EXPECT_EQ(stripped.arguments.Size(), 1); + EXPECT_PROP_EQ(stripped.arguments.At(0), TypedValue(true)); + EXPECT_EQ(stripped.query, "return $stripped_arg_0 "); +} + +TEST(QueryStripper, ListLiteral) { + StrippedQuery stripped = query::Strip("MATCH (n) RETURN [n, n.prop]"); + EXPECT_EQ(stripped.arguments.Size(), 0); + EXPECT_EQ(stripped.query, "match ( n ) return [ n , n . prop ] "); +} + +TEST(QueryStripper, MapLiteral) { + StrippedQuery stripped = query::Strip("MATCH (n) RETURN {val: n}"); + EXPECT_EQ(stripped.arguments.Size(), 0); + EXPECT_EQ(stripped.query, "match ( n ) return { val : n } "); +} + +TEST(QueryStripper, RangeLiteral) { + StrippedQuery stripped = query::Strip("MATCH (n)-[*2..3]-() RETURN n"); + EXPECT_EQ(stripped.arguments.Size(), 0); + EXPECT_EQ(stripped.query, "match ( n ) - [ * 2 .. 3 ] - ( ) return n "); +} +