Fixed Query compiler to use new interface.

This commit is contained in:
Kruno Tomola Fabro
2016-08-19 18:40:04 +01:00
parent e5f161974f
commit eba7fd8be4
25 changed files with 292 additions and 161 deletions

View File

@@ -4,6 +4,9 @@
#include <map>
#include <string>
#include "query_engine/code_generator/namer.hpp"
#include "storage/model/properties/flags.hpp"
// main states that are used while ast is traversed
// in order to generate ActionSequence
enum class CypherState : uint8_t
@@ -36,10 +39,11 @@ class CypherStateData
private:
std::map<std::string, EntityStatus> entity_status;
std::map<std::string, EntityType> entity_type;
// TODO: container that keeps track about c++ variable names
public:
bool exist(const std::string& name) const
bool exist(const std::string &name) const
{
return entity_status.find(name) != entity_status.end();
}
@@ -52,7 +56,7 @@ public:
return entity_status.at(name);
}
EntityType type(const std::string &name)
EntityType type(const std::string &name) const
{
if (entity_type.find(name) == entity_type.end())
return EntityType::NotFound;
@@ -60,6 +64,11 @@ public:
return entity_type.at(name);
}
const std::map<std::string, EntityType> &all_typed_enteties()
{
return entity_type;
}
void node_matched(const std::string &name)
{
entity_type[name] = EntityType::Node;

View File

@@ -1,9 +1,9 @@
#pragma once
#include "query_engine/code_generator/handlers/create.hpp"
#include "query_engine/code_generator/handlers/delete.hpp"
#include "query_engine/code_generator/handlers/match.hpp"
#include "query_engine/code_generator/handlers/return.hpp"
#include "query_engine/code_generator/handlers/set.hpp"
#include "query_engine/code_generator/handlers/delete.hpp"
#include "query_engine/code_generator/handlers/transaction_begin.hpp"
#include "query_engine/code_generator/handlers/transaction_commit.hpp"

View File

@@ -16,7 +16,7 @@ auto create_query_action =
code += code_line(code::create_vertex, name);
// update properties
code += update_properties(action_data, name);
code += update_properties(cypher_data, action_data, name);
// update labels
auto entity_data = action_data.get_entity_property(name);
@@ -30,19 +30,7 @@ auto create_query_action =
}
if (kv.second == ClauseAction::CreateRelationship) {
// create relationship
auto name = kv.first;
code += code_line(code::create_edge, name);
// update properties
code += update_properties(action_data, name);
// update tag
auto entity_data = action_data.get_entity_property(name);
for (auto &tag : entity_data.tags) {
code += code_line(code::find_type, tag);
code += code_line(code::set_type, name, tag);
}
// find start and end node
auto &relationships_data = action_data.relationship_data;
@@ -63,19 +51,32 @@ auto create_query_action =
" can't be found");
}
// define direction
if (relationship_data.direction == Direction::Right) {
code += code_line(code::node_out, left_node, name);
code += code_line(code::node_in, right_node, name);
code += code_line(code::edge_from, name, left_node);
code += code_line(code::edge_to, name, right_node);
} else if (relationship_data.direction == Direction::Left) {
code += code_line(code::node_out, right_node, name);
code += code_line(code::node_in, left_node, name);
code += code_line(code::edge_from, name, right_node);
code += code_line(code::edge_to, name, left_node);
// create relationship
code += code_line(code::create_edge, name, left_node, right_node);
// update properties
code += update_properties(cypher_data, action_data, name);
// update tag
auto entity_data = action_data.get_entity_property(name);
for (auto &tag : entity_data.tags) {
code += code_line(code::find_type, tag);
code += code_line(code::set_type, name, tag);
}
// define direction
// if (relationship_data.direction == Direction::Right) {
// code += code_line(code::node_out, left_node, name);
// code += code_line(code::node_in, right_node, name);
// code += code_line(code::edge_from, name, left_node);
// code += code_line(code::edge_to, name, right_node);
// } else if (relationship_data.direction == Direction::Left) {
// code += code_line(code::node_out, right_node, name);
// code += code_line(code::node_in, left_node, name);
// code += code_line(code::edge_from, name, right_node);
// code += code_line(code::edge_to, name, left_node);
// }
// mark relationship as created
cypher_data.relationship_created(name);
}

View File

