Skip to content

Commit 8f75060

Browse files
authored
Auto resolve archive namespace (#254)
This allows using flatdata-inspector on archives that are nested inside a namespace. Signed-off-by: mohapatr3 <prasanta.mohapatra@here.com>
1 parent 4563927 commit 8f75060

File tree

3 files changed

+34
-4
lines changed

3 files changed

+34
-4
lines changed

flatdata-generator/flatdata/generator/engine.py

Lines changed: 10 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,7 @@
77

88
from flatdata.generator.tree.builder import build_ast
99
from flatdata.generator.tree.nodes.trivial.namespace import Namespace
10+
from flatdata.generator.tree.nodes.node import Node
1011

1112
from .generators.cpp import CppGenerator
1213
from .generators.dot import DotGenerator
@@ -69,7 +70,7 @@ def render_python_module(self, module_name=None, archive_name=None, root_namespa
6970
if specified, archive type is returned along with the model
7071
:param root_namespace: Root namespace to pick in case of multiple top level namespaces.
7172
"""
72-
root_namespace = self._find_root_namespace(self.tree, root_namespace)
73+
root_namespace = self._find_root_namespace(self.tree, archive_name, root_namespace)
7374
module_code = self.render("py")
7475
module = types.ModuleType(module_name if module_name is not None else root_namespace.name)
7576
#pylint: disable=exec-used
@@ -90,7 +91,7 @@ def _create_generator(cls, name):
9091
return generator_type()
9192

9293
@staticmethod
93-
def _find_root_namespace(tree, root_namespace=None):
94+
def _find_root_namespace(tree, archive_name, root_namespace=None):
9495
root_children = tree.root.children
9596
root_namespaces = [
9697
child for child in root_children
@@ -103,6 +104,13 @@ def _find_root_namespace(tree, root_namespace=None):
103104
if namespace.name == root_namespace:
104105
return namespace
105106
raise RuntimeError("Invalid root namespace provided. Could not find root namespace in archive.")
107+
elif archive_name:
108+
for namespace in root_namespaces:
109+
archive_path = namespace.name + Node.PATH_SEPARATOR + archive_name
110+
archive_node = namespace.get(archive_path)
111+
if archive_node is not None:
112+
return namespace
113+
raise RuntimeError("Archive direct parent namespace is not a root namespace.")
106114
elif len(root_namespaces) > 1:
107115
raise RuntimeError("Ambiguous root namespace. Could not find root archive.")
108116

flatdata-generator/flatdata/generator/tree/syntax_tree.py

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -39,6 +39,12 @@ def find(self, path):
3939
"""
4040
return self._root.find(path)
4141

42+
def get(self, path, default=None):
43+
"""
44+
Returns the node like find() does, but allows default value specification.
45+
"""
46+
return self._root.get(path, default)
47+
4248
def subtree(self, path):
4349
"""
4450
Returns subtree of the given tree as a SyntaxTree

flatdata-py/tests/test_backward_compatibility.py

Lines changed: 18 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -29,9 +29,25 @@ def test_instance_reading():
2929
check_signed_struct(archive.resource[0])
3030

3131

32-
def test_multi_namespace_instance_reading():
32+
def test_multi_namespace_instance_reading_implicit():
33+
root_namespace = None
34+
archive_name = "Archive"
35+
module, archive_type = Engine(MULTI_NAMESPACE_TEST_SCHEMA).render_python_module(None, archive_name, root_namespace)
36+
valid_data = {
37+
"Archive.archive": ARCHIVE_SIGNATURE_PAYLOAD,
38+
"Archive.archive.schema": module.backward_compatibility_Archive.schema().encode(),
39+
"resource": RESOURCE_PAYLOAD,
40+
"resource.schema": module.backward_compatibility_Archive.resource_schema('resource').encode()
41+
}
42+
archive = module.backward_compatibility_Archive(DictResourceStorage(valid_data))
43+
check_signed_struct(archive.resource)
44+
check_signed_struct(archive.resource[0])
45+
46+
47+
def test_multi_namespace_instance_reading_explicit():
3348
root_namespace = "backward_compatibility"
34-
module = Engine(MULTI_NAMESPACE_TEST_SCHEMA).render_python_module(None, None, root_namespace)
49+
archive_name = None
50+
module = Engine(MULTI_NAMESPACE_TEST_SCHEMA).render_python_module(None, archive_name, root_namespace)
3551
valid_data = {
3652
"Archive.archive": ARCHIVE_SIGNATURE_PAYLOAD,
3753
"Archive.archive.schema": module.backward_compatibility_Archive.schema().encode(),

0 commit comments

Comments
 (0)