]>
Commit | Line | Data |
---|---|---|
53e1b683 | 1 | /* SPDX-License-Identifier: LGPL-2.1+ */ |
d4205751 | 2 | |
844ec79b | 3 | #include <errno.h> |
2d5bdf5b | 4 | #include <fcntl.h> |
cf0fbc49 TA |
5 | #include <locale.h> |
6 | #include <unistd.h> | |
d4205751 | 7 | |
07630cea LP |
8 | #include "sd-messages.h" |
9 | ||
b5efdb8a | 10 | #include "alloc-util.h" |
3ffd4af2 LP |
11 | #include "catalog.h" |
12 | #include "fd-util.h" | |
627d2bac | 13 | #include "fs-util.h" |
d4205751 | 14 | #include "log.h" |
844ec79b | 15 | #include "macro.h" |
d9b6baa6 | 16 | #include "path-util.h" |
07630cea | 17 | #include "string-util.h" |
d9b6baa6 YW |
18 | #include "strv.h" |
19 | #include "tests.h" | |
e4de7287 | 20 | #include "tmpfile-util.h" |
3ffd4af2 | 21 | #include "util.h" |
d4205751 | 22 | |
d9b6baa6 | 23 | static char** catalog_dirs = NULL; |
143bfdaf HHPF |
24 | static const char *no_catalog_dirs[] = { |
25 | "/bin/hopefully/with/no/catalog", | |
26 | NULL | |
27 | }; | |
28 | ||
a95686bb | 29 | static OrderedHashmap* test_import(const char* contents, ssize_t size, int code) { |
627d2bac | 30 | _cleanup_(unlink_tempfilep) char name[] = "/tmp/test-catalog.XXXXXX"; |
2d5bdf5b | 31 | _cleanup_close_ int fd; |
a95686bb | 32 | OrderedHashmap *h; |
9d85882a SW |
33 | |
34 | if (size < 0) | |
35 | size = strlen(contents); | |
36 | ||
a95686bb | 37 | assert_se(h = ordered_hashmap_new(&catalog_hash_ops)); |
2d5bdf5b | 38 | |
646853bd | 39 | fd = mkostemp_safe(name); |
787784c4 | 40 | assert_se(fd >= 0); |
844ec79b ZJS |
41 | assert_se(write(fd, contents, size) == size); |
42 | ||
627d2bac | 43 | assert_se(catalog_import_file(h, name) == code); |
844ec79b | 44 | |
9d85882a SW |
45 | return h; |
46 | } | |
844ec79b | 47 | |
9d85882a | 48 | static void test_catalog_import_invalid(void) { |
a95686bb | 49 | _cleanup_ordered_hashmap_free_free_free_ OrderedHashmap *h = NULL; |
844ec79b | 50 | |
9d85882a | 51 | h = test_import("xxx", -1, -EINVAL); |
a95686bb | 52 | assert_se(ordered_hashmap_isempty(h)); |
9d85882a | 53 | } |
844ec79b | 54 | |
9d85882a | 55 | static void test_catalog_import_badid(void) { |
a95686bb | 56 | _cleanup_ordered_hashmap_free_free_free_ OrderedHashmap *h = NULL; |
9d85882a | 57 | const char *input = |
844ec79b ZJS |
58 | "-- 0027229ca0644181a76c4e92458afaff dededededededededededededededede\n" \ |
59 | "Subject: message\n" \ | |
60 | "\n" \ | |
9d85882a SW |
61 | "payload\n"; |
62 | h = test_import(input, -1, -EINVAL); | |
63 | } | |
844ec79b | 64 | |
9d85882a | 65 | static void test_catalog_import_one(void) { |
a95686bb | 66 | _cleanup_ordered_hashmap_free_free_free_ OrderedHashmap *h = NULL; |
9d85882a | 67 | char *payload; |
844ec79b | 68 | |
9d85882a | 69 | const char *input = |
844ec79b ZJS |
70 | "-- 0027229ca0644181a76c4e92458afaff dededededededededededededededed\n" \ |
71 | "Subject: message\n" \ | |
72 | "\n" \ | |
9d85882a SW |
73 | "payload\n"; |
74 | const char *expect = | |
75 | "Subject: message\n" \ | |
76 | "\n" \ | |
77 | "payload\n"; | |
844ec79b | 78 | |
9d85882a | 79 | h = test_import(input, -1, 0); |
a95686bb | 80 | assert_se(ordered_hashmap_size(h) == 1); |
d4205751 | 81 | |
90e74a66 | 82 | ORDERED_HASHMAP_FOREACH(payload, h) { |
06466a7f ZJS |
83 | printf("expect: %s\n", expect); |
84 | printf("actual: %s\n", payload); | |
9d85882a SW |
85 | assert_se(streq(expect, payload)); |
86 | } | |
844ec79b ZJS |
87 | } |
88 | ||
c059b62f | 89 | static void test_catalog_import_merge(void) { |
a95686bb | 90 | _cleanup_ordered_hashmap_free_free_free_ OrderedHashmap *h = NULL; |
c059b62f | 91 | char *payload; |
c059b62f SW |
92 | |
93 | const char *input = | |
94 | "-- 0027229ca0644181a76c4e92458afaff dededededededededededededededed\n" \ | |
95 | "Subject: message\n" \ | |
96 | "Defined-By: me\n" \ | |
97 | "\n" \ | |
98 | "payload\n" \ | |
99 | "\n" \ | |
100 | "-- 0027229ca0644181a76c4e92458afaff dededededededededededededededed\n" \ | |
101 | "Subject: override subject\n" \ | |
102 | "X-Header: hello\n" \ | |
103 | "\n" \ | |
104 | "override payload\n"; | |
105 | ||
106 | const char *combined = | |
107 | "Subject: override subject\n" \ | |
108 | "X-Header: hello\n" \ | |
109 | "Subject: message\n" \ | |
110 | "Defined-By: me\n" \ | |
111 | "\n" \ | |
112 | "override payload\n"; | |
113 | ||
114 | h = test_import(input, -1, 0); | |
a95686bb | 115 | assert_se(ordered_hashmap_size(h) == 1); |
c059b62f | 116 | |
90e74a66 | 117 | ORDERED_HASHMAP_FOREACH(payload, h) |
c059b62f | 118 | assert_se(streq(combined, payload)); |
c059b62f SW |
119 | } |
120 | ||
121 | static void test_catalog_import_merge_no_body(void) { | |
a95686bb | 122 | _cleanup_ordered_hashmap_free_free_free_ OrderedHashmap *h = NULL; |
c059b62f | 123 | char *payload; |
c059b62f SW |
124 | |
125 | const char *input = | |
126 | "-- 0027229ca0644181a76c4e92458afaff dededededededededededededededed\n" \ | |
127 | "Subject: message\n" \ | |
128 | "Defined-By: me\n" \ | |
129 | "\n" \ | |
130 | "payload\n" \ | |
131 | "\n" \ | |
132 | "-- 0027229ca0644181a76c4e92458afaff dededededededededededededededed\n" \ | |
133 | "Subject: override subject\n" \ | |
134 | "X-Header: hello\n" \ | |
135 | "\n"; | |
136 | ||
137 | const char *combined = | |
138 | "Subject: override subject\n" \ | |
139 | "X-Header: hello\n" \ | |
140 | "Subject: message\n" \ | |
141 | "Defined-By: me\n" \ | |
142 | "\n" \ | |
143 | "payload\n"; | |
144 | ||
145 | h = test_import(input, -1, 0); | |
a95686bb | 146 | assert_se(ordered_hashmap_size(h) == 1); |
c059b62f | 147 | |
90e74a66 | 148 | ORDERED_HASHMAP_FOREACH(payload, h) |
c059b62f | 149 | assert_se(streq(combined, payload)); |
c059b62f SW |
150 | } |
151 | ||
627d2bac | 152 | static void test_catalog_update(const char *database) { |
844ec79b | 153 | int r; |
844ec79b | 154 | |
844ec79b ZJS |
155 | /* Test what happens if there are no files. */ |
156 | r = catalog_update(database, NULL, NULL); | |
f201daec | 157 | assert_se(r == 0); |
844ec79b | 158 | |
143bfdaf HHPF |
159 | /* Test what happens if there are no files in the directory. */ |
160 | r = catalog_update(database, NULL, no_catalog_dirs); | |
f201daec | 161 | assert_se(r == 0); |
143bfdaf HHPF |
162 | |
163 | /* Make sure that we at least have some files loaded or the | |
d9b6baa6 YW |
164 | * catalog_list below will fail. */ |
165 | r = catalog_update(database, NULL, (const char * const *) catalog_dirs); | |
f201daec | 166 | assert_se(r == 0); |
844ec79b ZJS |
167 | } |
168 | ||
c7332b08 | 169 | static void test_catalog_file_lang(void) { |
4b8268f8 | 170 | _cleanup_free_ char *lang = NULL, *lang2 = NULL, *lang3 = NULL, *lang4 = NULL; |
c7332b08 ZJS |
171 | |
172 | assert_se(catalog_file_lang("systemd.de_DE.catalog", &lang) == 1); | |
173 | assert_se(streq(lang, "de_DE")); | |
174 | ||
175 | assert_se(catalog_file_lang("systemd..catalog", &lang2) == 0); | |
176 | assert_se(lang2 == NULL); | |
177 | ||
178 | assert_se(catalog_file_lang("systemd.fr.catalog", &lang2) == 1); | |
179 | assert_se(streq(lang2, "fr")); | |
180 | ||
181 | assert_se(catalog_file_lang("systemd.fr.catalog.gz", &lang3) == 0); | |
182 | assert_se(lang3 == NULL); | |
183 | ||
184 | assert_se(catalog_file_lang("systemd.01234567890123456789012345678901.catalog", &lang3) == 0); | |
185 | assert_se(lang3 == NULL); | |
186 | ||
187 | assert_se(catalog_file_lang("systemd.0123456789012345678901234567890.catalog", &lang3) == 1); | |
188 | assert_se(streq(lang3, "0123456789012345678901234567890")); | |
4b8268f8 ZJS |
189 | |
190 | assert_se(catalog_file_lang("/x/y/systemd.catalog", &lang4) == 0); | |
191 | assert_se(lang4 == NULL); | |
192 | ||
193 | assert_se(catalog_file_lang("/x/y/systemd.ru_RU.catalog", &lang4) == 1); | |
194 | assert_se(streq(lang4, "ru_RU")); | |
c7332b08 ZJS |
195 | } |
196 | ||
844ec79b | 197 | int main(int argc, char *argv[]) { |
627d2bac | 198 | _cleanup_(unlink_tempfilep) char database[] = "/tmp/test-catalog.XXXXXX"; |
3332004e | 199 | _cleanup_free_ char *text = NULL; |
844ec79b | 200 | int r; |
d4205751 LP |
201 | |
202 | setlocale(LC_ALL, "de_DE.UTF-8"); | |
203 | ||
6d7c4033 | 204 | test_setup_logging(LOG_DEBUG); |
d4205751 | 205 | |
d9b6baa6 YW |
206 | /* If test-catalog is located at the build directory, then use catalogs in that. |
207 | * If it is not, e.g. installed by systemd-tests package, then use installed catalogs. */ | |
49cdae63 | 208 | catalog_dirs = STRV_MAKE(get_catalog_dir()); |
d9b6baa6 YW |
209 | |
210 | assert_se(access(catalog_dirs[0], F_OK) >= 0); | |
211 | log_notice("Using catalog directory '%s'", catalog_dirs[0]); | |
212 | ||
4b8268f8 ZJS |
213 | test_catalog_file_lang(); |
214 | ||
9d85882a SW |
215 | test_catalog_import_invalid(); |
216 | test_catalog_import_badid(); | |
217 | test_catalog_import_one(); | |
c059b62f SW |
218 | test_catalog_import_merge(); |
219 | test_catalog_import_merge_no_body(); | |
d4205751 | 220 | |
627d2bac ZJS |
221 | assert_se(mkostemp_safe(database) >= 0); |
222 | ||
223 | test_catalog_update(database); | |
54b7254c | 224 | |
844ec79b ZJS |
225 | r = catalog_list(stdout, database, true); |
226 | assert_se(r >= 0); | |
d4205751 | 227 | |
844ec79b ZJS |
228 | r = catalog_list(stdout, database, false); |
229 | assert_se(r >= 0); | |
d4205751 | 230 | |
844ec79b | 231 | assert_se(catalog_get(database, SD_MESSAGE_COREDUMP, &text) >= 0); |
d4205751 LP |
232 | printf(">>>%s<<<\n", text); |
233 | ||
d4205751 LP |
234 | return 0; |
235 | } |