The Battle for Wesnoth  1.19.11+dev
test_serialization.cpp
Go to the documentation of this file.
1 /*
2  Copyright (C) 2009 - 2025
3  by Karol Nowak <grywacz@gmail.com>
4  Part of the Battle for Wesnoth Project https://www.wesnoth.org/
5 
6  This program is free software; you can redistribute it and/or modify
7  it under the terms of the GNU General Public License as published by
8  the Free Software Foundation; either version 2 of the License, or
9  (at your option) any later version.
10  This program is distributed in the hope that it will be useful,
11  but WITHOUT ANY WARRANTY.
12 
13  See the COPYING file for more details.
14 */
15 
16 #define GETTEXT_DOMAIN "wesnoth-test"
17 
18 #include <array>
19 #include <vector>
20 #include <string>
21 #include "serialization/base64.hpp"
24 #include <boost/test/unit_test.hpp>
25 
26 namespace std {
27 static std::ostream& operator<<(std::ostream& str, const std::pair<const std::string, std::string>& p)
28 {
29  return str << '(' << p.first << " => " << p.second << ')';
30 }
31 }
32 
33 BOOST_AUTO_TEST_SUITE ( test_serialization_utils_and_unicode )
34 
35 BOOST_AUTO_TEST_CASE( utils_join_test )
36 {
37  std::vector<std::string> fruit;
38 
39  BOOST_CHECK( utils::join(fruit).empty() );
40  BOOST_CHECK( utils::join(fruit, "---").empty() );
41 
42  fruit.push_back("apples");
43 
44  BOOST_CHECK( utils::join(fruit) == "apples" );
45  BOOST_CHECK( utils::join(fruit, "---") == "apples" );
46 
47  fruit.push_back("oranges");
48  fruit.push_back("lemons");
49 
50  BOOST_CHECK( utils::join(fruit) == "apples,oranges,lemons" );
51  BOOST_CHECK( utils::join(fruit, "---") == "apples---oranges---lemons" );
52 }
53 
54 BOOST_AUTO_TEST_CASE( utils_split_test )
55 {
56  const std::string test_string = "a, , bb, ccc || d, ee,, fff | | g, , hh, iii";
57 
58  {
59  auto split = utils::split(test_string);
60  std::array expect = {"a", "bb", "ccc || d", "ee", "fff | | g", "hh", "iii"};
61  BOOST_CHECK_EQUAL_COLLECTIONS(split.begin(), split.end(), expect.begin(), expect.end());
62  }
63  {
64  auto split = utils::split(test_string, ',', utils::REMOVE_EMPTY | utils::STRIP_SPACES);
65  std::array expect = {"a", "bb", "ccc || d", "ee", "fff | | g", "hh", "iii"};
66  BOOST_CHECK_EQUAL_COLLECTIONS(split.begin(), split.end(), expect.begin(), expect.end());
67  }
68  {
69  auto split = utils::split(test_string, ',', utils::REMOVE_EMPTY);
70  std::array expect = {"a", " ", " bb", " ccc || d", " ee", " fff | | g", " ", " hh", " iii"};
71  BOOST_CHECK_EQUAL_COLLECTIONS(split.begin(), split.end(), expect.begin(), expect.end());
72  }
73  {
74  auto split = utils::split(test_string, ',', utils::STRIP_SPACES);
75  std::array expect = {"a", "", "bb", "ccc || d", "ee", "", "fff | | g", "", "hh", "iii"};
76  BOOST_CHECK_EQUAL_COLLECTIONS(split.begin(), split.end(), expect.begin(), expect.end());
77  }
78  {
79  auto split = utils::split(test_string, ',', 0);
80  std::array expect = {"a", " ", " bb", " ccc || d", " ee", "", " fff | | g", " ", " hh", " iii"};
81  BOOST_CHECK_EQUAL_COLLECTIONS(split.begin(), split.end(), expect.begin(), expect.end());
82  }
83  {
84  auto split = utils::split(test_string, '|');
85  std::array expect = {"a, , bb, ccc", "d, ee,, fff", "g, , hh, iii"};
86  BOOST_CHECK_EQUAL_COLLECTIONS(split.begin(), split.end(), expect.begin(), expect.end());
87  }
88  {
89  auto split = utils::split(test_string, '|', utils::REMOVE_EMPTY | utils::STRIP_SPACES);
90  std::array expect = {"a, , bb, ccc", "d, ee,, fff", "g, , hh, iii"};
91  BOOST_CHECK_EQUAL_COLLECTIONS(split.begin(), split.end(), expect.begin(), expect.end());
92  }
93  {
94  auto split = utils::split(test_string, '|', utils::REMOVE_EMPTY);
95  std::array expect = {"a, , bb, ccc ", " d, ee,, fff ", " ", " g, , hh, iii"};
96  BOOST_CHECK_EQUAL_COLLECTIONS(split.begin(), split.end(), expect.begin(), expect.end());
97  }
98  {
99  auto split = utils::split(test_string, '|', utils::STRIP_SPACES);
100  std::array expect = {"a, , bb, ccc", "", "d, ee,, fff", "", "g, , hh, iii"};
101  BOOST_CHECK_EQUAL_COLLECTIONS(split.begin(), split.end(), expect.begin(), expect.end());
102  }
103  {
104  auto split = utils::split(test_string, '|', 0);
105  std::array expect = {"a, , bb, ccc ", "", " d, ee,, fff ", " ", " g, , hh, iii"};
106  BOOST_CHECK_EQUAL_COLLECTIONS(split.begin(), split.end(), expect.begin(), expect.end());
107  }
108 }
109 
110 BOOST_AUTO_TEST_CASE( utils_quoted_split_test )
111 {
112  const std::string test_string = "a, `, bb, ccc || d, ee,, fff | `| g, `, hh, iii";
113 
114  {
115  auto split = utils::quoted_split(test_string, ',', utils::REMOVE_EMPTY | utils::STRIP_SPACES, '`');
116  std::array expect = {"a", "`, bb", "ccc || d", "ee", "fff | `| g", "`, hh", "iii"};
117  BOOST_CHECK_EQUAL_COLLECTIONS(split.begin(), split.end(), expect.begin(), expect.end());
118  }
119  {
120  auto split = utils::quoted_split(test_string, ',', utils::REMOVE_EMPTY, '`');
121  std::array expect = {"a", " `, bb", " ccc || d", " ee", " fff | `| g", " `, hh", " iii"};
122  BOOST_CHECK_EQUAL_COLLECTIONS(split.begin(), split.end(), expect.begin(), expect.end());
123  }
124  {
125  auto split = utils::quoted_split(test_string, ',', utils::STRIP_SPACES, '`');
126  std::array expect = {"a", "`, bb", "ccc || d", "ee", "", "fff | `| g", "`, hh", "iii"};
127  BOOST_CHECK_EQUAL_COLLECTIONS(split.begin(), split.end(), expect.begin(), expect.end());
128  }
129  {
130  auto split = utils::quoted_split(test_string, ',', 0, '`');
131  std::array expect = {"a", " `, bb", " ccc || d", " ee", "", " fff | `| g", " `, hh", " iii"};
132  BOOST_CHECK_EQUAL_COLLECTIONS(split.begin(), split.end(), expect.begin(), expect.end());
133  }
134  {
135  auto split = utils::quoted_split(test_string, '|', utils::REMOVE_EMPTY | utils::STRIP_SPACES, '`');
136  std::array expect = {"a, `, bb, ccc", "d, ee,, fff", "`| g, `, hh, iii"};
137  BOOST_CHECK_EQUAL_COLLECTIONS(split.begin(), split.end(), expect.begin(), expect.end());
138  }
139  {
140  auto split = utils::quoted_split(test_string, '|', utils::REMOVE_EMPTY, '`');
141  std::array expect = {"a, `, bb, ccc ", " d, ee,, fff ", " `| g, `, hh, iii"};
142  BOOST_CHECK_EQUAL_COLLECTIONS(split.begin(), split.end(), expect.begin(), expect.end());
143  }
144  {
145  auto split = utils::quoted_split(test_string, '|', utils::STRIP_SPACES, '`');
146  std::array expect = {"a, `, bb, ccc", "", "d, ee,, fff", "`| g, `, hh, iii"};
147  BOOST_CHECK_EQUAL_COLLECTIONS(split.begin(), split.end(), expect.begin(), expect.end());
148  }
149  {
150  auto split = utils::quoted_split(test_string, '|', 0, '`');
151  std::array expect = {"a, `, bb, ccc ", "", " d, ee,, fff ", " `| g, `, hh, iii"};
152  BOOST_CHECK_EQUAL_COLLECTIONS(split.begin(), split.end(), expect.begin(), expect.end());
153  }
154 }
155 
156 BOOST_AUTO_TEST_CASE( utils_map_split_test )
157 {
158  const std::string test_string = "a = b:2,, c = d:.9, e = f:5;; x = r:12, y = b:9.2,, z = g:45";
159 
160  {
161  auto split = utils::map_split(test_string);
162  std::map<std::string, std::string> expect = {
163  {"a = b", "2"},
164  {"c = d", ".9"},
165  {"e = f", "5;; x = r:12"},
166  {"y = b", "9.2"},
167  {"z = g", "45"}
168  };
169  BOOST_CHECK_EQUAL_COLLECTIONS(split.begin(), split.end(), expect.begin(), expect.end());
170  }
171 
172  {
173  auto split = utils::map_split(test_string, ',', ':', utils::REMOVE_EMPTY | utils::STRIP_SPACES);
174  std::map<std::string, std::string> expect = {
175  {"a = b", "2"},
176  {"c = d", ".9"},
177  {"e = f", "5;; x = r:12"},
178  {"y = b", "9.2"},
179  {"z = g", "45"},
180  };
181  BOOST_CHECK_EQUAL_COLLECTIONS(split.begin(), split.end(), expect.begin(), expect.end());
182  }
183  {
184  auto split = utils::map_split(test_string, ';', ':', utils::REMOVE_EMPTY | utils::STRIP_SPACES);
185  std::map<std::string, std::string> expect = {
186  {"a = b", "2,, c = d:.9, e = f:5"},
187  {"x = r", "12, y = b:9.2,, z = g:45"},
188  };
189  BOOST_CHECK_EQUAL_COLLECTIONS(split.begin(), split.end(), expect.begin(), expect.end());
190  }
191  {
192  auto split = utils::map_split(test_string, ',', '=', utils::REMOVE_EMPTY | utils::STRIP_SPACES);
193  std::map<std::string, std::string> expect = {
194  {"a ", " b:2"},
195  {"c ", " d:.9"},
196  {"e ", " f:5;; x = r:12"},
197  {"y ", " b:9.2"},
198  {"z ", " g:45"},
199  };
200  BOOST_CHECK_EQUAL_COLLECTIONS(split.begin(), split.end(), expect.begin(), expect.end());
201  }
202  {
203  auto split = utils::map_split(test_string, ';', '.', utils::REMOVE_EMPTY | utils::STRIP_SPACES);
204  std::map<std::string, std::string> expect = {
205  {"a = b:2,, c = d:", "9, e = f:5"},
206  {"x = r:12, y = b:9", "2,, z = g:45"}
207  };
208  BOOST_CHECK_EQUAL_COLLECTIONS(split.begin(), split.end(), expect.begin(), expect.end());
209  }
210 
211  {
212  auto split = utils::map_split(test_string, ',', ':', utils::REMOVE_EMPTY);
213  std::map<std::string, std::string> expect = {
214  {"a = b", "2"},
215  {" c = d", ".9"},
216  {" e = f", "5;; x = r:12"},
217  {" y = b", "9.2"},
218  {" z = g", "45"},
219  };
220  BOOST_CHECK_EQUAL_COLLECTIONS(split.begin(), split.end(), expect.begin(), expect.end());
221  }
222  {
223  auto split = utils::map_split(test_string, ';', ':', utils::REMOVE_EMPTY);
224  std::map<std::string, std::string> expect = {
225  {"a = b", "2,, c = d:.9, e = f:5"},
226  {" x = r", "12, y = b:9.2,, z = g:45"},
227  };
228  BOOST_CHECK_EQUAL_COLLECTIONS(split.begin(), split.end(), expect.begin(), expect.end());
229  }
230  {
231  auto split = utils::map_split(test_string, ',', '=', utils::REMOVE_EMPTY);
232  std::map<std::string, std::string> expect = {
233  {"a ", " b:2"},
234  {" c ", " d:.9"},
235  {" e ", " f:5;; x = r:12"},
236  {" y ", " b:9.2"},
237  {" z ", " g:45"},
238  };
239  BOOST_CHECK_EQUAL_COLLECTIONS(split.begin(), split.end(), expect.begin(), expect.end());
240  }
241  {
242  auto split = utils::map_split(test_string, ';', '.', utils::REMOVE_EMPTY);
243  std::map<std::string, std::string> expect = {
244  {"a = b:2,, c = d:", "9, e = f:5"},
245  {" x = r:12, y = b:9", "2,, z = g:45"}
246  };
247  BOOST_CHECK_EQUAL_COLLECTIONS(split.begin(), split.end(), expect.begin(), expect.end());
248  }
249 
250  {
251  auto split = utils::map_split(test_string, ',', ':', utils::STRIP_SPACES);
252  std::map<std::string, std::string> expect = {
253  {"a = b", "2"},
254  {"", ""},
255  {"c = d", ".9"},
256  {"e = f", "5;; x = r:12"},
257  {"y = b", "9.2"},
258  {"", ""},
259  {"z = g", "45"},
260  };
261  BOOST_CHECK_EQUAL_COLLECTIONS(split.begin(), split.end(), expect.begin(), expect.end());
262  }
263  {
264  auto split = utils::map_split(test_string, ';', ':', utils::STRIP_SPACES);
265  std::map<std::string, std::string> expect = {
266  {"a = b", "2,, c = d:.9, e = f:5"},
267  {"", ""},
268  {"x = r", "12, y = b:9.2,, z = g:45"},
269  };
270  BOOST_CHECK_EQUAL_COLLECTIONS(split.begin(), split.end(), expect.begin(), expect.end());
271  }
272  {
273  auto split = utils::map_split(test_string, ',', '=', utils::STRIP_SPACES);
274  std::map<std::string, std::string> expect = {
275  {"a ", " b:2"},
276  {"", ""},
277  {"c ", " d:.9"},
278  {"e ", " f:5;; x = r:12"},
279  {"y ", " b:9.2"},
280  {"", ""},
281  {"z ", " g:45"},
282  };
283  BOOST_CHECK_EQUAL_COLLECTIONS(split.begin(), split.end(), expect.begin(), expect.end());
284  }
285  {
286  auto split = utils::map_split(test_string, ';', '.', utils::STRIP_SPACES);
287  std::map<std::string, std::string> expect = {
288  {"a = b:2,, c = d:", "9, e = f:5"},
289  {"", ""},
290  {"x = r:12, y = b:9", "2,, z = g:45"}
291  };
292  BOOST_CHECK_EQUAL_COLLECTIONS(split.begin(), split.end(), expect.begin(), expect.end());
293  }
294 
295  {
296  auto split = utils::map_split(test_string, ',', ':', 0);
297  std::map<std::string, std::string> expect = {
298  {"a = b", "2"},
299  {"", ""},
300  {" c = d", ".9"},
301  {" e = f", "5;; x = r:12"},
302  {" y = b", "9.2"},
303  {"", ""},
304  {" z = g", "45"},
305  };
306  BOOST_CHECK_EQUAL_COLLECTIONS(split.begin(), split.end(), expect.begin(), expect.end());
307  }
308  {
309  auto split = utils::map_split(test_string, ';', ':', 0);
310  std::map<std::string, std::string> expect = {
311  {"a = b", "2,, c = d:.9, e = f:5"},
312  {"", ""},
313  {" x = r", "12, y = b:9.2,, z = g:45"},
314  };
315  BOOST_CHECK_EQUAL_COLLECTIONS(split.begin(), split.end(), expect.begin(), expect.end());
316  }
317  {
318  auto split = utils::map_split(test_string, ',', '=', 0);
319  std::map<std::string, std::string> expect = {
320  {"a ", " b:2"},
321  {"", ""},
322  {" c ", " d:.9"},
323  {" e ", " f:5;; x = r:12"},
324  {" y ", " b:9.2"},
325  {"", ""},
326  {" z ", " g:45"},
327  };
328  BOOST_CHECK_EQUAL_COLLECTIONS(split.begin(), split.end(), expect.begin(), expect.end());
329  }
330  {
331  auto split = utils::map_split(test_string, ';', '.', 0);
332  std::map<std::string, std::string> expect = {
333  {"a = b:2,, c = d:", "9, e = f:5"},
334  {"", ""},
335  {" x = r:12, y = b:9", "2,, z = g:45"}
336  };
337  BOOST_CHECK_EQUAL_COLLECTIONS(split.begin(), split.end(), expect.begin(), expect.end());
338  }
339 }
340 
341 BOOST_AUTO_TEST_CASE( utils_parenthetical_split_test )
342 {
343  {
344  auto split = utils::parenthetical_split("a ( b ) c { d } e ( f { g } ) h", 0, "({", ")}");
345  std::array expect = {"a", "b", "c", "d", "e", "f { g }", "h"};
346  BOOST_CHECK_EQUAL_COLLECTIONS(split.begin(), split.end(), expect.begin(), expect.end());
347  }
348  {
349  auto split = utils::parenthetical_split("a ( b ) c { d } e ( f { g } ) h", 0, "({", ")}", utils::STRIP_SPACES);
350  std::array expect = {"a", "b", "c", "d", "e", "f { g }", "h"};
351  BOOST_CHECK_EQUAL_COLLECTIONS(split.begin(), split.end(), expect.begin(), expect.end());
352  }
353  {
354  auto split = utils::parenthetical_split("a ( b ) c { d } e ( f { g } ) h", 0, "({", ")}", 0);
355  std::array expect = {"a ", " b ", " c ", " d ", " e ", " f { g } ", " h"};
356  BOOST_CHECK_EQUAL_COLLECTIONS(split.begin(), split.end(), expect.begin(), expect.end());
357  }
358 
359  {
360  auto split = utils::parenthetical_split("a, (b, c), {d, e},, f(g,g), h{i,i}", ',', "({", ")}");
361  std::array expect = {"a", "(b, c)", "{d, e}", "f(g,g)", "h{i,i}"};
362  BOOST_CHECK_EQUAL_COLLECTIONS(split.begin(), split.end(), expect.begin(), expect.end());
363  }
364  {
365  auto split = utils::parenthetical_split("a, (b, c), {d, e},, f(g,g), h{i,i}", ',', "({", ")}", utils::REMOVE_EMPTY | utils::STRIP_SPACES);
366  std::array expect = {"a", "(b, c)", "{d, e}", "f(g,g)", "h{i,i}"};
367  BOOST_CHECK_EQUAL_COLLECTIONS(split.begin(), split.end(), expect.begin(), expect.end());
368  }
369  {
370  auto split = utils::parenthetical_split("a, (b, c), {d, e},, f(g,g), h{i,i}", ',', "({", ")}", utils::REMOVE_EMPTY);
371  std::array expect = {"a", " (b, c)", " {d, e}", " f(g,g)", " h{i,i}"};
372  BOOST_CHECK_EQUAL_COLLECTIONS(split.begin(), split.end(), expect.begin(), expect.end());
373  }
374  {
375  auto split = utils::parenthetical_split("a, (b, c), {d, e},, f(g,g), h{i,i}", ',', "({", ")}", utils::STRIP_SPACES);
376  std::array expect = {"a", "(b, c)", "{d, e}", "", "f(g,g)", "h{i,i}"};
377  BOOST_CHECK_EQUAL_COLLECTIONS(split.begin(), split.end(), expect.begin(), expect.end());
378  }
379  {
380  auto split = utils::parenthetical_split("a, (b, c), {d, e},, f(g,g), h{i,i}", ',', "({", ")}", 0);
381  std::array expect = {"a", " (b, c)", " {d, e}", "", " f(g,g)", " h{i,i}"};
382  BOOST_CHECK_EQUAL_COLLECTIONS(split.begin(), split.end(), expect.begin(), expect.end());
383  }
384 }
385 
386 BOOST_AUTO_TEST_CASE( utils_square_parenthetical_split )
387 {
388  {
389  auto split = utils::square_parenthetical_split(" a ,, b ,, c ");
390  std::array expect = {"a", "b", "c"};
391  BOOST_CHECK_EQUAL_COLLECTIONS(split.begin(), split.end(), expect.begin(), expect.end());
392  }
393  {
394  auto split = utils::square_parenthetical_split(" a ,, b ,, c ", ',', "([", ")]", utils::REMOVE_EMPTY | utils::STRIP_SPACES);
395  std::array expect = {"a", "b", "c"};
396  BOOST_CHECK_EQUAL_COLLECTIONS(split.begin(), split.end(), expect.begin(), expect.end());
397  }
398  {
399  auto split = utils::square_parenthetical_split(" a ,, b ,, c ", ',', "([", ")]", utils::REMOVE_EMPTY);
400  std::array expect = {" a ", " b ", " c "};
401  BOOST_CHECK_EQUAL_COLLECTIONS(split.begin(), split.end(), expect.begin(), expect.end());
402  }
403  {
404  auto split = utils::square_parenthetical_split(" a ,, b ,, c ", ',', "([", ")]", utils::STRIP_SPACES);
405  std::array expect = {"a", "", "b", "", "c"};
406  BOOST_CHECK_EQUAL_COLLECTIONS(split.begin(), split.end(), expect.begin(), expect.end());
407  }
408  {
409  auto split = utils::square_parenthetical_split(" a ,, b ,, c ", ',', "([", ")]", 0);
410  std::array expect = {" a ", "", " b ", "", " c "};
411  BOOST_CHECK_EQUAL_COLLECTIONS(split.begin(), split.end(), expect.begin(), expect.end());
412  }
413  {
415  std::array expect = {"a", "a", "a"};
416  BOOST_CHECK_EQUAL_COLLECTIONS(split.begin(), split.end(), expect.begin(), expect.end());
417  }
418  {
419  auto split = utils::square_parenthetical_split("q[a*3,b,c*2]");
420  std::array expect = {"qa", "qa", "qa", "qb", "qc", "qc"};
421  BOOST_CHECK_EQUAL_COLLECTIONS(split.begin(), split.end(), expect.begin(), expect.end());
422  }
423  {
424  auto split = utils::square_parenthetical_split("q[a,b,c]");
425  std::array expect = {"qa", "qb", "qc"};
426  BOOST_CHECK_EQUAL_COLLECTIONS(split.begin(), split.end(), expect.begin(), expect.end());
427  }
428  {
429  auto split = utils::square_parenthetical_split("q[1~5]");
430  std::array expect = {"q1", "q2", "q3", "q4", "q5"};
431  BOOST_CHECK_EQUAL_COLLECTIONS(split.begin(), split.end(), expect.begin(), expect.end());
432  }
433  {
434  auto split = utils::square_parenthetical_split("q[5~1]");
435  std::array expect = {"q5", "q4", "q3", "q2", "q1"};
436  BOOST_CHECK_EQUAL_COLLECTIONS(split.begin(), split.end(), expect.begin(), expect.end());
437  }
438  {
439  auto split = utils::square_parenthetical_split("q[001~005]");
440  std::array expect = {"q001", "q002", "q003", "q004", "q005"};
441  BOOST_CHECK_EQUAL_COLLECTIONS(split.begin(), split.end(), expect.begin(), expect.end());
442  }
443  {
444  auto split = utils::square_parenthetical_split("q[007~012]");
445  std::array expect = {"q007", "q008", "q009", "q010", "q011", "q012"};
446  BOOST_CHECK_EQUAL_COLLECTIONS(split.begin(), split.end(), expect.begin(), expect.end());
447  }
448  {
449  auto split = utils::square_parenthetical_split("a[1~3](1,[5,6,7]),b[8,9]");
450  std::array expect = {"a1(1,5)", "a2(1,6)", "a3(1,7)", "b8", "b9"};
451  BOOST_CHECK_EQUAL_COLLECTIONS(split.begin(), split.end(), expect.begin(), expect.end());
452  }
453  {
454  auto split = utils::square_parenthetical_split("abc[07~10]");
455  std::array expect = {"abc07", "abc08", "abc09", "abc10"};
456  BOOST_CHECK_EQUAL_COLLECTIONS(split.begin(), split.end(), expect.begin(), expect.end());
457  }
458  {
459  auto split = utils::square_parenthetical_split("a[1,2]b[3~4]:c[5,6]");
460  std::array expect = {"a1b3:c5", "a2b4:c6"};
461  BOOST_CHECK_EQUAL_COLLECTIONS(split.begin(), split.end(), expect.begin(), expect.end());
462  }
463  {
464  auto split = utils::square_parenthetical_split("abc[3~1].png");
465  std::array expect = {"abc3.png", "abc2.png", "abc1.png"};
466  BOOST_CHECK_EQUAL_COLLECTIONS(split.begin(), split.end(), expect.begin(), expect.end());
467  }
468  {
469  auto split = utils::square_parenthetical_split("abc[3,1].png");
470  std::array expect = {"abc3.png", "abc1.png"};
471  BOOST_CHECK_EQUAL_COLLECTIONS(split.begin(), split.end(), expect.begin(), expect.end());
472  }
473  {
474  auto split = utils::square_parenthetical_split("abc[de,xyz]");
475  std::array expect = {"abcde", "abcxyz"};
476  BOOST_CHECK_EQUAL_COLLECTIONS(split.begin(), split.end(), expect.begin(), expect.end());
477  }
478  {
479  auto split = utils::square_parenthetical_split("abc[1*3]");
480  std::array expect = {"abc1", "abc1", "abc1"};
481  BOOST_CHECK_EQUAL_COLLECTIONS(split.begin(), split.end(), expect.begin(), expect.end());
482  }
483 }
484 
485 BOOST_AUTO_TEST_CASE( utils_unicode_test )
486 {
487  std::string unicode = "ünicod€ check";
488  BOOST_CHECK( utf8::size(unicode) == 13 );
489 
490  int euro = utf8::index(unicode,6);
491  BOOST_CHECK( unicode.substr(euro,utf8::index(unicode,7)-euro) == "€" );
492 
493  BOOST_CHECK( utf8::truncate(unicode,3) == "üni");
494 
495  std::string apple_u8("apple");
496  std::u32string apple_u4 = unicode_cast<std::u32string>(apple_u8);
497  std::u16string apple_u16 = unicode_cast<std::u16string>(apple_u4);
498 
499  BOOST_CHECK( apple_u4.size() == 5 );
500  BOOST_CHECK_EQUAL( apple_u8, unicode_cast<std::string>(apple_u4) );
501  BOOST_CHECK_EQUAL( apple_u8, unicode_cast<std::string>(apple_u16) );
502  BOOST_CHECK( apple_u4 == unicode_cast<std::u32string>(apple_u16) );
503  BOOST_CHECK( apple_u16 == unicode_cast<std::u16string>(apple_u4) );
504  BOOST_CHECK_EQUAL( apple_u8.size(), apple_u16.size() );
505 
506  std::u32string water_u4;
507  water_u4.push_back(0x6C34);
508  std::string water_u8 = unicode_cast<std::string>(water_u4);
509 
510 #if defined(_WIN32) || defined(_WIN64)
511  // Windows complains it can't be represented in the currentl code-page.
512  // So instead, check directly for its UTF-8 representation.
513  BOOST_CHECK_EQUAL(water_u8, "\xE6\xB0\xB4");
514 #else
515  BOOST_CHECK_EQUAL(water_u8, "\u6C34");
516 #endif
517 
518 #if defined(_WIN32) || defined(_WIN64)
519  // Same as above.
520  std::string nonbmp_u8("\xF0\x90\x80\x80");
521 #else
522  std::string nonbmp_u8("\U00010000");
523 #endif
524  std::u32string nonbmp_u4 = unicode_cast<std::u32string>(nonbmp_u8);
525  std::u16string nonbmp_u16 = unicode_cast<std::u16string>(nonbmp_u4);
526 
527  BOOST_CHECK_EQUAL(nonbmp_u8.size(), 4u);
528  BOOST_CHECK_EQUAL(nonbmp_u8, unicode_cast<std::string>(nonbmp_u4));
529  BOOST_CHECK_EQUAL(nonbmp_u8, unicode_cast<std::string>(nonbmp_u16));
530  BOOST_CHECK(nonbmp_u16 == unicode_cast<std::u16string>(nonbmp_u4));
531  BOOST_CHECK(nonbmp_u4 == unicode_cast<std::u32string>(nonbmp_u16));
532 }
533 
534 BOOST_AUTO_TEST_CASE( test_lowercase )
535 {
536  BOOST_CHECK_EQUAL ( utf8::lowercase("FOO") , "foo" );
537  BOOST_CHECK_EQUAL ( utf8::lowercase("foo") , "foo" );
538  BOOST_CHECK_EQUAL ( utf8::lowercase("FoO") , "foo" );
539  BOOST_CHECK_EQUAL ( utf8::lowercase("fO0") , "fo0" );
540 }
541 
542 BOOST_AUTO_TEST_CASE( test_wildcard_string_match )
543 {
544  const std::string str = "foo bar baz";
545 
546  BOOST_CHECK(utils::wildcard_string_match(str, "*bar*"));
547  BOOST_CHECK(utils::wildcard_string_match(str, "+bar+"));
548 
549  BOOST_CHECK(!utils::wildcard_string_match(str, "*BAR*"));
550  BOOST_CHECK(!utils::wildcard_string_match(str, "+BAR+"));
551  BOOST_CHECK(!utils::wildcard_string_match(str, "bar"));
552 
553  BOOST_CHECK(utils::wildcard_string_match(str, "*ba? b*"));
554  BOOST_CHECK(utils::wildcard_string_match(str, "+ba? b+"));
555  BOOST_CHECK(utils::wildcard_string_match(str, "*?a?*"));
556  BOOST_CHECK(utils::wildcard_string_match(str, "+?a?+"));
557 
558  BOOST_CHECK(!utils::wildcard_string_match(str, "foo? "));
559  BOOST_CHECK(!utils::wildcard_string_match(str, "?foo"));
560 
561  std::string superfluous_mask;
562 
563  superfluous_mask = std::string(str.length(), '?');
564  BOOST_CHECK(utils::wildcard_string_match(str, superfluous_mask));
565  BOOST_CHECK(!utils::wildcard_string_match(str, superfluous_mask + '?'));
566 
567  superfluous_mask = std::string(str.length(), '*');
568  BOOST_CHECK(utils::wildcard_string_match(str, superfluous_mask));
569  BOOST_CHECK(utils::wildcard_string_match(str, superfluous_mask + '*'));
570 
571  superfluous_mask = std::string(str.length(), '+');
572  BOOST_CHECK(utils::wildcard_string_match(str, superfluous_mask));
573  BOOST_CHECK(!utils::wildcard_string_match(str, superfluous_mask + '+'));
574 
575  BOOST_CHECK(utils::wildcard_string_match("", ""));
576  BOOST_CHECK(!utils::wildcard_string_match(str, ""));
577 
578  BOOST_CHECK(utils::wildcard_string_match("", "*"));
579  BOOST_CHECK(utils::wildcard_string_match("", "***"));
580  BOOST_CHECK(!utils::wildcard_string_match("", "+"));
581  BOOST_CHECK(!utils::wildcard_string_match("", "*bar"));
582  BOOST_CHECK(!utils::wildcard_string_match("", "***?**"));
583  BOOST_CHECK(!utils::wildcard_string_match("", "+++?++"));
584  BOOST_CHECK(!utils::wildcard_string_match("", "?"));
585  BOOST_CHECK(!utils::wildcard_string_match("", "???"));
586 
587  BOOST_CHECK(utils::wildcard_string_match("hello.txt", "*.txt"));
588  BOOST_CHECK(utils::wildcard_string_match("hello.txt", "h*t"));
589  BOOST_CHECK(utils::wildcard_string_match("hello.txt", "?ello.*"));
590  BOOST_CHECK(!utils::wildcard_string_match("hello.txt", "*.doc"));
591  BOOST_CHECK(utils::wildcard_string_match("file123.tmp", "file?2*.tmp"));
592  BOOST_CHECK(utils::wildcard_string_match("test", "t*t"));
593  BOOST_CHECK(utils::wildcard_string_match("multiple.dots.file", "*.dots.*"));
594  BOOST_CHECK(!utils::wildcard_string_match("case.txt", "CASE.TXT"));
595  BOOST_CHECK(utils::wildcard_string_match("single", "?ingle"));
596  BOOST_CHECK(!utils::wildcard_string_match("different", "diff*txt"));
597 
598  BOOST_CHECK(utils::wildcard_string_match("foo bar baz bar baz", "*bar baz"));
599  BOOST_CHECK(!utils::wildcard_string_match("abc", "ab*d"));
600  BOOST_CHECK(utils::wildcard_string_match("abcccd", "*ccd"));
601  BOOST_CHECK(utils::wildcard_string_match("mississipissippi", "*issip*ss*"));
602  BOOST_CHECK(!utils::wildcard_string_match("xxxx*zzzzzzzzy*f", "xxxx*zzy*fffff"));
603  BOOST_CHECK(utils::wildcard_string_match("xxxx*zzzzzzzzy*f", "xxx*zzy*f"));
604  BOOST_CHECK(!utils::wildcard_string_match("xxxxzzzzzzzzyf", "xxxx*zzy*fffff"));
605  BOOST_CHECK(utils::wildcard_string_match("xxxxzzzzzzzzyf", "xxxx*zzy*f"));
606  BOOST_CHECK(utils::wildcard_string_match("xyxyxyzyxyz", "xy*z*xyz"));
607  BOOST_CHECK(utils::wildcard_string_match("mississippi", "*sip*"));
608  BOOST_CHECK(utils::wildcard_string_match("xyxyxyxyz", "xy*xyz"));
609  BOOST_CHECK(utils::wildcard_string_match("mississippi", "mi*sip*"));
610  BOOST_CHECK(utils::wildcard_string_match("ababac", "*abac*"));
611  BOOST_CHECK(utils::wildcard_string_match("ababac", "*abac*"));
612  BOOST_CHECK(utils::wildcard_string_match("aaazz", "a*zz*"));
613  BOOST_CHECK(!utils::wildcard_string_match("a12b12", "*12*23"));
614  BOOST_CHECK(!utils::wildcard_string_match("a12b12", "a12b"));
615  BOOST_CHECK(utils::wildcard_string_match("a12b12", "*12*12*"));
616  BOOST_CHECK(utils::wildcard_string_match("caaab", "*a?b"));
617  BOOST_CHECK(utils::wildcard_string_match("*", "*"));
618  BOOST_CHECK(utils::wildcard_string_match("a*abab", "a*b"));
619  BOOST_CHECK(utils::wildcard_string_match("a*r", "a*"));
620  BOOST_CHECK(!utils::wildcard_string_match("a*ar", "a*aar"));
621  BOOST_CHECK(utils::wildcard_string_match("XYXYXYZYXYz", "XY*Z*XYz"));
622  BOOST_CHECK(utils::wildcard_string_match("missisSIPpi", "*SIP*"));
623  BOOST_CHECK(utils::wildcard_string_match("mississipPI", "*issip*PI"));
624  BOOST_CHECK(utils::wildcard_string_match("xyxyxyxyz", "xy*xyz"));
625  BOOST_CHECK(utils::wildcard_string_match("miSsissippi", "mi*sip*"));
626  BOOST_CHECK(utils::wildcard_string_match("c+od", "**c+d"));
627 }
628 
629 BOOST_AUTO_TEST_CASE( test_base64_encodings )
630 {
631  const std::vector<uint8_t> empty;
632  const std::string empty_b64;
633  const std::string empty_c64;
634  const std::vector<uint8_t> foo = {'f', 'o', 'o'};
635  const std::string foo_b64 = "Zm9v";
636  const std::string foo_c64 = "axqP";
637  const std::vector<uint8_t> foob = {'f', 'o', 'o', 'b'};
638  const std::string foob_b64 = "Zm9vYg==";
639  const std::string foob_c64 = "axqPW/";
640 
641  std::vector<uint8_t> many_bytes;
642 
643  many_bytes.resize(1024);
644  for(int i = 0; i < 1024; ++i) {
645  many_bytes[i] = i % 256;
646  }
647 
648  BOOST_CHECK(base64::encode(empty).empty());
649  BOOST_CHECK_EQUAL(base64::encode(foo), foo_b64);
650  BOOST_CHECK_EQUAL(base64::encode(foob), foob_b64);
651 
652  BOOST_CHECK(base64::decode(empty_b64).empty());
653  // Not using CHECK_EQUAL because vector<uint8_t> is not printable
654  BOOST_CHECK(base64::decode(foo_b64) == foo);
655  BOOST_CHECK(base64::decode(foob_b64) == foob);
656 
657  BOOST_CHECK(crypt64::encode(empty).empty());
658  BOOST_CHECK_EQUAL(crypt64::encode(foo), foo_c64);
659  BOOST_CHECK_EQUAL(crypt64::encode(foob), foob_c64);
660 
661  BOOST_CHECK(crypt64::decode(empty_c64).empty());
662  // Not using CHECK_EQUAL because vector<uint8_t> is not printable
663  BOOST_CHECK(crypt64::decode(foo_c64) == foo);
664  BOOST_CHECK(crypt64::decode(foob_c64) == foob);
665 
666  BOOST_CHECK_EQUAL(crypt64::decode('.'), 0);
667  BOOST_CHECK_EQUAL(crypt64::decode('z'), 63);
668  BOOST_CHECK_EQUAL(crypt64::encode(0), '.');
669  BOOST_CHECK_EQUAL(crypt64::encode(63), 'z');
670 
671  BOOST_CHECK(base64::decode(base64::encode(many_bytes)) == many_bytes);
672  BOOST_CHECK(crypt64::decode(crypt64::encode(many_bytes)) == many_bytes);
673 }
674 
675 BOOST_AUTO_TEST_SUITE_END()
std::ostream & operator<<(std::ostream &s, const ai::attack_result &r)
Definition: actions.cpp:1118
std::size_t i
Definition: function.cpp:1030
std::string encode(utils::byte_view bytes)
Definition: base64.cpp:225
std::vector< uint8_t > decode(std::string_view in)
Definition: base64.cpp:221
std::string encode(utils::byte_view bytes)
Definition: base64.cpp:235
std::vector< uint8_t > decode(std::string_view in)
Definition: base64.cpp:231
std::string lowercase(std::string_view s)
Returns a lowercased version of the string.
Definition: unicode.cpp:50
std::size_t size(std::string_view str)
Length in characters of a UTF-8 string.
Definition: unicode.cpp:85
std::string & truncate(std::string &str, const std::size_t size)
Truncates a UTF-8 string to the specified number of characters.
Definition: unicode.cpp:116
std::size_t index(std::string_view str, const std::size_t index)
Codepoint index corresponding to the nth character in a UTF-8 string.
Definition: unicode.cpp:70
@ STRIP_SPACES
REMOVE_EMPTY: remove empty elements.
@ REMOVE_EMPTY
std::map< std::string, std::string > map_split(const std::string &val, char major, char minor, int flags, const std::string &default_value)
Splits a string based on two separators into a map.
std::vector< std::string > quoted_split(const std::string &val, char c, int flags, char quote)
This function is identical to split(), except it does not split when it otherwise would if the previo...
std::vector< std::string > parenthetical_split(std::string_view val, const char separator, std::string_view left, std::string_view right, const int flags)
Splits a string based either on a separator, except then the text appears within specified parenthesi...
bool wildcard_string_match(std::string_view str, std::string_view pat) noexcept
Performs pattern matching with wildcards.
std::vector< std::string > square_parenthetical_split(const std::string &val, const char separator, const std::string &left, const std::string &right, const int flags)
Similar to parenthetical_split, but also expands embedded square brackets.
std::string join(const T &v, const std::string &s=",")
Generates a new string joining container items in a list.
std::vector< std::string > split(const config_attribute_value &val)
BOOST_AUTO_TEST_SUITE(filesystem)
mock_party p
BOOST_AUTO_TEST_CASE(utils_join_test)