This library is a C++ parser, AST (Abstract Syntax Tree) and syntax analyzer implementation for the GQL graph database language (ISO/IEC 39075:2024). It requires C++17 or later and is distributed under the Apache License 2.0.
- GQL Parser and AST
- GQL Syntax Analyzer
- Build
- GQL Demo Application
- GQLLab.com Interactive Environment
- Current Status
- License
The library is designed to map GQL syntax to C++ types, enabling full static type checking and type safety. The AST does not use virtual functions.
Below are examples demonstrating how GQL expressions are represented in C++ types.
<graph pattern> ::=
[ <match mode> ] <path pattern list>
[ <keep clause> ]
[ <graph pattern where clause> ]
<path pattern list> ::=
<path pattern> [ { <comma> <path pattern> }... ]
using PathPatternList = std::vector<PathPattern>;
struct GraphPattern {
std::optional<MatchMode> matchMode;
PathPatternList patterns;
std::optional<KeepClause> keep;
std::optional<GraphPatternWhereClause> where;
};<primitive data-modifying statement> ::=
<insert statement>
| <set statement>
| <remove statement>
| <delete statement>
using PrimitiveDataModifyingStatement =
std::variant<InsertStatement, SetStatement, RemoveStatement, DeleteStatement>;To parse a GQL query from a string:
#include <gql/parser/parser.h>
void load_query(const char* query) {
try {
gql::ast::GQLProgram program = gql::parser::ParseProgram(query);
} catch (const gql::parser::ParserError& e) {
std::cerr << "Error: " << e.what() << std::endl;
}
}The AST provided by the library follows these principles:
- Simple
structs std::optionalfor optional child nodesstd::variantfor alternative child nodesstd::vectorfor sequences of child nodes
The root node of the AST is gql::ast::GQLProgram. All AST nodes are defined in include/gql/ast/nodes/.
Thanks to static typing, traversing the AST should work seamlessly with full IDE support. Handling variants can be somewhat cumbersome, so here’s a recommended approach:
void process(const gql::ast::LinearDataModifyingStatementBody& body) {
for (const auto& stmt : body.statements) {
gql::ast::variant_switch(
stmt,
[&](const gql::ast::SimpleQueryStatement& value) {
// Execute simple data-accessing statement
...
},
[&](const gql::ast::PrimitiveDataModifyingStatement& value) {
// Execute primitive data-modifying statement
...
},
[&](const gql::ast::CallProcedureStatement& value) {
// Execute call procedure statement
...
});
}
}In certain cases, the library employs the value_ptr smart pointer class (with type aliases ending in Ptr) to manage recursive types. The parser ensures these pointers are always initialized, allowing safe access without additional checks.
The AST data structures are intentionally simple, but you may need to store additional information in the AST beyond the parsing stage.
To facilitate this, you can provide a custom base class for AST nodes. If you define GQL_AST_CUSTOM_NODE_BASE_INCLUDE as a preprocessor macro with a header filename,
the specified file will be included before the AST node class definitions. This file can define a custom gql::ast::NodeBase<T> template, allowing you to override
the default base class for specific or all AST node types.
Refer to include/gql/ast/nodes/base.h for further details.
The Syntax Analyzer component performs the following functions:
- Applies the Syntax Rules of the ISO/IEC 39075:2024 standard to the GQL program code.
- Reports errors in the GQL program.
- Checks the fulfillment of Conformance Rules, reporting an error if the GQL program uses an optional GQL feature not supported by this GQL implementation. The list of unsupported features is specified in the client code.
- Performs transformations of the GQL program as provided by the Syntax Rules.
- Complements some AST nodes with information (called
auxDatain the code) that simplifies the execution of the GQL program.
Although the Syntax Analyzer makes relatively few changes to the AST, its use greatly simplifies the code that directly executes the GQL program, removing the need for many checks.
#include <gql/parser/parser.h>
#include <gql/syntax_analyzer/syntax_analyzer.h>
void analyze_query(const char* query) {
try {
gql::ast::GQLProgram program = gql::parser::ParseProgram(query);
gql::SyntaxAnalyzerConfig config;
gql::AnalyzeSyntax(program, config);
} catch (const gql::ParserError& e) {
std::cerr << "Error: " << e.what() << std::endl;
}
}The library uses CMake as its build system. Client code should link against the gql_parser static library for parser component and gql_syntax_analyzer for
syntax analyzer.
To build the library:
mkdir build
cd build
cmake ..
makeIf your project does not use CMake, you can manually include the library sources in your build system with minimal effort.
The GQL Demo application (located in src/demo) demonstrates how to use the AST and Syntax Analyzer components to build a GQL server implementation. While the AST and Syntax Analyzer components aim for full standard compliance, the set of features implemented in GQL Demo is limited. The GQL Demo code prioritizes readability and brevity over performance - it is not intended for production use and is not optimized. GQL Demo serves as the backend for GQLLab.com.
The GQLLab.com website (currently in active development) utilizes this library as its backend component. The website provides an interactive environment for learning GQL language capabilities and experimenting with queries on small-scale databases. While the GQL implementation on this site is not intended for production use or processing large data volumes, it is being developed to achieve maximum compliance with the ISO/IEC 39075:2024 standard.
The Sample Queries section on the website aims to progressively demonstrate all GQL language features.
The AST and parser components are production-ready with no known bugs. They provide complete coverage of the GQL language syntax as defined in ISO/IEC 39075:2024.
The Syntax Analyzer is under active development. Current status:
- Well-supported: Query statements and graph patterns
- In progress: Value expressions and value handling
- Ongoing: Reliability improvements and comprehensive testing
The goal is to implement 100% of the Syntax Rules specified in the ISO/IEC 39075:2024 standard.
Demo application is in active development. This implementation prioritizes:
- Standards compliance: Full adherence to ISO/IEC 39075:2024
- Maintainability: Clear, readable code over optimization
- Educational value: Demonstrating language features comprehensively
Note that this implementation intentionally trades some optional features and performance for simplicity and standard compliance.
This library is distributed under the Apache License 2.0.