Lumiera  0.pre.03
»edit your freedom«
text-template-gen-node-binding.hpp
Go to the documentation of this file.
1 /*
2  TEXT-TEMPLATE-GEN-NODE-BINDING.hpp - data binding adapter for ETD
3 
4  Copyright (C)
5  2024, Hermann Vosseler <Ichthyostega@web.de>
6 
7   **Lumiera** is free software; you can redistribute it and/or modify it
8   under the terms of the GNU General Public License as published by the
9   Free Software Foundation; either version 2 of the License, or (at your
10   option) any later version. See the file COPYING for further details.
11 
12 */
13 
14 
47 #ifndef LIB_TEXT_TEMPLATE_GEN_NODE_BINDING_H
48 #define LIB_TEXT_TEMPLATE_GEN_NODE_BINDING_H
49 
50 
51 #include "lib/diff/gen-node.hpp"
52 #include "lib/text-template.hpp"
53 
54 #include <string>
55 
56 
57 namespace lib {
58 
59  using std::string;
60 
61 
62  namespace text_template {
63 
64  /* ======= Data binding for GenNode (ETD) ======= */
65 
72  template<>
73  struct DataSource<diff::GenNode>
74  {
75  using Node = diff::GenNode;
76  using Rec = diff::Rec;
77 
78  Node const* data_;
79  DataSource* parScope_;
80  bool isSubScope() { return bool(parScope_); }
81 
82  DataSource(Node const& root)
83  : data_{&root}
84  , parScope_{nullptr}
85  { }
86 
87 
88  using Value = std::string;
89  using Iter = Rec::scopeIter;
90 
91  Node const*
92  findNode (string key)
93  {
94  if (data_->isNested())
95  {// standard case: Attribute lookup
96  Rec const& record = data_->data.get<Rec>();
97  if (record.hasAttribute (key))
98  return & record.get (key);
99  }
100  else
101  if ("value" == key) // special treatment for a »pseudo context«
102  return data_; // comprised only of a single value node
103  // ask parent scope...
104  if (isSubScope())
105  return parScope_->findNode (key);
106 
107  return nullptr;
108  }
109 
110  bool
111  contains (string key)
112  {
113  return bool(findNode (key));
114  }
115 
116  Value
117  retrieveContent (string key)
118  {
119  return renderCompact (*findNode(key));
120  }
121 
122  Iter
123  getSequence (string key)
124  {
125  if (not contains(key))
126  return Iter{};
127  Node const* node = findNode (key);
128  if (not node->isNested())
129  return Iter{};
130  else
131  return node->data.get<Rec>().scope();
132  }
133 
134  DataSource
135  openContext (Iter& iter)
136  {
137  REQUIRE (iter);
138  DataSource nested{*this};
139  nested.parScope_ = this;
140  nested.data_ = & *iter;
141  return nested;
142  }
143  };
144 
145  }// namespace text_template
146 
147 }// namespace lib
148 #endif /*LIB_TEXT_TEMPLATE_GEN_NODE_BINDING_H*/
Binding to a specific data source.
Implementation namespace for support and library code.
A minimalistic text templating engine with flexible data binding.
Generic building block for tree shaped (meta)data structures.
object-like record of data.
Definition: record.hpp:141
generic data element node within a tree
Definition: gen-node.hpp:222