add test for basic cd parsing
Change-Id: If35d62e323d48db11dc4128fb5c2898ef4ef63a6
diff --git a/src/ast.hpp b/src/ast.hpp
index 6c60dc9..f55ab39 100644
--- a/src/ast.hpp
+++ b/src/ast.hpp
@@ -1,15 +1,18 @@
/*
* Copyright (C) 2018 CESNET, https://photonics.cesnet.cz/
+ * Copyright (C) 2018 FIT CVUT, https://fit.cvut.cz/
*
* Written by Václav Kubernát <kubervac@fit.cvut.cz>
*
*/
#pragma once
#include <boost/spirit/home/x3.hpp>
-#include <vector>
#include <boost/spirit/home/x3/support/ast/position_tagged.hpp>
+
#include <boost/fusion/adapted/struct/adapt_struct.hpp>
#include <boost/fusion/include/adapt_struct.hpp>
+#include <vector>
+
#include "CTree.hpp"
namespace x3 = boost::spirit::x3;
namespace ascii = boost::spirit::x3::ascii;
@@ -22,76 +25,88 @@
using x3::lexeme;
using ascii::space;
-using nodeString = std::string;
-
-struct ParserContext
-{
+struct ParserContext {
ParserContext(const CTree& tree);
const CTree& m_tree;
- std::string m_currentContext;
+ std::string m_curPath;
};
struct parser_context_tag;
-struct container_
-{
- char m_first;
+struct container_ {
+ container_() {}
+ container_(const std::string& name);
+
+ bool operator==(const container_& b) const;
+
+ char m_first = ' ';
std::string m_name;
};
BOOST_FUSION_ADAPT_STRUCT(container_, m_first, m_name)
-struct path_
-{
+struct path_ {
+ bool operator==(const path_& b) const;
std::vector<container_> m_nodes;
};
BOOST_FUSION_ADAPT_STRUCT(path_, m_nodes)
-struct cd_
-{
+struct cd_ {
+ bool operator==(const cd_& b) const;
path_ m_path;
};
BOOST_FUSION_ADAPT_STRUCT(cd_, m_path)
-struct container_class
-{
+struct container_class {
template <typename T, typename Iterator, typename Context>
- inline void on_success(Iterator const& first, Iterator const& last
- , T& ast, Context const& context);
+ void on_success(Iterator const&, Iterator const&, T& ast, Context const& context)
+ {
+ ast.m_name = ast.m_first + ast.m_name;
+ auto& parserContext = x3::get<parser_context_tag>(context);
+ const auto& tree = parserContext.m_tree;
+
+ if (tree.isContainer(parserContext.m_curPath, ast.m_name)) {
+ if (!parserContext.m_curPath.empty()) {
+ parserContext.m_curPath += '/';
+ }
+ parserContext.m_curPath += ast.m_name;
+ } else {
+ throw InvalidNodeException("No container with the name \"" + ast.m_name + "\" in \"" + parserContext.m_curPath + "\"");
+ }
+ }
};
-struct path_class
-{
+struct path_class {
template <typename T, typename Iterator, typename Context>
- inline void on_success(Iterator const& first, Iterator const& last
- , T& ast, Context const& context);
+ void on_success(Iterator const&, Iterator const&, T&, Context const&)
+ {
+ }
};
-struct cd_class
-{
+struct cd_class {
template <typename T, typename Iterator, typename Context>
- inline void on_success(Iterator const& first, Iterator const& last
- , T& ast, Context const& context);
-
+ void on_success(Iterator const&, Iterator const&, T&, Context const&)
+ {
+ }
};
-typedef x3::rule<container_class, container_> container_type;
-typedef x3::rule<path_class, path_> path_type;
-typedef x3::rule<cd_class, cd_> cd_type;
+x3::rule<container_class, container_> const container = "container";
+x3::rule<path_class, path_> const path = "path";
+x3::rule<cd_class, cd_> const cd = "cd";
-container_type const container = "container";
-path_type const path = "path";
-cd_type const cd = "cd";
+auto const identifier =
+ lexeme[
+ ((alpha | char_("_")) >> *(alnum | char_("_") | char_("-") | char_(".")))
+ ];
auto const container_def =
- lexeme[
- ((alpha | x3::string("_")) >> *(alnum | x3::string("_") | x3::string("-") | x3::string(".")))
- ];
+ identifier;
+
auto const path_def =
container % '/';