@@ -6,11 +6,12 @@
#include <utility>
#include <vector>
#include "query_engine/util.hpp"
#include "query_engine/code_generator/cypher_state.hpp"
#include "query_engine/code_generator/namer.hpp"
#include "query_engine/code_generator/query_action_data.hpp"
#include "query_engine/traverser/code.hpp"
#include "query_engine/exceptions/errors.hpp"
#include "query_engine/traverser/code.hpp"
#include "query_engine/util.hpp"
using ParameterIndexKey::Type::InternalId;
using Direction = RelationshipData::Direction;
@@ -18,7 +19,8 @@ using Direction = RelationshipData::Direction;
namespace
{
auto update_properties(const QueryActionData &action_data,
auto update_properties(const CypherStateData &cypher_state,
const QueryActionData &action_data,
const std::string &name)
{
std::string code = "";
@@ -27,10 +29,14 @@ auto update_properties(const QueryActionData &action_data,
for (auto &property : entity_data.properties) {
auto index =
action_data.parameter_index.at(ParameterIndexKey(name, property));
code += code_line(code::set_property, name, property, index);
auto tmp_name = name::unique();
code += code_line((cypher_state.type(name) == EntityType::Node
? code::vertex_property_key
: code::edge_property_key),
tmp_name, property, index);
code += code_line(code::set_property, name, tmp_name, index);
}
return code;
}
}

View File

@@ -20,7 +20,6 @@ auto fetch_internal_index(const QueryActionData &action_data,
{
return action_data.parameter_index.at(ParameterIndexKey(InternalId, name));
}
}
auto match_query_action =
@@ -40,8 +39,7 @@ auto match_query_action =
auto place = action_data.csm.min(kv.first);
if (place == entity_search::search_internal_id) {
auto index = fetch_internal_index(action_data, name);
code +=
code_line(code::match_vertex_by_id, name, index);
code += code_line(code::match_vertex_by_id, name, index);
}
}

View File

@@ -12,7 +12,7 @@ auto return_query_action =
code += code_line("// number of elements {}", elements.size());
// TODO: call bolt serialization
for (const auto& element : elements) {
for (const auto &element : elements) {
auto &entity = element.entity;
if (!cypher_data.exist(entity)) {
throw SemanticError(
@@ -26,6 +26,6 @@ auto return_query_action =
// code += code_line(code::print_property, entity, property);
}
}
return code;
};

View File

@@ -13,13 +13,13 @@ auto set_query_action = [](CypherStateData &cypher_data,
if (kv.second == ClauseAction::UpdateNode &&
cypher_data.status(name) == EntityStatus::Matched &&
cypher_data.type(name) == EntityType::Node) {
code += update_properties(action_data, name);
code += update_properties(cypher_data, action_data, name);
}
if (kv.second == ClauseAction::UpdateRelationship &&
cypher_data.status(name) == EntityStatus::Matched &&
cypher_data.type(name) == EntityType::Relationship) {
code += update_properties(action_data, name);
code += update_properties(cypher_data, action_data, name);
}
}

View File

@@ -0,0 +1,18 @@
#pragma once
#include "storage/model/properties/flags.hpp"
// This namespace names stuff
namespace
{
namespace name
{
std::string variable_property_key(const std::string &property_name, Type type)
{
return "prop_" + property_name + "_" + type.to_str();
}
std::string unique() { return "unique_" + std::to_string(std::rand()); }
}
}

View File

@@ -4,9 +4,9 @@
#include <map>
#include <vector>
#include "query_engine/exceptions/exceptions.hpp"
#include "query_engine/code_generator/clause_action.hpp"
#include "query_engine/code_generator/entity_search.hpp"
#include "query_engine/exceptions/exceptions.hpp"
#include "storage/model/properties/all.hpp"
#include "utils/assert.hpp"
#include "utils/underlying_cast.hpp"
@@ -97,9 +97,9 @@ struct RelationshipData
struct ReturnElement
{
ReturnElement(const std::string& entity) : entity(entity) {}
ReturnElement(const std::string& entity, const std::string& property) :
entity(entity), property(property) {};
ReturnElement(const std::string &entity) : entity(entity) {}
ReturnElement(const std::string &entity, const std::string &property)
: entity(entity), property(property){};
std::string entity;
std::string property;
@@ -143,7 +143,7 @@ struct QueryActionData
}
// TODO: refactor name
auto get_entity_property(const std::string& entity) const
auto get_entity_property(const std::string &entity) const
{
if (entity_data.find(entity) == entity_data.end())
throw CppGeneratorException("Entity " + entity + " doesn't exist");

View File

@@ -18,9 +18,7 @@ auto load_queries(Db &db)
// CREATE (n {prop: 0}) RETURN n)
auto create_node = [&db](const properties_t &args) {
DbAccessor t(db);
auto prop_key = t.vertex_property_family_get("prop")
.get(args[0]->flags)
.family_key();
auto prop_key = t.vertex_property_key("prop", args[0]->flags);
auto vertex_accessor = t.vertex_insert();
vertex_accessor.set(prop_key, args[0]);
@@ -31,13 +29,11 @@ auto load_queries(Db &db)
auto create_labeled_and_named_node = [&db](const properties_t &args) {
DbAccessor t(db);
auto prop_key = t.vertex_property_family_get("name")
.get(args[0]->flags)
.family_key();
auto prop_key = t.vertex_property_key("name", args[0]->flags);
auto &label = t.label_find_or_create("LABEL");
auto vertex_accessor = t.vertex_insert();
vertex_accessor.set(prop_key, args[0]);
auto &label = t.label_find_or_create("LABEL");
vertex_accessor.add_label(label);
cout_properties(vertex_accessor.properties());
t.commit();
@@ -46,24 +42,17 @@ auto load_queries(Db &db)
auto create_account = [&db](const properties_t &args) {
DbAccessor t(db);
auto prop_id =
t.vertex_property_family_get("id").get(args[0]->flags).family_key();
auto prop_name = t.vertex_property_family_get("name")
.get(args[1]->flags)
.family_key();
auto prop_country = t.vertex_property_family_get("country")
.get(args[2]->flags)
.family_key();
auto prop_created = t.vertex_property_family_get("created_at")
.get(args[3]->flags)
.family_key();
auto prop_id = t.vertex_property_key("id", args[0]->flags);
auto prop_name = t.vertex_property_key("name", args[1]->flags);
auto prop_country = t.vertex_property_key("country", args[2]->flags);
auto prop_created = t.vertex_property_key("created_at", args[3]->flags);
auto &label = t.label_find_or_create("ACCOUNT");
auto vertex_accessor = t.vertex_insert();
vertex_accessor.set(prop_id, args[0]);
vertex_accessor.set(prop_name, args[1]);
vertex_accessor.set(prop_country, args[2]);
vertex_accessor.set(prop_created, args[3]);
auto &label = t.label_find_or_create("ACCOUNT");
vertex_accessor.add_label(label);
cout_properties(vertex_accessor.properties());
t.commit();
@@ -90,6 +79,7 @@ auto load_queries(Db &db)
auto create_edge = [&db](const properties_t &args) {
DbAccessor t(db);
auto &edge_type = t.type_find_or_create("IS");
auto v1 = t.vertex_find(args[0]->as<Int32>().value);
if (!option_fill(v1)) return t.commit(), false;
@@ -99,7 +89,6 @@ auto load_queries(Db &db)
auto edge_accessor = t.edge_insert(v1.get(), v2.get());
auto &edge_type = t.type_find_or_create("IS");
edge_accessor.edge_type(edge_type);
t.commit();
@@ -139,9 +128,7 @@ auto load_queries(Db &db)
auto update_node = [&db](const properties_t &args) {
DbAccessor t(db);
auto prop_name = t.vertex_property_family_get("name")
.get(args[1]->flags)
.family_key();
auto prop_name = t.vertex_property_key("name", args[1]->flags);
auto maybe_v = t.vertex_find(args[0]->as<Int32>().value);
if (!option_fill(maybe_v)) return t.commit(), false;
@@ -160,11 +147,8 @@ auto load_queries(Db &db)
auto create_edge_v2 = [&db](const properties_t &args) {
DbAccessor t(db);
auto prop_age =
t.edge_property_family_get("age").get(args[2]->flags).family_key();
auto prop_weight = t.edge_property_family_get("weight")
.get(args[3]->flags)
.family_key();
auto prop_age = t.edge_property_key("age", args[2]->flags);
auto prop_weight = t.edge_property_key("weight", args[3]->flags);
auto n1 = t.vertex_find(args[0]->as<Int64>().value);
if (!option_fill(n1)) return t.commit(), false;
@@ -202,8 +186,7 @@ auto load_queries(Db &db)
DbAccessor t(db);
auto &label = t.label_find_or_create("LABEL");
auto prop_key =
t.vertex_property_family_get("name").get(Type::String).family_key();
auto prop_key = t.vertex_property_key("name", Flags::String);
cout << "VERTICES" << endl;
iter::for_all(label.index->for_range_exact(t),

View File

@@ -2,6 +2,7 @@
#include "communication/communication.hpp"
#include "database/db.hpp"
#include "database/db_accessor.hpp"
#include "query_engine/query_stripped.hpp"
class ICodeCPU

View File

@@ -16,56 +16,53 @@ namespace code
// TODO: UNIT tests
const std::string transaction_begin = "auto& t = db.tx_engine.begin();";
const std::string transaction_begin = "DbAccessor t(db);";
const std::string transaction_commit = "t.commit();";
const std::string set_property = "{}.property(\"{}\", args[{}]);";
const std::string set_property = "{}.set({}, args[{}]);";
// create vertex e.g. CREATE (n:PERSON {name: "Test", age: 23})
const std::string create_vertex = "auto {} = db.graph.vertices.insert(t);";
const std::string create_label =
"auto &{0} = db.graph.label_store.find_or_create(\"{0}\");";
const std::string create_vertex = "auto {} = t.vertex_insert();";
const std::string create_label = "auto &{0} = t.label_find_or_create(\"{0}\");";
const std::string add_label = "{}.add_label({});";
const std::string vertex_property_key =
"auto {}=t.vertex_property_key(\"{}\",args[{}]->flags);";
const std::string edge_property_key =
"auto {}=t.edge_property_key(\"{}\",args[{}]->flags);";
// create edge e.g CREATE (n1)-[r:COST {cost: 100}]->(n2)
const std::string create_edge = "auto {} = db.graph.edges.insert(t);";
const std::string find_type =
"auto &{0} = db.graph.edge_type_store.find_or_create(\"{0}\");";
const std::string create_edge = "auto {} = t.edge_insert({},{});";
const std::string find_type = "auto &{0} = t.type_find_or_create(\"{0}\");";
const std::string set_type = "{}.edge_type({});";
const std::string node_out = "{}.vlist->update(t)->data.out.add({}.vlist);";
const std::string node_in = "{}.vlist->update(t)->data.in.add({}.vlist);";
const std::string edge_from = "{}.from({}.vlist);";
const std::string edge_to = "{}.to({}.vlist);";
const std::string args_id = "auto id = args[{}]->as<Int32>();";
const std::string vertex_accessor_args_id =
"auto vertex_accessor = db.graph.vertices.find(t, id.value);";
"auto vertex_accessor = t.vertex_find(id.value);";
const std::string match_vertex_by_id =
"auto {0} = db.graph.vertices.find(t, args[{1}]->as<Int64>().value);\n"
" if (!{0}) return t.commit(), false;";
"auto option_{0} = t.vertex_find(args[{1}]->as<Int64>().value);\n"
" if (!option_fill(option_{0})) return t.commit(), false;\n"
" auto {0}=option_{0}.take();";
const std::string match_edge_by_id =
"auto {0} = db.graph.edges.find(t, args[{1}]->as<Int64>().value);\n"
" if (!{0}) return t.commit(), false;";
"auto option_{0} = t.edge_find(args[{1}]->as<Int64>().value);\n"
" if (!option_fill(option_{0})) return t.commit(), false;\n"
" auto {0}=option_{0}.take();";
const std::string write_entity =
"stream.write_field(\"{0}\");\n"
" stream.write_record();\n"
" stream.write_list_header(1);\n"
" stream.write({0});\n"
" stream.write_success_empty();\n";
const std::string write_entity = "stream.write_field(\"{0}\");\n"
" stream.write_record();\n"
" stream.write_list_header(1);\n"
" stream.write({0});\n"
" stream.write_success_empty();\n";
const std::string return_true = "return true;";
const std::string update_property = "{}.property(\"{}\", args[{}]);";
const std::string todo = "// TODO: {}";
const std::string print_properties =
"cout << \"{0}\" << endl;\n"
" cout_properties({0}.properties());";
const std::string print_property =
"cout_property(\"{0}\", {0}.property(\"{1}\"));";
}