diff --git a/nnimap.el b/nnimap.el --- a/nnimap.el +++ b/nnimap.el @@ -103,10 +103,21 @@ Possible choices are nil (use default methods), `anonymous', `login', `plain' and `cram-md5'.") -(defvoo nnimap-expunge t - "If non-nil, expunge articles after deleting them. -This is always done if the server supports UID EXPUNGE, but it's -not done by default on servers that doesn't support that command.") +(defvoo nnimap-expunge 'on-exit + "When to expunge deleted messages. +If 'never, deleted articles are marked with the IMAP \\Delete +flag but not automatically expunged. If 'immediately, deleted +articles are immediately expunged (this requires the server to +support the UID EXPUNGE command). If 'on-exit, deleted articles +are flagged, and all flagged articles are expunged when the +group is closed. + +For backwards compatibility, this variable may also be set to t +or nil. If the server supports UID EXPUNGE, both t and nil are +equivalent to 'immediately. If the server does not support UID +EXPUNGE nil is equivalent to 'never, while t will immediately +expunge ALL articles that are currently flagged as deleted +(i.e., potentially not only the article that was just deleted).") (defvoo nnimap-streaming t "If non-nil, try to use streaming commands with IMAP servers. @@ -865,7 +876,11 @@ (nreverse articles))) (deffoo nnimap-close-group (group &optional server) - t) + (when (eq nnimap-expunge 'on-exit) + (nnoo-change-server 'nnimap server nil) + (with-current-buffer (nnimap-buffer) + (nnimap-wait-for-response + (nnimap-send-command "EXPUNGE"))))) (deffoo nnimap-request-move-article (article group server accept-form &optional last internal-move-group) @@ -910,8 +925,7 @@ articles) ((and force (eq nnmail-expiry-target 'delete)) - (unless (nnimap-delete-article (gnus-compress-sequence articles)) - (nnheader-message 7 "Article marked for deletion, but not expunged.")) + (nnimap-delete-article (gnus-compress-sequence articles)) nil) (t (let ((deletable-articles @@ -1027,21 +1041,36 @@ (when (and limit number-of-article) (nnimap-find-article-by-message-id group server message-id)))))))) -(defun nnimap-delete-article (articles) +(defun nnimap-delete-article (articles &optional sync) + "Delete ARTICLES. + +If sync is non-nil, wait for server response." (with-current-buffer (nnimap-buffer) (nnimap-command "UID STORE %s +FLAGS.SILENT (\\Deleted)" (nnimap-article-ranges articles)) + (let ((sequence (cond - ((nnimap-capability "UIDPLUS") + ((eq nnimap-expunge 'immediately) + (if (nnimap-capability "UIDPLUS") (nnimap-command "UID EXPUNGE %s" (nnimap-article-ranges articles)) - t) + (nnheader-message 3 (concat "nnimap-expunge set to 'immediately, but " + "server doesn't support UIDPLUS")))) + + ((memq nnimap-expunge '(on-exit never)) nil) + + ((nnimap-capability "UIDPLUS") + (nnimap-command "UID EXPUNGE %s" + (nnimap-article-ranges articles))) + (nnimap-expunge - (nnimap-command "EXPUNGE") - t) - (t (gnus-message 7 (concat "nnimap: nnimap-expunge is not set and the " - "server doesn't support UIDPLUS, so we won't " - "delete this article now")))))) + (nnimap-command "EXPUNGE")) + + (t + (nnheader-message 7 "Article marked for deletion, but not expunged."))))) + + (if (and sync sequence) + (nnimap-wait-for-response sequence))))) (deffoo nnimap-request-scan (&optional group server) (when group @@ -2043,27 +2072,9 @@ (nnimap-wait-for-response (caar sequences)) ;; And then mark the successful copy actions as deleted, ;; and possibly expunge them. - (nnimap-mark-and-expunge-incoming - (nnimap-parse-copied-articles sequences))) - (nnimap-mark-and-expunge-incoming junk-articles))))))) - -(defun nnimap-mark-and-expunge-incoming (range) - (when range - (setq range (nnimap-article-ranges range)) - (erase-buffer) - (let ((sequence - (nnimap-send-command - "UID STORE %s +FLAGS.SILENT (\\Deleted)" range))) - (cond - ;; If the server supports it, we now delete the message we have - ;; just copied over. - ((nnimap-capability "UIDPLUS") - (setq sequence (nnimap-send-command "UID EXPUNGE %s" range))) - ;; If it doesn't support UID EXPUNGE, then we only expunge if the - ;; user has configured it. - (nnimap-expunge - (setq sequence (nnimap-send-command "EXPUNGE")))) - (nnimap-wait-for-response sequence)))) + (nnimap-delete-article + (nnimap-parse-copied-articles sequences) t)) + (nnimap-delete-article junk-articles t))))))) (defun nnimap-parse-copied-articles (sequences) (let (sequence copied range)