blob: c62c24080b4fb2ea0bed640d20c6f8a1433ed986 [file] [log] [blame]
Václav Kubernátab612e92019-11-26 19:51:31 +01001/*
2 * Copyright (C) 2019 CESNET, https://photonics.cesnet.cz/
3 *
4 * Written by Václav Kubernát <kubervac@fit.cvut.cz>
5 *
6*/
7
8#include <experimental/iterator>
9#include "trompeloeil_doctest.h"
10
11#ifdef sysrepo_BACKEND
12#include "sysrepo_access.hpp"
13#elif defined(netconf_BACKEND)
14#include "netconf_access.hpp"
15#include "netopeer_vars.hpp"
16#else
17#error "Unknown backend"
18#endif
19#include "data_query.hpp"
20#include "sysrepo_subscription.hpp"
21#include "utils.hpp"
22
23namespace std {
24std::ostream& operator<<(std::ostream& s, const std::vector<std::map<std::string, leaf_data_>> set)
25{
26 s << std::endl << "{" << std::endl;
27 std::transform(set.begin(), set.end(), std::experimental::make_ostream_joiner(s, ", \n"), [](const auto& map) {
28 std::ostringstream ss;
29 ss << " {" << std::endl << " ";
30 std::transform(map.begin(), map.end(), std::experimental::make_ostream_joiner(ss, ", \n "), [](const auto& keyValue){
31 return "{" + keyValue.first + "{" + boost::core::demangle(keyValue.second.type().name()) + "}" + ", " + leafDataToString(keyValue.second) + "}";
32 });
33 ss << std::endl << " }";
34 return ss.str();
35 });
36 s << std::endl << "}" << std::endl;
37 return s;
38}
39}
40
41TEST_CASE("data query")
42{
43 trompeloeil::sequence seq1;
44 SysrepoSubscription subscriptionExample("example-schema");
45 SysrepoSubscription subscriptionOther("other-module");
46
47#ifdef sysrepo_BACKEND
48 SysrepoAccess datastore("netconf-cli-test");
49#elif defined(netconf_BACKEND)
50 NetconfAccess datastore(NETOPEER_SOCKET_PATH);
51#else
52#error "Unknown backend"
53#endif
54
55 DataQuery dataquery(datastore);
56
57 SECTION("listKeys")
58 {
59 dataPath_ location;
60 location.m_scope = Scope::Absolute;
61 ModuleNodePair node;
62 std::vector<std::map<std::string, leaf_data_>> expected;
63
64 SECTION("example-schema:person")
65 {
66 datastore.createListInstance("/example-schema:person[name='Vaclav']");
67 datastore.createListInstance("/example-schema:person[name='Tomas']");
68 datastore.createListInstance("/example-schema:person[name='Jan Novak']");
69 node.first = "example-schema";
70 node.second = "person";
71 expected = {
72 {{"name", std::string{"Jan Novak"}}},
73 {{"name", std::string{"Tomas"}}},
74 {{"name", std::string{"Vaclav"}}}
75 };
76 }
77
78 SECTION("example-schema:selectedNumbers")
79 {
80 datastore.createListInstance("/example-schema:selectedNumbers[value='45']");
81 datastore.createListInstance("/example-schema:selectedNumbers[value='99']");
82 datastore.createListInstance("/example-schema:selectedNumbers[value='127']");
83 node.first = "example-schema";
84 node.second = "selectedNumbers";
85 expected = {
86 {{"value", int8_t{127}}},
87 {{"value", int8_t{45}}},
88 {{"value", int8_t{99}}}
89 };
90 }
91
92 SECTION("example-schema:animalWithColor")
93 {
94 datastore.createListInstance("/example-schema:animalWithColor[name='Dog'][color='brown']");
95 datastore.createListInstance("/example-schema:animalWithColor[name='Dog'][color='white']");
96 datastore.createListInstance("/example-schema:animalWithColor[name='Cat'][color='grey']");
97 node.first = "example-schema";
98 node.second = "animalWithColor";
99 expected = {
100 {{"name", std::string{"Cat"}}, {"color", std::string{"grey"}}},
101 {{"name", std::string{"Dog"}}, {"color", std::string{"brown"}}},
102 {{"name", std::string{"Dog"}}, {"color", std::string{"white"}}}
103 };
104 }
105
106 SECTION("example-schema:animalWithColor - quotes in values")
107 {
108 datastore.createListInstance("/example-schema:animalWithColor[name='D\"o\"g'][color=\"b'r'own\"]");
109 node.first = "example-schema";
110 node.second = "animalWithColor";
111 expected = {
112 {{"name", std::string{"D\"o\"g"}}, {"color", std::string{"b'r'own"}}}
113 };
114 }
115
116 SECTION("example-schema:ports")
117 {
118 datastore.createListInstance("/example-schema:ports[name='A']");
119 datastore.createListInstance("/example-schema:ports[name='B']");
120 datastore.createListInstance("/example-schema:ports[name='E']");
121 node.first = "example-schema";
122 node.second = "ports";
123 expected = {
124 {{"name", enum_{"A"}}},
125 {{"name", enum_{"B"}}},
126 {{"name", enum_{"E"}}},
127 };
128 }
129
130 SECTION("example-schema:org/example:people - nested list")
131 {
132 datastore.createListInstance("/example-schema:org[department='accounting']");
133 datastore.createListInstance("/example-schema:org[department='sales']");
134 datastore.createListInstance("/example-schema:org[department='programmers']");
135 datastore.createListInstance("/example-schema:org[department='accounting']/people[name='Alice']");
136 datastore.createListInstance("/example-schema:org[department='accounting']/people[name='Bob']");
137 datastore.createListInstance("/example-schema:org[department='sales']/people[name='Alice']");
138 datastore.createListInstance("/example-schema:org[department='sales']/people[name='Cyril']");
139 datastore.createListInstance("/example-schema:org[department='sales']/people[name='Alice']/computers[type='laptop']");
140 datastore.createListInstance("/example-schema:org[department='sales']/people[name='Alice']/computers[type='server']");
141 datastore.createListInstance("/example-schema:org[department='sales']/people[name='Cyril']/computers[type='PC']");
142 datastore.createListInstance("/example-schema:org[department='sales']/people[name='Cyril']/computers[type='server']");
143
144 SECTION("outer list")
145 {
146 node.first = "example-schema";
147 node.second = "org";
148 expected = {
149 {{"department", std::string{"accounting"}}},
150 {{"department", std::string{"sales"}}},
151 {{"department", std::string{"programmers"}}},
152 };
153 }
154
155 SECTION("nested list")
156 {
157 listElement_ list;
158 list.m_name = "org";
159 node.second = "people";
160 SECTION("accounting department")
161 {
162 list.m_keys = {
163 {"department", std::string{"accounting"}}
164 };
165 expected = {
166 {{"name", std::string{"Alice"}}},
167 {{"name", std::string{"Bob"}}},
168 };
169 }
170 SECTION("sales department")
171 {
172 list.m_keys = {
173 {"department", std::string{"sales"}}
174 };
175 expected = {
176 {{"name", std::string{"Alice"}}},
177 {{"name", std::string{"Cyril"}}},
178 };
179 }
180 SECTION("programmers department")
181 {
182 list.m_keys = {
183 {"department", std::string{"programmers"}}
184 };
185 expected = {
186 };
187 }
188 location.m_nodes.push_back(dataNode_{{"example-schema"}, list});
189 }
190
191 SECTION("THREE MF NESTED LISTS")
192 {
193 listElement_ listOrg;
194 listOrg.m_name = "org";
195 listOrg.m_keys = {
196 {"department", std::string{"sales"}}
197 };
198
199 listElement_ listPeople;
200 node.second = "computers";
201
202 SECTION("alice computers")
203 {
204 listPeople.m_name = "people";
205 listPeople.m_keys = {
206 {"name", std::string{"Alice"}}
207 };
208 expected = {
209 {{"type", enum_{"laptop"}}},
210 {{"type", enum_{"server"}}},
211 };
212
213 }
214
215 SECTION("cyril computers")
216 {
217 listPeople.m_name = "people";
218 listPeople.m_keys = {
219 {"name", std::string{"Cyril"}}
220 };
221 expected = {
222 {{"type", enum_{"PC"}}},
223 {{"type", enum_{"server"}}},
224 };
225 }
226
227 location.m_nodes.push_back(dataNode_{{"example-schema"}, listOrg});
228 location.m_nodes.push_back(dataNode_{listPeople});
229
230 }
231 }
232
233 SECTION("/other-module:parking-lot/example-schema:cars - list coming from an augment")
234 {
235 datastore.createListInstance("/other-module:parking-lot/example-schema:cars[id='1']");
236 datastore.createListInstance("/other-module:parking-lot/example-schema:cars[id='2']");
237
238 location.m_nodes.push_back(dataNode_{{"other-module"}, container_{"parking-lot"}});
239 node.first = "example-schema";
240 node.second = "cars";
241 expected = {
242 {{"id", int32_t{1}}},
243 {{"id", int32_t{2}}},
244 };
245
246 }
247
248 datastore.commitChanges();
249 std::sort(expected.begin(), expected.end());
250 auto keys = dataquery.listKeys(location, node);
251 std::sort(keys.begin(), keys.end());
252 REQUIRE(keys == expected);
253 }
254
255 waitForCompletionAndBitMore(seq1);
256}