blob: 0c429a43b42586f687388e9602d8c5783ea3716d [file] [log] [blame]
Michal Vasko4490d312020-06-16 13:08:55 +02001/**
2 * @file test_merge.c
3 * @author Michal Vasko <mvasko@cesnet.cz>
4 * @brief tests for complex data merges.
5 *
6 * Copyright (c) 2020 CESNET, z.s.p.o.
7 *
8 * This source code is licensed under BSD 3-Clause License (the "License").
9 * You may not use this file except in compliance with the License.
10 * You may obtain a copy of the License at
11 *
12 * https://opensource.org/licenses/BSD-3-Clause
13 */
Radek Iša56ca9e42020-09-08 18:42:00 +020014#define _UTEST_MAIN_
Radek Krejcib4ac5a92020-11-23 17:54:33 +010015#include "utests.h"
Michal Vasko4490d312020-06-16 13:08:55 +020016
Radek Iša56ca9e42020-09-08 18:42:00 +020017#include "libyang.h"
Michal Vasko4490d312020-06-16 13:08:55 +020018
Radek Iša56ca9e42020-09-08 18:42:00 +020019#define LYD_TREE_CREATE(INPUT, MODEL) \
20 CHECK_PARSE_LYD_PARAM(INPUT, LYD_XML, 0, LYD_VALIDATE_PRESENT, LY_SUCCESS, MODEL)
Michal Vasko4490d312020-06-16 13:08:55 +020021
Radek Iša56ca9e42020-09-08 18:42:00 +020022#define CONTEXT_CREATE \
23 CONTEXT_CREATE_PATH(NULL)
Michal Vasko4490d312020-06-16 13:08:55 +020024
Radek Iša56ca9e42020-09-08 18:42:00 +020025#define LYD_TREE_CHECK_CHAR(MODEL, TEXT, PARAMS) \
26 CHECK_LYD_STRING_PARAM(MODEL, TEXT, LYD_XML, LYD_PRINT_WITHSIBLINGS | PARAMS)
Michal Vasko4490d312020-06-16 13:08:55 +020027
28static void
29test_batch(void **state)
30{
Michal Vasko4490d312020-06-16 13:08:55 +020031 const char *start =
Radek Krejcib4ac5a92020-11-23 17:54:33 +010032 "<modules-state xmlns=\"urn:ietf:params:xml:ns:yang:ietf-yang-library\">\n"
33 " <module>\n"
34 " <name>yang</name>\n"
35 " <revision>2016-02-11</revision>\n"
36 " <conformance-type>implement</conformance-type>\n"
37 " </module>\n"
38 "</modules-state>\n";
Michal Vasko4490d312020-06-16 13:08:55 +020039 const char *data[] = {
Radek Krejcib4ac5a92020-11-23 17:54:33 +010040 "<modules-state xmlns=\"urn:ietf:params:xml:ns:yang:ietf-yang-library\">\n"
41 " <module>\n"
42 " <name>ietf-yang-library</name>\n"
43 " <revision>2016-02-01</revision>\n"
44 " <conformance-type>implement</conformance-type>\n"
45 " </module>\n"
46 "</modules-state>\n",
47 "<modules-state xmlns=\"urn:ietf:params:xml:ns:yang:ietf-yang-library\">\n"
48 " <module>\n"
49 " <name>ietf-netconf-acm</name>\n"
50 " <revision>2012-02-22</revision>\n"
51 " <conformance-type>implement</conformance-type>\n"
52 " </module>\n"
53 "</modules-state>\n",
54 "<modules-state xmlns=\"urn:ietf:params:xml:ns:yang:ietf-yang-library\">\n"
55 " <module>\n"
56 " <name>ietf-netconf</name>\n"
57 " <revision>2011-06-01</revision>\n"
58 " <conformance-type>implement</conformance-type>\n"
59 " </module>\n"
60 "</modules-state>\n",
61 "<modules-state xmlns=\"urn:ietf:params:xml:ns:yang:ietf-yang-library\">\n"
62 " <module>\n"
63 " <name>ietf-netconf-monitoring</name>\n"
64 " <revision>2010-10-04</revision>\n"
65 " <conformance-type>implement</conformance-type>\n"
66 " </module>\n"
67 "</modules-state>\n",
68 "<modules-state xmlns=\"urn:ietf:params:xml:ns:yang:ietf-yang-library\">\n"
69 " <module>\n"
70 " <name>ietf-netconf-with-defaults</name>\n"
71 " <revision>2011-06-01</revision>\n"
72 " <conformance-type>implement</conformance-type>\n"
73 " </module>\n"
74 "</modules-state>\n",
75 "<modules-state xmlns=\"urn:ietf:params:xml:ns:yang:ietf-yang-library\">\n"
76 " <module>\n"
77 " <name>yang</name>\n"
78 " <revision>2016-02-11</revision>\n"
79 " <namespace>urn:ietf:params:xml:ns:yang:1</namespace>\n"
80 " <conformance-type>implement</conformance-type>\n"
81 " </module>\n"
82 "</modules-state>\n",
83 "<modules-state xmlns=\"urn:ietf:params:xml:ns:yang:ietf-yang-library\">\n"
84 " <module>\n"
85 " <name>ietf-yang-library</name>\n"
86 " <revision>2016-02-01</revision>\n"
87 " <namespace>urn:ietf:params:xml:ns:yang:ietf-yang-library</namespace>\n"
88 " <conformance-type>implement</conformance-type>\n"
89 " </module>\n"
90 "</modules-state>\n",
91 "<modules-state xmlns=\"urn:ietf:params:xml:ns:yang:ietf-yang-library\">\n"
92 " <module>\n"
93 " <name>ietf-netconf-acm</name>\n"
94 " <revision>2012-02-22</revision>\n"
95 " <namespace>urn:ietf:params:xml:ns:yang:ietf-netconf-acm</namespace>\n"
96 " <conformance-type>implement</conformance-type>\n"
97 " </module>\n"
98 "</modules-state>\n",
99 "<modules-state xmlns=\"urn:ietf:params:xml:ns:yang:ietf-yang-library\">\n"
100 " <module>\n"
101 " <name>ietf-netconf</name>\n"
102 " <revision>2011-06-01</revision>\n"
103 " <namespace>urn:ietf:params:xml:ns:netconf:base:1.0</namespace>\n"
104 " <feature>writable-running</feature>\n"
105 " <feature>candidate</feature>\n"
106 " <feature>rollback-on-error</feature>\n"
107 " <feature>validate</feature>\n"
108 " <feature>startup</feature>\n"
109 " <feature>xpath</feature>\n"
110 " <conformance-type>implement</conformance-type>\n"
111 " </module>\n"
112 "</modules-state>\n",
113 "<modules-state xmlns=\"urn:ietf:params:xml:ns:yang:ietf-yang-library\">\n"
114 " <module>\n"
115 " <name>ietf-netconf-monitoring</name>\n"
116 " <revision>2010-10-04</revision>\n"
117 " <namespace>urn:ietf:params:xml:ns:yang:ietf-netconf-monitoring</namespace>\n"
118 " <conformance-type>implement</conformance-type>\n"
119 " </module>\n"
120 "</modules-state>\n",
121 "<modules-state xmlns=\"urn:ietf:params:xml:ns:yang:ietf-yang-library\">\n"
122 " <module>\n"
123 " <name>ietf-netconf-with-defaults</name>\n"
124 " <revision>2011-06-01</revision>\n"
125 " <namespace>urn:ietf:params:xml:ns:yang:ietf-netconf-with-defaults</namespace>\n"
126 " <conformance-type>implement</conformance-type>\n"
127 " </module>\n"
128 "</modules-state>\n"
Michal Vasko4490d312020-06-16 13:08:55 +0200129 };
130 const char *output_template =
Radek Krejcib4ac5a92020-11-23 17:54:33 +0100131 "<modules-state xmlns=\"urn:ietf:params:xml:ns:yang:ietf-yang-library\">\n"
132 " <module>\n"
133 " <name>yang</name>\n"
134 " <revision>2016-02-11</revision>\n"
135 " <namespace>urn:ietf:params:xml:ns:yang:1</namespace>\n"
136 " <conformance-type>implement</conformance-type>\n"
137 " </module>\n"
138 " <module>\n"
139 " <name>ietf-yang-library</name>\n"
140 " <revision>2016-02-01</revision>\n"
141 " <namespace>urn:ietf:params:xml:ns:yang:ietf-yang-library</namespace>\n"
142 " <conformance-type>implement</conformance-type>\n"
143 " </module>\n"
144 " <module>\n"
145 " <name>ietf-netconf-acm</name>\n"
146 " <revision>2012-02-22</revision>\n"
147 " <namespace>urn:ietf:params:xml:ns:yang:ietf-netconf-acm</namespace>\n"
148 " <conformance-type>implement</conformance-type>\n"
149 " </module>\n"
150 " <module>\n"
151 " <name>ietf-netconf</name>\n"
152 " <revision>2011-06-01</revision>\n"
153 " <namespace>urn:ietf:params:xml:ns:netconf:base:1.0</namespace>\n"
154 " <feature>writable-running</feature>\n"
155 " <feature>candidate</feature>\n"
156 " <feature>rollback-on-error</feature>\n"
157 " <feature>validate</feature>\n"
158 " <feature>startup</feature>\n"
159 " <feature>xpath</feature>\n"
160 " <conformance-type>implement</conformance-type>\n"
161 " </module>\n"
162 " <module>\n"
163 " <name>ietf-netconf-monitoring</name>\n"
164 " <revision>2010-10-04</revision>\n"
165 " <namespace>urn:ietf:params:xml:ns:yang:ietf-netconf-monitoring</namespace>\n"
166 " <conformance-type>implement</conformance-type>\n"
167 " </module>\n"
168 " <module>\n"
169 " <name>ietf-netconf-with-defaults</name>\n"
170 " <revision>2011-06-01</revision>\n"
171 " <namespace>urn:ietf:params:xml:ns:yang:ietf-netconf-with-defaults</namespace>\n"
172 " <conformance-type>implement</conformance-type>\n"
173 " </module>\n"
174 "</modules-state>\n";
Michal Vasko4490d312020-06-16 13:08:55 +0200175
Radek Iša56ca9e42020-09-08 18:42:00 +0200176 struct lyd_node *target;
Michal Vasko4490d312020-06-16 13:08:55 +0200177
Radek Iša56ca9e42020-09-08 18:42:00 +0200178 CHECK_PARSE_LYD_PARAM(start, LYD_XML, LYD_PARSE_ONLY, 0, LY_SUCCESS, target);
Michal Vasko4490d312020-06-16 13:08:55 +0200179
Radek Iša56ca9e42020-09-08 18:42:00 +0200180 for (int32_t i = 0; i < 11; ++i) {
181 struct lyd_node *source;
182 CHECK_PARSE_LYD_PARAM(data[i], LYD_XML, LYD_PARSE_ONLY, 0, LY_SUCCESS, source);
183 assert_int_equal(LY_SUCCESS, lyd_merge_siblings(&target, source, LYD_MERGE_DESTRUCT));
Michal Vasko4490d312020-06-16 13:08:55 +0200184 }
185
Radek Iša56ca9e42020-09-08 18:42:00 +0200186 LYD_TREE_CHECK_CHAR(target, output_template, 0);
Radek Krejci7931b192020-06-25 17:05:03 +0200187
Radek Iša56ca9e42020-09-08 18:42:00 +0200188 lyd_free_all(target);
Michal Vasko4490d312020-06-16 13:08:55 +0200189}
190
191static void
192test_leaf(void **state)
193{
Michal Vasko4490d312020-06-16 13:08:55 +0200194 const char *sch = "module x {"
Radek Krejcib4ac5a92020-11-23 17:54:33 +0100195 " namespace urn:x;"
196 " prefix x;"
197 " container A {"
198 " leaf f1 {type string;}"
199 " container B {"
200 " leaf f2 {type string;}"
201 " }"
202 " }"
203 " }";
Michal Vasko4490d312020-06-16 13:08:55 +0200204 const char *trg = "<A xmlns=\"urn:x\"> <f1>block</f1> </A>";
205 const char *src = "<A xmlns=\"urn:x\"> <f1>aa</f1> <B> <f2>bb</f2> </B> </A>";
206 const char *result = "<A xmlns=\"urn:x\"><f1>aa</f1><B><f2>bb</f2></B></A>";
Radek Iša56ca9e42020-09-08 18:42:00 +0200207 struct lyd_node *source, *target;
Michal Vasko4490d312020-06-16 13:08:55 +0200208
Radek Iša56ca9e42020-09-08 18:42:00 +0200209 UTEST_ADD_MODULE(sch, LYS_IN_YANG, NULL, NULL);
Michal Vasko4490d312020-06-16 13:08:55 +0200210
Radek Iša56ca9e42020-09-08 18:42:00 +0200211 LYD_TREE_CREATE(src, source);
212 LYD_TREE_CREATE(trg, target);
Michal Vasko4490d312020-06-16 13:08:55 +0200213
214 /* merge them */
Radek Iša56ca9e42020-09-08 18:42:00 +0200215 assert_int_equal(lyd_merge_siblings(&target, source, 0), LY_SUCCESS);
216 assert_int_equal(lyd_validate_all(&target, NULL, LYD_VALIDATE_PRESENT, NULL), LY_SUCCESS);
Michal Vasko4490d312020-06-16 13:08:55 +0200217
218 /* check the result */
Radek Iša56ca9e42020-09-08 18:42:00 +0200219 LYD_TREE_CHECK_CHAR(target, result, LYD_PRINT_SHRINK);
220
221 lyd_free_all(target);
222 lyd_free_all(source);
Michal Vasko4490d312020-06-16 13:08:55 +0200223}
224
225static void
226test_container(void **state)
227{
Michal Vasko4490d312020-06-16 13:08:55 +0200228 const char *sch =
Radek Krejcib4ac5a92020-11-23 17:54:33 +0100229 "module A {\n"
230 " namespace \"aa:A\";\n"
231 " prefix A;\n"
232 " container A {\n"
233 " leaf f1 {type string;}\n"
234 " container B {\n"
235 " leaf f2 {type string;}\n"
236 " }\n"
237 " container C {\n"
238 " leaf f3 {type string;}\n"
239 " }\n"
240 " }\n"
241 "}\n";
Michal Vasko4490d312020-06-16 13:08:55 +0200242
243 const char *trg = "<A xmlns=\"aa:A\"> <B> <f2>aaa</f2> </B> </A>";
244 const char *src = "<A xmlns=\"aa:A\"> <C> <f3>bbb</f3> </C> </A>";
245 const char *result = "<A xmlns=\"aa:A\"><B><f2>aaa</f2></B><C><f3>bbb</f3></C></A>";
Radek Iša56ca9e42020-09-08 18:42:00 +0200246 struct lyd_node *source, *target;
Michal Vasko4490d312020-06-16 13:08:55 +0200247
Radek Iša56ca9e42020-09-08 18:42:00 +0200248 UTEST_ADD_MODULE(sch, LYS_IN_YANG, NULL, NULL);
Michal Vasko4490d312020-06-16 13:08:55 +0200249
Radek Iša56ca9e42020-09-08 18:42:00 +0200250 LYD_TREE_CREATE(src, source);
251 LYD_TREE_CREATE(trg, target);
Michal Vasko4490d312020-06-16 13:08:55 +0200252
253 /* merge them */
Radek Iša56ca9e42020-09-08 18:42:00 +0200254 assert_int_equal(lyd_merge_siblings(&target, source, 0), LY_SUCCESS);
255 assert_int_equal(lyd_validate_all(&target, NULL, LYD_VALIDATE_PRESENT, NULL), LY_SUCCESS);
Michal Vasko4490d312020-06-16 13:08:55 +0200256
257 /* check the result */
Radek Iša56ca9e42020-09-08 18:42:00 +0200258 LYD_TREE_CHECK_CHAR(target, result, LYD_PRINT_SHRINK);
259
260 /* destroy */
261 lyd_free_all(source);
262 lyd_free_all(target);
Michal Vasko4490d312020-06-16 13:08:55 +0200263}
264
265static void
266test_list(void **state)
267{
Michal Vasko4490d312020-06-16 13:08:55 +0200268 const char *sch =
Radek Krejcib4ac5a92020-11-23 17:54:33 +0100269 "module merge {\n"
270 " namespace \"http://test/merge\";\n"
271 " prefix merge;\n"
272 "\n"
273 " container inner1 {\n"
274 " list b-list1 {\n"
275 " key p1;\n"
276 " leaf p1 {\n"
277 " type uint8;\n"
278 " }\n"
279 " leaf p2 {\n"
280 " type string;\n"
281 " }\n"
282 " leaf p3 {\n"
283 " type boolean;\n"
284 " default false;\n"
285 " }\n"
286 " }\n"
287 " }\n"
288 "}\n";
Michal Vasko4490d312020-06-16 13:08:55 +0200289
290 const char *trg =
Radek Krejcib4ac5a92020-11-23 17:54:33 +0100291 "<inner1 xmlns=\"http://test/merge\">\n"
292 " <b-list1>\n"
293 " <p1>1</p1>\n"
294 " <p2>a</p2>\n"
295 " <p3>true</p3>\n"
296 " </b-list1>\n"
297 "</inner1>\n";
Michal Vasko4490d312020-06-16 13:08:55 +0200298 const char *src =
Radek Krejcib4ac5a92020-11-23 17:54:33 +0100299 "<inner1 xmlns=\"http://test/merge\">\n"
300 " <b-list1>\n"
301 " <p1>1</p1>\n"
302 " <p2>b</p2>\n"
303 " </b-list1>\n"
304 "</inner1>\n";
Michal Vasko4490d312020-06-16 13:08:55 +0200305 const char *result =
Radek Krejcib4ac5a92020-11-23 17:54:33 +0100306 "<inner1 xmlns=\"http://test/merge\">\n"
307 " <b-list1>\n"
308 " <p1>1</p1>\n"
309 " <p2>b</p2>\n"
310 " <p3>true</p3>\n"
311 " </b-list1>\n"
312 "</inner1>\n";
Radek Iša56ca9e42020-09-08 18:42:00 +0200313 struct lyd_node *source, *target;
Michal Vasko4490d312020-06-16 13:08:55 +0200314
Radek Iša56ca9e42020-09-08 18:42:00 +0200315 UTEST_ADD_MODULE(sch, LYS_IN_YANG, NULL, NULL);
Michal Vasko4490d312020-06-16 13:08:55 +0200316
Radek Iša56ca9e42020-09-08 18:42:00 +0200317 LYD_TREE_CREATE(src, source);
318 LYD_TREE_CREATE(trg, target);
Michal Vasko4490d312020-06-16 13:08:55 +0200319
320 /* merge them */
Radek Iša56ca9e42020-09-08 18:42:00 +0200321 assert_int_equal(lyd_merge_siblings(&target, source, 0), LY_SUCCESS);
322 assert_int_equal(lyd_validate_all(&target, NULL, LYD_VALIDATE_PRESENT, NULL), LY_SUCCESS);
Michal Vasko4490d312020-06-16 13:08:55 +0200323
324 /* check the result */
Radek Iša56ca9e42020-09-08 18:42:00 +0200325 LYD_TREE_CHECK_CHAR(target, result, 0);
326
327 lyd_free_all(target);
328 lyd_free_all(source);
Michal Vasko4490d312020-06-16 13:08:55 +0200329}
330
331static void
332test_list2(void **state)
333{
Michal Vasko4490d312020-06-16 13:08:55 +0200334 const char *sch =
Radek Krejcib4ac5a92020-11-23 17:54:33 +0100335 "module merge {\n"
336 " namespace \"http://test/merge\";\n"
337 " prefix merge;\n"
338 "\n"
339 " container inner1 {\n"
340 " list b-list1 {\n"
341 " key p1;\n"
342 " leaf p1 {\n"
343 " type uint8;\n"
344 " }\n"
345 " leaf p2 {\n"
346 " type string;\n"
347 " }\n"
348 " container inner2 {\n"
349 " leaf p3 {\n"
350 " type boolean;\n"
351 " default false;\n"
352 " }\n"
353 " leaf p4 {\n"
354 " type string;\n"
355 " }\n"
356 " }\n"
357 " }\n"
358 " }\n"
359 "}\n";
Michal Vasko4490d312020-06-16 13:08:55 +0200360
361 const char *trg =
Radek Krejcib4ac5a92020-11-23 17:54:33 +0100362 "<inner1 xmlns=\"http://test/merge\">\n"
363 " <b-list1>\n"
364 " <p1>1</p1>\n"
365 " <p2>a</p2>\n"
366 " <inner2>\n"
367 " <p4>val</p4>\n"
368 " </inner2>\n"
369 " </b-list1>\n"
370 "</inner1>\n";
Michal Vasko4490d312020-06-16 13:08:55 +0200371 const char *src =
Radek Krejcib4ac5a92020-11-23 17:54:33 +0100372 "<inner1 xmlns=\"http://test/merge\">\n"
373 " <b-list1>\n"
374 " <p1>1</p1>\n"
375 " <p2>b</p2>\n"
376 " </b-list1>\n"
377 "</inner1>\n";
Michal Vasko4490d312020-06-16 13:08:55 +0200378 const char *result =
Radek Krejcib4ac5a92020-11-23 17:54:33 +0100379 "<inner1 xmlns=\"http://test/merge\">\n"
380 " <b-list1>\n"
381 " <p1>1</p1>\n"
382 " <p2>b</p2>\n"
383 " <inner2>\n"
384 " <p4>val</p4>\n"
385 " </inner2>\n"
386 " </b-list1>\n"
387 "</inner1>\n";
Radek Iša56ca9e42020-09-08 18:42:00 +0200388 struct lyd_node *source, *target;
Michal Vasko4490d312020-06-16 13:08:55 +0200389
Radek Iša56ca9e42020-09-08 18:42:00 +0200390 UTEST_ADD_MODULE(sch, LYS_IN_YANG, NULL, NULL);
Michal Vasko4490d312020-06-16 13:08:55 +0200391
Radek Iša56ca9e42020-09-08 18:42:00 +0200392 LYD_TREE_CREATE(src, source);
393 LYD_TREE_CREATE(trg, target);
Michal Vasko4490d312020-06-16 13:08:55 +0200394
395 /* merge them */
Radek Iša56ca9e42020-09-08 18:42:00 +0200396 assert_int_equal(lyd_merge_siblings(&target, source, 0), LY_SUCCESS);
397 assert_int_equal(lyd_validate_all(&target, NULL, LYD_VALIDATE_PRESENT, NULL), LY_SUCCESS);
Michal Vasko4490d312020-06-16 13:08:55 +0200398
399 /* check the result */
Radek Iša56ca9e42020-09-08 18:42:00 +0200400 LYD_TREE_CHECK_CHAR(target, result, 0);
401
402 lyd_free_all(source);
403 lyd_free_all(target);
Michal Vasko4490d312020-06-16 13:08:55 +0200404}
405
406static void
407test_case(void **state)
408{
Michal Vasko4490d312020-06-16 13:08:55 +0200409 const char *sch =
Radek Krejcib4ac5a92020-11-23 17:54:33 +0100410 "module merge {\n"
411 " namespace \"http://test/merge\";\n"
412 " prefix merge;\n"
413 " container cont {\n"
414 " choice ch {\n"
415 " container inner {\n"
416 " leaf p1 {\n"
417 " type string;\n"
418 " }\n"
419 " }\n"
420 " case c2 {\n"
421 " leaf p1 {\n"
422 " type string;\n"
423 " }\n"
424 " }\n"
425 " }\n"
426 " }\n"
427 "}\n";
Michal Vasko4490d312020-06-16 13:08:55 +0200428
429 const char *trg =
Radek Krejcib4ac5a92020-11-23 17:54:33 +0100430 "<cont xmlns=\"http://test/merge\">\n"
431 " <inner>\n"
432 " <p1>1</p1>\n"
433 " </inner>\n"
434 "</cont>\n";
Michal Vasko4490d312020-06-16 13:08:55 +0200435 const char *src =
Radek Krejcib4ac5a92020-11-23 17:54:33 +0100436 "<cont xmlns=\"http://test/merge\">\n"
437 " <p1>1</p1>\n"
438 "</cont>\n";
Michal Vasko4490d312020-06-16 13:08:55 +0200439 const char *result =
Radek Krejcib4ac5a92020-11-23 17:54:33 +0100440 "<cont xmlns=\"http://test/merge\">\n"
441 " <p1>1</p1>\n"
442 "</cont>\n";
Radek Iša56ca9e42020-09-08 18:42:00 +0200443 struct lyd_node *source, *target;
Michal Vasko4490d312020-06-16 13:08:55 +0200444
Radek Iša56ca9e42020-09-08 18:42:00 +0200445 UTEST_ADD_MODULE(sch, LYS_IN_YANG, NULL, NULL);
Michal Vasko4490d312020-06-16 13:08:55 +0200446
Radek Iša56ca9e42020-09-08 18:42:00 +0200447 LYD_TREE_CREATE(src, source);
448 LYD_TREE_CREATE(trg, target);
Michal Vasko4490d312020-06-16 13:08:55 +0200449
450 /* merge them */
Radek Iša56ca9e42020-09-08 18:42:00 +0200451 assert_int_equal(lyd_merge_siblings(&target, source, 0), LY_SUCCESS);
452 assert_int_equal(lyd_validate_all(&target, NULL, LYD_VALIDATE_PRESENT, NULL), LY_SUCCESS);
Michal Vasko4490d312020-06-16 13:08:55 +0200453
454 /* check the result */
Radek Iša56ca9e42020-09-08 18:42:00 +0200455 LYD_TREE_CHECK_CHAR(target, result, 0);
456
457 lyd_free_all(source);
458 lyd_free_all(target);
Michal Vasko4490d312020-06-16 13:08:55 +0200459}
460
461static void
462test_dflt(void **state)
463{
Michal Vasko4490d312020-06-16 13:08:55 +0200464 const char *sch =
Radek Krejcib4ac5a92020-11-23 17:54:33 +0100465 "module merge-dflt {\n"
466 " namespace \"urn:merge-dflt\";\n"
467 " prefix md;\n"
468 " container top {\n"
469 " leaf a {\n"
470 " type string;\n"
471 " }\n"
472 " leaf b {\n"
473 " type string;\n"
474 " }\n"
475 " leaf c {\n"
476 " type string;\n"
477 " default \"c_dflt\";\n"
478 " }\n"
479 " }\n"
480 "}\n";
Radek Iša56ca9e42020-09-08 18:42:00 +0200481 struct lyd_node *target = NULL;
482 struct lyd_node *source = NULL;
Michal Vasko4490d312020-06-16 13:08:55 +0200483
Radek Iša56ca9e42020-09-08 18:42:00 +0200484 UTEST_ADD_MODULE(sch, LYS_IN_YANG, NULL, NULL);
Michal Vasko4490d312020-06-16 13:08:55 +0200485
Radek Iša56ca9e42020-09-08 18:42:00 +0200486 assert_int_equal(lyd_new_path(NULL, UTEST_LYCTX, "/merge-dflt:top/c", "c_dflt", 0, &target), LY_SUCCESS);
487 assert_int_equal(lyd_validate_all(&target, NULL, LYD_VALIDATE_PRESENT, NULL), LY_SUCCESS);
Michal Vasko4490d312020-06-16 13:08:55 +0200488
Radek Iša56ca9e42020-09-08 18:42:00 +0200489 assert_int_equal(lyd_new_path(NULL, UTEST_LYCTX, "/merge-dflt:top/a", "a_val", 0, &source), LY_SUCCESS);
490 assert_int_equal(lyd_new_path(source, UTEST_LYCTX, "/merge-dflt:top/b", "b_val", 0, NULL), LY_SUCCESS);
491 assert_int_equal(lyd_validate_all(&source, NULL, LYD_VALIDATE_PRESENT, NULL), LY_SUCCESS);
Michal Vasko4490d312020-06-16 13:08:55 +0200492
Radek Iša56ca9e42020-09-08 18:42:00 +0200493 assert_int_equal(lyd_merge_siblings(&target, source, LYD_MERGE_DESTRUCT | LYD_MERGE_DEFAULTS), LY_SUCCESS);
494 source = NULL;
Michal Vasko4490d312020-06-16 13:08:55 +0200495
496 /* c should be replaced and now be default */
Radek Iša56ca9e42020-09-08 18:42:00 +0200497 assert_string_equal(lyd_child(target)->prev->schema->name, "c");
498 assert_true(lyd_child(target)->prev->flags & LYD_DEFAULT);
499
500 lyd_free_all(target);
501 lyd_free_all(source);
Michal Vasko4490d312020-06-16 13:08:55 +0200502}
503
504static void
505test_dflt2(void **state)
506{
Michal Vasko4490d312020-06-16 13:08:55 +0200507 const char *sch =
Radek Krejcib4ac5a92020-11-23 17:54:33 +0100508 "module merge-dflt {\n"
509 " namespace \"urn:merge-dflt\";\n"
510 " prefix md;\n"
511 " container top {\n"
512 " leaf a {\n"
513 " type string;\n"
514 " }\n"
515 " leaf b {\n"
516 " type string;\n"
517 " }\n"
518 " leaf c {\n"
519 " type string;\n"
520 " default \"c_dflt\";\n"
521 " }\n"
522 " }\n"
523 "}\n";
Radek Iša56ca9e42020-09-08 18:42:00 +0200524 struct lyd_node *target;
525 struct lyd_node *source;
Michal Vasko4490d312020-06-16 13:08:55 +0200526
Radek Iša56ca9e42020-09-08 18:42:00 +0200527 UTEST_ADD_MODULE(sch, LYS_IN_YANG, NULL, NULL);
Michal Vasko4490d312020-06-16 13:08:55 +0200528
Radek Iša56ca9e42020-09-08 18:42:00 +0200529 assert_int_equal(lyd_new_path(NULL, UTEST_LYCTX, "/merge-dflt:top/c", "c_dflt", 0, &target), LY_SUCCESS);
530 assert_int_equal(lyd_validate_all(&target, NULL, LYD_VALIDATE_PRESENT, NULL), LY_SUCCESS);
Michal Vasko4490d312020-06-16 13:08:55 +0200531
Radek Iša56ca9e42020-09-08 18:42:00 +0200532 assert_int_equal(lyd_new_path(NULL, UTEST_LYCTX, "/merge-dflt:top/a", "a_val", 0, &source), LY_SUCCESS);
533 assert_int_equal(lyd_new_path(source, UTEST_LYCTX, "/merge-dflt:top/b", "b_val", 0, NULL), LY_SUCCESS);
534 assert_int_equal(lyd_validate_all(&source, NULL, LYD_VALIDATE_PRESENT, NULL), LY_SUCCESS);
Michal Vasko4490d312020-06-16 13:08:55 +0200535
Radek Iša56ca9e42020-09-08 18:42:00 +0200536 assert_int_equal(lyd_merge_siblings(&target, source, 0), LY_SUCCESS);
Michal Vasko4490d312020-06-16 13:08:55 +0200537
538 /* c should not be replaced, so c remains not default */
Radek Iša56ca9e42020-09-08 18:42:00 +0200539 assert_false(lyd_child(target)->flags & LYD_DEFAULT);
540
541 lyd_free_all(target);
542 lyd_free_all(source);
Michal Vasko4490d312020-06-16 13:08:55 +0200543}
544
545static void
546test_leafrefs(void **state)
547{
Michal Vasko4490d312020-06-16 13:08:55 +0200548 const char *sch = "module x {"
Radek Krejcib4ac5a92020-11-23 17:54:33 +0100549 " namespace urn:x;"
550 " prefix x;"
551 " list l {"
552 " key n;"
553 " leaf n { type string; }"
554 " leaf t { type string; }"
555 " leaf r { type leafref { path '/l/n'; } }}}";
Michal Vasko4490d312020-06-16 13:08:55 +0200556 const char *trg = "<l xmlns=\"urn:x\"><n>a</n></l>"
Radek Krejcib4ac5a92020-11-23 17:54:33 +0100557 "<l xmlns=\"urn:x\"><n>b</n><r>a</r></l>";
Michal Vasko4490d312020-06-16 13:08:55 +0200558 const char *src = "<l xmlns=\"urn:x\"><n>c</n><r>a</r></l>"
Radek Krejcib4ac5a92020-11-23 17:54:33 +0100559 "<l xmlns=\"urn:x\"><n>a</n><t>*</t></l>";
Michal Vasko4490d312020-06-16 13:08:55 +0200560 const char *res = "<l xmlns=\"urn:x\"><n>a</n><t>*</t></l>"
Radek Krejcib4ac5a92020-11-23 17:54:33 +0100561 "<l xmlns=\"urn:x\"><n>b</n><r>a</r></l>"
562 "<l xmlns=\"urn:x\"><n>c</n><r>a</r></l>";
Radek Iša56ca9e42020-09-08 18:42:00 +0200563 struct lyd_node *source, *target;
Michal Vasko4490d312020-06-16 13:08:55 +0200564
Radek Iša56ca9e42020-09-08 18:42:00 +0200565 UTEST_ADD_MODULE(sch, LYS_IN_YANG, NULL, NULL);
Michal Vasko4490d312020-06-16 13:08:55 +0200566
Radek Iša56ca9e42020-09-08 18:42:00 +0200567 LYD_TREE_CREATE(src, source);
568 LYD_TREE_CREATE(trg, target);
Michal Vasko4490d312020-06-16 13:08:55 +0200569
Radek Iša56ca9e42020-09-08 18:42:00 +0200570 assert_int_equal(lyd_merge_siblings(&target, source, 0), LY_SUCCESS);
Radek Krejci7931b192020-06-25 17:05:03 +0200571
Radek Iša56ca9e42020-09-08 18:42:00 +0200572 LYD_TREE_CHECK_CHAR(target, res, LYD_PRINT_SHRINK);
Michal Vasko4490d312020-06-16 13:08:55 +0200573
Radek Iša56ca9e42020-09-08 18:42:00 +0200574 lyd_free_all(source);
575 lyd_free_all(target);
Michal Vasko4490d312020-06-16 13:08:55 +0200576}
577
578int
579main(void)
580{
581 const struct CMUnitTest tests[] = {
Radek Iša56ca9e42020-09-08 18:42:00 +0200582 UTEST(test_batch),
583 UTEST(test_leaf),
584 UTEST(test_container),
585 UTEST(test_list),
586 UTEST(test_list2),
587 UTEST(test_case),
588 UTEST(test_dflt),
589 UTEST(test_dflt2),
590 UTEST(test_leafrefs),
Michal Vasko4490d312020-06-16 13:08:55 +0200591 };
592
593 return cmocka_run_group_tests(tests, NULL, NULL);
594}