103 #define STR vstring_str
104 #define LEN VSTRING_LEN
109 int in_form,
int query_form,
int out_form)
112 const char *myname =
"mail_addr_map";
120 const char *int_addr;
129 int_addr =
STR(int_address);
149 if (*
string ==
'@') {
151 if ((ratsign = strrchr(int_addr,
'@')) != 0)
160 string =
STR(ext_address);
174 for (i = 0; i < argv->
argc; i++)
175 msg_info(
"%s: %s -> %d: %s", myname, address, i, argv->
argv[i]);
176 if (argv->
argc == 0) {
177 msg_warn(
"%s lookup of %s returns non-address result \"%s\"",
178 path->
title, address,
string);
189 msg_info(
"%s: %s -> %s", myname, address,
190 path->
error ?
"(try again)" :
"(not found)");
245 #define STR vstring_str
248 const char *testname;
249 const char *database;
251 const char *delimiter;
256 const char *expect_argv[2];
258 } MAIL_ADDR_MAP_TEST;
260 #define DONT_PROPAGATE_UNMATCHED_EXTENSION 0
261 #define DO_PROPAGATE_UNMATCHED_EXTENSION 1
262 #define NO_RECIPIENT_DELIMITER ""
263 #define PLUS_RECIPIENT_DELIMITER "+"
264 #define DOT_RECIPIENT_DELIMITER "."
272 static MAIL_ADDR_MAP_TEST pass_tests[] = {
274 "1 external -external-> external, no extension",
275 "inline:{ aa@example.com=bb@example.com }",
276 DO_PROPAGATE_UNMATCHED_EXTENSION, PLUS_RECIPIENT_DELIMITER,
279 {
"bb@example.com"}, 1,
282 "2 external -external-> external, extension, propagation",
283 "inline:{ aa@example.com=bb@example.com }",
284 DO_PROPAGATE_UNMATCHED_EXTENSION, PLUS_RECIPIENT_DELIMITER,
286 "aa+ext@example.com",
287 {
"bb+ext@example.com"}, 1,
290 "3 external -external-> external, extension, no propagation, no match",
291 "inline:{ aa@example.com=bb@example.com }",
292 DONT_PROPAGATE_UNMATCHED_EXTENSION, NO_RECIPIENT_DELIMITER,
294 "aa+ext@example.com",
298 "4 external -external-> external, extension, full match",
299 "inline:{{cc+ext@example.com=dd@example.com,ee@example.com}}",
300 DO_PROPAGATE_UNMATCHED_EXTENSION, PLUS_RECIPIENT_DELIMITER,
302 "cc+ext@example.com",
303 {
"dd@example.com",
"ee@example.com"}, 2,
306 "5 external -external-> external, no extension, quoted",
307 "inline:{ {\"a a\"@example.com=\"b b\"@example.com} }",
308 DO_PROPAGATE_UNMATCHED_EXTENSION, PLUS_RECIPIENT_DELIMITER,
310 "\"a a\"@example.com",
311 {
"\"b b\"@example.com"}, 1,
314 "6 external -external-> external, extension, propagation, quoted",
315 "inline:{ {\"a a\"@example.com=\"b b\"@example.com} }",
316 DO_PROPAGATE_UNMATCHED_EXTENSION, PLUS_RECIPIENT_DELIMITER,
318 "\"a a+ext\"@example.com",
319 {
"\"b b+ext\"@example.com"}, 1,
322 "7 internal -external-> internal, no extension, propagation, embedded space",
323 "inline:{ {\"a a\"@example.com=\"b b\"@example.com} }",
324 DO_PROPAGATE_UNMATCHED_EXTENSION, PLUS_RECIPIENT_DELIMITER,
327 {
"b b@example.com"}, 1,
330 "8 internal -external-> internal, extension, propagation, embedded space",
331 "inline:{ {\"a a\"@example.com=\"b b\"@example.com} }",
332 DO_PROPAGATE_UNMATCHED_EXTENSION, PLUS_RECIPIENT_DELIMITER,
334 "a a+ext@example.com",
335 {
"b b+ext@example.com"}, 1,
338 "9 internal -external-> internal, no extension, propagation, embedded space",
339 "inline:{ {a_a@example.com=\"b b\"@example.com} }",
340 DO_PROPAGATE_UNMATCHED_EXTENSION, PLUS_RECIPIENT_DELIMITER,
343 {
"b b@example.com"}, 1,
346 "10 internal -external-> internal, extension, propagation, embedded space",
347 "inline:{ {a_a@example.com=\"b b\"@example.com} }",
348 DO_PROPAGATE_UNMATCHED_EXTENSION, PLUS_RECIPIENT_DELIMITER,
350 "a_a+ext@example.com",
351 {
"b b+ext@example.com"}, 1,
354 "11 internal -external-> internal, no extension, @domain",
355 "inline:{ {@example.com=@example.net} }",
356 DO_PROPAGATE_UNMATCHED_EXTENSION, PLUS_RECIPIENT_DELIMITER,
359 {
"\"a@a\"@example.net"}, 1,
362 "12 external -external-> external, extension, propagation",
363 "inline:{ aa@example.com=bb@example.com }",
364 DO_PROPAGATE_UNMATCHED_EXTENSION, DOT_RECIPIENT_DELIMITER,
366 "aa.ext@example.com",
367 {
"bb.ext@example.com"}, 1,
375 static MAIL_ADDR_MAP_TEST fail_tests[] = {
377 "selftest 1 external -external-> external, no extension, quoted",
378 "inline:{ {\"a a\"@example.com=\"b b\"@example.com} }",
379 DO_PROPAGATE_UNMATCHED_EXTENSION, PLUS_RECIPIENT_DELIMITER,
381 "\"a a\"@example.com",
382 {
"\"bXb\"@example.com"}, 1,
385 "selftest 2 external -external-> external, no extension, quoted",
386 "inline:{ {\"a a\"@example.com=\"b b\"@example.com} }",
387 DO_PROPAGATE_UNMATCHED_EXTENSION, PLUS_RECIPIENT_DELIMITER,
389 "\"aXa\"@example.com",
390 {
"\"b b\"@example.com"}, 1,
393 "selftest 3 external -external-> external, no extension, quoted",
394 "inline:{ {\"a a\"@example.com=\"b b\"@example.com} }",
395 DO_PROPAGATE_UNMATCHED_EXTENSION, PLUS_RECIPIENT_DELIMITER,
397 "\"a a\"@example.com",
410 static int compare(
const char *testname,
411 const char **expect_argv,
int expect_argc,
412 char **result_argv,
int result_argc)
417 if (expect_argc != 0 && result_argc != 0) {
418 for (n = 0; n < expect_argc && n < result_argc; n++) {
419 if (strcmp(expect_argv[n], result_argv[n]) != 0) {
420 msg_warn(
"fail test %s: expect[%d]='%s', result[%d]='%s'",
421 testname, n, expect_argv[n], n, result_argv[n]);
426 if (expect_argc != result_argc) {
427 msg_warn(
"fail test %s: expects %d results but there were %d",
428 testname, expect_argc, result_argc);
429 for (n = expect_argc; n < result_argc; n++)
430 msg_info(
"no expect to match result[%d]='%s'", n, result_argv[n]);
431 for (n = result_argc; n < expect_argc; n++)
432 msg_info(
"no result to match expect[%d]='%s'", n, expect_argv[n]);
438 static char *progname;
442 msg_fatal(
"usage: %s pass_test | fail_test", progname);
445 int main(
int argc,
char **argv)
447 MAIL_ADDR_MAP_TEST *test;
448 MAIL_ADDR_MAP_TEST *tests;
451 #define UPDATE(dst, src) { if (dst) myfree(dst); dst = mystrdup(src); }
459 }
else if (strcmp(argv[1],
"pass_tests") == 0) {
461 }
else if (strcmp(argv[1],
"fail_tests") == 0) {
476 for (test = tests; test->testname; test++) {
481 msg_warn(
"test %s: bad in_form field: %d",
482 test->testname, test->in_form);
487 msg_warn(
"test %s: bad query_form field: %d",
488 test->testname, test->query_form);
493 msg_warn(
"test %s: bad out_form field: %d",
494 test->testname, test->out_form);
503 test->in_form, test->query_form, test->out_form);
504 if (compare(test->testname, test->expect_argv, test->expect_argc,
505 result ? result->
argv : 0, result ? result->
argc : 0) != 0) {
506 msg_info(
"database = %s", test->database);
507 msg_info(
"propagate = %d", test->propagate);
512 msg_info(
"address = %s", test->address);
522 errs += (tests == pass_tests ? fail : !fail);
ARGV * argv_free(ARGV *argvp)
int main(int argc, char **argv)
VSTRING * unquote_822_local(VSTRING *dst, const char *mbox)
VSTRING * vstring_truncate(VSTRING *vp, ssize_t len)
#define DICT_FLAG_UTF8_REQUEST
#define DICT_FLAG_FOLD_FIX
VSTRING * vstring_strcpy(VSTRING *vp, const char *src)
const char * mail_addr_find_opt(MAPS *path, const char *address, char **extp, int in_form, int query_form, int out_form, int strategy)
MAPS * maps_create(const char *title, const char *map_names, int dict_flags)
VSTRING * canon_addr_external(VSTRING *result, const char *addr)
void msg_warn(const char *fmt,...)
VSTRING * vstring_alloc(ssize_t len)
NORETURN msg_fatal(const char *fmt,...)
MAPS * maps_free(MAPS *maps)
ARGV * mail_addr_crunch_opt(const char *string, const char *extension, int in_form, int out_form)
#define quote_822_local(dst, src)
VSTRING * vstring_free(VSTRING *vp)
ARGV * mail_addr_map_opt(MAPS *path, const char *address, int propagate, int in_form, int query_form, int out_form)
VSTRING * vstring_strncpy(VSTRING *vp, const char *src, ssize_t len)
VSTRING * vstring_strcat(VSTRING *vp, const char *src)
void msg_info(const char *fmt,...)