diff --git a/hyperon_das_atomdb_cpp/src/constants.cc b/hyperon_das_atomdb_cpp/src/constants.cc
new file mode 100644
index 00000000..1cf3d993
--- /dev/null
+++ b/hyperon_das_atomdb_cpp/src/constants.cc
@@ -0,0 +1,19 @@
+#include "constants.h"
+
+namespace atomdb {
+
+const char* FieldNames::ID_HASH = "_id";
+const char* FieldNames::HANDLE = "handle";
+const char* FieldNames::COMPOSITE_TYPE = "composite_type";
+const char* FieldNames::COMPOSITE_TYPE_HASH = "composite_type_hash";
+const char* FieldNames::NODE_NAME = "name";
+const char* FieldNames::TYPE_NAME = "named_type";
+const char* FieldNames::TYPE_NAME_HASH = "named_type_hash";
+const char* FieldNames::KEY_PREFIX = "key";
+const char* FieldNames::KEYS = "keys";
+const char* FieldNames::IS_TOPLEVEL = "is_toplevel";
+const char* FieldNames::TARGETS = "targets";
+const char* FieldNames::TARGETS_DOCUMENTS = "targets_documents";
+const char* FieldNames::CUSTOM_ATTRIBUTES = "custom_attributes";
+
+} // namespace atomdb
\ No newline at end of file
diff --git a/hyperon_das_atomdb_cpp/src/constants.h b/hyperon_das_atomdb_cpp/src/constants.h
index e9b55467..826e66c7 100644
--- a/hyperon_das_atomdb_cpp/src/constants.h
+++ b/hyperon_das_atomdb_cpp/src/constants.h
@@ -16,4 +16,20 @@ static const string TYPEDEF_MARK_HASH = ExpressionHasher::named_type_hash(":");
enum FieldIndexType { BINARY_TREE = 0, TOKEN_INVERTED_LIST };
+struct FieldNames {
+ static const char* ID_HASH;
+ static const char* HANDLE;
+ static const char* COMPOSITE_TYPE;
+ static const char* COMPOSITE_TYPE_HASH;
+ static const char* NODE_NAME;
+ static const char* TYPE_NAME;
+ static const char* TYPE_NAME_HASH;
+ static const char* KEY_PREFIX;
+ static const char* KEYS;
+ static const char* IS_TOPLEVEL;
+ static const char* TARGETS;
+ static const char* TARGETS_DOCUMENTS;
+ static const char* CUSTOM_ATTRIBUTES;
+};
+
} // namespace atomdb
\ No newline at end of file
diff --git a/hyperon_das_atomdb_cpp/src/database.cc b/hyperon_das_atomdb_cpp/src/database.cc
index b6f52648..0f8b44fa 100644
--- a/hyperon_das_atomdb_cpp/src/database.cc
+++ b/hyperon_das_atomdb_cpp/src/database.cc
@@ -101,7 +101,7 @@ shared_ptr AtomDB::_build_link(const Link& link_params, bool is_toplevel)
const auto& targets = link_params.targets_documents;
if (link_type.empty() or targets.empty()) {
// TODO: log error ???
- throw AddLinkException("'type' and 'targets_documents' are required.",
+ throw AddLinkException("'type' and 'targets' are required.",
"link_params: " + link_params.to_string() +
", is_toplevel: " + (is_toplevel ? "true" : "false"));
}
diff --git a/hyperon_das_atomdb_cpp/src/hyperon_das_atomdb_cpp/constants/__init__.py b/hyperon_das_atomdb_cpp/src/hyperon_das_atomdb_cpp/constants/__init__.py
new file mode 100644
index 00000000..48786eff
--- /dev/null
+++ b/hyperon_das_atomdb_cpp/src/hyperon_das_atomdb_cpp/constants/__init__.py
@@ -0,0 +1 @@
+from ..ext.constants import * # type: ignore
diff --git a/hyperon_das_atomdb_cpp/src/hyperon_das_atomdb_cpp/database/__init__.py b/hyperon_das_atomdb_cpp/src/hyperon_das_atomdb_cpp/database/__init__.py
new file mode 100644
index 00000000..49131f1a
--- /dev/null
+++ b/hyperon_das_atomdb_cpp/src/hyperon_das_atomdb_cpp/database/__init__.py
@@ -0,0 +1 @@
+from ..ext.database import * # type: ignore
diff --git a/hyperon_das_atomdb_cpp/src/nanobind/bind_helpers.h b/hyperon_das_atomdb_cpp/src/nanobind/bind_helpers.h
index 403cd2bf..6d6c2990 100644
--- a/hyperon_das_atomdb_cpp/src/nanobind/bind_helpers.h
+++ b/hyperon_das_atomdb_cpp/src/nanobind/bind_helpers.h
@@ -99,11 +99,11 @@ static ListOfAny pylist_to_composite_type(const nb::list& py_list) {
*/
static nb::dict atom_to_dict(const Atom& self) {
nb::dict dict;
- dict["_id"] = self._id;
- dict["handle"] = self.handle;
- dict["composite_type_hash"] = self.composite_type_hash;
- dict["named_type"] = self.named_type;
- dict["custom_attributes"] = self.custom_attributes;
+ dict[FieldNames::ID_HASH] = self._id;
+ dict[FieldNames::HANDLE] = self.handle;
+ dict[FieldNames::COMPOSITE_TYPE_HASH] = self.composite_type_hash;
+ dict[FieldNames::TYPE_NAME] = self.named_type;
+ dict[FieldNames::CUSTOM_ATTRIBUTES] = self.custom_attributes;
return move(dict);
};
@@ -114,7 +114,7 @@ static nb::dict atom_to_dict(const Atom& self) {
*/
static nb::dict node_to_dict(const Node& self) {
nb::dict dict = atom_to_dict(self);
- dict["name"] = self.name;
+ dict[FieldNames::NODE_NAME] = self.name;
return move(dict);
};
@@ -125,10 +125,10 @@ static nb::dict node_to_dict(const Node& self) {
*/
static nb::dict link_to_dict(const Link& self) {
nb::dict dict = atom_to_dict(self);
- dict["composite_type"] = composite_type_to_pylist(self.composite_type);
- dict["named_type_hash"] = self.named_type_hash;
- dict["targets"] = self.targets;
- dict["is_toplevel"] = self.is_toplevel;
+ dict[FieldNames::COMPOSITE_TYPE] = composite_type_to_pylist(self.composite_type);
+ dict[FieldNames::TYPE_NAME_HASH] = self.named_type_hash;
+ dict[FieldNames::TARGETS] = self.targets;
+ dict[FieldNames::IS_TOPLEVEL] = self.is_toplevel;
nb::list targets_documents;
for (const auto& target : self.targets_documents) {
if (auto node = std::get_if(&target)) {
@@ -137,7 +137,7 @@ static nb::dict link_to_dict(const Link& self) {
targets_documents.append(link_to_dict(*link));
}
}
- dict["targets_documents"] = move(targets_documents);
+ dict[FieldNames::TARGETS_DOCUMENTS] = move(targets_documents);
return move(dict);
};
diff --git a/hyperon_das_atomdb_cpp/src/nanobind/hyperon_das_atomdb_cpp_bind.cc b/hyperon_das_atomdb_cpp/src/nanobind/hyperon_das_atomdb_cpp_bind.cc
index a7836ef1..50c65b05 100644
--- a/hyperon_das_atomdb_cpp/src/nanobind/hyperon_das_atomdb_cpp_bind.cc
+++ b/hyperon_das_atomdb_cpp/src/nanobind/hyperon_das_atomdb_cpp_bind.cc
@@ -29,16 +29,35 @@ namespace nb = nanobind;
using namespace nb::literals;
NB_MODULE(ext, m) {
- // root module ---------------------------------------------------------------------------------
- m.attr("WILDCARD") = WILDCARD;
- m.attr("WILDCARD_HASH") = WILDCARD_HASH;
- m.attr("TYPE_HASH") = TYPE_HASH;
- m.attr("TYPEDEF_MARK_HASH") = TYPEDEF_MARK_HASH;
- nb::enum_(m, "FieldIndexType", nb::is_arithmetic())
+ // ---------------------------------------------------------------------------------------------
+ // constants submodule -------------------------------------------------------------------------
+ nb::module_ constants = m.def_submodule("constants");
+ constants.attr("WILDCARD") = WILDCARD;
+ constants.attr("WILDCARD_HASH") = WILDCARD_HASH;
+ constants.attr("TYPE_HASH") = TYPE_HASH;
+ constants.attr("TYPEDEF_MARK_HASH") = TYPEDEF_MARK_HASH;
+ nb::enum_(constants, "FieldIndexType", nb::is_arithmetic())
.value("BINARY_TREE", FieldIndexType::BINARY_TREE)
.value("TOKEN_INVERTED_LIST", FieldIndexType::TOKEN_INVERTED_LIST)
.export_values();
- nb::class_(m, "AtomDB")
+ nb::class_(constants, "FieldNames")
+ .def_ro_static("ID_HASH", &FieldNames::ID_HASH)
+ .def_ro_static("HANDLE", &FieldNames::HANDLE)
+ .def_ro_static("COMPOSITE_TYPE", &FieldNames::COMPOSITE_TYPE)
+ .def_ro_static("COMPOSITE_TYPE_HASH", &FieldNames::COMPOSITE_TYPE_HASH)
+ .def_ro_static("NODE_NAME", &FieldNames::NODE_NAME)
+ .def_ro_static("TYPE_NAME", &FieldNames::TYPE_NAME)
+ .def_ro_static("TYPE_NAME_HASH", &FieldNames::TYPE_NAME_HASH)
+ .def_ro_static("KEY_PREFIX", &FieldNames::KEY_PREFIX)
+ .def_ro_static("KEYS", &FieldNames::KEYS)
+ .def_ro_static("IS_TOPLEVEL", &FieldNames::IS_TOPLEVEL)
+ .def_ro_static("TARGETS", &FieldNames::TARGETS)
+ .def_ro_static("TARGETS_DOCUMENTS", &FieldNames::TARGETS_DOCUMENTS)
+ .def_ro_static("CUSTOM_ATTRIBUTES", &FieldNames::CUSTOM_ATTRIBUTES);
+ // ---------------------------------------------------------------------------------------------
+ // database submodule --------------------------------------------------------------------------
+ nb::module_ database = m.def_submodule("database");
+ nb::class_(database, "AtomDB")
.def(nb::init<>())
.def_static("build_node_handle", &AtomDB::build_node_handle, "node_type"_a, "node_name"_a)
.def_static("node_handle", // retrocompatibility