diff options
author | Sergey Poznyakoff <gray@gnu.org> | 2020-11-16 14:04:13 +0200 |
---|---|---|
committer | Sergey Poznyakoff <gray@gnu.org> | 2020-11-16 14:04:13 +0200 |
commit | 645bfb5b4da280808f537929064807ba5abd8626 (patch) | |
tree | b6a2d39f498200612a07df91ede2c5a0d95d862a | |
parent | 500bab2e34400206f0e8982b11d6cc07fac52ffa (diff) | |
download | mailutils-645bfb5b4da280808f537929064807ba5abd8626.tar.gz mailutils-645bfb5b4da280808f537929064807ba5abd8626.tar.bz2 |
Fix message append notifications for maildir, mh, and dotmail.
* testsuite/mbop.c: Implement notification mode.
* comsat/tests/testsuite.at: Fix mh qid.
* libproto/dotmail/dotmail.c (dotmail_append_message): Lock the
monitor before and unlock it after the operation.
* libproto/dotmail/tests/notify.at: New file.
* libproto/dotmail/tests/Makefile.am: Add notify.at
* libproto/dotmail/tests/testsuite.at: Include notify.at.
* include/mailutils/sys/amd.h (cur_msg_file_name): Change signature.
* libmailutils/base/amd.c: Use amd->cur_msg_file_name with 0 as its second
argument to get qid.
* libproto/maildir/mbox.c (maildir_cur_message_name): Take three
argument, second one specifying whether an absolute or relative
filename is requested.
All uses changed.
* libproto/maildir/tests/notify.at: New file.
* libproto/maildir/tests/Makefile.am: Add notify.at
* libproto/maildir/tests/testsuite.at: Include notify.at
* libproto/mh/mbox.c (_mh_cur_message_name): Take three
argument, second one specifying whether an absolute or relative
filename is requested.
All uses changed.
* libproto/mh/tests/notify.at: New file.
* libproto/mh/tests/Makefile.am: Add notify.at
* libproto/mh/tests/testsuite.at: Include notify.at
-rw-r--r-- | comsat/tests/testsuite.at | 2 | ||||
-rw-r--r-- | include/mailutils/sys/amd.h | 2 | ||||
-rw-r--r-- | libmailutils/base/amd.c | 14 | ||||
-rw-r--r-- | libproto/dotmail/dotmail.c | 17 | ||||
-rw-r--r-- | libproto/dotmail/tests/Makefile.am | 3 | ||||
-rw-r--r-- | libproto/dotmail/tests/notify.at | 79 | ||||
-rw-r--r-- | libproto/dotmail/tests/testsuite.at | 1 | ||||
-rw-r--r-- | libproto/maildir/mbox.c | 15 | ||||
-rw-r--r-- | libproto/maildir/tests/Makefile.am | 1 | ||||
-rw-r--r-- | libproto/maildir/tests/notify.at | 41 | ||||
-rw-r--r-- | libproto/maildir/tests/testsuite.at | 1 | ||||
-rw-r--r-- | libproto/mh/mbox.c | 17 | ||||
-rw-r--r-- | libproto/mh/tests/Makefile.am | 1 | ||||
-rw-r--r-- | libproto/mh/tests/notify.at | 40 | ||||
-rw-r--r-- | libproto/mh/tests/testsuite.at | 1 | ||||
-rw-r--r-- | testsuite/mbop.c | 59 |
16 files changed, 267 insertions, 27 deletions
diff --git a/comsat/tests/testsuite.at b/comsat/tests/testsuite.at index 9cdce48f2..7fec9f626 100644 --- a/comsat/tests/testsuite.at +++ b/comsat/tests/testsuite.at @@ -103,7 +103,7 @@ BIFFTEST([MH qid],[comsatd03], [ MUT_MBCOPY($abs_top_srcdir/testsuite/mh/teaparty, mailbox) test "$MH_SUPPORT" = yes || AT_SKIP_TEST -comsatcmd mh:$cwd/mailbox teaparty/58 +comsatcmd mh:$cwd/mailbox 58 sed '1s/^Mail to .*/Mail to test user/' output ], [Mail to test user diff --git a/include/mailutils/sys/amd.h b/include/mailutils/sys/amd.h index cf1842ea3..9fa08c447 100644 --- a/include/mailutils/sys/amd.h +++ b/include/mailutils/sys/amd.h @@ -78,7 +78,7 @@ struct _amd_data int (*msg_finish_delivery) (struct _amd_data *, struct _amd_message *, const mu_message_t); void (*msg_free) (struct _amd_message *); - int (*cur_msg_file_name) (struct _amd_message *, char **); + int (*cur_msg_file_name) (struct _amd_message *, int, char **); int (*new_msg_file_name) (struct _amd_message *, int, int, char **); int (*scan0) (mu_mailbox_t mailbox, size_t msgno, size_t *pcount, int do_notify); diff --git a/libmailutils/base/amd.c b/libmailutils/base/amd.c index 9b8728d15..d209ffce3 100644 --- a/libmailutils/base/amd.c +++ b/libmailutils/base/amd.c @@ -542,7 +542,7 @@ amd_message_qid (mu_message_t msg, mu_message_qid_t *pqid) { struct _amd_message *mhm = mu_message_get_owner (msg); - return mhm->amd->cur_msg_file_name (mhm, pqid); + return mhm->amd->cur_msg_file_name (mhm, 0, pqid); } static void @@ -810,7 +810,7 @@ _amd_message_save (struct _amd_data *amd, struct _amd_message *mhm, { /* Unlink the original file */ char *old_name; - status = amd->cur_msg_file_name (mhm, &old_name); + status = amd->cur_msg_file_name (mhm, 1, &old_name); free (msg_name); if (status == 0 && unlink (old_name)) status = errno; @@ -946,7 +946,7 @@ _amd_message_save (struct _amd_data *amd, struct _amd_message *mhm, free (buf); fclose (fp); - status = amd->cur_msg_file_name (mhm, &old_name); + status = amd->cur_msg_file_name (mhm, 1, &old_name); if (status == 0) { if (rename (name, msg_name)) @@ -1053,7 +1053,7 @@ amd_append_message (mu_mailbox_t mailbox, mu_message_t msg) if (status == 0 && mailbox->observable) { char *qid; - if (amd->cur_msg_file_name (mhm, &qid) == 0) + if (amd->cur_msg_file_name (mhm, 0, &qid) == 0) { mu_observable_notify (mailbox->observable, MU_EVT_MAILBOX_MESSAGE_APPEND, @@ -1339,7 +1339,7 @@ amd_expunge (mu_mailbox_t mailbox) char *old_name; char *new_name; - rc = amd->cur_msg_file_name (mhm, &old_name); + rc = amd->cur_msg_file_name (mhm, 1, &old_name); if (rc) return rc; rc = amd->new_msg_file_name (mhm, mhm->attr_flags, 1, @@ -1613,7 +1613,7 @@ amd_scan_message (struct _amd_message *mhm) int amd_capa = amd->capabilities; /* Check if the message was modified after the last scan */ - status = mhm->amd->cur_msg_file_name (mhm, &msg_name); + status = mhm->amd->cur_msg_file_name (mhm, 1, &msg_name); if (status) { mu_debug (MU_DEBCAT_MAILBOX, MU_DEBUG_ERROR, @@ -1811,7 +1811,7 @@ amd_message_stream_open (struct _amd_message *mhm) int status; int flags = 0; - status = amd->cur_msg_file_name (mhm, &filename); + status = amd->cur_msg_file_name (mhm, 1, &filename); if (status) { mu_debug (MU_DEBCAT_MAILBOX, MU_DEBUG_ERROR, diff --git a/libproto/dotmail/dotmail.c b/libproto/dotmail/dotmail.c index de712da65..92a2df5a8 100644 --- a/libproto/dotmail/dotmail.c +++ b/libproto/dotmail/dotmail.c @@ -937,20 +937,23 @@ dotmail_append_message (mu_mailbox_t mailbox, mu_message_t msg) rc = dotmail_refresh (mailbox); if (rc) return rc; - if (mailbox->locker - && (rc = mu_locker_lock (mailbox->locker)) != 0) + + mu_monitor_wrlock (mailbox->monitor); + if (mailbox->locker && (rc = mu_locker_lock (mailbox->locker)) != 0) { mu_debug (MU_DEBCAT_MAILBOX, MU_DEBUG_ERROR, ("%s(%s):%s: %s", __func__, dmp->name, "mu_locker_lock", mu_strerror (rc))); - return rc; } + else + { + rc = mailbox_append_message (mailbox, msg); - rc = mailbox_append_message (mailbox, msg); - - if (mailbox->locker) - mu_locker_unlock (mailbox->locker); + if (mailbox->locker) + mu_locker_unlock (mailbox->locker); + } + mu_monitor_unlock (mailbox->monitor); return rc; } diff --git a/libproto/dotmail/tests/Makefile.am b/libproto/dotmail/tests/Makefile.am index c1fc8f46a..41af4312a 100644 --- a/libproto/dotmail/tests/Makefile.am +++ b/libproto/dotmail/tests/Makefile.am @@ -51,7 +51,8 @@ TESTSUITE_AT += \ qget.at\ append.at\ delete.at\ - setattr.at + setattr.at\ + notify.at diff --git a/libproto/dotmail/tests/notify.at b/libproto/dotmail/tests/notify.at new file mode 100644 index 000000000..667bcc4d2 --- /dev/null +++ b/libproto/dotmail/tests/notify.at @@ -0,0 +1,79 @@ +# GNU Mailutils -- a suite of utilities for electronic mail +# Copyright (C) 2020 Free Software Foundation, Inc. +# +# This library is free software; you can redistribute it and/or modify +# it under the terms of the GNU Lesser General Public License as published by +# the Free Software Foundation; either version 3, or (at your option) +# any later version. +# +# This library is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU Lesser General Public License for more details. +# +# You should have received a copy of the GNU Lesser General Public License +# along with GNU Mailutils. If not, see <http://www.gnu.org/licenses/>. + +AT_SETUP([append notification]) + +AT_DATA([inbox], +[Received: (from hare@wonder.land) + by wonder.land id 3301 + for alice@wonder.land; Mon, 29 Jul 2002 22:00:06 +0100 +Date: Mon, 29 Jul 2002 22:00:01 +0100 +From: March Hare <hare@wonder.land> +Message-Id: <200207292200.3301@wonder.land> +To: Alice <alice@wonder.land> +Subject: Invitation +Return-Path: hare@wonder.land + +Have some wine +. +Received: (from alice@wonder.land) + by wonder.land id 3302 + for hare@wonder.land; Mon, 29 Jul 2002 22:00:07 +0100 +Date: Mon, 29 Jul 2002 22:00:02 +0100 +From: Alice <alice@wonder.land> +Message-Id: <200207292200.3302@wonder.land> +To: March Hare <hare@wonder.land> +Subject: Re: Invitation +Return-Path: alice@wonder.land + +I don't see any wine +. +Received: (from hare@wonder.land) + by wonder.land id 3303 + for alice@wonder.land; Mon, 29 Jul 2002 22:00:08 +0100 +Date: Mon, 29 Jul 2002 22:00:03 +0100 +From: March Hare <hare@wonder.land> +Message-Id: <200207292200.3303@wonder.land> +To: Alice <alice@wonder.land> +Subject: Re: Invitation +Return-Path: hare@wonder.land + +There isn't any +. +]) +AT_DATA([msg], +[Received: (from alice@wonder.land) + by wonder.land id 3304 + for hare@wonder.land; Mon, 29 Jul 2002 22:00:09 +0100 +Date: Mon, 29 Jul 2002 22:00:04 +0100 +From: Alice <alice@wonder.land> +Message-Id: <200207292200.3304@wonder.land> +To: March Hare <hare@wonder.land> +Subject: Re: Invitation +Return-Path: alice@wonder.land +X-UID: 1034 + +Then it wasn't very civil of you to offer it +]) +AT_CHECK( +[mbop -m inbox --notify append msg +], +[0], +[append: OK +], +[mbop: new message: Alice <alice@wonder.land> Re: Invitation +]) +AT_CLEANUP diff --git a/libproto/dotmail/tests/testsuite.at b/libproto/dotmail/tests/testsuite.at index e39d33238..980bd76f8 100644 --- a/libproto/dotmail/tests/testsuite.at +++ b/libproto/dotmail/tests/testsuite.at @@ -57,6 +57,7 @@ m4_include([uidvalidity.at]) m4_include([uid.at]) m4_include([qget.at]) m4_include([append.at]) +m4_include([notify.at]) m4_include([delete.at]) m4_include([autodetect.at]) m4_include([setattr.at]) diff --git a/libproto/maildir/mbox.c b/libproto/maildir/mbox.c index ba7a38b55..87edc4b38 100644 --- a/libproto/maildir/mbox.c +++ b/libproto/maildir/mbox.c @@ -1266,14 +1266,21 @@ maildir_uniq_create (struct _amd_data *amd, int fd) * AMD interface functions. */ static int -maildir_cur_message_name (struct _amd_message *amsg, char **pname) +maildir_cur_message_name (struct _amd_message *amsg, int abs, char **pname) { struct _maildir_message *msg = (struct _maildir_message *) amsg; struct string_buffer sb = STRING_BUFFER_INITIALIZER; int rc; - if ((rc = string_buffer_appendz (&sb, amsg->amd->name)) == 0 && - (rc = string_buffer_append (&sb, "/", 1)) == 0 && + if (abs) + { + if ((rc = string_buffer_appendz (&sb, amsg->amd->name)) == 0) + rc = string_buffer_append (&sb, "/", 1); + } + else + rc = 0; + + if (rc == 0 && (rc = string_buffer_appendz (&sb, subdir_name[msg->subdir])) == 0 && (rc = string_buffer_append (&sb, "/", 1)) == 0 && (rc = string_buffer_appendz (&sb, msg->file_name)) == 0 && @@ -1621,7 +1628,7 @@ maildir_chattr_msg (struct _amd_message *amsg, int expunge) int old_subdir; char *cur_name, *new_name; - rc = maildir_cur_message_name (amsg, &cur_name); + rc = maildir_cur_message_name (amsg, 1, &cur_name); if (rc) return rc; diff --git a/libproto/maildir/tests/Makefile.am b/libproto/maildir/tests/Makefile.am index 85ab4659a..c82fb1881 100644 --- a/libproto/maildir/tests/Makefile.am +++ b/libproto/maildir/tests/Makefile.am @@ -47,6 +47,7 @@ TESTSUITE_AT += \ delete.at\ envelope.at\ header.at\ + notify.at\ uid.at\ uidfixup.at\ uidvalidity.at\ diff --git a/libproto/maildir/tests/notify.at b/libproto/maildir/tests/notify.at new file mode 100644 index 000000000..dd311ce69 --- /dev/null +++ b/libproto/maildir/tests/notify.at @@ -0,0 +1,41 @@ +# GNU Mailutils -- a suite of utilities for electronic mail +# Copyright (C) 2020 Free Software Foundation, Inc. +# +# This library is free software; you can redistribute it and/or modify +# it under the terms of the GNU Lesser General Public License as published by +# the Free Software Foundation; either version 3, or (at your option) +# any later version. +# +# This library is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU Lesser General Public License for more details. +# +# You should have received a copy of the GNU Lesser General Public License +# along with GNU Mailutils. If not, see <http://www.gnu.org/licenses/>. + +AT_SETUP([append notification]) +AT_CHECK([mbox2dir -p -v 10 -u inbox $spooldir/mbox1]) +AT_DATA([msg], +[Received: (from alice@wonder.land) + by wonder.land id 3304 + for hare@wonder.land; Mon, 29 Jul 2002 22:00:09 +0100 +Date: Mon, 29 Jul 2002 22:00:04 +0100 +From: Alice <alice@wonder.land> +Message-Id: <200207292200.3304@wonder.land> +To: March Hare <hare@wonder.land> +Subject: Re: Invitation +Return-Path: alice@wonder.land + +Then it wasn't very civil of you to offer it +]) +AT_CHECK([ +mbop -m inbox --notify append msg +], +[0], +[append: OK +], +[mbop: new message: Alice <alice@wonder.land> Re: Invitation +]) +AT_CLEANUP + diff --git a/libproto/maildir/tests/testsuite.at b/libproto/maildir/tests/testsuite.at index c1bbc40eb..0242ce03f 100644 --- a/libproto/maildir/tests/testsuite.at +++ b/libproto/maildir/tests/testsuite.at @@ -30,6 +30,7 @@ m4_include([uidvalidity.at]) m4_include([qget.at]) m4_include([append.at]) +m4_include([notify.at]) m4_include([delete.at]) m4_include([attfixup.at]) diff --git a/libproto/mh/mbox.c b/libproto/mh/mbox.c index 6d0ebfa45..030930e73 100644 --- a/libproto/mh/mbox.c +++ b/libproto/mh/mbox.c @@ -96,7 +96,7 @@ _mh_next_seq (struct _amd_data *amd) /* Return current filename for the message. NOTE: Allocates memory. */ static int -_mh_cur_message_name (struct _amd_message *amsg, char **pname) +_mh_cur_message_name (struct _amd_message *amsg, int abs, char **pname) { int status = 0; struct _mh_message *mhm = (struct _mh_message *) amsg; @@ -107,12 +107,19 @@ _mh_cur_message_name (struct _amd_message *amsg, char **pname) status = mu_asprintf (&pnum, "%lu", (unsigned long) mhm->seq_number); if (status) return status; - len = strlen (amsg->amd->name) + 1 + strlen (pnum) + 1; + len = strlen (pnum) + 1; + if (abs) + len += strlen (amsg->amd->name) + 1; filename = malloc (len); if (filename) { - strcpy (filename, amsg->amd->name); - strcat (filename, "/"); + if (abs) + { + strcpy (filename, amsg->amd->name); + strcat (filename, "/"); + } + else + filename[0] = 0; strcat (filename, pnum); *pname = filename; } @@ -408,7 +415,7 @@ _mh_msg_delete (struct _amd_data *amd, struct _amd_message *amm) if (!proc) return ENOSYS; - rc = amd->cur_msg_file_name (amm, &name); + rc = amd->cur_msg_file_name (amm, 1, &name); if (rc) return rc; diff --git a/libproto/mh/tests/Makefile.am b/libproto/mh/tests/Makefile.am index aadccf074..be80c3d7e 100644 --- a/libproto/mh/tests/Makefile.am +++ b/libproto/mh/tests/Makefile.am @@ -46,6 +46,7 @@ TESTSUITE_AT += \ delete.at\ envelope.at\ header.at\ + notify.at\ qget.at\ uid.at\ uidvalidity.at diff --git a/libproto/mh/tests/notify.at b/libproto/mh/tests/notify.at new file mode 100644 index 000000000..a412b90e3 --- /dev/null +++ b/libproto/mh/tests/notify.at @@ -0,0 +1,40 @@ +# GNU Mailutils -- a suite of utilities for electronic mail +# Copyright (C) 2020 Free Software Foundation, Inc. +# +# This library is free software; you can redistribute it and/or modify +# it under the terms of the GNU Lesser General Public License as published by +# the Free Software Foundation; either version 3, or (at your option) +# any later version. +# +# This library is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU Lesser General Public License for more details. +# +# You should have received a copy of the GNU Lesser General Public License +# along with GNU Mailutils. If not, see <http://www.gnu.org/licenses/>. + +AT_SETUP([append notification]) +AT_CHECK([mbox2dir -m -p -v 10 -u inbox $spooldir/mbox1]) +AT_DATA([msg], +[Received: (from alice@wonder.land) + by wonder.land id 3304 + for hare@wonder.land; Mon, 29 Jul 2002 22:00:09 +0100 +Date: Mon, 29 Jul 2002 22:00:04 +0100 +From: Alice <alice@wonder.land> +Message-Id: <200207292200.3304@wonder.land> +To: March Hare <hare@wonder.land> +Subject: Re: Invitation +Return-Path: alice@wonder.land + +Then it wasn't very civil of you to offer it +]) +AT_CHECK([ +mbop -m inbox --notify append msg +], +[0], +[append: OK +], +[mbop: new message: Alice <alice@wonder.land> Re: Invitation +]) +AT_CLEANUP diff --git a/libproto/mh/tests/testsuite.at b/libproto/mh/tests/testsuite.at index c1b18ce41..f85b5f167 100644 --- a/libproto/mh/tests/testsuite.at +++ b/libproto/mh/tests/testsuite.at @@ -30,6 +30,7 @@ m4_include([uidvalidity.at]) m4_include([qget.at]) m4_include([append.at]) +m4_include([notify.at]) m4_include([delete.at]) # Local Variables: diff --git a/testsuite/mbop.c b/testsuite/mbop.c index bfaab0550..ee7de5a1f 100644 --- a/testsuite/mbop.c +++ b/testsuite/mbop.c @@ -466,13 +466,55 @@ struct mu_tesh_command commands[] = { { NULL } }; +static int +test_notify (mu_observer_t obs, size_t type, void *data, void *action_data) +{ + struct interp_env *env = mu_observer_get_owner (obs); + mu_mailbox_t mbx; + mu_message_qid_t qid = data; + int rc; + mu_message_t msg; + mu_header_t hdr; + char const *from = "(NONE)", *subj = "(NONE)"; + MU_ASSERT (mu_mailbox_create_default (&mbx, env->mbxname)); + MU_ASSERT (mu_mailbox_open (mbx, MU_STREAM_READ|MU_STREAM_QACCESS)); + + rc = mu_mailbox_quick_get_message (mbx, qid, &msg); + if (rc) + { + mu_diag_funcall (MU_DIAG_ERROR, "mu_mailbox_quick_get_message", + NULL, rc); + goto err; + } + + rc = mu_message_get_header (msg, &hdr); + if (rc) + { + mu_diag_funcall (MU_DIAG_ERROR, "mu_message_get_header", + NULL, rc); + goto err; + } + + mu_header_sget_value (hdr, MU_HEADER_FROM, &from); + mu_header_sget_value (hdr, MU_HEADER_SUBJECT, &subj); + mu_stream_printf (mu_strerr, "new message: %s %s\n", from, subj); + + err: + mu_mailbox_close (mbx); + mu_mailbox_destroy (&mbx); + + return 0; +} + + int main (int argc, char **argv) { struct interp_env env = { NULL, NULL, NULL, 0 }; int debug_option = 0; int detect_option = 0; + int notify_option = 0; struct mu_option options[] = { { "debug", 'd', NULL, MU_OPTION_DEFAULT, "enable debugging", @@ -483,6 +525,9 @@ main (int argc, char **argv) { "detect", 'D', NULL, MU_OPTION_DEFAULT, "detect mailbox format", mu_c_incr, &detect_option }, + { "notify", 'N', NULL, MU_OPTION_DEFAULT, + "test notification code", + mu_c_incr, ¬ify_option }, MU_OPTION_END }; @@ -519,10 +564,22 @@ main (int argc, char **argv) mu_url_destroy (&url); exit (n & MU_FOLDER_ATTRIBUTE_FILE ? 0 : 1); } - + MU_ASSERT (mu_mailbox_create_default (&env.mbx, env.mbxname)); MU_ASSERT (mu_mailbox_open (env.mbx, MU_STREAM_RDWR)); + if (notify_option) + { + mu_observer_t observer; + mu_observable_t observable; + + mu_observer_create (&observer, &env); + mu_observer_set_action (observer, test_notify, &env); + mu_mailbox_get_observable (env.mbx, &observable); + mu_observable_attach (observable, MU_EVT_MAILBOX_MESSAGE_APPEND, + observer); + } + mu_tesh_read_and_eval (argc, argv, commands, &env); mu_mailbox_close (env.mbx); mu_mailbox_destroy (&env.mbx); |