+2004-01-04 Katsumi Yamaoka <yamaoka@jpl.org>
+
+ * lisp/gnus-vers.el: T-gnus 6.16.4 revision 00.
+
+2004-01-02 Reiner Steib <Reiner.Steib@gmx.de>
+
+ * GNUS-NEWS: Add `gnus-group-read-ephemeral-group'.
+
2003-12-30 Katsumi Yamaoka <yamaoka@jpl.org>
* lisp/gnus-vers.el: T-gnus 6.16.3 revision 00.
\f
* Changes in Oort Gnus
+** `gnus-group-read-ephemeral-group' can be called interactively, using `G M'.
+
** In draft groups, `e' is now bound to `gnus-draft-edit-message'.
Use `B w' for `gnus-summary-edit-article' instead.
* T-gnus 6.16 - this is based on Gnus.
- The latest T-gnus is T-gnus 6.16.3 (based on Gnus 5.10.3). It
+ The latest T-gnus is T-gnus 6.16.4 (based on Gnus 5.10.4). It
requires SEMI 1.14, FLIM 1.14, and APEL 10.0 or later.
+2004-01-03 Lars Magne Ingebrigtsen <lars@ingebrigtsen.no>
+
+ * gnus.el: Gnus v5.10.4 is released.
+
+2004-01-02 Reiner Steib <Reiner.Steib@gmx.de>
+
+ * gnus.el (gnus-mode-line-buffer-identification): Show version in
+ help-echo.
+ (gnus-read-group): Allow most group names. Changed warning.
+
+2004-01-02 Lars Magne Ingebrigtsen <larsi@gnus.org>
+
+ * gnus-dired.el (gnus-dired-mode-map): Change keymaps.
+
+2004-01-02 Arne J\e,Ax\e(Brgensen <arne@arnested.dk>
+
+ * smime.el (smime-crl-check): Doc fix.
+
+2004-01-02 Edwin Steiner <edwin.steiner@gmx.net>
+
+ * gnus-nocem.el (gnus-nocem-enter-article): Use the real group
+ hashtb (tiny patch).
+
+2004-01-02 Kai Grossjohann <kai@emptydomain.de>
+
+ * nnml.el (nnml-save-mail): Grok compressed articles. From
+ Michael Albinus <Michael.Albinus@alcatel.de>.
+
+2004-01-02 Teodor Zlatanov <tzz@lifelogs.com>
+
+ * spam.el (spam-ham-copy-or-move-routine): use spam-list-articles
+ (spam-list-articles): rewritten to only check a mark once per
+ invocation
+
+2004-01-01 Simon Josefsson <jas@extundo.com>
+
+ * mml-sec.el (mml-default-encrypt-method)
+ (mml-default-sign-method): Defcustom.
+
+2003-12-31 Lars Magne Ingebrigtsen <larsi@gnus.org>
+
+ * mml.el (mml-generate-mime-1): Remove extra ).
+
+ * gnus-group.el (gnus-group-set-current-level): Signal errors on
+ topic lines.
+ (gnus-group-set-current-level): Fix fix.
+
+2003-12-31 Jeremy Maitin-Shepard <jbms@attbi.com>
+
+ * mml.el (mml-generate-mime-1): Use mml-compute-boundary (tiny
+ change).
+
+2003-12-30 Reiner Steib <Reiner.Steib@gmx.de>
+
+ * gnus-group.el: Removed `(when t ...)' around `gnus-define-keys'.
+ (gnus-group-group-map): Added `gnus-group-read-ephemeral-group'
+ (already in previous commit inadvertently).
+ (gnus-group-make-menu-bar): Added `gnus-group-read-ephemeral-group'.
+ (gnus-group-read-ephemeral-group): Made interactive.
+
+ * gnus-score.el (gnus-score-find-trace): Added comment on sync
+ with `gnus-score-edit-file-at-point'.
+
+ * gnus-logic.el (gnus-score-advanced): Ditto.
+
+ * gnus-score.el (gnus-score-edit-file-at-point): Fix for
+ advanced scoring.
+
+2003-12-30 Simon Josefsson <jas@extundo.com>
+
+ * gnus-score.el (gnus-score-edit-file-at-point): Use
+ gnus-point-at-*, for portability.
+
+2003-12-30 Reiner Steib <Reiner.Steib@gmx.de>
+
+ * gnus-art.el (gnus-treat-body-boundary): Fix doc-string and
+ custom type.
+ (gnus-button-mid-or-mail-regexp): Don't be too restrictive.
+ Suggested by Felix Wiemann <Felix.Wiemann@gmx.net>.
+ (gnus-button-alist): Added "M-x ... RET" and "mid:" buttons.
+ Added comments about relevant RFCs.
+
+ * gnus-sum.el (gnus-summary-mode): Untabify doc-string.
+ (gnus-summary-goto-article): Allow `%40'.
+ (gnus-summary-refer-article): Convert `%40' to `@'.
+
+2003-12-30 Simon Josefsson <jas@extundo.com>
+
+ * smime.el (smime-crl-check): New.
+ (smime-verify-region): Use it. From Arne J\e,Ax\e(Brgensen
+ <arne@arnested.dk> in <87llpk9v5q.fsf@seamus.arnested.dk> (tiny
+ change).
+
+2003-12-30 Reiner Steib <Reiner.Steib@gmx.de>
+
+ * gnus-score.el (gnus-score-edit-file-at-point): Consider the
+ whole match element. From Karl Pfl\e,Ad\e(Bsterer <sigurd@12move.de>.
+ (gnus-score-find-trace): Use it. Added `f' and `t' commands,
+ added quick help. With some suggestions from Karl Pfl\e,Ad\e(Bsterer
+ <sigurd@12move.de>.
+
+ * gnus-util.el (gnus-emacs-version): Added doc-string.
+
+ * mml.el (mml-minibuffer-read-disposition): New function.
+ (mml-attach-file): Use it.
+ (mml-preview): Added MIME preview to gnus-buffers.
+
+2003-12-30 Jesper Harder <harder@ifa.au.dk>
+
+ * gnus-sum.el (gnus-summary-make-menu-bar): Add ellipses.
+
+2003-12-30 Lars Magne Ingebrigtsen <larsi@gnus.org>
+
+ * gnus-start.el (gnus-get-unread-articles): Inline gnus-server-get-method.
+ (gnus-get-unread-articles): Cache methods.
+ (gnus-get-unread-articles-in-group): Indent.
+
+ * gnus.el (gnus-version-number): Bump.
+ (gnus-secondary-method-p): Extend servers to methods before comparing.
+ (gnus-secondary-method-p): Revert.
+
2003-12-30 Lars Magne Ingebrigtsen <lars@ingebrigtsen.no>
* gnus.el: Gnus v5.10.3 is released.
gnus-treat-from-picon)
'head nil)
"Draw a boundary at the end of the headers.
-Valid values are nil, t, `head', `last', an integer or a predicate.
+Valid values are nil and `head'.
See Info node `(gnus)Customizing Articles' for details."
:version "21.1"
:group 'gnus-article-treat
:link '(custom-manual "(gnus)Customizing Articles")
- :type gnus-article-treat-custom)
+ :type gnus-article-treat-head-custom)
(defcustom gnus-treat-capitalize-sentences nil
"Capitalize sentence-starting words.
:type 'regexp)
(defcustom gnus-button-mid-or-mail-regexp
- (concat "\\b\\(<?[a-z0-9][^<>\")!;:,{}\n\t ]*@"
+ (concat "\\b\\(<?[a-z0-9$%(*-=?[_][^<>\")!;:,{}\n\t ]*@"
+ ;; Felix Wiemann in <87oeuomcz9.fsf@news2.ososo.de>
gnus-button-valid-fqdn-regexp
">?\\)\\b")
"Regular expression that matches a message ID or a mail address."
1 (>= gnus-button-message-level 0) gnus-button-fetch-group 5)
("\\b\\(nntp\\|news\\):\\(//\\)?\\([^'\">\n\t ]+\\)"
0 (>= gnus-button-message-level 0) gnus-button-fetch-group 3)
+ ;; RFC 2392 (Don't allow `/' in domain part --> CID)
+ ("\\bmid:\\(//\\)?\\([^'\">\n\t ]+@[^'\">\n\t /]+\\)"
+ 0 (>= gnus-button-message-level 0) gnus-button-message-id 2)
("\\bin\\( +article\\| +message\\)? +\\(<\\([^\n @<>]+@[^\n @<>]+\\)>\\)"
2 (>= gnus-button-message-level 0) gnus-button-message-id 3)
("\\(<URL: *\\)mailto: *\\([^> \n\t]+\\)>"
0 (>= gnus-button-message-level 0) gnus-url-mailto 2)
+ ;; RFC 2368 (The mailto URL scheme)
("mailto:\\([-a-z.@_+0-9%=?&]+\\)"
0 (>= gnus-button-message-level 0) gnus-url-mailto 1)
("\\bmailto:\\([^ \n\t]+\\)"
0 (>= gnus-button-emacs-level 9) gnus-button-handle-symbol 1)
("(setq[ \t\n]+\\([a-z][a-z0-9]+-[-a-z0-9]+\\)[ \t\n]+.+)"
1 (>= gnus-button-emacs-level 7) gnus-button-handle-describe-variable 1)
+ ("\\bM-x[ \t\n]+\\([^ \t\n]+\\)[ \t\n]+RET"
+ 1 (>= gnus-button-emacs-level 7) gnus-button-handle-describe-function 1)
("\\b\\(C-h\\|<?[Ff]1>?\\)[ \t\n]+f[ \t\n]+\\([^ \t\n]+\\)[ \t\n]+RET"
0 (>= gnus-button-emacs-level 1) gnus-button-handle-describe-function 2)
("\\b\\(C-h\\|<?[Ff]1>?\\)[ \t\n]+v[ \t\n]+\\([^ \t\n]+\\)[ \t\n]+RET"
;; Unlike the other regexps we really have to require quoting
;; here to determine where it ends.
1 (>= gnus-button-emacs-level 1) gnus-button-handle-describe-key 3)
- ;; This is how URLs _should_ be embedded in text (RFC 1738)...
+ ;; This is how URLs _should_ be embedded in text (RFC 1738, RFC 2396)...
("<URL: *\\([^<>]*\\)>"
1 (>= gnus-button-browse-level 0) gnus-button-embedded-url 1)
+ ;; RFC 2396 (2.4.3., delims) ...
+ ("\"URL: *\\([^\"]*\\)\""
+ 1 (>= gnus-button-browse-level 0) gnus-button-embedded-url 1)
+ ;; RFC 2396 (2.4.3., delims) ...
+ ("\"URL: *\\([^\"]*\\)\""
+ 1 (>= gnus-button-browse-level 0) gnus-button-embedded-url 1)
;; Raw URLs.
(gnus-button-url-regexp
0 (>= gnus-button-browse-level 0) browse-url 0)
(setq gnus-dired-mode-map (make-sparse-keymap))
(gnus-define-keys gnus-dired-mode-map
- "\C-c\C-a" gnus-dired-attach
- "\C-c\C-l" gnus-dired-find-file-mailcap
- "\C-cP" gnus-dired-print))
+ "\C-c\C-m\C-a" gnus-dired-attach
+ "\C-c\C-m\C-l" gnus-dired-find-file-mailcap
+ "\C-c\C-m\C-p" gnus-dired-print))
(defun gnus-dired-mode (&optional arg)
"Minor mode for intersections of gnus and dired.
(put 'gnus-group-mode 'mode-class 'special)
-(when t
- (gnus-define-keys gnus-group-mode-map
- " " gnus-group-read-group
- "=" gnus-group-select-group
- "\r" gnus-group-select-group
- "\M-\r" gnus-group-quick-select-group
- "\M- " gnus-group-visible-select-group
- [(meta control return)] gnus-group-select-group-ephemerally
- "j" gnus-group-jump-to-group
- "n" gnus-group-next-unread-group
- "p" gnus-group-prev-unread-group
- "\177" gnus-group-prev-unread-group
- [delete] gnus-group-prev-unread-group
- [backspace] gnus-group-prev-unread-group
- "N" gnus-group-next-group
- "P" gnus-group-prev-group
- "\M-n" gnus-group-next-unread-group-same-level
- "\M-p" gnus-group-prev-unread-group-same-level
- "," gnus-group-best-unread-group
- "." gnus-group-first-unread-group
- "u" gnus-group-unsubscribe-current-group
- "U" gnus-group-unsubscribe-group
- "c" gnus-group-catchup-current
- "C" gnus-group-catchup-current-all
- "\M-c" gnus-group-clear-data
- "l" gnus-group-list-groups
- "L" gnus-group-list-all-groups
- "m" gnus-group-mail
- "i" gnus-group-news
- "g" gnus-group-get-new-news
- "\M-g" gnus-group-get-new-news-this-group
- "R" gnus-group-restart
- "r" gnus-group-read-init-file
- "B" gnus-group-browse-foreign-server
- "b" gnus-group-check-bogus-groups
- "F" gnus-group-find-new-groups
- "\C-c\C-d" gnus-group-describe-group
- "\M-d" gnus-group-describe-all-groups
- "\C-c\C-a" gnus-group-apropos
- "\C-c\M-\C-a" gnus-group-description-apropos
- "a" gnus-group-post-news
- "\ek" gnus-group-edit-local-kill
- "\eK" gnus-group-edit-global-kill
- "\C-k" gnus-group-kill-group
- "\C-y" gnus-group-yank-group
- "\C-w" gnus-group-kill-region
- "\C-x\C-t" gnus-group-transpose-groups
- "\C-c\C-l" gnus-group-list-killed
- "\C-c\C-x" gnus-group-expire-articles
- "\C-c\M-\C-x" gnus-group-expire-all-groups
- "V" gnus-version
- "s" gnus-group-save-newsrc
- "z" gnus-group-suspend
- "q" gnus-group-exit
- "Q" gnus-group-quit
- "?" gnus-group-describe-briefly
- "\C-c\C-i" gnus-info-find-node
- "\M-e" gnus-group-edit-group-method
- "^" gnus-group-enter-server-mode
- gnus-mouse-2 gnus-mouse-pick-group
- "<" beginning-of-buffer
- ">" end-of-buffer
- "\C-c\C-b" gnus-bug
- "\C-c\C-n" gnus-namazu-search
- "\C-c\C-s" gnus-group-sort-groups
- "t" gnus-topic-mode
- "\C-c\M-g" gnus-activate-all-groups
- "\M-&" gnus-group-universal-argument
- "#" gnus-group-mark-group
- "\M-#" gnus-group-unmark-group)
-
- (gnus-define-keys (gnus-group-mark-map "M" gnus-group-mode-map)
- "m" gnus-group-mark-group
- "u" gnus-group-unmark-group
- "w" gnus-group-mark-region
- "b" gnus-group-mark-buffer
- "r" gnus-group-mark-regexp
- "U" gnus-group-unmark-all-groups)
-
- (gnus-define-keys (gnus-group-sieve-map "D" gnus-group-mode-map)
- "u" gnus-sieve-update
- "g" gnus-sieve-generate)
-
- (gnus-define-keys (gnus-group-group-map "G" gnus-group-mode-map)
- "d" gnus-group-make-directory-group
- "h" gnus-group-make-help-group
- "u" gnus-group-make-useful-group
- "a" gnus-group-make-archive-group
- "k" gnus-group-make-kiboze-group
- "l" gnus-group-nnimap-edit-acl
- "m" gnus-group-make-group
- "n" gnus-group-make-shimbun-group
- "E" gnus-group-edit-group
- "e" gnus-group-edit-group-method
- "p" gnus-group-edit-group-parameters
- "v" gnus-group-add-to-virtual
- "V" gnus-group-make-empty-virtual
- "D" gnus-group-enter-directory
- "f" gnus-group-make-doc-group
- "G" gnus-group-make-nnir-group
- "w" gnus-group-make-web-group
- "r" gnus-group-rename-group
- "R" gnus-group-make-rss-group
- "c" gnus-group-customize
- "x" gnus-group-nnimap-expunge
- "\177" gnus-group-delete-group
- [delete] gnus-group-delete-group)
-
- (gnus-define-keys (gnus-group-soup-map "s" gnus-group-group-map)
- "b" gnus-group-brew-soup
- "w" gnus-soup-save-areas
- "s" gnus-soup-send-replies
- "p" gnus-soup-pack-packet
- "r" nnsoup-pack-replies)
-
- (gnus-define-keys (gnus-group-sort-map "S" gnus-group-group-map)
- "s" gnus-group-sort-groups
- "a" gnus-group-sort-groups-by-alphabet
- "u" gnus-group-sort-groups-by-unread
- "l" gnus-group-sort-groups-by-level
- "v" gnus-group-sort-groups-by-score
- "r" gnus-group-sort-groups-by-rank
- "m" gnus-group-sort-groups-by-method
- "n" gnus-group-sort-groups-by-real-name)
-
- (gnus-define-keys (gnus-group-sort-selected-map "P" gnus-group-group-map)
- "s" gnus-group-sort-selected-groups
- "a" gnus-group-sort-selected-groups-by-alphabet
- "u" gnus-group-sort-selected-groups-by-unread
- "l" gnus-group-sort-selected-groups-by-level
- "v" gnus-group-sort-selected-groups-by-score
- "r" gnus-group-sort-selected-groups-by-rank
- "m" gnus-group-sort-selected-groups-by-method
- "n" gnus-group-sort-selected-groups-by-real-name)
-
- (gnus-define-keys (gnus-group-list-map "A" gnus-group-mode-map)
- "k" gnus-group-list-killed
- "z" gnus-group-list-zombies
- "s" gnus-group-list-groups
- "u" gnus-group-list-all-groups
- "A" gnus-group-list-active
- "a" gnus-group-apropos
- "d" gnus-group-description-apropos
- "m" gnus-group-list-matching
- "M" gnus-group-list-all-matching
- "l" gnus-group-list-level
- "c" gnus-group-list-cached
- "?" gnus-group-list-dormant)
-
- (gnus-define-keys (gnus-group-list-limit-map "/" gnus-group-list-map)
- "k" gnus-group-list-limit
- "z" gnus-group-list-limit
- "s" gnus-group-list-limit
- "u" gnus-group-list-limit
- "A" gnus-group-list-limit
- "m" gnus-group-list-limit
- "M" gnus-group-list-limit
- "l" gnus-group-list-limit
- "c" gnus-group-list-limit
- "?" gnus-group-list-limit)
-
- (gnus-define-keys (gnus-group-list-flush-map "f" gnus-group-list-map)
- "k" gnus-group-list-flush
- "z" gnus-group-list-flush
- "s" gnus-group-list-flush
- "u" gnus-group-list-flush
- "A" gnus-group-list-flush
- "m" gnus-group-list-flush
- "M" gnus-group-list-flush
- "l" gnus-group-list-flush
- "c" gnus-group-list-flush
- "?" gnus-group-list-flush)
-
- (gnus-define-keys (gnus-group-list-plus-map "p" gnus-group-list-map)
- "k" gnus-group-list-plus
- "z" gnus-group-list-plus
- "s" gnus-group-list-plus
- "u" gnus-group-list-plus
- "A" gnus-group-list-plus
- "m" gnus-group-list-plus
- "M" gnus-group-list-plus
- "l" gnus-group-list-plus
- "c" gnus-group-list-plus
- "?" gnus-group-list-plus)
-
- (gnus-define-keys (gnus-group-score-map "W" gnus-group-mode-map)
- "f" gnus-score-flush-cache)
-
- (gnus-define-keys (gnus-group-help-map "H" gnus-group-mode-map)
- "c" gnus-group-fetch-charter
- "C" gnus-group-fetch-control
- "d" gnus-group-describe-group
- "f" gnus-group-fetch-faq
- "v" gnus-version)
-
- (gnus-define-keys (gnus-group-sub-map "S" gnus-group-mode-map)
- "l" gnus-group-set-current-level
- "t" gnus-group-unsubscribe-current-group
- "s" gnus-group-unsubscribe-group
- "k" gnus-group-kill-group
- "y" gnus-group-yank-group
- "w" gnus-group-kill-region
- "\C-k" gnus-group-kill-level
- "z" gnus-group-kill-all-zombies))
+(gnus-define-keys gnus-group-mode-map
+ " " gnus-group-read-group
+ "=" gnus-group-select-group
+ "\r" gnus-group-select-group
+ "\M-\r" gnus-group-quick-select-group
+ "\M- " gnus-group-visible-select-group
+ [(meta control return)] gnus-group-select-group-ephemerally
+ "j" gnus-group-jump-to-group
+ "n" gnus-group-next-unread-group
+ "p" gnus-group-prev-unread-group
+ "\177" gnus-group-prev-unread-group
+ [delete] gnus-group-prev-unread-group
+ [backspace] gnus-group-prev-unread-group
+ "N" gnus-group-next-group
+ "P" gnus-group-prev-group
+ "\M-n" gnus-group-next-unread-group-same-level
+ "\M-p" gnus-group-prev-unread-group-same-level
+ "," gnus-group-best-unread-group
+ "." gnus-group-first-unread-group
+ "u" gnus-group-unsubscribe-current-group
+ "U" gnus-group-unsubscribe-group
+ "c" gnus-group-catchup-current
+ "C" gnus-group-catchup-current-all
+ "\M-c" gnus-group-clear-data
+ "l" gnus-group-list-groups
+ "L" gnus-group-list-all-groups
+ "m" gnus-group-mail
+ "i" gnus-group-news
+ "g" gnus-group-get-new-news
+ "\M-g" gnus-group-get-new-news-this-group
+ "R" gnus-group-restart
+ "r" gnus-group-read-init-file
+ "B" gnus-group-browse-foreign-server
+ "b" gnus-group-check-bogus-groups
+ "F" gnus-group-find-new-groups
+ "\C-c\C-d" gnus-group-describe-group
+ "\M-d" gnus-group-describe-all-groups
+ "\C-c\C-a" gnus-group-apropos
+ "\C-c\M-\C-a" gnus-group-description-apropos
+ "a" gnus-group-post-news
+ "\ek" gnus-group-edit-local-kill
+ "\eK" gnus-group-edit-global-kill
+ "\C-k" gnus-group-kill-group
+ "\C-y" gnus-group-yank-group
+ "\C-w" gnus-group-kill-region
+ "\C-x\C-t" gnus-group-transpose-groups
+ "\C-c\C-l" gnus-group-list-killed
+ "\C-c\C-x" gnus-group-expire-articles
+ "\C-c\M-\C-x" gnus-group-expire-all-groups
+ "V" gnus-version
+ "s" gnus-group-save-newsrc
+ "z" gnus-group-suspend
+ "q" gnus-group-exit
+ "Q" gnus-group-quit
+ "?" gnus-group-describe-briefly
+ "\C-c\C-i" gnus-info-find-node
+ "\M-e" gnus-group-edit-group-method
+ "^" gnus-group-enter-server-mode
+ gnus-mouse-2 gnus-mouse-pick-group
+ "<" beginning-of-buffer
+ ">" end-of-buffer
+ "\C-c\C-b" gnus-bug
+ "\C-c\C-n" gnus-namazu-search
+ "\C-c\C-s" gnus-group-sort-groups
+ "t" gnus-topic-mode
+ "\C-c\M-g" gnus-activate-all-groups
+ "\M-&" gnus-group-universal-argument
+ "#" gnus-group-mark-group
+ "\M-#" gnus-group-unmark-group)
+
+(gnus-define-keys (gnus-group-mark-map "M" gnus-group-mode-map)
+ "m" gnus-group-mark-group
+ "u" gnus-group-unmark-group
+ "w" gnus-group-mark-region
+ "b" gnus-group-mark-buffer
+ "r" gnus-group-mark-regexp
+ "U" gnus-group-unmark-all-groups)
+
+(gnus-define-keys (gnus-group-sieve-map "D" gnus-group-mode-map)
+ "u" gnus-sieve-update
+ "g" gnus-sieve-generate)
+
+(gnus-define-keys (gnus-group-group-map "G" gnus-group-mode-map)
+ "d" gnus-group-make-directory-group
+ "h" gnus-group-make-help-group
+ "u" gnus-group-make-useful-group
+ "a" gnus-group-make-archive-group
+ "k" gnus-group-make-kiboze-group
+ "l" gnus-group-nnimap-edit-acl
+ "m" gnus-group-make-group
+ "n" gnus-group-make-shimbun-group
+ "E" gnus-group-edit-group
+ "e" gnus-group-edit-group-method
+ "p" gnus-group-edit-group-parameters
+ "v" gnus-group-add-to-virtual
+ "V" gnus-group-make-empty-virtual
+ "D" gnus-group-enter-directory
+ "f" gnus-group-make-doc-group
+ "G" gnus-group-make-nnir-group
+ "w" gnus-group-make-web-group
+ "M" gnus-group-read-ephemeral-group
+ "r" gnus-group-rename-group
+ "R" gnus-group-make-rss-group
+ "c" gnus-group-customize
+ "x" gnus-group-nnimap-expunge
+ "\177" gnus-group-delete-group
+ [delete] gnus-group-delete-group)
+
+(gnus-define-keys (gnus-group-soup-map "s" gnus-group-group-map)
+ "b" gnus-group-brew-soup
+ "w" gnus-soup-save-areas
+ "s" gnus-soup-send-replies
+ "p" gnus-soup-pack-packet
+ "r" nnsoup-pack-replies)
+
+(gnus-define-keys (gnus-group-sort-map "S" gnus-group-group-map)
+ "s" gnus-group-sort-groups
+ "a" gnus-group-sort-groups-by-alphabet
+ "u" gnus-group-sort-groups-by-unread
+ "l" gnus-group-sort-groups-by-level
+ "v" gnus-group-sort-groups-by-score
+ "r" gnus-group-sort-groups-by-rank
+ "m" gnus-group-sort-groups-by-method
+ "n" gnus-group-sort-groups-by-real-name)
+
+(gnus-define-keys (gnus-group-sort-selected-map "P" gnus-group-group-map)
+ "s" gnus-group-sort-selected-groups
+ "a" gnus-group-sort-selected-groups-by-alphabet
+ "u" gnus-group-sort-selected-groups-by-unread
+ "l" gnus-group-sort-selected-groups-by-level
+ "v" gnus-group-sort-selected-groups-by-score
+ "r" gnus-group-sort-selected-groups-by-rank
+ "m" gnus-group-sort-selected-groups-by-method
+ "n" gnus-group-sort-selected-groups-by-real-name)
+
+(gnus-define-keys (gnus-group-list-map "A" gnus-group-mode-map)
+ "k" gnus-group-list-killed
+ "z" gnus-group-list-zombies
+ "s" gnus-group-list-groups
+ "u" gnus-group-list-all-groups
+ "A" gnus-group-list-active
+ "a" gnus-group-apropos
+ "d" gnus-group-description-apropos
+ "m" gnus-group-list-matching
+ "M" gnus-group-list-all-matching
+ "l" gnus-group-list-level
+ "c" gnus-group-list-cached
+ "?" gnus-group-list-dormant)
+
+(gnus-define-keys (gnus-group-list-limit-map "/" gnus-group-list-map)
+ "k" gnus-group-list-limit
+ "z" gnus-group-list-limit
+ "s" gnus-group-list-limit
+ "u" gnus-group-list-limit
+ "A" gnus-group-list-limit
+ "m" gnus-group-list-limit
+ "M" gnus-group-list-limit
+ "l" gnus-group-list-limit
+ "c" gnus-group-list-limit
+ "?" gnus-group-list-limit)
+
+(gnus-define-keys (gnus-group-list-flush-map "f" gnus-group-list-map)
+ "k" gnus-group-list-flush
+ "z" gnus-group-list-flush
+ "s" gnus-group-list-flush
+ "u" gnus-group-list-flush
+ "A" gnus-group-list-flush
+ "m" gnus-group-list-flush
+ "M" gnus-group-list-flush
+ "l" gnus-group-list-flush
+ "c" gnus-group-list-flush
+ "?" gnus-group-list-flush)
+
+(gnus-define-keys (gnus-group-list-plus-map "p" gnus-group-list-map)
+ "k" gnus-group-list-plus
+ "z" gnus-group-list-plus
+ "s" gnus-group-list-plus
+ "u" gnus-group-list-plus
+ "A" gnus-group-list-plus
+ "m" gnus-group-list-plus
+ "M" gnus-group-list-plus
+ "l" gnus-group-list-plus
+ "c" gnus-group-list-plus
+ "?" gnus-group-list-plus)
+
+(gnus-define-keys (gnus-group-score-map "W" gnus-group-mode-map)
+ "f" gnus-score-flush-cache)
+
+(gnus-define-keys (gnus-group-help-map "H" gnus-group-mode-map)
+ "c" gnus-group-fetch-charter
+ "C" gnus-group-fetch-control
+ "d" gnus-group-describe-group
+ "f" gnus-group-fetch-faq
+ "v" gnus-version)
+
+(gnus-define-keys (gnus-group-sub-map "S" gnus-group-mode-map)
+ "l" gnus-group-set-current-level
+ "t" gnus-group-unsubscribe-current-group
+ "s" gnus-group-unsubscribe-group
+ "k" gnus-group-kill-group
+ "y" gnus-group-yank-group
+ "w" gnus-group-kill-region
+ "\C-k" gnus-group-kill-level
+ "z" gnus-group-kill-all-zombies)
(defun gnus-topic-mode-p ()
"Return non-nil in `gnus-topic-mode'."
(active (gnus-active group))
(total (if active (1+ (- (cdr active) (car active))) 0))
(info (nth 2 entry))
- (method (gnus-server-get-method group (gnus-info-method info)))
+ (method (inline (gnus-server-get-method group (gnus-info-method info))))
(marked (gnus-info-marks info))
(mailp (apply 'append
(mapcar
If PARAMETERS, use those as the group parameters.
Return the name of the group if selection was successful."
+ (interactive
+ (list
+ ;; (gnus-read-group "Group name: ")
+ (completing-read
+ "Group: " gnus-active-hashtb
+ nil nil nil
+ 'gnus-group-history)
+ (gnus-read-method "From method: ")))
;; Transform the select method into a unique server.
(when (stringp method)
(setq method (gnus-server-to-method method)))
(interactive
(list
current-prefix-arg
- (string-to-int
- (let ((s (read-string
- (format "Level (default %s): "
- (or (gnus-group-group-level)
- gnus-level-default-subscribed)))))
- (if (string-match "^\\s-*$" s)
- (int-to-string (or (gnus-group-group-level)
- gnus-level-default-subscribed))
- s)))))
+ (progn
+ (unless (gnus-group-process-prefix current-prefix-arg)
+ (error "No group on the current line"))
+ (string-to-int
+ (let ((s (read-string
+ (format "Level (default %s): "
+ (or (gnus-group-group-level)
+ gnus-level-default-subscribed)))))
+ (if (string-match "^\\s-*$" s)
+ (int-to-string (or (gnus-group-group-level)
+ gnus-level-default-subscribed))
+ s))))))
(unless (and (>= level 1) (<= level gnus-level-killed))
(error "Invalid level: %d" level))
(let ((groups (gnus-group-process-prefix n))
gnus-newsgroup-scored)
(when trace
(push (cons "A file" rule)
+ ;; Must be synced with `gnus-score-edit-file-at-point'.
gnus-score-trace)))))))
(defun gnus-advanced-score-rule (rule)
(while (search-forward "\t" nil t)
(cond
((not (ignore-errors
- (setq group (let ((obarray gnus-active-hashtb)) (read buf)))))
+ (setq group (let ((obarray gnus-nocem-real-group-hashtb))
+ (read buf)))))
;; An error.
)
((not (symbolp group))
4 (substitute-command-keys
"\\<gnus-score-mode-map>\\[gnus-score-edit-exit] to save edits")))
-(defun gnus-score-edit-file-at-point ()
- "Edit score file at point. Useful especially after `V t'."
- (interactive)
- (let* ((string (ffap-string-at-point))
- ;; FIXME: Should be the full `match element', not just string at
- ;; point.
- file)
- (save-excursion
- (end-of-line)
- (setq file (ffap-string-at-point)))
- (gnus-score-edit-file file)
- (unless (string= string file)
- (goto-char (point-min))
- ;; Goto first match
- (search-forward string nil t))))
+(defun gnus-score-edit-file-at-point (&optional format)
+ "Edit score file at point in Score Trace buffers.
+If FORMAT, also format the current score file."
+ (let* ((rule (save-excursion
+ (beginning-of-line)
+ (read (current-buffer))))
+ (sep "[ \n\r\t]*")
+ ;; Must be synced with `gnus-score-find-trace':
+ (reg " -> +")
+ (file (save-excursion
+ (end-of-line)
+ (if (and (re-search-backward reg (gnus-point-at-bol) t)
+ (re-search-forward reg (gnus-point-at-eol) t))
+ (buffer-substring (point) (gnus-point-at-eol))
+ nil))))
+ (if (or (not file)
+ (string-match "\\<\\(non-file rule\\|A file\\)\\>" file)
+ ;; (see `gnus-score-find-trace' and `gnus-score-advanced')
+ (string= "" file))
+ (gnus-error 3 "Can't find a score file in current line.")
+ (gnus-score-edit-file file)
+ (when format
+ (gnus-score-pretty-print))
+ (when (consp rule) ;; the rule exists
+ (setq rule (mapconcat #'(lambda (obj)
+ (regexp-quote (format "%S" obj)))
+ rule
+ sep))
+ (goto-char (point-min))
+ (re-search-forward rule nil t)
+ ;; make it easy to use `kill-sexp':
+ (goto-char (1- (match-beginning 0)))))))
(defun gnus-score-load-file (file)
;; Load score file FILE. Returns a list a retrieved score-alists.
(let ((gnus-newsgroup-headers
(list (gnus-summary-article-header)))
(gnus-newsgroup-scored nil)
- trace)
+ ;; Must be synced with `gnus-score-edit-file-at-point':
+ (frmt "%S [%s] -> %s\n")
+ trace
+ file)
(save-excursion
(nnheader-set-temp-buffer "*Score Trace*"))
(setq gnus-score-trace nil)
1 "No score rules apply to the current article (default score %d)."
gnus-summary-default-score)
(set-buffer "*Score Trace*")
- ;; ToDo: Use a keymap instead?
+ ;; Use a keymap instead?
(local-set-key "q"
(lambda ()
(interactive)
(bury-buffer nil)
(gnus-summary-expand-window)))
- (local-set-key "e" 'gnus-score-edit-file-at-point)
+ (local-set-key "e" (lambda ()
+ "Run `gnus-score-edit-file-at-point'."
+ (interactive)
+ (gnus-score-edit-file-at-point)))
+ (local-set-key "f" (lambda ()
+ "Run `gnus-score-edit-file-at-point'."
+ (interactive)
+ (gnus-score-edit-file-at-point 'format)))
+ (local-set-key "t" 'toggle-truncate-lines)
(setq truncate-lines t)
- (while trace
- (insert (format "%S -> %s\n" (cdar trace)
- (or (caar trace) "(non-file rule)")))
- (setq trace (cdr trace)))
+ (dolist (entry trace)
+ (setq file (or (car entry)
+ ;; Must be synced with
+ ;; `gnus-score-edit-file-at-point':
+ "(non-file rule)"))
+ (insert
+ (format frmt
+ (cdr entry)
+ ;; Don't use `file-name-sans-extension' to see .SCORE and
+ ;; .ADAPT directly:
+ (file-name-nondirectory file)
+ (abbreviate-file-name file))))
+ (insert
+ "\n\nQuick help:
+
+Type `e' to edit score file corresponding to the score rule on current line,
+`f' to format (pretty print) the score file and edit it,
+`t' toggle to truncate long lines in this buffer,
+`q' to quit.
+
+The first sexp on each line is the score rule, followed by the file name of
+the score file and its full name, including the directory.")
(goto-char (point-min))
(gnus-configure-windows 'score-trace)))
(set-buffer gnus-summary-buffer)
;; If the agent is enabled, we may have to alter the active info.
(when (and gnus-agent info)
(gnus-agent-possibly-alter-active
- (gnus-info-group info) active))
+ (gnus-info-group info) active))
;; Modify the list of read articles according to what articles
;; are available; then tally the unread articles and add the
gnus-activate-foreign-newsgroups)
(t 0))
level))
- scanned-methods info group active method retrieve-groups)
+ (methods-cache nil)
+ (type-cache nil)
+ scanned-methods info group active method retrieve-groups cmethod
+ method-type)
(gnus-message 6 "Checking new news...")
(while newsrc
;; nil for non-foreign groups that the user has requested not be checked
;; t for unchecked foreign groups or bogus groups, or groups that can't
;; be checked, for one reason or other.
- (if (and (setq method (gnus-info-method info))
- (not (inline
- (gnus-server-equal
- gnus-select-method
- (setq method (gnus-server-get-method nil method)))))
- (not (gnus-secondary-method-p method)))
+ (when (setq method (gnus-info-method info))
+ (if (setq cmethod (assoc method methods-cache))
+ (setq method (cdr cmethod))
+ (setq cmethod (inline (gnus-server-get-method nil method)))
+ (push (cons method cmethod) methods-cache)
+ (setq method cmethod)))
+ (when (and method
+ (not (setq method-type (cdr (assoc method type-cache)))))
+ (setq method-type
+ (cond
+ ((gnus-secondary-method-p method)
+ 'secondary)
+ ((inline (gnus-server-equal gnus-select-method method))
+ 'primary)
+ (t
+ 'foreign)))
+ (push (cons method method-type) type-cache))
+ (if (and method
+ (eq method-type 'foreign))
;; These groups are foreign. Check the level.
(when (and (<= (gnus-info-level info) foreign-level)
(setq active (gnus-activate-group group 'scan)))
gnus-article-outlook-deuglify-article t])
)
("Output"
- ["Save in default format" gnus-summary-save-article
+ ["Save in default format..." gnus-summary-save-article
,@(if (featurep 'xemacs) '(t)
'(:help "Save article using default method"))]
- ["Save in file" gnus-summary-save-article-file
+ ["Save in file..." gnus-summary-save-article-file
,@(if (featurep 'xemacs) '(t)
'(:help "Save article in file"))]
- ["Save in Unix mail format" gnus-summary-save-article-mail t]
- ["Save in MH folder" gnus-summary-save-article-folder t]
- ["Save in VM folder" gnus-summary-save-article-vm t]
- ["Save in RMAIL mbox" gnus-summary-save-article-rmail t]
- ["Save body in file" gnus-summary-save-article-body-file t]
- ["Pipe through a filter" gnus-summary-pipe-output t]
+ ["Save in Unix mail format..." gnus-summary-save-article-mail t]
+ ["Save in MH folder..." gnus-summary-save-article-folder t]
+ ["Save in VM folder..." gnus-summary-save-article-vm t]
+ ["Save in RMAIL mbox..." gnus-summary-save-article-rmail t]
+ ["Save body in file..." gnus-summary-save-article-body-file t]
+ ["Pipe through a filter..." gnus-summary-pipe-output t]
["Add to SOUP packet" gnus-soup-add-article t]
- ["Print with Muttprint" gnus-summary-muttprint t]
+ ["Print with Muttprint..." gnus-summary-muttprint t]
["Print" gnus-summary-print-article t])
("Backend"
["Respool article..." gnus-summary-respool-article t]
respectively.
You can also post articles and send mail from this buffer. To
-follow up an article, type `\\[gnus-summary-followup]'. To mail a reply to the author
+follow up an article, type `\\[gnus-summary-followup]'. To mail a reply to the author
of an article, type `\\[gnus-summary-reply]'.
There are approx. one gazillion commands you can execute in this
t))
(prog1
(if (and (stringp article)
- (string-match "@" article))
+ (string-match "@\\|%40" article))
(gnus-summary-refer-article article)
(when (stringp article)
(setq article (string-to-number article)))
(setq message-id (concat "<" message-id)))
(unless (string-match ">$" message-id)
(setq message-id (concat message-id ">")))
+ ;; People often post MIDs from URLs, so unhex it:
+ (unless (string-match "@" message-id)
+ (setq message-id (gnus-url-unhex-string message-id)))
(let* ((header (gnus-id-to-header message-id))
(sparse (and header
(gnus-summary-article-sparse-p
(defvar xemacs-codename))
(defun gnus-emacs-version ()
+ "Stringified Emacs version."
(let ((system-v
(cond
((eq gnus-user-agent 'emacs-gnus-config)
;; Product information of this gnus.
(product-provide 'gnus-vers
(product-define "T-gnus" nil
- (list 6 16 3
+ (list 6 16 4
(string-to-number gnus-revision-number))))
-(defconst gnus-original-version-number "5.10.3"
+(defconst gnus-original-version-number "5.10.4"
"Version number for this version of Gnus.")
(provide 'running-pterodactyl-gnus-0_73-or-later)
(:type xbm :file "gnus-pointer.xbm"
:ascent center))))
gnus-mode-line-image-cache)
- 'help-echo "This is Gnus")
+ 'help-echo (format
+ "This is %s, %s."
+ gnus-version (gnus-emacs-version)))
str)
(list str))
line)))
(defsubst gnus-secondary-method-p (method)
"Return whether METHOD is a secondary select method."
(let ((methods gnus-secondary-select-methods)
- (gmethod (gnus-server-get-method nil method)))
+ (gmethod (inline (gnus-server-get-method nil method))))
(while (and methods
(not (gnus-method-equal
- (gnus-server-get-method nil (car methods))
+ (inline (gnus-server-get-method nil (car methods)))
gmethod)))
(setq methods (cdr methods)))
methods))
(cons (or default "") 0)
'gnus-group-history)))
(let ((match (match-string 0 group)))
- ;; `/' may be okay (e.g. for nnimap), so ask the user:
- (unless (and (string-match "/" match)
+ ;; Might be okay (e.g. for nnimap), so ask the user:
+ (unless (and (not (string-match "^$\\|:" match))
(message-y-or-n-p
"Proceed and create group anyway? " t
"The group name \"" group "\" contains a forbidden character: \"" match "\".
Usually, it's dangerous to create a group with this name, because it's not
-supported by all back ends and servers. On some IMAP servers, it's valid to
-use the character \"/\".
-
-If you are really sure, you can proceed anyway and create the group.
+supported by all back ends and servers. On IMAP servers it should work,
+though. If you are really sure, you can proceed anyway and create the group.
You may customize the variable `gnus-invalid-group-regexp', which currently is
set to \"" gnus-invalid-group-regexp
-"\", if you want to get rid of this query."))
+"\", if you want to get rid of this query permanently."))
(setq prefix (format "Invalid group name: \"%s\". " group)
group nil)))))
group))
(defun gnus (&optional arg dont-connect slave)
"Read network news.
If ARG is non-nil and a positive number, Gnus will use that as the
-startup level. If ARG is non-nil and not a positive number, Gnus will
+startup level. If ARG is non-nil and not a positive number, Gnus will
prompt the user for the name of an NNTP server to use."
(interactive "P")
(unless (byte-code-function-p (symbol-function 'gnus))
(error
(split-line))))
-
(defun message-fill-header (header value)
(let ((begin (point))
(fill-column 78)
;;; mml-sec.el --- A package with security functions for MML documents
-;; Copyright (C) 2000, 2001, 2002, 2003 Free Software Foundation, Inc.
+;; Copyright (C) 2000, 2001, 2002, 2003, 2004 Free Software Foundation, Inc.
;; Author: Simon Josefsson <simon@josefsson.org>
("pgpmime" mml-pgpmime-sign-buffer list))
"Alist of MIME signer functions.")
-(defvar mml-default-sign-method (caar mml-sign-alist)
- "Default sign method.")
+(defcustom mml-default-sign-method "pgpmime"
+ "Default sign method.
+The string must have an entry in `mml-sign-alist'."
+ :type '(choice (const "smime")
+ (const "pgp")
+ (const "pgpauto")
+ (const "pgpmime")
+ string)
+ :group 'message)
(defvar mml-encrypt-alist
'(("smime" mml-smime-encrypt-buffer mml-smime-encrypt-query)
("pgpmime" mml-pgpmime-encrypt-buffer list))
"Alist of MIME encryption functions.")
-(defvar mml-default-encrypt-method (caar mml-encrypt-alist)
- "Default encryption method.")
+(defcustom mml-default-encrypt-method "pgpmime"
+ "Default encryption method.
+The string must have an entry in `mml-encrypt-alist'."
+ :type '(choice (const "smime")
+ (const "pgp")
+ (const "pgpauto")
+ (const "pgpmime")
+ string)
+ :group 'message)
(defcustom mml-signencrypt-style-alist
'(("smime" separate)
(string :tag "User defined"))
(choice (const :tag "Separate" separate)
(const :tag "Combined" combined)))))
-
+
;;; Configuration/helper functions
(defun mml-signencrypt-style (method &optional style)
(+ (match-beginning 0) 3))))))
(cond
((eq (car cont) 'mml)
- (let ((mml-boundary (funcall mml-boundary-function
- (incf mml-multipart-number)))
+ (let ((mml-boundary (mml-compute-boundary cont))
(mml-generate-default-type "text/plain"))
(mml-to-mime))
(let ((mm-7bit-chars (concat mm-7bit-chars "\x1b")))
(setq description nil))
description))
+(defun mml-minibuffer-read-disposition (type &optional default)
+ (let* ((default (or default
+ (if (string-match "^text/.*" type)
+ "inline"
+ "attachment")))
+ (disposition (completing-read "Disposition: "
+ '(("attachment") ("inline") (""))
+ nil
+ nil)))
+ (if (not (equal disposition ""))
+ disposition
+ default)))
+
(defun mml-quote-region (beg end)
"Quote the MML tags in the region."
(interactive "r")
;;; Attachment functions.
-(defun mml-attach-file (file &optional type description)
+(defun mml-attach-file (file &optional type description disposition)
"Attach a file to the outgoing MIME message.
The file is not inserted or encoded until you send the message with
`\\[message-send-and-exit]' or `\\[message-send]'.
(interactive
(let* ((file (mml-minibuffer-read-file "Attach file: "))
(type (mml-minibuffer-read-type file))
- (description (mml-minibuffer-read-description)))
- (list file type description)))
- (mml-insert-empty-tag 'part 'type type 'filename file
- 'disposition "attachment" 'description description))
+ (description (mml-minibuffer-read-description))
+ (disposition (mml-minibuffer-read-disposition type)))
+ (list file type description disposition)))
+ (mml-insert-empty-tag 'part
+ 'type type
+ 'filename file
+ 'disposition (or disposition "attachment")
+ 'description description))
(defun mml-attach-buffer (buffer &optional type description)
"Attach a buffer to the outgoing MIME message.
(switch-to-buffer (generate-new-buffer
(concat (if raw "*Raw MIME preview of "
"*MIME preview of ") (buffer-name))))
+ (when (boundp 'gnus-buffers)
+ (push (current-buffer) gnus-buffers))
(erase-buffer)
(insert-buffer-substring buf)
(mml-preview-insert-mail-followup-to)
(defun mml2015-mailcrypt-sign (cont)
(mc-sign-generic (message-options-get 'message-sender)
nil nil nil nil)
- (let ((boundary
- (funcall mml-boundary-function (incf mml-multipart-number)))
+ (let ((boundary (mml-compute-boundary cont))
hash point)
(goto-char (point-min))
(unless (re-search-forward "^-----BEGIN PGP SIGNED MESSAGE-----\r?$" nil t)
(goto-char (point-min))
(unless (looking-at "-----BEGIN PGP MESSAGE-----")
(error "Fail to encrypt the message"))
- (let ((boundary
- (funcall mml-boundary-function (incf mml-multipart-number))))
+ (let ((boundary (mml-compute-boundary cont)))
(insert (format "Content-Type: multipart/encrypted; boundary=\"%s\";\n"
boundary))
(insert "\tprotocol=\"application/pgp-encrypted\"\n\n")
mm-security-handle 'gnus-info "Failed")))
(defun mml2015-gpg-sign (cont)
- (let ((boundary
- (funcall mml-boundary-function (incf mml-multipart-number)))
+ (let ((boundary (mml-compute-boundary cont))
(text (current-buffer)) signature)
(goto-char (point-max))
(unless (bolp)
(goto-char (point-max)))))
(defun mml2015-gpg-encrypt (cont &optional sign)
- (let ((boundary
- (funcall mml-boundary-function (incf mml-multipart-number)))
+ (let ((boundary (mml-compute-boundary cont))
(text (current-buffer))
cipher)
(mm-with-unibyte-current-buffer
(defun mml2015-pgg-sign (cont)
(let ((pgg-errors-buffer mml2015-result-buffer)
- (boundary (funcall mml-boundary-function (incf mml-multipart-number)))
+ (boundary (mml-compute-boundary cont))
(pgg-default-user-id (or (message-options-get 'mml-sender)
pgg-default-user-id)))
(unless (pgg-sign-region (point-min) (point-max))
(defun mml2015-pgg-encrypt (cont &optional sign)
(let ((pgg-errors-buffer mml2015-result-buffer)
- (boundary (funcall mml-boundary-function (incf mml-multipart-number))))
+ (boundary (mml-compute-boundary cont)))
(unless (pgg-encrypt-region (point-min) (point-max)
(split-string
(or
(defun nnml-save-mail (group-art)
"Called narrowed to an article."
- (let (chars headers)
+ (let (chars headers extension)
(setq chars (nnmail-insert-lines))
+ (setq extension
+ (and nnml-use-compressed-files
+ (> chars 1000)
+ ".gz"))
(nnmail-insert-xref group-art)
(run-hooks 'nnmail-prepare-save-mail-hook)
(run-hooks 'nnml-prepare-save-mail-hook)
(nnml-possibly-create-directory (caar ga))
(let ((file (concat (nnmail-group-pathname
(caar ga) nnml-directory)
- (int-to-string (cdar ga)))))
+ (int-to-string (cdar ga))
+ extension)))
(if first
;; It was already saved, so we just make a hard link.
(funcall nnmail-crosspost-link-function first file t)
(const :tag "RC2 128 bits" "-rc2-128"))
:group 'smime)
+(defcustom smime-crl-check nil
+ "*Check revocation status of signers certificate using CRLs.
+Enabling this will have OpenSSL check the signers certificate
+against a certificate revocation list (CRL).
+
+For this to work the CRL must be up-to-date and since they are
+normally updated quite often (ie. several times a day) you
+probably need some tool to keep them up-to-date. Unfortunately
+Gnus cannot do this for you.
+
+The CRL should either be appended (in PEM format) to your
+`smime-CA-file' or be located in a file (also in PEM format) in
+your `smime-certificate-directory' named to the X.509 hash of the
+certificate with .r0 as file name extension.
+
+At least OpenSSL version 0.9.7 is required for this to work."
+ :type '(choice (const :tag "No check" nil)
+ (const :tag "Check certificate" "-crl_check")
+ (const :tag "Check certificate chain" "-crl_check_all"))
+ :group 'smime)
+
(defcustom smime-dns-server nil
"*DNS server to query certificates from.
If nil, use system defaults."
(expand-file-name smime-CA-directory))))))
(unless CAs
(error "No CA configured"))
+ (if smime-crl-check
+ (add-to-list 'CAs smime-crl-check))
(if (apply 'smime-call-openssl-region b e (list smime-details-buffer t)
"smime" "-verify" "-out" "/dev/null" CAs)
t
(defun spam-ham-copy-or-move-routine (copy groups)
(gnus-summary-kill-process-mark)
- (let ((articles gnus-newsgroup-articles)
+ (let ((todo (spam-list-articles gnus-newsgroup-articles 'ham))
(backend-supports-deletions
(gnus-check-backend-function
'request-move-article gnus-newsgroup-name))
(respool-method (gnus-find-method-for-group gnus-newsgroup-name))
article mark todo deletep respool)
- (dolist (article articles)
- (when (spam-group-ham-mark-p gnus-newsgroup-name
- (gnus-summary-article-mark article))
- (push article todo)))
(when (member 'respool groups)
(setq respool t) ; boolean for later
(let ((mark-check (if (eq classification 'spam)
'spam-group-spam-mark-p
'spam-group-ham-mark-p))
- mark list)
+ list mark-cache-yes mark-cache-no)
(dolist (article articles)
- (when (funcall mark-check
- gnus-newsgroup-name
- (gnus-summary-article-mark article))
- (push article list)))
+ (let ((mark (gnus-summary-article-mark article)))
+ (unless (memq mark mark-cache-no)
+ (if (memq mark mark-cache-yes)
+ (push article list)
+ ;; else, we have to actually check the mark
+ (if (funcall mark-check
+ gnus-newsgroup-name
+ mark)
+ (progn
+ (push article list)
+ (push mark mark-cache-yes))
+ (push mark mark-cache-no))))))
list))
(defun spam-register-routine (classification
+2004-01-02 Teodor Zlatanov <tzz@lifelogs.com>
+
+ * gnus.texi (Top): updated menu with new manual nodes
+ (The problem of spam): more ranting
+ (Anti-Spam Basics): "spammers are wise to [filtering on From:]"
+ (SpamAssassin): mention spam.el
+ (Hashcash): do not a sentence end proposition with
+ (Filtering Spam Using The Spam ELisp Package): more and better
+ explanation, took lots of information out into subsections
+ (Spam ELisp Package Sequence of Events)
+ (Spam ELisp Package Filtering of Incoming Mail)
+ (Spam ELisp Package Global Variables): new or updated content all
+ around
+ (Spam ELisp Package Configuration Examples): promised new
+ section, empty for now
+ (Blacklists and Whitelists, BBDB Whitelists)
+ (Gmane Spam Reporting, Bogofilter, spam-stat spam filtering)
+ (SpamOracle): mention that spam/ham processor variables are being
+ obsoleted
+ (Extending the Spam ELisp package): add some new documentation
+ for adding a new backend to spam.el
+
+2004-01-02 Reiner Steib <Reiner.Steib@gmx.de>
+
+ * gnus.texi (Foreign Groups): Add `gnus-group-read-ephemeral-group'.
+ (Oort Gnus): Ditto.
+
+2004-01-02 Lars Magne Ingebrigtsen <larsi@gnus.org>
+
+ * message.texi (Key Index): Untabified.
+
+ * gnus.texi (RSS): kindex.
+
+2003-12-30 Reiner Steib <Reiner.Steib@gmx.de>
+
+ * gnus.texi (Summary Score Commands): Add `f' to
+ `gnus-score-find-trace'.
+ (Score File Editing): Added `V t'.
+
+2003-12-31 Steve Youngs <sryoungs@bigpond.net.au>
+
+ * gnus.texi (XEmacs): Update list of Gnus XEmacs package
+ requirements.
+
+2003-12-30 Reiner Steib <Reiner.Steib@gmx.de>
+
+ * gnus.texi (Canceling and Superseding): Mention `Cancel-Lock'.
+
2003-12-30 Lars Magne Ingebrigtsen <larsi@gnus.org>
* gnus.texi (Maildir): Filled.
+ (Key Index): Untabified.
2003-12-29 Lars Magne Ingebrigtsen <larsi@gnus.org>
* Unread Articles:: \e$BL$FI5-;v$X$N0u\e(B
* Read Articles:: \e$B4{FI5-;v$X$N0u\e(B
* Other Marks:: \e$B9XFIEY$K1F6A$7$J$$0u\e(B
+
+Marking Articles
+
* Setting Marks:: \e$B0u$NIU$1J}$H>C$7J}\e(B
* Generic Mark Commands:: \e$B0u$r$I$N$h$&$K%+%9%?%^%$%:$9$k$+\e(B
* Setting Process Marks:: \e$B8e$N<B9T$N$?$a$N5-;v$N0u$NIU$1J}\e(B
Filtering Spam Using The Spam ELisp Package
+* Spam ELisp Package Sequence of Events::
+* Spam ELisp Package Filtering of Incoming Mail::
+* Spam ELisp Package Global Variables::
+* Spam ELisp Package Configuration Examples::
* Blacklists and Whitelists::
* BBDB Whitelists::
* Gmane Spam Reporting::
* ifile spam filtering::
* spam-stat spam filtering::
* SpamOracle::
-* Extending the spam elisp package::
+* Extending the Spam ELisp package::
Filtering Spam Using Statistics with spam-stat
\e$B$F$-$^$9!#$h$j4JC1$K\e(B @acronym{NNTP} \e$B%0%k!<%W$r9XFI$9$kJ}K!$K$D$$$F$O!"\e(B
@ref{Browse Foreign Server} \e$B$r;2>H$7$F2<$5$$!#\e(B
+@item G M
+@kindex G M (\e$B%0%k!<%W\e(B)
+@findex gnus-group-read-ephemeral-group
+\e$B0l;~%K%e!<%9%0%k!<%W$r:n@.$7$^\e(B
+\e$B$9\e(B (@code{gnus-group-read-ephemeral-group})\e$B!#\e(B Gnus \e$B$O%W%m%s%W%H$rI=<($7\e(B
+\e$B$F!"L>A0!"J}K!$*$h$S\e(B @dfn{address} \e$B$NF~NO$r5a$a$^$9!#\e(B
+
@item G n
@kindex G n (\e$B%0%k!<%W\e(B)
@findex gnus-group-make-shimbun-group
\e$B%a!<%k$r$I$3$+$KAw$j$^$9\e(B (@code{gnus-group-mail})\e$B!#$b$7@\F,<-$,M?$($i$l\e(B
\e$B$?$i8=:_0LCV$N%0%k!<%W$NEj9FMM<0\e(B (posting style) \e$B$r;H$$$^$9!#$b$7@\F,<-\e(B
\e$B$,\e(B 1 \e$B$@$C$?$i!"$I$N%0%k!<%W$NEj9FMM<0$r;H$&$+$r?R$M$^$9!#\e(B
-@xref{Composing Messages}\e$B!#\e(B
+@xref{Composing Messages}.
@item i
@kindex i (\e$B%0%k!<%W\e(B)
\e$B$$$?$$$N$G$"$l$P!"J8;z@\F,0z?t\e(B @samp{a} \e$B$r;H$C$F$/$@$5\e(B
\e$B$$\e(B (@pxref{Symbolic Prefixes})\e$B!#\e(B
+Gnus \e$B$O\e(B @code{Cancel-Lock} \e$B%X%C%@!<\e(B (@pxref{Canceling News, Canceling
+News, , message, Message Manual}) \e$B$r;H$C$F!"$"$J$?$@$1$,$"$J$?$N%a%C%;!<\e(B
+\e$B%8$r%-%c%s%;%k$G$-$k$3$H$rJ]>Z$7$^$9!#\e(B
+
\e$B$b$72?$+4V0c$$$r$7$?$N$K5$IU$$$F!"D{@5$r$7$?$$$N$G$"$l$P!"\e(B
@dfn{\e$BBeBX\e(B} (@dfn{superseding}) \e$B5-;v$rEj9F$7$FK\5-;v$rCV$-49$($k$3$H$,$G\e(B
\e$B$-$^$9!#\e(B
@acronym{RSS} \e$B$O$H$F$b5,B'E*$+$DNI<A$J%$%s%?!<%U%'!<%9$G!"\e(Bgnus \e$B$,%0%k!<\e(B
\e$B%W$r>o$K?7$7$/$7$F$*$/$?$a$N>pJs$rF@$k$3$H$,$G$-$^$9!#\e(B
+@kindex G R (\e$B35N,\e(B)
Feed \e$B$r9VFI$9$k$K$O!"35N,%P%C%U%!$+$i\e(B @kbd{G R} \e$B$r;H$C$F2<$5$$\e(B---feed \e$B$N\e(B
\e$B=j:_$NF~NO$r5a$a$i$l$k$G$7$g$&!#\e(B
@kindex V t (\e$B35N,\e(B)
@findex gnus-score-find-trace
\e$B8=:_$N5-;v$K;H$o$l$F$$$kA4$F$N%9%3%"K!B'\e(B (score rule) \e$B$rI=<($7$^\e(B
-\e$B$9\e(B (@code{gnus-score-find-trace})\e$B!#\e(B@code{*Score Trace*} \e$B%P%C%U%!$G\e(B
-\e$B$O\e(B @kbd{q} \e$B$G=*N;$9$k$3$H$,$G$-$^$9!#\e(B@kbd{e} \e$B$GBP1~$9$k%9%3%"%U%!%$%k$r\e(B
-\e$BJT=8$7$^$9!#%]%$%s%H$,9gCW$7$?AG;R$NCf$NJ8;zNs>e$K$"$k$H$-!"\e(B@kbd{e} \e$B$O%9\e(B
-\e$B%3%"%U%!%$%k$NCf$N$3$NJ8;zNs$N>l=j$X0\F0$7$h$&$H$7$^$9!#\e(B
+\e$B$9\e(B (@code{gnus-score-find-trace})\e$B!#\e(B@code{*Score Trace*} \e$B%P%C%U%!\e(B
+\e$B$G!"\e(B@kbd{e} \e$B$r%?%$%W$7$F8=:_9T$N%9%3%"K!B'$KBP1~$9$k%9%3%"%U%!%$%k$rJT=8\e(B
+\e$B$9$k$3$H$,$G$-!"\e(B@kbd{f} \e$B$G$O%9%3%"%U%!%$%k$N%U%)!<%^%C\e(B
+\e$B%H\e(B (@code{gnus-score-pretty-print}) \e$B$HJT=8$r9T$J$&$3$H$,$G$-$^$9!#\e(B
@item V w
@kindex V w (\e$B35N,\e(B)
@vindex gnus-score-mode-hook
@code{gnus-score-menu-hook} \e$B$,%9%3%"%b!<%I%P%C%U%!$G<B9T$5$l$^$9!#\e(B
-\e$B35N,%P%C%U%!$G$O!"\e(B@kbd{V f} \e$B$d\e(B @kbd{V e} \e$B$N$h$&$JL?Na$G%9%3%"%U%!%$%k$N\e(B
-\e$BJT=8$r;O$a$k;v$,$G$-$^$9!#\e(B
+\e$B35N,%P%C%U%!$G$O!"\e(B@kbd{V f}\e$B!"\e(B@kbd{V e} \e$B$*$h$S\e(B @kbd{V t} \e$B$N$h$&$JL?Na$G%9\e(B
+\e$B%3%"%U%!%$%k$NJT=8$r;O$a$k;v$,$G$-$^$9!#\e(B
@node Adaptive Scoring
@section \e$BE,1~@-%9%3%"\e(B
\e$B3d9g$N?M!9$,\e(B UCE \e$B$K1~Ez$9$k$@$1$G9-9p<g$KMx1W$r$b$?$i$9$N$G$9!#HiFy$J$3\e(B
\e$B$H$K:G$b0lHLE*$J\e(B spam \e$B$N0l$D$O!"$5$i$K\e(B spam \e$B$r=uD9$9$k$?$a$NEE;R%a!<%k%"\e(B
\e$B%I%l%9$N%G!<%?%Y!<%9$rDs6!$7$^$9!#\e(BSpam \e$B$NAw?.<T$O$U$D\e(B
-\e$B$&\e(B @emph{spammers} \e$B$H8F$P$l$^$9$,!"\e(B@emph{vermin}\e$B!"\e(B@emph{scum} \e$B$*$h\e(B
-\e$B$S\e(B @emph{morons} \e$B$N$h$&$JMQ8l$b$h$/;H$o$l$F$$$^$9!#\e(B
+\e$B$&\e(B @emph{spammers} \e$B$H8F$P$l$^$9$,!"\e(B@emph{vermin}\e$B!"\e(B@emph{scum}\e$B!"\e(B
+@emph{sociopaths} \e$B$*$h$S\e(B @emph{morons} \e$B$N$h$&$JMQ8l$b$h$/;H$o$l$F$$$^$9!#\e(B
Spam \e$B$O<o!9$5$^$6$^$J=P$I$3$m$+$i$d$C$FMh$^$9!#M-MQ$J%a%C%;!<%8$r<N$F$:\e(B
\e$B$K$9$Y$F$N\e(B spam \e$B$rC1$K;OKv$9$k$3$H$OIT2DG=$G$9!#NI$$Nc$O\e(B TMDA (\e$BLuCm\e(B: \e$BAw\e(B
\e$B$&0l$D$N\e(B TMDA \e$B$NLdBj$O!"EE;R%a!<%k$NG[Aw$H=hM}$X$N4pK\E*$JM}2r$r%f!<%6!<\e(B
\e$B$K5a$a$F$$$k$3$H$G$9!#\e(B
-Spam \e$B$N=|5n\e(B (filtering) \e$B$X$N:G$bC1=c$J<h$jAH$_$O_I2a$9$k$3\e(B
-\e$B$H\e(B (filtering) \e$B$G$9!#KhF|\e(B @samp{random-address@@vmadmin.com} \e$B$+$i\e(B 200\e$BDL\e(B
-\e$B$N\e(B spam \e$B%a%C%;!<%8$r<u$1<h$k$N$J$i$P!"\e(B@samp{vmadmin.com} \e$B$rAK;_$9$l$P$h\e(B
-\e$B$m$7$$!#\e(B@samp{\e$B%P%$%"%0%i\e(B} \e$B$K4X$9$k%a%C%;!<%8$r\e(B 200\e$BDL<u$1<h$k$N$J$i$P!"\e(B
-@samp{\e$B%P%$%"%0%i\e(B} \e$B$r4^$`$9$Y$F$N%a%C%;!<%8$r<N$F$F$7$^$($P$h$m$7$$!#$3$l\e(B
-\e$B$O!";DG0$J$,$i@5Ev$JEE;R%a!<%k$r<N$F$k$?$a$N$9$0$l$?J}K!$G$9!#Nc$($P!"$H\e(B
-\e$B$F$b<(:6$KIY$s$GM-1W$J\e(B RISKS \e$B%@%$%8%'%9%H$O!"$=$l$,\e(B spam \e$B%a%C%;!<%8$H6&\e(B
-\e$BDL$N8l$r\e(B @strong{\e$B4^$s$G\e(B} \e$B$$$k$?$a$K!"G.?4$9$.$k%a!<%k_I2a4o$K$h$C$FAK;_\e(B
-\e$B$5$l$F$7$^$$$^$9!#$=$l$G$b$J$*8IN)$7$?4D6-$G$O!"Cm0U?<$/;H$&$3$H$K$h$C$F\e(B
-\e$BD>@\$N_I2a$OM-1W$K$J$jF@$^$9!#\e(B
+Spam \e$B$N=|5n\e(B (filtering) \e$B$X$N:G$bC1=c$J<h$jAH$_$O!"%a!<%k%5!<%P!<$G!"$"$k\e(B
+\e$B$$$OF~$C$F$-$?%a!<%k$rJ,N`$9$k$H$-$K_I2a$9$k$3$H\e(B (filtering) \e$B$G$9!#Kh\e(B
+\e$BF|\e(B @samp{random-address@@vmadmin.com} \e$B$+$i\e(B 200\e$BDL$N\e(B spam \e$B%a%C%;!<%8$r<u$1\e(B
+\e$B<h$k$N$J$i$P!"\e(B@samp{vmadmin.com} \e$B$rAK;_$9$l$P$h$m$7$$!#\e(B
+@samp{\e$B%P%$%"%0%i\e(B} \e$B$K4X$9$k%a%C%;!<%8$r\e(B 200\e$BDL<u$1<h$k$N$J$i$P!"\e(B
+@samp{\e$B%P%$%"%0%i\e(B} \e$B$r4^$`$9$Y$F$N%a%C%;!<%8$r<N$F$F$7$^$($P$h$m$7$$!#Nc$(\e(B
+\e$B$P!"Cf9q$+$i$?$/$5$s$N\e(B spam \e$B$,$d$C$FMh$k$N$J$i$P!"Cf9q$N\e(B IP \e$B$+$iMh$k$9$Y\e(B
+\e$B$F$N%a!<%k$r_I2a$9$l$P$h$m$7$$!#\e(B
+
+\e$B$3$l$O!";DG0$J$,$i@5Ev$JEE;R%a!<%k$r<N$F$k$?$a$N$9$0$l$?J}K!$G$9!#Nc$($P!"\e(B
+\e$B$H$F$b<(:6$KIY$s$GM-1W$J\e(B RISKS \e$B%@%$%8%'%9%H$O!"$=$l$,\e(B spam \e$B%a%C%;!<%8$H\e(B
+\e$B6&DL$N8l$r\e(B @strong{\e$B4^$s$G\e(B} \e$B$$$k$?$a$K!"G.?4$9$.$k%a!<%k_I2a4o$K$h$C$FAK\e(B
+\e$B;_$5$l$F$7$^$$$^$9!#$"$J$?$K@\?($7$h$&$H$9$kCO0hA4BN$rIu$89~$a$F$7$^$&4m\e(B
+\e$B81$bL@$i$+$G$9!#$G$9$+$i!"$"$J$?$KA*Br8"$,$"$k$N$J$i$P!"$=$s$J$3$H$O$7$J\e(B
+\e$B$$$G2<$5$$!#$=$l$G$b$J$*8IN)$7$?4D6-$G$O!"Cm0U?<$/;H$&$3$H$K$h$C$FD>@\$N\e(B
+\e$B_I2a$OM-1W$K$J$jF@$^$9!#\e(B
\e$B$b$&0l$D$NEE;R%a!<%k_I2a$X$N<h$jAH$_$OJ,;67?\e(B spam \e$B=hM}$G!"\e(BDCC (\e$BLuCm\e(B:
Distributed Checksum Clearinghouse --
@uref{http://www.rhyolite.com/anti-spam/dcc/}) \e$B$,$=$N$h$&$J%7%9%F%`$rF3\e(B
-\e$BF~$7$F$$$^$9!#K\<AE*$K$O!"@$3&Cf$N\e(B @var{N} \e$B8D$N%7%9%F%`$,!"Cf9q!"%,!<%J\e(B
-\e$B$"$k$$$O%+%j%U%)%k%K%"$K$"$k%^%7%s\e(B @var{X} \e$B$,\e(B spam \e$BEE;R%a!<%k$rAw=P$7$F\e(B
-\e$B$$$k$3$H$rG'$a$?$i!"$=$l$i\e(B @var{N} \e$B8D$N%7%9%F%`$O\e(B @var{X} \e$B$^$?\e(B
+\e$BF~$7$F$$$^$9!#K\<AE*$K$O!"@$3&Cf$N\e(B @var{N} \e$B8D$N%7%9%F%`$,!"%,!<%J!"%(%9\e(B
+\e$B%H%K%"$"$k$$$O%+%j%U%)%k%K%"$K$"$k%^%7%s\e(B @var{X} \e$B$,\e(B spam \e$BEE;R%a!<%k$rAw\e(B
+\e$B=P$7$F$$$k$3$H$rG'$a$?$i!"$=$l$i\e(B @var{N} \e$B8D$N%7%9%F%`$O\e(B @var{X} \e$B$^$?\e(B
\e$B$O\e(B @var{X} \e$B$+$i$d$C$FMh$?\e(B spam \e$B%a!<%k$r%G!<%?%Y!<%9$K5-F~$7$^$9!#\e(BSpam \e$B8!\e(B
\e$B=P$N4p=`$OJQ$o$j$^$9!#$=$l$OAw$i$l$?%a%C%;!<%8$N?t$d%a%C%;!<%8$NFbMF$J$I\e(B
\e$B$G$"$k$+$b$7$l$^$;$s!#%a%C%;!<%8$,\e(B spam \e$B$+$I$&$+$rJ,;6=hM}%7%9%F%`$N%f!<\e(B
\e$B$F$/$l$^$9$,!"$=$l$O%f!<%6!<$,$+$J$jJ#;($J%A%'%C%/$r@_Dj$9$k$3$H$r5a$a$^\e(B
\e$B$9!#>&MQ$H!"%U%j!<$JJ,;67?\e(B spam \e$B=hM}%7%9%F%`$,$"$j$^$9!#J,;67?\e(B spam \e$B=hM}\e(B
\e$B$O!"$=$l<+BN$N4m81$b$O$i$s$G$$$^$9!#Nc$($P!"@5Ev$JAw?.<T$,\e(B spam \e$B$rAw$C$?\e(B
-\e$B$+$I$GHsFq$5$l!"H`$i$N%&%'%V%5%$%H$,$=$N;v7o$N$?$a$K;C$/$N4VJD:?$5$l$F$7\e(B
-\e$B$^$&!"$H$+!#\e(B
+\e$B$+$I$GHsFq$5$l!"H`$i$N%&%'%V%5%$%H$d%a!<%j%s%0%j%9%H$,$=$N;v7o$N$?$a$K;C\e(B
+\e$B$/$N4VJD:?$5$l$F$7$^$&!"$H$+!#\e(B
Spam \e$B_I2a$X$NE}7WE*$J<h$jAH$_$b$^$?Ia5Z$7$F$$$^$9!#$=$l$O2a5n$N\e(B spam \e$B%a%C\e(B
\e$B%;!<%8$NE}7WJ,@O$K4p$E$$$F$$$^$9!#DL>o$=$NJ,@O$O!"$*$=$i$/C18l$NBP$+;0$D\e(B
\e$BJ,@O$O$[$H$s$I$N>l9g$K$H$F$b$h$/F/$/$N$G$9$,!";~$H$7$F@5Ev$JEE;R%a!<%k\e(B
\e$B$r\e(B spam \e$B$H$7$FJ,N`$7$F$7$^$&$3$H$,$"$j$^$9!#J,@O$K$O;~4V$,$+$+$j$^$9!#$9\e(B
\e$B$Y$F$N%a%C%;!<%8$rJ,@O$7$J$1$l$P$J$j$^$;$s!#$=$7$F%f!<%6!<$O\e(B spam \e$B$rJ,@O\e(B
-\e$B$9$k$?$a$N%G!<%?%Y!<%9$rMQ0U$7$J$1$l$P$J$j$^$;$s!#\e(B
+\e$B$9$k$?$a$N%G!<%?%Y!<%9$rMQ0U$7$J$1$l$P$J$j$^$;$s!#%5!<%P!<$G$NE}7WJ,@O$O\e(B
+\e$B?M5$$rF@$F$$$^$9!#$3$l$K$O!"%f!<%6!<$OC1$K%a!<%k$rFI$a$PNI$$$H$$$&D9=j$H!"\e(B
+\e$B$7$+$7%5!<%P!<$K$=$l$,2a$C$F%a!<%k$rJ,N`$7$?$3$H$rEA$($k$N$,:$Fq$@$H$$$&\e(B
+\e$BC;=j$,$"$j$^$9!#\e(B
+
+\e$BM>?M$N8@$rBT$?$:$H$b!"\e(Bspam \e$B$H$N@o$$$O3Z$G$O$"$j$^$;$s!#%^%^$+$i$NEE;R%a!<\e(B
+\e$B%k$H%P%$%"%0%i9-9p$r6hJL$9$kKbK!$N%9%$%C%A$O$"$j$^$;$s!#?M!9$O\e(B
+\e$BHs\e(B-spam \e$B$H\e(B spam \e$B$r6hJL$9$k$N$K<j$r>F$$$F$$$k$H$$$&$N$K!#$=$l$O!"\e(B
+spammers \e$B$,7|L?$K$=$l$i$r%^%^$@$H;W$o$;$h$&$H$7$F$$$k$N$,K\<A$@$+$i$G$9!#\e(B
+Spamming \e$B$O!"@$3&$,H`$i$K285A$,$"$k$H;W$C$F$$$k?M!9$N0lCD$+$i$N!"J"N)$?\e(B
+\e$B$7$/!"L5@UG$$G!"$P$+$2$?9T0Y$G$9!#0J2<$N3F9`$,\e(B spam \e$B$J$k1VIB$H$N@o$$$N=u\e(B
+\e$B$1$K$J$k$3$H$rK>$_$^$9!#\e(B
@node Anti-Spam Basics
@subsection Spam \e$BB`<#$N4pAC\e(B
\e$B$3$H$OA4$/$"$j$^$;$s!#F@!9>uBV$G$9!#;d$N0U8+$H$7$F$O!"\e(B@code{From} \e$B%X%C%@!<\e(B
\e$B$r56B$$7$FB8:_$7$J$$%I%a%$%s$KAw$i$;$k$N$O%-%?%J%$$G$9!#\e(B
+\e$B$3$N<jK!$K$OCm0U$7$F2<$5$$!#\e(BSpammers \e$B$O$=$l$K5$IU$$$F$$$^$9!#\e(B
+
@node SpamAssassin
@subsection SpamAssassin, Vipul's Razor, DCC, etc
@cindex SpamAssassin
\e$B$F\e(B SpamAssassin \e$B$r;H$C$F$$$^$9$,!"B>$N$[$H$s$I$NF;6q$K$b4JC1$KE,9g$9$k$O\e(B
\e$B$:$G$9!#\e(B
+\e$B$3$N9`$O\e(B @code{spam.el} \e$B%Q%C%1!<%8$H$O4X78L5$$$3$H$KCm0U$7$F2<$5$$!#$=$l\e(B
+\e$B$O<!$N9`$GO@$8$i$l$^$9!#$9$Y$F$N\e(B @code{spam.el} \e$B$N5!G=$K4X?4$,L5$$$N$J$i\e(B
+\e$B$P!"$3$l$i$NC1=c$J%l%7%T$G4V$K9g$o$;$k$3$H$,$G$-$^$9!#\e(B
+
\e$B$b$7$"$J$?$,;H$&F;6q$,%a!<%k%5!<%P!<$K%$%s%9%H!<%k$5$l$F$$$J$$$J$i$P!"$"\e(B
\e$B$J$?<+?H$,$=$l$r8F$S=P$9I,MW$,$"$j$^$9!#0J2<$K\e(B @code{:postscript} \e$B%a!<%k\e(B
\e$B%=!<%9;X<(;R\e(B (@pxref{Mail Source Specifiers}) \e$B$r;H$&>l9g$N9M$(J}$r<($7$^\e(B
\e$B$3$H$O!">.$5$J%Q!<%;%s%F!<%8$N\e(B spam \e$B$,$$$D$bAGDL$j$7$F$7$^$&$3$H$r0UL#$7\e(B
\e$B$^$9!#$=$l$O$^$?!"$I$3$+$G$@$l$+$,$=$l$i$NF;6q$r99?7$9$k$?$a$K!"$?$/$5$s\e(B
\e$B$N\e(B spam \e$B$rFI$^$J$1$l$P$J$i$J$$$3$H$r$b0UL#$7$^$9!#\e(BHashcash \e$B$O$=$l$r2sHr\e(B
-\e$B$7$^$9$,!"Be$o$j$K$"$J$?$,DL?.$9$k$9$Y$F$N?M$?$A$,!"$=$N;EAH$_$r;H$C$F$$\e(B
-\e$B$k$3$H$,I,MW$G$9!#$"$J$?$O<BMQ\e(B (pragmatic) \e$B$H65>r\e(B (dogmatic) \e$B$NFs$D$N<h\e(B
-\e$B$jAH$_$r9M$($k$3$H$,$G$-$^$9!#$=$l$i$N<h$jAH$_$K$OMxE@$b$"$l$PITMx$JE@$b\e(B
-\e$B$"$j$^$9$,!"$=$l$O@$$NCf$G$OIaDL$N$3$H$G!"$=$l$i$rO"78$5$;$?$b$N$,B>$N$P\e(B
-\e$B$i$P$i$J$b$N$h$j6/NO$J$N$G$9!#\e(B
+\e$B$7$^$9$,!"Be$o$j$K$"$J$?$,EE;R%a!<%k$GO"Mm$9$k$9$Y$F$N?M$?$A$K!"$J$k$Y$/\e(B
+\e$B$=$N;EAH$_$r;H$C$F$b$i$&I,MW$,$"$j$^$9!#$"$J$?$O<BMQ\e(B (pragmatic) \e$B$H65\e(B
+\e$B>r\e(B (dogmatic) \e$B$NFs$D$N<h$jAH$_$r9M$($k$3$H$,$G$-$^$9!#$=$l$i$N<h$jAH$_$K\e(B
+\e$B$OMxE@$b$"$l$PITMx$JE@$b$"$j$^$9$,!"$=$l$O@$$NCf$G$OIaDL$N$3$H$G!"$=$l$i\e(B
+\e$B$rO"78$5$;$?$b$N$,B>$N$P$i$P$i$J$b$N$h$j6/NO$J$N$G$9!#\e(B
@cindex X-Hashcash
\e$B!V$$$/$P$/$+$NIiC4!W$H$O\e(B CPU \e$B;~4V$r>CHq$9$k$3$H$G!"6qBNE*$K$O0lDj?t$N%S%C\e(B
@file{spam.el} \e$B$N??$NL\E*$O\e(B spam \e$B8!=P$H_I2a$N$?$a$N41@)%;%s%?!<\e(B
\e$B$r\e(B gnus \e$B$NCf$K;}$D$3$H$G$9!#$=$N$?$a$K\e(B @file{spam.el} \e$B$OFs$D$N$3$H$r9T$J\e(B
-\e$B$$$^$9\e(B: \e$BF~$C$F$/$k%a!<%k$r_I2a$7!"\e(Bspam \e$B$^$?$O\e(B ham \e$B$H$7$FCN$i$l$k%a!<%k$r\e(B
-\e$BJ,@O$9$k$3$H$G$9!#\e(B@dfn{Ham} \e$B$O\e(B @file{spam.el} \e$B$N$$$?$k=j$G\e(B spam \e$B$G$O$J$$\e(B
-\e$B%a%C%;!<%8$r<($9$?$a$K;H$&L>A0$G$9!#\e(B
+\e$B$$$^$9\e(B: \e$B?7$7$$%a!<%k$r_I2a$7!"\e(Bspam \e$B$^$?$O\e(B ham \e$B$H$7$FCN$i$l$k%a!<%k$rJ,@O\e(B
+\e$B$9$k$3$H$G$9!#\e(B@dfn{Ham} \e$B$O\e(B @file{spam.el} \e$B$N$$$?$k=j$G\e(B spam \e$B$G$O$J$$%a%C\e(B
+\e$B%;!<%8$r<($9$?$a$K;H$&L>A0$G$9!#\e(B
\e$BBh0l$K!"\e(B@code{spam.el} \e$B$r<+F0FI$_9~$_\e(B (autoload) \e$B$7$F\e(B @code{spam.el} \e$B$N\e(B
\e$B3F%U%C%/$r%$%s%9%H!<%k$9$k$?$a$K!"4X\e(B
\e$B$G$O\e(B @file{spam.el} \e$B$rFI$_9~$`$H2?$,5/$-$k$G$7$g$&$+\e(B?
+\e$BBh0l$K\e(B @code{spam-initialize} \e$B$K$h$C$F$$$/$D$+$N%U%C%/$,F0:n$9$k$h$&$K$J\e(B
+\e$B$j$^$9!#\e(B@code{spam-stat} \e$B$,$=$l$i$N%G!<%?%Y!<%9$r%;!<%V$G$-$k$h$&$K$9$k\e(B
+\e$B%U%C%/$H!"%0%k!<%W$KF~$k$H$-$HH4$1$k$H$-$K6=L#?<$$J*;v$r5/$3$9%U%C%/$,$"\e(B
+\e$B$j$^$9!#%$%Y%s%H$N%7!<%1%s%9$K$D$$$F$N>\:Y$O8e=R\e(B (@pxref{Spam ELisp
+Package Sequence of Events})\e$B!#\e(B
+
\e$B0J2<$N%-!<%\!<%IL?Na$,;H$($k$h$&$K$J$j$^$9\e(B:
@table @kbd
\e$B$-$k$h$&$K$J$j$^$9!#\e(B@samp{spam} \e$BJQ?t%0%k!<%W$K$D$$\e(B
\e$B$F\e(B @code{customize-group} \e$B$r;n$7$F$_$F2<$5$$!#\e(B
+@menu
+* Spam ELisp Package Sequence of Events::
+* Spam ELisp Package Filtering of Incoming Mail::
+* Spam ELisp Package Global Variables::
+* Spam ELisp Package Configuration Examples::
+* Blacklists and Whitelists::
+* BBDB Whitelists::
+* Gmane Spam Reporting::
+* Anti-spam Hashcash Payments::
+* Blackholes::
+* Regular Expressions Header Matching::
+* Bogofilter::
+* ifile spam filtering::
+* spam-stat spam filtering::
+* SpamOracle::
+* Extending the Spam ELisp package::
+@end menu
+
+@node Spam ELisp Package Sequence of Events
+@subsubsection Spam ELisp Package Sequence of Events
+@cindex spam filtering
+@cindex spam filtering sequence of events
+@cindex spam
+
+\e$BI,$:$3$N9`$rFI$s$G2<$5$$!#\e(B@code{spam.el} \e$B$NF0:n$rM}2r$9$k$?$a$K!#FI$_Ht\e(B
+\e$B$P$7!"B.FI!"<P$aFI$_$O876X$G$9!#\e(B
+
+\e$B$"$J$?$,0U?^$9$k$J$i$P\e(B @code{spam.el} \e$B$H\e(B Gnus \e$B$NB>$NItJ,$N4V$KFs$D$N@\E@\e(B
+\e$B$,$"$j$^$9\e(B: spam \e$B$N$?$a$N?7Ce%a!<%k$N8!::!"$*$h$S%0%k!<%W$rH4$1$k>l9g$G\e(B
+\e$B$9!#\e(B
+
+\e$B?7Ce%a!<%k$N<hF@$OFs$D$N$&$A$N0lJ}$G9T$J$o$l$^$9!#$d$C$FCe$?%a!<%k$rJ,3d\e(B
+\e$B$7$?$j!"%0%k!<%W$KF~$k$H$-$K?7$7$$5-;v$r\e(B ham \e$B$H\e(B spam \e$B$KJ,N`$9$k$3$H$,$G\e(B
+\e$B$-$^$9!#\e(B
+
+\e$B$d$C$FMh$?%a!<%k$NJ,3d$O!"\e(B@code{nnml} \e$B$d\e(B @code{nnimap} \e$B$N$h$&$J!"?7$7$$\e(B
+\e$B%a!<%k$,\e(B @dfn{Spool File} \e$B$H8F$P$l$k0l$D$N%U%!%$%k$K$J$k%P%C%/%(%s%I$K!"\e(B
+\e$B$h$jE,$7$F$$$^$9!#\e(B
+@xref{Spam ELisp Package Filtering of Incoming Mail} \e$B$r;2>H$7$F2<$5$$!#\e(B
+
+@code{nntp} \e$B$N$h$&$J%P%C%/%(%s%I$K$O$d$C$FMh$k%a!<%k$N%9%W!<%k$,L5$$$N$G!"\e(B
+\e$BBe$o$j$N5!9=$r;H$o$J$1$l$P$J$j$^$;$s!#$3$l$O!"%5!<%P!<$,$d$C$FMh$?%a!<%k\e(B
+\e$B$NJ,3d$rC4Ev$7$F$$$F!"\e(BGnus \e$B$,$5$i$KJ,3d$r9T$J$o$J$$%P%C%/%(%s%I$G$b5/$-\e(B
+\e$B$k$+$b$7$l$^$;$s!#%0%k!<%W%Q%i%a!<\e(B
+\e$B%?\e(B @code{spam-autodetect} \e$B$H\e(B @code{spam-autodetect-methods} (\e$BIaDL\e(B @kbd{G
+c} and @kbd{G p} \e$B$GA`:n2D\e(B)\e$B!"$=$7$FBP1~$9$kJQ\e(B
+\e$B?t\e(B @code{gnus-spam-autodetect-methods} \e$B$*$h\e(B
+\e$B$S\e(B @code{gnus-spam-autodetect-methods} (@kbd{M-x customize-variable} \e$B$G\e(B
+\e$BA`:n2D\e(B) \e$B$G$9!#\e(B
+
+@code{spam-autodetect} \e$B$,;H$o$l$k>l9g!"$=$l$O%0%k!<%W$KF~$k=hM}$K0z$C$+\e(B
+\e$B$1$i$l$^$9!#$7$?$,$C$F!"$^$@FI$^$l$?$3$H$,L5$$!"$^$?$OL$FI$N5-;v$,$"$k%0\e(B
+\e$B%k!<%W$KF~$k$3$H$O!"$d$C$FMh$?%a!<%k$N8!::$NBe$o$j$K$J$j$^$9!#$^$@FI$^$l\e(B
+\e$B$?$3$H$,L5$$5-;v!"$^$?$O$9$Y$F$NL$FI$N5-;v$,=hM}$5$l$k$+$I$&$+$O!"\e(B
+@code{spam-autodetect-recheck-messages} \e$B$K$h$C$F7h$^$j$^$9!#\e(Bt \e$B$K@_Dj$5$l\e(B
+\e$B$k$H!"L$FI$N%a%C%;!<%8$,:F8!::$5$l$^$9!#\e(B
+
+@code{spam-autodetect} \e$B$O!"%f!<%6$K\e(B spam \e$B_I2a$NB?>/$N4IM}$rB(9oG'$a$^$9!#\e(B
+\e$B%f!<%6$O3F%0%k!<%W$N\e(B spam \e$B$N<jCJ$r$h$jB?$/4IM}$9$k$3$H$,$G$-$k$G$7$g$&!#\e(B
+\e$B$7$?$,$C$F!"\e(B@samp{suspect} \e$B%0%k!<%W$G\e(B @code{spam-use-blacklist} \e$B$*$h\e(B
+\e$B$S\e(B @code{spam-use-bogofilter} \e$B$N<jCJ$,M-8z$K$J$C$F$$$F$b!"\e(B
+\e$BNc$($P\e(B @samp{ding} \e$B%0%k!<%W$O<+F08!CN<jCJ$H$7$F\e(B @code{spam-use-BBDB} \e$B$r\e(B
+\e$B;}$D$3$H$,$G$-$^$9!#\e(BSpam \e$B$H$7$F8!CN$5$l$k$9$Y$F$N5-;v$K\e(B
+\e$B$O\e(B spam \e$B0u\e(B @samp{$}\e$B$,IU$1$i$l!"%0%k!<%W$rH4$1$k$H$-$KDL>o$N\e(B spam \e$B$H$7$F\e(B
+\e$B=hM}$5$l$^$9!#H`$,\e(B @code{spam-split} \e$B$G9T$J$C$F$bNI$$$h$&$K!"%f!<%6$O8!\e(B
+\e$B::$N\e(B @emph{sequence} \e$B$r$h$j>/$J$/4IM}$7$^$9!#\e(B
+
+\e$B?7$?$KJ,3d$5$l$?%a!<%k$,%0%k!<%W$KF~$C$?!"$^$?$O%a%C%;!<%8$,\e(B ham \e$B$^$?\e(B
+\e$B$O\e(B spam \e$B$H$7$F<+F08!CN$5$l$?>l9g!"8e$K\e(B spam \e$B=hM}$r9T$J$o$;$k$?$a$K!"$=$l\e(B
+\e$B$i$N%0%k!<%W$r\e(B (\e$BI,MW$J$iF~$C$?8e$G\e(B) \e$BH4$1=P$J$/$F$O$J$j$^$;$s!#%0%k!<%W$,\e(B
+\e$B$=$N\e(B @code{spam-content} \e$B%Q%i%a!<%?\e(B (@pxref{Spam ELisp Package Global
+Variables}) \e$B$K4p$E$$$F\e(B ham \e$B$^$?$O\e(B spam \e$B%0%k!<%W$H9M$($i$l$k$+!"L$J,N`$+\e(B
+\e$B$I$&$+$O=EMW$G$9!#\e(BSpam \e$B%0%k!<%W$O!"$=$3$KF~$k$H!"$^$@FI$^$l$?$3$H$,L5$$!"\e(B
+\e$B$^$?$OL$FI$N5-;v$K\e(B spam \e$B$N0u$,IU$1$i$l$k\e(B (\e$BJQ\e(B
+\e$B?t\e(B @code{spam-mark-only-unseen-as-spam} \e$B$K0MB8\e(B) \e$B$H$$$&DI2C$NFC@-$r;}$A$^\e(B
+\e$B$9!#$3$N$h$&$K!"J,3d$5$l$F\e(B spam \e$B%0%k!<%W$KF~$l$i$l$?5-;v$K$O!"$"$J$?$,$=\e(B
+\e$B$N%0%k!<%W$KF~$C$?$H$-$K<+F0E*$K\e(B spam \e$B$N0u$,IU$1$i$l$^$9!#\e(B
+
+\e$B$7$?$,$C$F!"%0%k!<%W$rH4$1$k$H\e(B @code{spam-processors} \e$B$,\e(B (\e$B2?$G$"$l@_Dj$5\e(B
+\e$B$l$F$$$l$P\e(B) \e$BE,MQ$5$l!"=hM}$5$l$?%a!<%k$O5-;v$NJ,N`$K4p$E$$\e(B
+\e$B$F\e(B @code{ham-process-destination} \e$B$+\e(B @code{spam-process-destination} \e$B$K\e(B
+\e$B0\F0$5$;$i$l$^$9!#\e(B@code{ham-process-destination} \e$B$^$?\e(B
+\e$B$O\e(B @code{spam-process-destination} \e$B$N$I$A$i$+$,\e(B (\e$BLuCp\e(B: \e$B0\F0@h$H$7$F\e(B) \e$BE,\e(B
+\e$B@Z$G!"$=$l$i$,\e(B nil \e$B$@$C$?>l9g!"$=$N5-;v$O8=:_$N%0%k!<%W$K;D$5$l$^$9!#\e(B
+
+\e$B$I$l$+$N%0%k!<%W$G\e(B spam \e$B$,8+$D$+$C$?$i\e(B (\e$BHs\e(B-spam \e$B%0%k!<%W$K8B$C\e(B
+\e$B$F\e(B @code{spam-move-spam-nonspam-groups-only} \e$B$GJQ992D\e(B)\e$B!"%0%k!<%W$rH4$1$k\e(B
+\e$B$H$-$K3h$-$F$$$k\e(B @code{spam-processors} (@pxref{Spam ELisp Package
+Global Variables}) \e$B$G=hM}$5$l$^$9!#$5$i$K!"8e$G%H%l!<%K%s%0$^$?$O:o=|$9\e(B
+\e$B$k$?$a$K!"\e(Bspam \e$B$O\e(B @code{spam-process-destination} (@pxref{Spam ELisp
+Package Global Variables}) \e$B$K0\F0$5$;$i$l$^$9!#\e(BSpam \e$B$,:F;0=hM}$5$l$k$3$H\e(B
+\e$B$rK>$^$J$$$J$i$P!"\e(B@file{gnus-registry.el} \e$B%Q%C%1!<%8$rFI$_9~$_!"\e(B
+@code{spam-log-to-registry} \e$BJQ?t$rM-8z$K$7$J$1$l$P$J$j$^$;$s!#$3$N$h$&\e(B
+\e$B$K\e(B spam \e$B$O$I$3$G$b8!CN$5$l=hM}$5$l$^$9!#$=$l$O$[$H$s$I$N?M!9$,K>$`$b$N$G\e(B
+\e$B$9!#\e(B
+
+Ham \e$B%0%k!<%W$G\e(B @code{ham-marks} \e$B%Q%i%a!<%?$G7hDj$5$l$k\e(B ham \e$B%a!<%k$,8+$D\e(B
+\e$B$+$C$?$i!"%0%k!<%W$rH4$1$k$H$-$K3h$-$F$$$k\e(B ham @code{spam-processor} \e$B$G\e(B
+\e$B=hM}$5$l$^$9!#$5$i$K!"JQ?t\e(B @code{spam-process-ham-in-spam-groups} \e$B$*$h\e(B
+\e$B$S\e(B @code{spam-process-ham-in-nonham-groups} \e$B$K$h$C$F!"$I$3$G8+$D$+$C\e(B
+\e$B$?\e(B ham \e$B$G$b=hM}$G$-$k$h$&$KF0:n$rJQ99$9$k$3$H$,$G$-$^$9!#\e(BHam \e$B$,:F;0=hM}\e(B
+\e$B$5$l$k$3$H$rK>$^$J$$$J$i$P!"\e(B@file{gnus-registry.el} \e$B%Q%C%1!<%8$rFI$_9~$_!"\e(B
+@code{spam-log-to-registry} \e$BJQ?t$rM-8z$K$7$J$1$l$P$J$j$^$;$s!#$3$N$h$&\e(B
+\e$B$K\e(B ham \e$B$OI,MW$J>l9g$@$18!CN$5$l=hM}$5$l$^$9!#$=$l$O$[$H$s$I$N?M!9$,K>$`\e(B
+\e$B$b$N$G$9!#$3$l$K4X$9$k>\:Y$O\e(B @xref{Spam ELisp Package Configuration
+Examples}.
+
+\e$B$3$l$i$9$Y$F$,$o$1$,$o$+$i$J$/$F$b!"?4G[$OL5MQ$G$9\e(B (\e$BLuCm\e(B: \e$B$G$bLuJ8$,@53N\e(B
+\e$B$G$O$J$$$+$b$7$l$J$$$N$G!"JQ$@$H;W$C$?$i86J8$r;2>H$N$3$H\e(B :-p)\e$B!#$9$0$K$=\e(B
+\e$B$l$O?@7P%$%s%?!<%U%'!<%9>e$K\e(B Lisp \e$B<0$r%?%$%W$9$k$h$&$K<+A3$J$3$H$K$J$j$^\e(B
+\e$B$9\e(B... \e$B$(!+$4$a$s!"$=$l$K$O$^$@\e(B 50\e$BG/Aa$$$G$9$M!#$?$@;d$?$A$r?.Mj$7$F2<$5\e(B
+\e$B$$!#$=$l$O<N$F$?$b$N$G$O$"$j$^$;$s!#\e(B
+
+@node Spam ELisp Package Filtering of Incoming Mail
+@subsubsection Spam ELisp Package Filtering of Incoming Mail
+@cindex spam filtering
+@cindex spam filtering incoming mail
+@cindex spam
+
+\e$BF~$C$F$/$k%a!<%k$r_I2a$9$kL\E*$G\e(B @file{spam.el} \e$B$r;H$&$K$O!"FC5iJ,3d%j%9\e(B
+\e$B%H\e(B @code{nnmail-split-fancy} \e$B$^$?$O\e(B @code{nnimap-split-fancy} \e$B$K0J2<$rDI\e(B
+\e$B2C$7$J$1$l$P$J$j$^$;$s\e(B:
+
+@example
+(: spam-split)
+@end example
+
+\e$BFC5iJ,3d$O!"%a!<%k$N<h$j9~$_$K\e(B nnmail \e$B$+\e(B nnimap \e$B$N$I$A$i$N%P%C%/%(%s%I$r\e(B
+\e$B;H$C$F$$$k$+$K1~$8$F!"\e(B@code{nnmail-split-fancy} \e$B$^$?\e(B
+\e$B$O\e(B @code{nnimap-split-fancy} \e$B$+$i8F$P$l$k$3$H$KCm0U$7$F2<$5$$!#\e(B
+
+@code{spam-split} \e$B4X?t$OF~$C$F$/$k%a!<%k$r=hM}$7!"\e(Bspam \e$B$H;W$o$l$k%a!<%k\e(B
+\e$B$rJQ?t\e(B @code{spam-split-group} \e$B$GM?$($i$l$kL>A0$N%0%k!<%W$KAw$j$^$9!#%G%#\e(B
+\e$B%U%)%k%H$G$O$=$N%0%k!<%WL>$O\e(B @samp{spam} \e$B$G$9$,!"\e(B
+@code{spam-split-group} \e$B$r%+%9%?%^%$%:$9$k$3$H$,2DG=$G$9!#\e(B
+@code{spam-split-group} \e$B$NFbMF$,\e(B @emph{\e$B@dBP\e(B} \e$B%0%k!<%WL>$G$"$k$3$H!"Nc$(\e(B
+\e$B$P\e(B @samp{your-server} \e$B$H$$$&\e(B @code{nnimap} \e$B%5!<%P!<$N>l9g$O!"\e(B
+@samp{spam} \e$BJQ?t$,:G=*E*$K\e(B @samp{nnimap+your-server:spam} \e$B$K$J$k$3$H$r3N\e(B
+\e$B$+$a$F2<$5$$!#=>$C$F\e(B @samp{nnimap+server:spam} \e$B$H$$$&CM$O4V0c$$$G!"$=$l\e(B
+\e$B$O<B:]$K$O\e(B @samp{nnimap+your-server:nnimap+server:spam} \e$B$H$$$&%0%k!<%W$K\e(B
+\e$B$J$j!"$=$l$,F/$/$+F/$+$J$$$+$O!"$"$J$?$N%5!<%P!<$,4qL/$J%0%k!<%WL>$KBP$7\e(B
+\e$B$F42MF$+$I$&$+$K0MB8$9$k$G$7$g$&!#\e(B
+
+\e$B$^$?!"\e(B@code{spam-split} \e$B$K%Q%i%a!<%?!"Nc$(\e(B
+\e$B$P\e(B @samp{spam-use-regex-headers} \e$B$^$?$O\e(B @samp{"maybe-spam"} \e$B$rM?$($k$3$H\e(B
+\e$B$b$G$-$^$9!#$J$<$3$l$,M-MQ$J$N$G$7$g$&$+\e(B?
+
+\e$B$3$l$i$N\e(B (@code{spam-use-regex-headers} \e$B$H\e(B @code{spam-use-blackholes} \e$B$N\e(B
+\e$B@_Dj$K$h$k\e(B) \e$BJ,3d$N5,B'$r8+$F2<$5$$\e(B:
+
+@example
+ nnimap-split-fancy '(|
+ (any "ding" "ding")
+ (: spam-split)
+ ;; default mailbox
+ "mail")
+@end example
+
+\e$B$5$F!"LdBj$O\e(B ding \e$B08$F$N%a%C%;!<%8$r$9$Y$F\e(B ding \e$B%U%)%k%@!<$KF~$l$h$&$H$7\e(B
+\e$B$F$$$k$3$H$G$9!#$G$b$=$l$O\e(B ding \e$B%a!<%j%s%0%j%9%H08$F$KAw$i$l$?\e(B spam (\e$BNc\e(B
+\e$B$($P\e(B SpamAssassin \e$B$H\e(B @code{spam-use-regex-headers} \e$B$K$h$C$F8!=P$5$l\e(B
+\e$B$k\e(B spam) \e$B$r5v$7$F$7$^$&$G$7$g$&!#0lJ}!"$$$/$D$+$N\e(B ding \e$B08$F$N%a%C%;!<%8\e(B
+\e$B$O%V%i%C%/%[!<%k%j%9%H$K:\$C$F$$$k%a!<%k%5!<%P!<$+$i$d$C$FMh$k$N$G!"\e(B
+ding \e$B$N5,B'$h$jA0$K\e(B @code{spam-split} \e$B$rH/F0$9$k$3$H$,$G$-$^$;$s!#\e(B
+
+SpamAssassin \e$B%X%C%@!<$K\e(B ding \e$B$N5,B'$rCV$-49$($5$;$k$3$H$O$G$-$^$9$,!"B>\e(B
+\e$B$N$9$Y$F$N\e(B @code{spam-split} \e$B$N5,B'\e(B (\e$BBhFs$N@55,I=8=%X%C%@!<8!::$r4^\e(B
+\e$B$`\e(B) \e$B$O\e(B ding \e$B$N5,B'$N8e$K$J$C$F$7$^$&$G$7$g$&!#\e(B
+
+@example
+ nnimap-split-fancy '(|
+;;; spam-use-regex-headers \e$B$G8!=P$5$l$?$9$Y$F$N\e(B spam \e$B$O\e(B "regex-spam" \e$B$X!#\e(B
+ (: spam-split "regex-spam" 'spam-use-regex-headers)
+ (any "ding" "ding")
+;;; spam-split \e$B$G8!=P$5$l$?B>$N$9$Y$F$N\e(B spam \e$B$O\e(B spam-split-group \e$B$X!#\e(B
+ (: spam-split)
+ ;; default mailbox
+ "mail")
+@end example
+
+\e$B4pK\E*$K!"$3$l$OFC$K$"$J$?$NI,MW$K0MB8$7$?FCDj$N\e(B @code{spam-split} \e$B8!\e(B
+\e$B::$r5/F0$5$;!"$=$l$i$N8!::$N7k2L$OFCDj$N\e(B spam \e$B%0%k!<%W$r;X$7<($7$^$9!#$9\e(B
+\e$B$Y$F$N%a!<%k$r$9$Y$F$N\e(B spam \e$B%F%9%H$KEj$2$kI,MW$O$"$j$^$;$s!#$3$l$,NI$$JL\e(B
+\e$B$NM}M3$O!"5,B'$r;}$C$F$$$k%a!<%j%s%0%j%9%H$X$N%a%C%;!<%8$KBP$7$F!";q8;=8\e(B
+\e$BLsE*$J%V%i%C%/%[!<%k!&%A%'%C%/$r<B9T$9$kI,MW$,$J$$$H$$$&$3$H$G$9!#$5$i\e(B
+\e$B$K\e(B nnmail \e$BJ,3d$KBP$7$F\e(B nnimap \e$BJ,3d$N$?$a$N!"0[$J$k\e(B spam \e$B8!::$r;XDj$9$k$3\e(B
+\e$B$H$b$G$-$^$9!#5$$,68$&!<!#\e(B
+
+\e$B8!::$HF1;~$KL@$i$+$K\e(B @code{spam-split} \e$B$r<B9T$9$k$H$7$F$b!":#$^$G$H$*\e(B
+\e$B$j\e(B @code{spam-use-regex-headers} \e$B$r\e(B @code{t} \e$B$K@_Dj$9$k$h$&$J8!::$r9T$C\e(B
+\e$B$F$$$J$1$l$P$J$j$^$;$s!#$J$<$J$i\e(B @file{spam.el} \e$B$rFI$_9~$`$H$-$K!"$"$J$?\e(B
+\e$B$,2?$N\e(B @code{spam-use-xyz} \e$BJQ?t$r@_Dj$7$F$$$k$+$K1~$8$?!"$$$/$D$+$N>r7o\e(B
+\e$BIU$-$NFI$_9~$_$,9T$o$l$k$+$i$G$9!#\e(B
+
+@emph{@acronym{IMAP} \e$BMxMQ<T$X$NCm0U\e(B}
+
+\e$B%X%C%@!<$@$1$G$O$J$/$F%a%C%;!<%8A4BN$K4p$E$$$FJ,3d$r9T$J$$$?$$>l9g$O!"%V!<\e(B
+\e$B%kJQ?t\e(B @code{nnimap-split-download-body} \e$B$,@_Dj$5$l$kI,MW$,$"$j$^$9!#%G%#\e(B
+\e$B%U%)%k%H$G$O!"\e(Bnnimap \e$B%P%C%/%(%s%I$O%a%C%;!<%8%X%C%@!<$@$1$r<h$j9~$_$^$9!#\e(B
+@code{spam-check-bogofilter}\e$B!"\e(B@code{spam-check-ifile} \e$B$^$?\e(B
+\e$B$O\e(B @code{spam-check-stat} (\e$B$=$l$i$NJ,3d4o$O%a%C%;!<%8$NK\J8A4BN$+$i>pJs\e(B
+\e$B$rF@$k\e(B) \e$B$r;H$&$J$i$P!"$3$NJQ?t$r@_Dj$7$J$1$l$P$J$j$^$;$s!#$=$l\e(B
+\e$B$O\e(B @acronym{IMAP} \e$B$NF0:n$rCY$/$7$F$7$^$$!"%f!<%6$rBeI=$9$k$N$K$U$5$o$7$$\e(B
+\e$B7hDj$G$O$J$$$N$G!"%G%#%U%)%k%H$G$O@_Dj$5$l$F$$$^$;$s!#\e(B
+
+@xref{Splitting in IMAP}.
+
+@emph{TODO: spam.el \e$B$O$9$Y$F$NE}7W%G!<%?%Y!<%9$r%H%l!<%K%s%0$9$k$?$a$N0l\e(B
+\e$BDjITJQ$NJ}K!$rDs6!$9$kI,MW$,$"$j$^$9!#$$$/$D$+$O$=$N5!G=$r<+A0$G;}$C$F$$\e(B
+\e$B$^$9$,!"$=$&$G$J$$$b$N$b$"$j$^$9!#\e(B}
+
+@node Spam ELisp Package Global Variables
+@subsubsection Spam ELisp Package Global Variables
+@cindex spam filtering
+@cindex spam filtering variables
+@cindex spam variables
+@cindex spam
+
@vindex gnus-spam-process-newsgroups
Ham \e$B%W%m%;%C%5!<$H\e(B spam \e$B%W%m%;%C%5!<$N35G0$OHs>o$K=EMW$G$9!#$"$k%0%k!<%W\e(B
\e$B$N\e(B ham \e$B%W%m%;%C%5!<$H\e(B spam \e$B%W%m%;%C%5!<$O!"\e(B@code{spam-process} \e$B%0%k!<%W\e(B
\e$B$N\e(B spam \e$B$,8!=P$5$l$k$h$&$K!"\e(Bspam \e$B$G$"$k$3$H$,$o$+$C$F$$$k%a!<%k$r<u$1<h$C\e(B
\e$B$F=hM}$7$^$9!#\e(B
+Spam \e$B$^$?$O\e(B ham \e$B%W%m%;%C%5!<$r;XDj$9$k7A<0$r!"$+$D$F$O%7%s%\%k$GI=$7$F$$\e(B
+\e$B$?$N$G$9$,!"8=:_$O\e(B cons \e$B%;%k$K$J$C$F$$$^$9!#>\$7$/$O8D!9$N\e(B spam \e$B%W%m%;%C\e(B
+\e$B%5!<$N9`$r;2>H$7$F2<$5$$!#\e(B
+
@vindex gnus-spam-newsgroup-contents
gnus \e$B$O$"$J$?$,<u$1<h$C$?\e(B spam \e$B$+$i3X$S$^$9!#$"$J$?$O0l$D0J>e$N\e(B spam \e$B%0\e(B
\e$B%k!<%W$K\e(B spam \e$B5-;v$r=8$a$F!"JQ?t\e(B @code{spam-junk-mailgroups} \e$B$rE,@Z$K@_\e(B
\e$B$3$N%0%k!<%W$^$?$O%H%T%C%/%Q%i%a!<%?$r\e(B ham \e$B$G$"$k$H2r<a$7$?$$0u$N%j%9%H\e(B
\e$B$K@_Dj$9$k$3$H$,$G$-$^$9!#%G%#%U%)%k%H$G$O!">C5n\e(B (deleted)\e$B!"4{FI\e(B (read)\e$B!"\e(B
\e$B:o=|\e(B (killed)\e$B!"\e(Bkill \e$B%U%!%$%k$K$"$k$b$N\e(B (kill-filed) \e$B$*$h$SDc$$%9%3\e(B
-\e$B%"\e(B (low-score) \e$B0u$N%j%9%H$G$9!#\e(B
+\e$B%"\e(B (low-score\e$B!"4{FI$@$1$l$I$b\e(B spam \e$B$G$O$J$$$H9M$($k\e(B) \e$B0u$N%j%9%H$G$9!#\e(B
+Ham \e$B0u$N%j%9%H$K2D;k\e(B (tick) \e$B0u$r4^$a$k$3$H$,LrN)$D$3$H$b$"$j$^$9!#L$FI0u\e(B
+\e$B$r\e(B ham \e$B0u$K$9$k$3$H$O!"DL>o$=$l$,J,N`$,B-$j$F$$$J$$$3$H$rI=$9$N$G!"4+$a\e(B
+\e$B$i$l$^$;$s!#$7$+$7!"$"$J$?$,$=$l$r9T$J$&$3$H$O$G$-$k$7!";d$?$A$KITK~$O$"\e(B
+\e$B$j$^$;$s!#\e(B
@end defvar
@defvar spam-marks
\e$B$3$N%0%k!<%W$^$?$O%H%T%C%/%Q%i%a!<%?$r\e(B spam \e$B$G$"$k$H2r<a$7$?$$0u$N%j%9%H\e(B
\e$B$K@_Dj$9$k$3$H$,$G$-$^$9!#%G%#%U%)%k%H$G$O\e(B spam \e$B0u$@$1$r;}$D%j%9%H$G$9!#\e(B
+\e$B$=$l$rJQ99$9$k$3$H$O4+$a$^$;$s$,!"K\Ev$K$=$&$7$?$$$N$J$i$4>!<j$K!#\e(B
@end defvar
\e$B%0%k!<%W$rH4$1$k$H$-$K\e(B (\e$B$=$N%0%k!<%W$,\e(B @emph{\e$B2?\e(B} \e$B$G$"$C$F$b\e(B)\e$B!"$=\e(B
\e$BJQ?t$r%+%9%?%^%$%:$9$k$N$,:G$b4JC1$G$9\e(B)\e$B!#JQ?t$r<j$G%+%9%?%^%$%:$9$kJ}$,\e(B
\e$B9%$-$J?M$N$?$a$K8@$C$F$*$/$H!"$=$l$i$OIaDL$N\e(B Lisp \e$B$N\e(B list \e$B$G!"$=$l$>$l$N\e(B
\e$B%K%e!<%9%0%k!<%W$N;EMM@_Dj$O\e(B @code{(REGEXP PROCESSOR)} \e$B$N7A<0$NCM$r;}$A\e(B
-\e$B$^$9!#:G=*E*$J>l=j$O%0%k!<%WL>$G$9!#\e(B@code{ham-process-destination} \e$B%Q%i\e(B
-\e$B%a!<%?$,@_Dj$5$l$F$$$J$$$H!"\e(Bham \e$B5-;v$O$=$3$KN1$aCV$+$l$^$9!#\e(B
+\e$B$^$9!#:G=*E*$J>l=j$O\e(B (\e$BC1?t$^$?$OJ#?t$N\e(B) \e$B%0%k!<%WL>$G$9!#\e(B
+@code{ham-process-destination} \e$B%Q%i%a!<%?$,@_Dj$5$l$F$$$J$$$H!"\e(Bham \e$B5-;v\e(B
+\e$B$O$=$3$KN1$aCV$+$l$^$9!#\e(B
@code{spam-mark-ham-unread-before-move-from-spam-group} \e$B%Q%i%a!<%?$,@_Dj\e(B
\e$B$5$l$F$$$k$H!"\e(Bham \e$B5-;v$O0\F0$5$;$i$l$kA0$KL$FI$N0u$,IU$1$i$l$^$9!#\e(B
+\e$B%0%k!<%W$^$?$O@55,I=8=$4$H$KJ#?t$N0\F0@h$r;XDj$G$-$k$3$H$KCmL\$7$F2<$5$$\e(B!
+\e$B$3$l$K$h$C$F\e(B ham \e$B5-;v$r@55,$N%a!<%k%0%k!<%W$H\e(B @emph{ham \e$B%H%l!<%K%s%0\e(B} \e$B%0\e(B
+\e$B%k!<%W$KAw$k$3$H$,$G$-$^$9!#\e(B
+
@emph{Ham} \e$B%0%k!<%W$rH4$1$k$H$-$K!"\e(Bham \e$B0u$,IU$$$F$$$k$9$Y$F$N5-;v\e(B
\e$B$O\e(B ham \e$B%W%m%;%C%5!<$KAw$i$l!"$=$l$i$r\e(B spam \e$B$G$O$J$$I8K\$H$7$F3X=,$7$^$9!#\e(B
\e$B$9\e(B (@code{customize-variable gnus-spam-process-destinations} \e$B$K$h$C$F$3\e(B
\e$B$NJQ?t$r%+%9%?%^%$%:$9$k$N$,:G$b4JC1$G$9\e(B)\e$B!#JQ?t$r<j$G%+%9%?%^%$%:$9$kJ}\e(B
\e$B$,9%$-$J?M$N$?$a$K8@$C$F$*$/$H!"$=$l$i$OIaDL$N\e(B Lisp \e$B$N\e(B list \e$B$G!"$=$l$>$l\e(B
-\e$B$N%K%e!<%9%0%k!<%W$N;EMM@_Dj$O\e(B @code{(REGEXP PROCESSOR)} \e$B$N7A<0$NCM$r;}\e(B
-\e$B$A$^$9!#:G=*E*$J>l=j$O%0%k!<%WL>$G$9!#\e(B@code{spam-process-destination} \e$B%Q\e(B
-\e$B%i%a!<%?$,@_Dj$5$l$F$$$J$$$H!"\e(Bspam \e$B5-;v$OC1$K4|8B@Z$l>C5n$5$l$^$9!#\e(B
-
-\e$BF~$C$F$/$k%a!<%k$r_I2a$9$kL\E*$G\e(B @file{spam.el} \e$B$r;H$&$K$O!"FC5iJ,3d%j%9\e(B
-\e$B%H\e(B @code{nnmail-split-fancy} \e$B$^$?$O\e(B @code{nnimap-split-fancy} \e$B$K0J2<$rDI\e(B
-\e$B2C$7$J$1$l$P$J$j$^$;$s\e(B:
-
-@example
-(: spam-split)
-@end example
-
-\e$BFC5iJ,3d$O!"%a!<%k$N<h$j9~$_$K\e(B nnmail \e$B$+\e(B nnimap \e$B$N$I$A$i$N%P%C%/%(%s%I$r\e(B
-\e$B;H$C$F$$$k$+$K1~$8$F!"\e(B@code{nnmail-split-fancy} \e$B$^$?\e(B
-\e$B$O\e(B @code{nnimap-split-fancy} \e$B$+$i8F$P$l$k$3$H$KCm0U$7$F2<$5$$!#\e(B
-
-@code{spam-split} \e$B4X?t$OF~$C$F$/$k%a!<%k$r=hM}$7!"\e(Bspam \e$B$H;W$o$l$k%a!<%k\e(B
-\e$B$rJQ?t\e(B @code{spam-split-group} \e$B$GM?$($i$l$kL>A0$N%0%k!<%W$KAw$j$^$9!#%G%#\e(B
-\e$B%U%)%k%H$G$O$=$N%0%k!<%WL>$O\e(B @samp{spam} \e$B$G$9$,!"\e(B
-@code{spam-split-group} \e$B$r%+%9%?%^%$%:$9$k$3$H$,2DG=$G$9!#\e(B
-@code{spam-split-group} \e$B$NFbMF$,\e(B @emph{\e$B@dBP\e(B} \e$B%0%k!<%WL>$G$"$k$3$H!"Nc$(\e(B
-\e$B$P\e(B @samp{your-server} \e$B$H$$$&\e(B @code{nnimap} \e$B%5!<%P!<$N>l9g$O!"\e(B
-@samp{spam} \e$BJQ?t$,:G=*E*$K\e(B @samp{nnimap+your-server:spam} \e$B$K$J$k$3$H$r3N\e(B
-\e$B$+$a$F2<$5$$!#=>$C$F\e(B @samp{nnimap+server:spam} \e$B$H$$$&CM$O4V0c$$$G!"$=$l\e(B
-\e$B$O<B:]$K$O\e(B @samp{nnimap+your-server:nnimap+server:spam} \e$B$H$$$&%0%k!<%W$K\e(B
-\e$B$J$j!"$=$l$,F/$/$+F/$+$J$$$+$O!"$"$J$?$N%5!<%P!<$,4qL/$J%0%k!<%WL>$KBP$7\e(B
-\e$B$F42MF$+$I$&$+$K0MB8$9$k$G$7$g$&!#\e(B
-
-\e$B$^$?!"\e(B@code{spam-split} \e$B$K%Q%i%a!<%?!"Nc$(\e(B
-\e$B$P\e(B @samp{spam-use-regex-headers} \e$B$^$?$O\e(B @samp{"maybe-spam"} \e$B$rM?$($k$3$H\e(B
-\e$B$b$G$-$^$9!#$J$<$3$l$,M-MQ$J$N$G$7$g$&$+\e(B?
-
-\e$B$3$l$i$N\e(B (@code{spam-use-regex-headers} \e$B$H\e(B @code{spam-use-blackholes} \e$B$N\e(B
-\e$B@_Dj$K$h$k\e(B) \e$BJ,3d$N5,B'$r8+$F2<$5$$\e(B:
-
-@example
- nnimap-split-fancy '(|
- (any "ding" "ding")
- (: spam-split)
- ;; default mailbox
- "mail")
-@end example
-
-\e$B$5$F!"LdBj$O\e(B ding \e$B08$F$N%a%C%;!<%8$r$9$Y$F\e(B ding \e$B%U%)%k%@!<$KF~$l$h$&$H$7\e(B
-\e$B$F$$$k$3$H$G$9!#$G$b$=$l$O\e(B ding \e$B%a!<%j%s%0%j%9%H08$F$KAw$i$l$?\e(B spam (\e$BNc\e(B
-\e$B$($P\e(B SpamAssassin \e$B$H\e(B @code{spam-use-regex-headers} \e$B$K$h$C$F8!=P$5$l\e(B
-\e$B$k\e(B spam) \e$B$r5v$7$F$7$^$&$G$7$g$&!#0lJ}!"$$$/$D$+$N\e(B ding \e$B08$F$N%a%C%;!<%8\e(B
-\e$B$O%V%i%C%/%[!<%k%j%9%H$K:\$C$F$$$k%a!<%k%5!<%P!<$+$i$d$C$FMh$k$N$G!"\e(B
-ding \e$B$N5,B'$h$jA0$K\e(B @code{spam-split} \e$B$rH/F0$9$k$3$H$,$G$-$^$;$s!#\e(B
-
-SpamAssassin \e$B%X%C%@!<$K\e(B ding \e$B$N5,B'$rCV$-49$($5$;$k$3$H$O$G$-$^$9$,!"B>\e(B
-\e$B$N$9$Y$F$N\e(B @code{spam-split} \e$B$N5,B'\e(B (\e$BBhFs$N@55,I=8=%X%C%@!<8!::$r4^\e(B
-\e$B$`\e(B) \e$B$O\e(B ding \e$B$N5,B'$N8e$K$J$C$F$7$^$&$G$7$g$&!#\e(B
-
-@example
- nnimap-split-fancy '(|
-;;; spam-use-regex-headers \e$B$G8!=P$5$l$?$9$Y$F$N\e(B spam \e$B$O\e(B "regex-spam" \e$B$X!#\e(B
- (: spam-split "regex-spam" 'spam-use-regex-headers)
- (any "ding" "ding")
-;;; spam-split \e$B$G8!=P$5$l$?B>$N$9$Y$F$N\e(B spam \e$B$O\e(B spam-split-group \e$B$X!#\e(B
- (: spam-split)
- ;; default mailbox
- "mail")
-@end example
-
-\e$B4pK\E*$K!"$3$l$OFC$K$"$J$?$NI,MW$K0MB8$7$?FCDj$N\e(B @code{spam-split} \e$B8!\e(B
-\e$B::$r5/F0$5$;!"$=$l$i$N8!::$N7k2L$OFCDj$N\e(B spam \e$B%0%k!<%W$r;X$7<($7$^$9!#$9\e(B
-\e$B$Y$F$N%a!<%k$r$9$Y$F$N\e(B spam \e$B%F%9%H$KEj$2$kI,MW$O$"$j$^$;$s!#$3$l$,NI$$JL\e(B
-\e$B$NM}M3$O!"5,B'$r;}$C$F$$$k%a!<%j%s%0%j%9%H$X$N%a%C%;!<%8$KBP$7$F!";q8;=8\e(B
-\e$BLsE*$J%V%i%C%/%[!<%k!&%A%'%C%/$r<B9T$9$kI,MW$,$J$$$H$$$&$3$H$G$9!#$5$i\e(B
-\e$B$K\e(B nnmail \e$BJ,3d$KBP$7$F\e(B nnimap \e$BJ,3d$N$?$a$N!"0[$J$k\e(B spam \e$B8!::$r;XDj$9$k$3\e(B
-\e$B$H$b$G$-$^$9!#5$$,68$&!<!#\e(B
-
-\e$B8!::$HF1;~$KL@$i$+$K\e(B @code{spam-split} \e$B$r<B9T$9$k$H$7$F$b!":#$^$G$H$*\e(B
-\e$B$j\e(B @code{spam-use-regex-headers} \e$B$r\e(B @code{t} \e$B$K@_Dj$9$k$h$&$J8!::$r9T$C\e(B
-\e$B$F$$$J$1$l$P$J$j$^$;$s!#$J$<$J$i\e(B @file{spam.el} \e$B$rFI$_9~$`$H$-$K!"$"$J$?\e(B
-\e$B$,2?$N\e(B @code{spam-use-xyz} \e$BJQ?t$r@_Dj$7$F$$$k$+$K1~$8$?!"$$$/$D$+$N>r7o\e(B
-\e$BIU$-$NFI$_9~$_$,9T$o$l$k$+$i$G$9!#\e(B
-
-@emph{@acronym{IMAP} \e$BMxMQ<T$X$NCm0U\e(B}
-
-\e$B%X%C%@!<$@$1$G$O$J$/$F%a%C%;!<%8A4BN$K4p$E$$$FJ,3d$r9T$J$$$?$$>l9g$O!"%V!<\e(B
-\e$B%kJQ?t\e(B @code{nnimap-split-download-body} \e$B$,@_Dj$5$l$kI,MW$,$"$j$^$9!#%G%#\e(B
-\e$B%U%)%k%H$G$O!"\e(Bnnimap \e$B%P%C%/%(%s%I$O%a%C%;!<%8%X%C%@!<$@$1$r<h$j9~$_$^$9!#\e(B
-@code{spam-check-bogofilter}\e$B!"\e(B@code{spam-check-ifile} \e$B$^$?\e(B
-\e$B$O\e(B @code{spam-check-stat} (\e$B$=$l$i$NJ,3d4o$O%a%C%;!<%8$NK\J8A4BN$+$i>pJs\e(B
-\e$B$rF@$k\e(B) \e$B$r;H$&$J$i$P!"$3$NJQ?t$r@_Dj$7$J$1$l$P$J$j$^$;$s!#$=$l\e(B
-\e$B$O\e(B @acronym{IMAP} \e$B$NF0:n$rCY$/$7$F$7$^$$!"%f!<%6$rBeI=$9$k$N$K$U$5$o$7$$\e(B
-\e$B7hDj$G$O$J$$$N$G!"%G%#%U%)%k%H$G$O@_Dj$5$l$F$$$^$;$s!#\e(B
-
-@xref{Splitting in IMAP}.
-
-@emph{TODO: \e$B8=>u\e(B spam.el \e$B$O5-;v$r%P%C%/%(%s%I$KEjF~$9$k$3$H$@$1$r%5%]!<\e(B
-\e$B%H$7$^$9!#5-;v$,$b$O$d\e(B spam \e$B$^$?$O\e(B ham \e$B$G$O$J$$$H\e(B spam.el \e$B$KEA$($kJ}K!$O\e(B
-\e$B$"$j$^$;$s!#\e(B}
-
-@emph{TODO: spam.el \e$B$O$9$Y$F$NE}7W%G!<%?%Y!<%9$r71N}$9$k$?$a$N0lDjITJQ$N\e(B
-\e$BJ}K!$rDs6!$9$kI,MW$,$"$j$^$9!#$$$/$D$+$O$=$N5!G=$r<+A0$G;}$C$F$$$^$9$,!"\e(B
-\e$B$=$&$G$J$$$b$N$b$"$j$^$9!#\e(B}
+\e$B$N%K%e!<%9%0%k!<%W$N;EMM@_Dj$O\e(B @code{(REGEXP GROUP)} \e$B$N7A<0$NCM$r;}$A$^\e(B
+\e$B$9!#:G=*E*$J>l=j$O\e(B (\e$BC1?t$^$?$OJ#?t$N\e(B) \e$B%0%k!<%WL>$G$9!#\e(B
+@code{spam-process-destination} \e$B%Q%i%a!<%?$,@_Dj$5$l$F$$$J$$$H!"\e(Bspam \e$B5-\e(B
+\e$B;v$OC1$K4|8B@Z$l>C5n$5$l$^$9!#%0%k!<%WL>$O40A47A$G$"$k$3$H!"$9$J$o$A%0%k!<\e(B
+\e$B%W%P%C%U%!$G%0%k!<%WL>$NA0$K\e(B @samp{nntp:servername} \e$B$N$h$&$J$b$N$,8+$($k\e(B
+\e$B>l9g$O!"$3$3$G$b$=$l$r;H$&I,MW$,$"$j$^$9!#\e(B
+
+\e$B%0%k!<%W$^$?$O@55,I=8=$4$H$KJ#?t$N0\F0@h$r;XDj$G$-$k$3$H$KCmL\$7$F2<$5$$\e(B!
+\e$B$3$l$K$h$C$F\e(B spam \e$B5-;v$r@55,$N%a!<%k%0%k!<%W\e(B
+\e$B$H\e(B @emph{spam \e$B%H%l!<%K%s%0\e(B} \e$B%0%k!<%W$KAw$k$3$H$,$G$-$^$9!#\e(B
+
+@vindex spam-log-to-registry
+Ham \e$B$H\e(B spam \e$B$K4X$9$kLdBj$O!"\e(BGnus \e$B$,%G%#%U%)%k%H$G$O$3$N=hM}$rDI@W$7$F$/\e(B
+\e$B$l$J$$$3$H$G$9!#=hM}$5$l$?5-;v$rDI@W$7!"$+$DJ#?t2s$K$o$?$C$F=hM}$9$k$3$H\e(B
+\e$B$r2sHr$9$k$?$a$K\e(B @code{spam.el} \e$B$,\e(B @code{gnus-registry.el} \e$B$r;H$&$h$&$K!"\e(B
+@code{spam-log-to-registry} \e$BJQ?t$rM-8z$K$7$F$/$@$5$$!#EPO??t$r@)8B$9$k$H!"\e(B
+\e$B@)8B$,L5$$>l9g$N$h$&$KF0:n$7$J$$$3$H$r3P$($F$*$$$F2<$5$$!#\e(B
+
+@vindex spam-mark-only-unseen-as-spam
+Spam \e$B%0%k!<%W$K$"$k!"$^$@FI$^$l$?$3$H$,L5$$5-;v$@$1$K\e(B spam \e$B$N0u$rIU$1$?\e(B
+\e$B$$>l9g$O!"$3$NJQ?t$r%;%C%H$7$F2<$5$$!#%G%#%U%)%k%H$G$O%;%C%H$5$l$F$$$^$9!#\e(B
+\e$B$3$l$r\e(B nil \e$B$K$9$k$H!"L$FI$N5-;v$K$b\e(B spam \e$B0u$,IU$1$i$l$^$9!#\e(B
+
+@vindex spam-mark-ham-unread-before-move-from-spam-group
+Ham \e$B$,\e(B spam \e$B%0%k!<%W$+$i0\F0$5$l$kA0$K0u$r>C$7$?$$>l9g$O!"$3$NJQ?t$r%;%C\e(B
+\e$B%H$7$F2<$5$$!#$3$l$O\e(B ham \e$B$K0u$rIU$1$k$?$a$K2D;k\e(B (tick) \e$B0u$N$h$&$J$b$N$r\e(B
+\e$B;H$&>l9g$K!"$H$F$bLr$KN)$A$^$9!#5-;v$O$"$?$+$b$=$l$,%a!<%k%5!<%P$r=P$?$P\e(B
+\e$B$+$j$N$h$&$K!"L50u$G\e(B ham \e$B=hM}>l$KCV$+$l$k$G$7$g$&!#\e(B
+
+@vindex spam-autodetect-recheck-messages
+\e$B$3$NJQ?t$O\e(B @code{spam.el} \e$B$,\e(B spam \e$B$N<+F08!CN$r9T$J$&>l9g$K!"$^$@FI$^$l$?\e(B
+\e$B$3$H$,L5$$5-;v$@$1!"$^$?$O$9$Y$F$NL$FI5-;v$N\e(B spam \e$B8!::$r9T$J$&$+$I$&$+$r\e(B
+\e$B;X<($7$^$9!#$3$l$O$=$N$^$^$K$7$F$*$/$3$H$r4+$a$^$9!#\e(B
+
+@node Spam ELisp Package Configuration Examples
+@subsubsection Spam ELisp Package Configuration Examples
+@cindex spam filtering
+@cindex spam filtering configuration examples
+@cindex spam configuration examples
+@cindex spam
-\e$B0J2<$O\e(B @code{spam-split} \e$B$NF0:n$r@)8f$9$k$?$a$K;H$&$3$H$,$G$-$k3F<o$NJ}\e(B
-\e$BK!$H!"$=$l$i$KBP1~$9$k\e(B spam \e$B$H\e(B ham \e$B$N%W%m%;%C%5!<$G$9\e(B:
-
-@menu
-* Blacklists and Whitelists::
-* BBDB Whitelists::
-* Gmane Spam Reporting::
-* Anti-spam Hashcash Payments::
-* Blackholes::
-* Regular Expressions Header Matching::
-* Bogofilter::
-* ifile spam filtering::
-* spam-stat spam filtering::
-* SpamOracle::
-* Extending the spam elisp package::
-@end menu
+@emph{TODO}: \e$BF|:";H$&$?$a$N@bL@IU$-$G@_DjNc$r2C$($k!#\e(B
@node Blacklists and Whitelists
@subsubsection \e$B%V%i%C%/%j%9%H$H%[%o%$%H%j%9%H\e(B
\e$B$,%0%k!<%W$N\e(B @code{spam-process} \e$B%Q%i%a!<%?$K2C$($i$l$k$H!"\e(Bspam \e$B0u$,IU$$\e(B
\e$B$?5-;v$NAw?.<T$,%V%i%C%/%j%9%H$KDI2C$5$l$^$9!#\e(B
+@emph{\e$B7Y9p\e(B}
+
+\e$BGQ$l$?\e(B @code{gnus-group-spam-exit-processor-blacklist} \e$B$NBe$o$j$K!"\e(B
+@code{'(spam spam-use-blacklist)} \e$B$r;H$&$3$H$r?d>)$7$^$9!#$9$Y$FF1Ey$KF0\e(B
+\e$B:n$9$k$3$H$OJ]>Z$5$l$^$9!#\e(B
+
@end defvar
@defvar gnus-group-ham-exit-processor-whitelist
\e$B$N\e(B ham \e$B%W%m%;%C%5!<$O\e(B @emph{spam} \e$B$+\e(B @emph{\e$BL$J,N`\e(B} \e$B%0%k!<%W$K$O8z2L$r5Z\e(B
\e$B$\$5$J$$$3$H$KCm0U$7$F2<$5$$!#\e(B
+@emph{\e$B7Y9p\e(B}
+
+\e$BGQ$l$?\e(B @code{gnus-group-ham-exit-processor-whitelist} \e$B$NBe$o$j$K!"\e(B
+@code{'(ham spam-use-whitelist)} \e$B$r;H$&$3$H$r?d>)$7$^$9!#$9$Y$FF1Ey$KF0\e(B
+\e$B:n$9$k$3$H$OJ]>Z$5$l$^$9!#\e(B
+
@end defvar
\e$B%V%i%C%/%j%9%H$O!"$"$J$?$,\e(B spam \e$B$NAw?.<T$@$H9M$($k%"%I%l%9$K9gCW$9$k@55,\e(B
\e$B%m%;%C%5!<$O\e(B @emph{spam} \e$B$+\e(B @emph{\e$BL$J,N`\e(B} \e$B%0%k!<%W$K$O8z2L$r5Z$\$5$J$$$3\e(B
\e$B$H$KCm0U$7$F2<$5$$!#\e(B
+@emph{\e$B7Y9p\e(B}
+
+\e$BGQ$l$?\e(B @code{gnus-group-ham-exit-processor-BBDB} \e$B$NBe$o$j$K!"\e(B
+@code{'(ham spam-use-BBDB)} \e$B$r;H$&$3$H$r?d>)$7$^$9!#$9$Y$FF1Ey$KF0:n$9$k\e(B
+\e$B$3$H$OJ]>Z$5$l$^$9!#\e(B
+
@end defvar
@node Gmane Spam Reporting
Gmane \e$B$O\e(B @uref{http://gmane.org} \e$B$G8+$D$1$k$3$H$,$G$-$^$9!#\e(B
+@emph{\e$B7Y9p\e(B}
+
+\e$BGQ$l$?\e(B @code{gnus-group-spam-exit-processor-report-gmane} \e$B$NBe$o$j$K!"\e(B
+@code{'(spam spam-use-gmane)} \e$B$r;H$&$3$H$r?d>)$7$^$9!#$9$Y$FF1Ey$KF0:n$9\e(B
+\e$B$k$3$H$OJ]>Z$5$l$^$9!#\e(B
+
@end defvar
@defvar spam-report-gmane-use-article-number
\e$B$O\e(B @code{gnus-spam-process-newsgroups} \e$BJQ?t$K2C$($F2<$5$$!#$3$N%7%s%\%k\e(B
\e$B$,%0%k!<%W$N\e(B @code{spam-process} \e$B%Q%i%a!<%?$K2C$($i$l$k$H!"\e(Bspam \e$B0u$,IU$$\e(B
\e$B$?5-;v$,\e(B bogofilter \e$B$N\e(B spam \e$B%G!<%?%Y!<%9$K2C$($i$^$9!#\e(B
+
+@emph{\e$B7Y9p\e(B}
+
+\e$BGQ$l$?\e(B @code{gnus-group-spam-exit-processor-bogofilter} \e$B$NBe$o$j$K!"\e(B
+@code{'(spam spam-use-bogofilter)} \e$B$r;H$&$3$H$r?d>)$7$^$9!#$9$Y$FF1Ey$K\e(B
+\e$BF0:n$9$k$3$H$OJ]>Z$5$l$^$9!#\e(B
@end defvar
@defvar gnus-group-ham-exit-processor-bogofilter
\e$B$?\e(B @emph{ham} \e$B%0%k!<%W$N5-;v$,Hs\e(B-spam \e$B5-;vMQ$N\e(B Bogofilter \e$B%G!<%?%Y!<%9$K\e(B
\e$BDI2C$5$l$^$9!#$3$N\e(B ham \e$B%W%m%;%C%5!<$O\e(B @emph{spam} \e$B$+\e(B @emph{\e$BL$J,N`\e(B} \e$B%0%k!<\e(B
\e$B%W$K$O8z2L$r5Z$\$5$J$$$3$H$KCm0U$7$F2<$5$$!#\e(B
+
+@emph{\e$B7Y9p\e(B}
+
+\e$BGQ$l$?\e(B @code{gnus-group-ham-exit-processor-bogofilter} \e$B$NBe$o$j$K!"\e(B
+@code{'(ham spam-use-bogofilter)} \e$B$r;H$&$3$H$r?d>)$7$^$9!#$9$Y$FF1Ey$KF0\e(B
+\e$B:n$9$k$3$H$OJ]>Z$5$l$^$9!#\e(B
@end defvar
@defvar spam-bogofilter-database-directory
@code{spam-use-ifile} \e$B$K!"C1$J$k\e(B spam/\e$BHs\e(B-spam \e$B$G$O$J$/$F\e(B ifile \e$B$N$9$Y$F\e(B
\e$B$N%+%F%4%j!<$rM?$($F$b$i$$$?$$$J$i$P!"$3$NJQ?t$rM-8z$K$7$F2<$5$$!#$3$l$r\e(B
-\e$B;H$&>l9g$O!"$=$NJ88%$K=q$+$l$F$$$k$h$&$K\e(B ifile \e$B$r71N}$7$F$*$+$J$1$l$P$J\e(B
-\e$B$j$^$;$s!#\e(B
+\e$B;H$&>l9g$O!"$=$NJ88%$K=q$+$l$F$$$k$h$&$K\e(B ifile \e$B$r%H%l!<%K%s%0$7$F$*$+$J\e(B
+\e$B$1$l$P$J$j$^$;$s!#\e(B
@end defvar
\e$B$O\e(B @code{gnus-spam-process-newsgroups} \e$BJQ?t$K2C$($F2<$5$$!#$3$N%7%s%\%k\e(B
\e$B$,%0%k!<%W$N\e(B @code{spam-process} \e$B%Q%i%a!<%?$K2C$($i$l$k$H!"\e(Bspam \e$B0u$,IU$$\e(B
\e$B$?5-;v$,\e(B spam \e$B5-;vMQ$N\e(B spam-stat \e$B%G!<%?%Y!<%9$KDI2C$5$l$^$9!#\e(B
+
+@emph{\e$B7Y9p\e(B}
+
+\e$BGQ$l$?\e(B @code{gnus-group-spam-exit-processor-stat} \e$B$NBe$o$j$K!"\e(B
+@code{'(spam spam-use-stat)} \e$B$r;H$&$3$H$r?d>)$7$^$9!#$9$Y$FF1Ey$KF0:n$9\e(B
+\e$B$k$3$H$OJ]>Z$5$l$^$9!#\e(B
@end defvar
@defvar gnus-group-ham-exit-processor-stat
\e$B$?\e(B @emph{ham} \e$B%0%k!<%W$N5-;v$,Hs\e(B-spam \e$B5-;vMQ$N\e(B spam-stat \e$B%G!<%?%Y!<%9$K\e(B
\e$BDI2C$5$l$^$9!#$3$N\e(B ham \e$B%W%m%;%C%5!<$O\e(B @emph{spam} \e$B$+\e(B @emph{\e$BL$J,N`\e(B} \e$B%0%k!<\e(B
\e$B%W$K$O8z2L$r5Z$\$5$J$$$3$H$KCm0U$7$F2<$5$$!#\e(B
+
+@emph{\e$B7Y9p\e(B}
+
+\e$BGQ$l$?\e(B @code{gnus-group-ham-exit-processor-stat} \e$B$NBe$o$j$K!"\e(B
+@code{'(ham spam-use-stat)} \e$B$r;H$&$3$H$r?d>)$7$^$9!#$9$Y$FF1Ey$KF0:n$9$k\e(B
+\e$B$3$H$OJ]>Z$5$l$^$9!#\e(B
@end defvar
\e$B$3$l$O\e(B @file{spam.el} \e$B$,\e(B @file{spam-stat.el} \e$B$HF/$-9g$&$3$H$r2DG=$K$7$^\e(B
@end defvar
SpamOracle \e$B$O%a%C%;!<%8$,\e(B spam \e$B$+\e(B ham \e$B$+$r8+6K$a$k$?$a$KE}7WE*$J<jK!$r;H\e(B
-\e$B$$$^$9!#4V0c$$$d8+F($7$N>/$J$$NI$$7k2L$rF@$k$?$a$K!"\e(BSpamOracle \e$B$O71N}$r\e(B
-\e$BI,MW$H$7$^$9!#\e(BSpamOracle \e$B$O\e(B spam \e$B%a!<%k$NFCD'$r3X$S$^$9!#\e(B@emph{add} \e$B%b!<\e(B
-\e$B%I\e(B (\e$B71N}%b!<%I\e(B) \e$B$r;H$C$F!"NI$$%a!<%k\e(B (ham) \e$B$H\e(B spam \e$B$r\e(B SpamOracle \e$B$KM?$(\e(B
-\e$B$J$1$l$P$J$j$^$;$s!#$3$l$O!"35N,%P%C%U%!$G\e(B @kbd{|} \e$B$r2!$9$3$H$K$h$C$F%a!<\e(B
-\e$B%k$r\e(B SpamOracle \e$B$N%W%m%;%9$K%Q%$%W$9$k$+!"$^$?\e(B
-\e$B$O\e(B @file{spam.el} \e$B$N\e(B spam \e$B$*$h$S\e(B ham \e$B%W%m%;%C%5!<$r;H$&$3$H$K$h$C$F9T$J\e(B
-\e$B$&$3$H$,$G$-$^$9!"\e(B@xref{Filtering Spam Using The Spam ELisp Package}.
+\e$B$$$^$9!#4V0c$$$d8+F($7$N>/$J$$NI$$7k2L$rF@$k$?$a$K!"\e(BSpamOracle \e$B$O%H%l!<\e(B
+\e$B%K%s%0$rI,MW$H$7$^$9!#\e(BSpamOracle \e$B$O\e(B spam \e$B%a!<%k$NFCD'$r3X$S$^$9!#\e(B
+@emph{add} \e$B%b!<%I\e(B (\e$B%H%l!<%K%s%0!&%b!<%I\e(B) \e$B$r;H$C$F!"NI$$%a!<\e(B
+\e$B%k\e(B (ham) \e$B$H\e(B spam \e$B$r\e(B SpamOracle \e$B$KM?$($J$1$l$P$J$j$^$;$s!#$3$l$O!"35N,%P%C\e(B
+\e$B%U%!$G\e(B @kbd{|} \e$B$r2!$9$3$H$K$h$C$F%a!<%k$r\e(B SpamOracle \e$B$N%W%m%;%9$K%Q%$%W\e(B
+\e$B$9$k$+!"$^$?$O\e(B @file{spam.el} \e$B$N\e(B spam \e$B$*$h$S\e(B ham \e$B%W%m%;%C%5!<$r;H$&$3$H\e(B
+\e$B$K$h$C$F9T$J$&$3$H$,$G$-$^$9!"\e(B@xref{Filtering Spam Using The Spam ELisp
+Package}.
@defvar gnus-group-spam-exit-processor-spamoracle
\e$B$3$N%7%s%\%k$r!"%0%k!<%W%Q%i%a!<%?$N%+%9%?%^%$%:$K$h$C$F%0%k!<%W\e(B
\e$B$O\e(B @code{gnus-spam-process-newsgroups} \e$BJQ?t$K2C$($F2<$5$$!#$3$N%7%s%\%k\e(B
\e$B$,%0%k!<%W$N\e(B @code{spam-process} \e$B%Q%i%a!<%?$K2C$($i$l$k$H!"\e(Bspam \e$B0u$,IU$$\e(B
\e$B$?5-;v$,\e(B spam \e$B$N%5%s%W%k$H$7$F\e(B SpamOracle \e$B$KAw$i$l$^$9!#\e(B
+
+@emph{\e$B7Y9p\e(B}
+
+\e$BGQ$l$?\e(B @code{gnus-group-spam-exit-processor-spamoracle} \e$B$NBe$o$j$K!"\e(B
+@code{'(spam spam-use-spamoracle)} \e$B$r;H$&$3$H$r?d>)$7$^$9!#$9$Y$FF1Ey$K\e(B
+\e$BF0:n$9$k$3$H$OJ]>Z$5$l$^$9!#\e(B
@end defvar
@defvar gnus-group-ham-exit-processor-spamoracle
\e$B$F\e(B SpamOracle \e$B$KAw$i$l$^$9!#$3$N\e(B ham \e$B%W%m%;%C%5!<\e(B
\e$B$O\e(B @emph{spam} \e$B$+\e(B @emph{\e$BL$J,N`\e(B} \e$B%0%k!<%W$K$O8z2L$r5Z$\$5$J$$$3$H$KCm0U$7\e(B
\e$B$F2<$5$$!#\e(B
+
+@emph{\e$B7Y9p\e(B}
+
+\e$BGQ$l$?\e(B @code{gnus-group-ham-exit-processor-spamoracle} \e$B$NBe$o$j$K!"\e(B
+@code{'(ham spam-use-spamoracle)} \e$B$r;H$&$3$H$r?d>)$7$^$9!#$9$Y$FF1Ey$KF0\e(B
+\e$B:n$9$k$3$H$OJ]>Z$5$l$^$9!#\e(B
@end defvar
@emph{\e$BNc\e(B:} \e$B$3$l$i$O\e(B ham \e$B%0%k!<%W$H$7$FJ,N`$5$l$?!"$D$^$j\e(B ham \e$B$N5-;v$7$+\e(B
@example
((spam-contents gnus-group-spam-classification-ham)
- (spam-process
- (gnus-group-spam-exit-processor-spamoracle)))
+ (spam-process ((ham spam-use-spamoracle)
+ (spam spam-use-spamoracle))))
@end example
-\e$B$3$N%0%k!<%W$G$O\e(B @code{gnus-group-spam-exit-processor-spamoracle} \e$B$,;E;v\e(B
-\e$B$r$7$^$9!#$3$N%0%k!<%W$K\e(B spam \e$B5-;v$,$"$C$F\e(B (SpamOracle \e$B$,==J,$J%5%s%W%k\e(B
-\e$B$r?)$Y$5$;$F$b$i$C$F$$$J$1$l$P!"$=$&$J$j$^$9$M\e(B)\e$B!"$+$D%f!<%6$,$$$/$D$+$N\e(B
-\e$B5-;v$K\e(B spam \e$B$N0u$rIU$1$?$J$i$P!"$=$l$i$N5-;v\e(B
-\e$B$O\e(B @code{gnus-group-spam-exit-processor-spamoracle} \e$B$K$h$C$F=hM}$5$l$^$9!#\e(B
-\e$B$3$N%W%m%;%C%5!<$O!"?7$7$$\e(B spam \e$B$N%5%s%W%k$H$7$F\e(B SpamOracle \e$B$K5-;v$rAw$j\e(B
-\e$B$^$9!#\e(B
+\e$B$3$N%0%k!<%W$G$O\e(B @code{spam-use-spamoracle} \e$B$,\e(B ham \e$B$H\e(B spam \e$BN>J}$N=hM}$r\e(B
+\e$B9T$J$$$^$9!#$3$N%0%k!<%W$K\e(B spam \e$B5-;v$,$"$C$F\e(B (SpamOracle \e$B$,==J,$J%5%s%W\e(B
+\e$B%k$r?)$Y$5$;$F$b$i$C$F$$$J$1$l$P!"$=$&$J$j$^$9$M\e(B)\e$B!"$+$D%f!<%6$,$$$/$D$+\e(B
+\e$B$N5-;v$K\e(B spam \e$B$N0u$rIU$1$?$J$i$P!"$=$l$i$N5-;v$O\e(B SpamOracle \e$B$K$h$C$F=hM}\e(B
+\e$B$5$l$^$9!#$=$N%W%m%;%C%5!<$O!"?7$7$$\e(B spam \e$B$N%5%s%W%k$H$7$F\e(B SpamOracle \e$B$K\e(B
+\e$B5-;v$rAw$j$^$9!#\e(B
-@node Extending the spam elisp package
-@subsubsection Spam elisp \e$B%Q%C%1!<%8$N3HD%\e(B
+@node Extending the Spam ELisp package
+@subsubsection Spam ELisp \e$B%Q%C%1!<%8$N3HD%\e(B
@cindex spam filtering
@cindex spam elisp package, extending
@cindex extending the spam elisp package
(spam-use-blackbox . spam-check-blackbox)
@end example
+\e$B$rDI2C!#\e(B@code{spam-list-of-processors} \e$B$K\e(B
+
+@example
+ (gnus-group-ham-exit-processor-blackbox ham spam-use-blackbox)
+ (gnus-group-spam-exit-processor-blackbox spam spam-use-blackbox)
+@end example
+
+\e$B$rDI2C!#\e(B@code{spam-registration-functions} \e$B$K\e(B
+
+@example
+ (spam-use-blackbox spam-blackbox-register-routine
+ nil
+ spam-blackbox-unregister-routine
+ nil)
+@end example
+
\e$B$rDI2C!#\e(B
+\e$B<j;O$a$K\e(B bogofilter \e$B$NEPO?\e(B/\e$B:o=|%k!<%A%s$r;H$C$FEPO?\e(B/\e$B:o=|%k!<%A%s$r!"$^$?\e(B
+\e$B$O$b$C$H\e(B Blackbox \e$B$KE,@Z$JB>$NEPO?\e(B/\e$B:o=|%k!<%A%s$r=q$$$F2<$5$$!#\e(B
+
@item
\e$B4X?t\e(B
@code{spam-check-blackbox} \e$B4X?t$r=q$$$F2<$5$$!#$=$l\e(B
-\e$B$O\e(B @samp{nil} \e$B$+\e(B @code{spam-split-group} \e$B$rJV$5$J$1$l$P$J$j$^$;$s!#$"$J\e(B
-\e$B$?$K$G$-$k$3$H$NNc$O!"4{B8$N\e(B @code{spam-check-*} \e$B4X?t$r;2>H$7$F$/$@$5$$!#\e(B
+\e$B$OB>$N=,47$KJo$C$F\e(B @samp{nil} \e$B$+\e(B @code{spam-split-group} \e$B$rJV$5$J$1$l$P\e(B
+\e$B$J$j$^$;$s!#$"$J$?$K$G$-$k$3$H$NNc$O!"4{B8$N\e(B @code{spam-check-*} \e$B4X?t$r\e(B
+\e$B;2>H$7$F$/$@$5$$!#$^$?!"$"$J$?$,$=$&$G$J$$M}M3$r40A4$KM}2r$7$F$$$J$$$J$i\e(B
+\e$B$P!"%F%s%W%l!<%H$Ksv$jIU$$$F2<$5$$!#\e(B
\e$B%V%i%C%/%\%C%/%9$,!"$=$l$,F0:n$9$k$?$a$K%a%C%;!<%8A4BN$rI,MW$H$9$kE}7WE*\e(B
\e$B%a!<%kJ,@O4o$G$"$k$N$J$i$P!"\e(B
Blackbox \e$B$,\e(B spam \e$B$^$?$O\e(B ham \e$B$N=hM}$r%5%]!<%H$9$k>l9g$@$1!"$=$l$i$rMQ0U$7\e(B
\e$B$F2<$5$$!#\e(B
+\e$B$5$i$K\e(B ham \e$B$H\e(B spam \e$B$N%W%m%;%C%5!<$OC10l$NJQ?t$G$O$J$/$5$l$D$D$"$j!"Be$o\e(B
+\e$B$j$K\e(B @code{'(spam spam-use-blackbox)} \e$B$^$?\e(B
+\e$B$O\e(B @code{'(ham spam-use-blackbox)} \e$B$N7A<0$,?d>)$5$l$^$9!#:#$N$H$3\e(B
+\e$B$m\e(B spam/ham \e$B%W%m%;%C%5!<JQ?t$O$^$@$"$A$3$A$K$"$j$^$9$,!"D9$/$O$"$j$^$;$s!#\e(B
+
@lisp
-(defvar gnus-group-spam-exit-processor-blackbox "blackbox"
+(defvar gnus-group-spam-exit-processor-blackbox "blackbox-spam"
"\e$B35N,$r=P$k$H$-$K8F$P$l$k\e(B blackbox \e$B$N\e(B spam \e$B%W%m%;%C%5!<!#\e(B
Spam \e$B%0%k!<%W$@$1$KE,MQ$5$l$k!#\e(B")
-(defvar gnus-group-ham-exit-processor-blackbox "blackbox"
+(defvar gnus-group-ham-exit-processor-blackbox "blackbox-ham"
"\e$B35N,$r=P$k$H$-$K8F$P$l$k\e(B blackbox \e$B$N\e(B ham \e$B%W%m%;%C%5!<!#\e(B
Spam \e$B$G$O$J$$\e(B (\e$BL$J,N`$^$?$O\e(B ham) \e$B%0%k!<%W$@$1$KE,MQ$5$l$k!#\e(B")
@end lisp
@item
-\e$B4X?t\e(B
+Gnus \e$B$N%Q%i%a!<%?\e(B
-@lisp
-(defun spam-blackbox-register-spam-routine ()
- (spam-generic-register-routine
- ;; @r{spam \e$BMQ$N4X?t\e(B}
- (lambda (article)
- (let ((from (spam-fetch-field-from-fast article)))
- (when (stringp from)
- (blackbox-do-something-with-this-spammer from))))
- ;; @r{ham \e$BMQ$N4X?t\e(B}
- nil))
-
-(defun spam-blackbox-register-ham-routine ()
- (spam-generic-register-routine
- ;; @r{spam \e$BMQ$N4X?t\e(B}
- nil
- ;; @r{ham \e$BMQ$N4X?t\e(B}
- (lambda (article)
- (let ((from (spam-fetch-field-from-fast article)))
- (when (stringp from)
- (blackbox-do-something-with-this-ham-sender from))))))
-@end lisp
-
-\e$B4X?t\e(B @code{blackbox-do-something-with-this-ham-sender} \e$B$*$h\e(B
-\e$B$S\e(B @code{blackbox-do-something-with-this-spammer} \e$B$r=q$$$F2<$5$$!#%a%C%;!<\e(B
-\e$B%8$NAw?.<T$r<h$j=P$9$h$j$bJ#;($J%3!<%I$rDI2C$9$k$3$H$O2DG=$G$9$,!"%a%C%;!<\e(B
-\e$B%8A4BN$N<h$j9~$_$O!"\e(B@code{spam-fetch-field-from-fast} \e$B$GAw?.<T$r<h$j=P\e(B
-\e$B$9\e(B (\e$B%a%C%;!<%8$NAw?.<T$O\e(B gnus \e$B$K$h$C$F5-21$5$l$F$$$k\e(B) \e$B$h$j$bCx$7$/D9$/$+\e(B
-\e$B$+$k$3$H$r3P$($F$*$$$F2<$5$$!#\e(B
+@code{gnus.el} \e$B$K$"$k%0%k!<%W%Q%i%a!<%?\e(B @code{spam-process} \e$B$K\e(B
+
+@example
+ (const :tag "Spam: Blackbox" (spam spam-use-blackbox))
+ (const :tag "Ham: Blackbox" (ham spam-use-blackbox))
+@end example
+
+\e$B$r2C$($F2<$5$$!#$=$l$r%Q%i%a!<%?$HJQ?t$N%+%9%?%^%$%:$NFs2s$K$D$$$F9T$J$&\e(B
+\e$B$3$H$r3N$+$a$F2<$5$$!#\e(B
+
+@code{gnus.el} \e$B$N%0%k!<%W%Q%i%a!<%?\e(B @code{spam-autodetect-methods} \e$B$K\e(B
+
+@example
+ (variable-item spam-use-blackbox)
+@end example
+
+\e$B$r2C$($F2<$5$$!#\e(B
@end enumerate
XEmacs \e$B$O%Q%C%1!<%8$N=/=8$H$7$FG[I[$5$l$F$$$^$9!#\e(Bgnus \e$B$N\e(B XEmacs \e$B%Q%C%1!<\e(B
\e$B%8$,I,MW$H$9$k$b$N$O2?$G$"$l!"$"$J$?$O%$%s%9%H!<%k$9$Y$-$G$9!#:#$N$H$3$m\e(B
-\e$BI,MW$J$N$O\e(B @samp{gnus}, @samp{w3}, @samp{mh-e}, @samp{mailcrypt},
-@samp{rmail}, @samp{eterm}, @samp{mail-lib}, @samp{xemacs-base},
-@samp{sh-script} \e$B$*$h$S\e(B @samp{fsf-compat} \e$B$G$9!#%b!<%k%9I|9f$N$?$a$K\e(B
-\e$B$O\e(B @samp{misc-games} \e$B%Q%C%1!<%8$,I,MW$G$9!#\e(B
+\e$BI,MW$J$N$O\e(B @samp{gnus}, @samp{mail-lib}, @samp{xemacs-base},
+@samp{eterm}, @samp{sh-script}, @samp{net-utils}, @samp{os-utils},
+@samp{dired}, @samp{mh-e}, @samp{sieve}, @samp{ps-print}, @samp{w3},
+@samp{pgg}, @samp{mailcrypt}, @samp{ecrypto} \e$B$*$h$S\e(B @samp{sasl} \e$B$G$9!#\e(B
@node History
@section \e$BNr;K\e(B
@itemize @bullet
@item
+@code{gnus-group-read-ephemeral-group} \e$B$r\e(B @kbd{G M} \e$B%-!<$GBPOCE*$K8F$V$3\e(B
+\e$B$H$,$G$-$^$9!#\e(B
+
+@item
\e$B%I%i%U%H!&%0%k!<%W$G\e(B @kbd{e} \e$B%-!<$,\e(B @code{gnus-draft-edit-message} \e$B%3%^\e(B
\e$B%s%I$K3d$jEv$F$i$l$^$7$?!#\e(B@code{gnus-summary-edit-article} \e$B%3%^%s%I$K$O!"\e(B
\e$BBe$o$j$K\e(B @kbd{B w} \e$B%-!<$r;H$C$F2<$5$$!#\e(B
* Unread Articles:: Marks for unread articles.
* Read Articles:: Marks for read articles.
* Other Marks:: Marks that do not affect readedness.
-* Setting Marks:: How to set and remove marks.
-* Generic Marking Commands:: How to customize the marking.
-* Setting Process Marks:: How to mark articles for later processing.
+
+Marking Articles
+
+* Setting Marks:: How to set and remove marks.
+* Generic Marking Commands:: How to customize the marking.
+* Setting Process Marks:: How to mark articles for later processing.
Threading
Filtering Spam Using The Spam ELisp Package
-* Blacklists and Whitelists::
-* BBDB Whitelists::
-* Gmane Spam Reporting::
-* Anti-spam Hashcash Payments::
-* Blackholes::
-* Regular Expressions Header Matching::
-* Bogofilter::
-* ifile spam filtering::
-* spam-stat spam filtering::
-* SpamOracle::
-* Extending the spam elisp package::
+* Spam ELisp Package Sequence of Events::
+* Spam ELisp Package Filtering of Incoming Mail::
+* Spam ELisp Package Global Variables::
+* Spam ELisp Package Configuration Examples::
+* Blacklists and Whitelists::
+* BBDB Whitelists::
+* Gmane Spam Reporting::
+* Anti-spam Hashcash Payments::
+* Blackholes::
+* Regular Expressions Header Matching::
+* Bogofilter::
+* ifile spam filtering::
+* spam-stat spam filtering::
+* SpamOracle::
+* Extending the Spam ELisp package::
Filtering Spam Using Statistics with spam-stat
* Troubleshooting:: What you might try if things do not work.
* Gnus Reference Guide:: Rilly, rilly technical stuff.
* Emacs for Heathens:: A short introduction to Emacsian terms.
-* Frequently Asked Questions:: The Gnus FAQ.
+* Frequently Asked Questions:: The Gnus FAQ
History
for a name, a method and possibly an @dfn{address}. For an easier way
to subscribe to @acronym{NNTP} groups (@pxref{Browse Foreign Server}).
+@item G M
+@kindex G M (Group)
+@findex gnus-group-read-ephemeral-group
+Make an ephemeral group (@code{gnus-group-read-ephemeral-group}). Gnus
+will prompt you for a name, a method and an @dfn{address}.
+
@item G r
@kindex G r (Group)
@findex gnus-group-rename-group
want to use the standard posting method, use the @samp{a} symbolic
prefix (@pxref{Symbolic Prefixes}).
+Gnus ensures that only you can cancel your own messages using a
+@code{Cancel-Lock} header (@pxref{Canceling News, Canceling News, ,
+message, Message Manual}).
+
If you discover that you have made some mistakes and want to do some
corrections, you can post a @dfn{superseding} article that will replace
your original article.
@acronym{RSS} has a quite regular and nice interface, and it's
possible to get the information Gnus needs to keep groups updated.
+@kindex G R (Summary)
Use @kbd{G R} from the summary buffer to subscribe to a feed---you
will be prompted for the location of the feed.
@findex gnus-score-find-trace
Display all score rules that have been used on the current article
(@code{gnus-score-find-trace}). In the @code{*Score Trace*} buffer, you
-can use @kbd{q} to quit. @kbd{e} edits the corresponding score file.
-When point is on a string within the match element, @kbd{e} will try to
-bring you to this string in the score file.
+may type @kbd{e} to edit score file corresponding to the score rule on
+current line and @kbd{f} to format (@code{gnus-score-pretty-print}) the
+score file and edit it.
@item V w
@kindex V w (Summary)
@vindex gnus-score-mode-hook
@code{gnus-score-menu-hook} is run in score mode buffers.
-In the summary buffer you can use commands like @kbd{V f} and @kbd{V
-e} to begin editing score files.
+In the summary buffer you can use commands like @kbd{V f}, @kbd{V e} and
+@kbd{V t} to begin editing score files.
@node Adaptive Scoring
First, some background on spam.
If you have access to e-mail, you are familiar with spam (technically
-termed @acronym{UCE}, Unsolicited Commercial E-mail). Simply put, it exists
-because e-mail delivery is very cheap compared to paper mail, so only
-a very small percentage of people need to respond to an UCE to make it
-worthwhile to the advertiser. Ironically, one of the most common
-spams is the one offering a database of e-mail addresses for further
-spamming. Senders of spam are usually called @emph{spammers}, but terms like
-@emph{vermin}, @emph{scum}, and @emph{morons} are in common use as well.
+termed @acronym{UCE}, Unsolicited Commercial E-mail). Simply put, it
+exists because e-mail delivery is very cheap compared to paper mail,
+so only a very small percentage of people need to respond to an UCE to
+make it worthwhile to the advertiser. Ironically, one of the most
+common spams is the one offering a database of e-mail addresses for
+further spamming. Senders of spam are usually called @emph{spammers},
+but terms like @emph{vermin}, @emph{scum}, @emph{sociopaths}, and
+@emph{morons} are in common use as well.
Spam comes from a wide variety of sources. It is simply impossible to
dispose of all spam without discarding useful messages. A good
requires its users to have a basic understanding of e-mail delivery
and processing.
-The simplest approach to filtering spam is filtering. If you get 200
-spam messages per day from @samp{random-address@@vmadmin.com}, you
-block @samp{vmadmin.com}. If you get 200 messages about
-@samp{VIAGRA}, you discard all messages with @samp{VIAGRA} in the
-message. This, unfortunately, is a great way to discard legitimate
-e-mail. For instance, the very informative and useful RISKS digest
-has been blocked by overzealous mail filters because it
-@strong{contained} words that were common in spam messages.
-Nevertheless, in isolated cases, with great care, direct filtering of
-mail can be useful.
+The simplest approach to filtering spam is filtering, at the mail
+server or when you sort through incoming mail. If you get 200 spam
+messages per day from @samp{random-address@@vmadmin.com}, you block
+@samp{vmadmin.com}. If you get 200 messages about @samp{VIAGRA}, you
+discard all messages with @samp{VIAGRA} in the message. If you get
+lots of spam from China, for example, you try to filter all mail from
+Chinese IPs.
+
+This, unfortunately, is a great way to discard legitimate e-mail. For
+instance, the very informative and useful RISKS digest has been
+blocked by overzealous mail filters because it @strong{contained}
+words that were common in spam messages. The risks of blocking a
+whole country from contacting you should also be obvious, so don't do
+it if you have the choice. Nevertheless, in isolated cases, with
+great care, direct filtering of mail can be useful.
Another approach to filtering e-mail is the distributed spam
processing, for instance DCC implements such a system. In essence,
@var{N} systems around the world agree that a machine @var{X} in
-China, Ghana, or California is sending out spam e-mail, and these
-@var{N} systems enter @var{X} or the spam e-mail from @var{X} into
-a database. The criteria for spam detection vary---it may be the
-number of messages sent, the content of the messages, and so on. When
-a user of the distributed processing system wants to find out if a
-message is spam, he consults one of those @var{N} systems.
+Ghana, Estonia, or California is sending out spam e-mail, and these
+@var{N} systems enter @var{X} or the spam e-mail from @var{X} into a
+database. The criteria for spam detection vary---it may be the number
+of messages sent, the content of the messages, and so on. When a user
+of the distributed processing system wants to find out if a message is
+spam, he consults one of those @var{N} systems.
Distributed spam processing works very well against spammers that send
a large number of messages at once, but it requires the user to set up
fairly complicated checks. There are commercial and free distributed
spam processing systems. Distributed spam processing has its risks as
well. For instance legitimate e-mail senders have been accused of
-sending spam, and their web sites have been shut down for some time
-because of the incident.
+sending spam, and their web sites and mailing lists have been shut
+down for some time because of the incident.
The statistical approach to spam filtering is also popular. It is
based on a statistical analysis of previous spam messages. Usually
analysis of spam works very well in most of the cases, but it can
classify legitimate e-mail as spam in some cases. It takes time to
run the analysis, the full message must be analyzed, and the user has
-to store the database of spam analyses.
+to store the database of spam analyses. Statistical analysis on the
+server is gaining popularity. This has the advantage of letting the
+user Just Read Mail, but has the disadvantage that it's harder to tell
+the server that it has misclassified mail.
+
+Fighting spam is not easy, no matter what anyone says. There is no
+magic switch that will distinguish Viagra ads from Mom's e-mails.
+Even people are having a hard time telling spam apart from non-spam,
+because spammers are actively looking to fool us into thinking they
+are Mom, essentially. Spamming is irritating, irresponsible, and
+idiotic behavior from a bunch of people who think the world owes them
+a favor. We hope the following sections will help you in fighting the
+spam plague.
@node Anti-Spam Basics
@subsection Anti-Spam Basics
spam. It's a win-win situation. Forging @code{From} headers to point
to non-existent domains is yucky, in my opinion.
+Be careful with this approach. Spammers are wise to it.
@node SpamAssassin
@cindex Vipul's Razor
@cindex DCC
-The days where the hints in the previous section was sufficient in
+The days where the hints in the previous section were sufficient in
avoiding spam are coming to an end. There are many tools out there
that claim to reduce the amount of spam you get. This section could
easily become outdated fast, as new products replace old, but
though this section will use SpamAssassin as an example, it should be
easy to adapt it to most other tools.
+Note that this section does not involve the @code{spam.el} package,
+which is discussed in the next section. If you don't care for all
+the features of @code{spam.el}, you can make do with these simple
+recipes.
+
If the tool you are using is not installed on the mail server, you
need to invoke it yourself. Ideas on how to use the
@code{:postscript} mail source parameter (@pxref{Mail Source
new form of spam appears. This means that a small percentage of spam
will always get through. It also means that somewhere, someone needs
to read lots of spam to update these tools. Hashcash avoids that, but
-instead requires that everyone you communicate with supports the
+instead prefers that everyone you contact through e-mail supports the
scheme. You can view the two approaches as pragmatic vs dogmatic.
The approaches have their own advantages and disadvantages, but as
often in the real world, a combination of them is stronger than either
The idea behind @file{spam.el} is to have a control center for spam detection
and filtering in Gnus. To that end, @file{spam.el} does two things: it
-filters incoming mail, and it analyzes mail known to be spam or ham.
+filters new mail, and it analyzes mail known to be spam or ham.
@dfn{Ham} is the name used throughout @file{spam.el} to indicate
non-spam messages.
So, what happens when you load @file{spam.el}?
+First, some hooks will get installed by @code{spam-initialize}. There
+are some hooks for @code{spam-stat} so it can save its databases, and
+there are hooks so interesting things will happen when you enter and
+leave a group. More on the sequence of events later (@pxref{Spam
+ELisp Package Sequence of Events}).
+
You get the following keyboard commands:
@table @kbd
variables. Try @code{customize-group} on the @samp{spam} variable
group.
+@menu
+* Spam ELisp Package Sequence of Events::
+* Spam ELisp Package Filtering of Incoming Mail::
+* Spam ELisp Package Global Variables::
+* Spam ELisp Package Configuration Examples::
+* Blacklists and Whitelists::
+* BBDB Whitelists::
+* Gmane Spam Reporting::
+* Anti-spam Hashcash Payments::
+* Blackholes::
+* Regular Expressions Header Matching::
+* Bogofilter::
+* ifile spam filtering::
+* spam-stat spam filtering::
+* SpamOracle::
+* Extending the Spam ELisp package::
+@end menu
+
+@node Spam ELisp Package Sequence of Events
+@subsubsection Spam ELisp Package Sequence of Events
+@cindex spam filtering
+@cindex spam filtering sequence of events
+@cindex spam
+
+You must read this section to understand how @code{spam.el} works.
+Do not skip, speed-read, or glance through this section.
+
+There are two @emph{contact points}, if you will, between
+@code{spam.el} and the rest of Gnus: checking new mail for spam, and
+leaving a group.
+
+Getting new mail is done in one of two ways. You can either split
+your incoming mail or you can classify new articles as ham or spam
+when you enter the group.
+
+Splitting incoming mail is better suited to mail backends such as
+@code{nnml} or @code{nnimap} where new mail appears in a single file
+called a @dfn{Spool File}. See @xref{Spam ELisp Package Filtering of
+Incoming Mail}.
+
+For backends such as @code{nntp} there is no incoming mail spool, so
+an alternate mechanism must be used. This may also happen for
+backends where the server is in charge of splitting incoming mail, and
+Gnus does not do further splitting. The @code{spam-autodetect} and
+@code{spam-autodetect-methods} group parameters (accessible with
+@kbd{G c} and @kbd{G p} as usual), and the corresponding variables
+@code{gnus-spam-autodetect-methods} and
+@code{gnus-spam-autodetect-methods} (accessible with @kbd{M-x
+customize-variable} as usual).
+
+When @code{spam-autodetect} is used, it hooks into the process of
+entering a group. Thus, entering a group with unseen or unread
+articles becomes the substitute for checking incoming mail. Whether
+only unseen articles or all unread articles will be processed is
+determined by the @code{spam-autodetect-recheck-messages}. When set
+to t, unread messages will be rechecked.
+
+@code{spam-autodetect} grants the user at once more and less control
+of spam filtering. The user will have more control over each group's
+spam methods, so for instance the @samp{ding} group may have
+@code{spam-use-BBDB} as the autodetection method, while the
+@samp{suspect} group may have the @code{spam-use-blacklist} and
+@code{spam-use-bogofilter} methods enabled. Every article detected to
+be spam will be marked with the spam mark @samp{$} and processed on
+exit from the group as normal spam. The user has less control over
+the @emph{sequence} of checks, as he might with @code{spam-split}.
+
+When the newly split mail goes into groups, or messages are
+autodetected to be ham or spam, those groups must be exited (after
+entering, if needed) for further spam processing to happen. It
+matters whether the group is considered a ham group, a spam group, or
+is unclassified, based on its @code{spam-content} parameter
+(@pxref{Spam ELisp Package Global Variables}). Spam groups have the
+additional characteristic that, when entered, any unseen or unread
+articles (depending on the @code{spam-mark-only-unseen-as-spam}
+variable) will be marked as spam. Thus, mail split into a spam group
+gets automatically marked as spam when you enter the group.
+
+So, when you exit a group, the @code{spam-processors} are applied, if
+any are set, and the processed mail is moved to the
+@code{ham-process-destination} or the @code{spam-process-destination}
+depending on the article's classification. If the
+@code{ham-process-destination} or the @code{spam-process-destination},
+whichever is appropriate, are nil, the article is left in the current
+group.
+
+If a spam is found in any group (this can be changed to only non-spam
+groups with @code{spam-move-spam-nonspam-groups-only}), it is
+processed by the active @code{spam-processors} (@pxref{Spam ELisp
+Package Global Variables}) when the group is exited. Furthermore, the
+spam is moved to the @code{spam-process-destination} (@pxref{Spam
+ELisp Package Global Variables}) for further training or deletion.
+You have to load the @code{gnus-registry.el} package and enable the
+@code{spam-log-to-registry} variable if you want spam to be processed
+no more than once. Thus, spam is detected and processed everywhere,
+which is what most people want.
+
+If a ham mail is found in a ham group, as determineed by the
+@code{ham-marks} parameter, it is processed as ham by the active ham
+@code{spam-processor} when the group is exited. With the variables
+@code{spam-process-ham-in-spam-groups} and
+@code{spam-process-ham-in-nonham-groups} the behavior can be further
+altered so ham found anywhere can be processed. You have to load the
+@code{gnus-registry.el} package and enable the
+@code{spam-log-to-registry} variable if you want ham to be processed
+no more than once. Thus, ham is detected and processed only when
+necessary, which is what most people want. More on this in
+@xref{Spam ELisp Package Configuration Examples}.
+
+If all this seems confusing, don't worry. Soon it will be as natural
+as typing Lisp one-liners on a neural interface... err, sorry, that's
+50 years in the future yet. Just trust us, it's not so bad.
+
+@node Spam ELisp Package Filtering of Incoming Mail
+@subsubsection Spam ELisp Package Filtering of Incoming Mail
+@cindex spam filtering
+@cindex spam filtering incoming mail
+@cindex spam
+
+To use the @file{spam.el} facilities for incoming mail filtering, you
+must add the following to your fancy split list
+@code{nnmail-split-fancy} or @code{nnimap-split-fancy}:
+
+@example
+(: spam-split)
+@end example
+
+Note that the fancy split may be called @code{nnmail-split-fancy} or
+@code{nnimap-split-fancy}, depending on whether you use the nnmail or
+nnimap back ends to retrieve your mail.
+
+The @code{spam-split} function will process incoming mail and send the
+mail considered to be spam into the group name given by the variable
+@code{spam-split-group}. By default that group name is @samp{spam},
+but you can customize @code{spam-split-group}. Make sure the contents
+of @code{spam-split-group} are an @emph{unqualified} group name, for
+instance in an @code{nnimap} server @samp{your-server} the value
+@samp{spam} will turn out to be @samp{nnimap+your-server:spam}. The
+value @samp{nnimap+server:spam}, therefore, is wrong and will
+actually give you the group
+@samp{nnimap+your-server:nnimap+server:spam} which may or may not
+work depending on your server's tolerance for strange group names.
+
+You can also give @code{spam-split} a parameter,
+e.g. @samp{'spam-use-regex-headers} or @samp{"maybe-spam"}. Why is
+this useful?
+
+Take these split rules (with @code{spam-use-regex-headers} and
+@code{spam-use-blackholes} set):
+
+@example
+ nnimap-split-fancy '(|
+ (any "ding" "ding")
+ (: spam-split)
+ ;; default mailbox
+ "mail")
+@end example
+
+Now, the problem is that you want all ding messages to make it to the
+ding folder. But that will let obvious spam (for example, spam
+detected by SpamAssassin, and @code{spam-use-regex-headers}) through,
+when it's sent to the ding list. On the other hand, some messages to
+the ding list are from a mail server in the blackhole list, so the
+invocation of @code{spam-split} can't be before the ding rule.
+
+You can let SpamAssassin headers supersede ding rules, but all other
+@code{spam-split} rules (including a second invocation of the
+regex-headers check) will be after the ding rule:
+
+@example
+ nnimap-split-fancy '(|
+;;; all spam detected by spam-use-regex-headers goes to "regex-spam"
+ (: spam-split "regex-spam" 'spam-use-regex-headers)
+ (any "ding" "ding")
+;;; all other spam detected by spam-split goes to spam-split-group
+ (: spam-split)
+ ;; default mailbox
+ "mail")
+@end example
+
+This lets you invoke specific @code{spam-split} checks depending on
+your particular needs, and to target the results of those checks to a
+particular spam group. You don't have to throw all mail into all the
+spam tests. Another reason why this is nice is that messages to
+mailing lists you have rules for don't have to have resource-intensive
+blackhole checks performed on them. You could also specify different
+spam checks for your nnmail split vs. your nnimap split. Go crazy.
+
+You should still have specific checks such as
+@code{spam-use-regex-headers} set to @code{t}, even if you
+specifically invoke @code{spam-split} with the check. The reason is
+that when loading @file{spam.el}, some conditional loading is done
+depending on what @code{spam-use-xyz} variables you have set. This
+is usually not critical, though.
+
+@emph{Note for IMAP users}
+
+The boolean variable @code{nnimap-split-download-body} needs to be
+set, if you want to split based on the whole message instead of just
+the headers. By default, the nnimap back end will only retrieve the
+message headers. If you use @code{spam-check-bogofilter},
+@code{spam-check-ifile}, or @code{spam-check-stat} (the splitters that
+can benefit from the full message body), you should set this variable.
+It is not set by default because it will slow @acronym{IMAP} down, and
+that is not an appropriate decision to make on behalf of the user.
+
+@xref{Splitting in IMAP}.
+
+@emph{TODO: spam.el needs to provide a uniform way of training all the
+statistical databases. Some have that functionality built-in, others
+don't.}
+
+@node Spam ELisp Package Global Variables
+@subsubsection Spam ELisp Package Global Variables
+@cindex spam filtering
+@cindex spam filtering variables
+@cindex spam variables
+@cindex spam
+
@vindex gnus-spam-process-newsgroups
The concepts of ham processors and spam processors are very important.
Ham processors and spam processors for a group can be set with the
processors take mail known to be spam and process it so similar spam
will be detected later.
+The format of the spam or ham processor entry used to be a symbol,
+but now it is a cons cell. See the individual spam processor entries
+for more information.
+
@vindex gnus-spam-newsgroup-contents
Gnus learns from the spam you get. You have to collect your spam in
one or more spam groups, and set or customize the variable
@defvar ham-marks
You can customize this group or topic parameter to be the list of
marks you want to consider ham. By default, the list contains the
-deleted, read, killed, kill-filed, and low-score marks.
+deleted, read, killed, kill-filed, and low-score marks (the idea is
+that these articles have been read, but are not spam). It can be
+useful to also include the tick mark in the ham marks. It is not
+recommended to make the unread mark a ham mark, because it normally
+indicates a lack of classification. But you can do it, and we'll be
+happy for you.
@end defvar
@defvar spam-marks
You can customize this group or topic parameter to be the list of
marks you want to consider spam. By default, the list contains only
-the spam mark.
+the spam mark. It is not recommended to change that, but you can if
+you really want to.
@end defvar
When you leave @emph{any} group, regardless of its
@code{customize-variable gnus-ham-process-destinations}). Each
newsgroup specification has the format (REGEXP PROCESSOR) in a
standard Lisp list, if you prefer to customize the variable manually.
-The ultimate location is a group name. If the
+The ultimate location is a group name or names. If the
@code{ham-process-destination} parameter is not set, ham articles are
left in place. If the
@code{spam-mark-ham-unread-before-move-from-spam-group} parameter is
-set, the ham articles are marked as unread before being moved.
+set, the ham articles are marked as unread before being moved.
+
+Note that you can use multiples destinations per group or regular
+expression! This enables you to send your ham to a regular mail
+group and to a @emph{ham training} group.
When you leave a @emph{ham} group, all ham-marked articles are sent to
a ham processor, which will study these as non-spam samples.
regular expressions matched with group names (it's easiest to
customize this variable with @code{customize-variable
gnus-spam-process-destinations}). Each newsgroup specification has
-the repeated format (REGEXP PROCESSOR) and they are all in a standard
-Lisp list, if you prefer to customize the variable manually. The
-ultimate location is a group name. If the
+the repeated format (REGEXP GROUP) and they are all in a standard Lisp
+list, if you prefer to customize the variable manually. The ultimate
+location is a group name or names. If the
@code{spam-process-destination} parameter is not set, the spam
-articles are only expired.
-
-To use the @file{spam.el} facilities for incoming mail filtering, you
-must add the following to your fancy split list
-@code{nnmail-split-fancy} or @code{nnimap-split-fancy}:
-
-@example
-(: spam-split)
-@end example
-
-Note that the fancy split may be called @code{nnmail-split-fancy} or
-@code{nnimap-split-fancy}, depending on whether you use the nnmail or
-nnimap back ends to retrieve your mail.
-
-The @code{spam-split} function will process incoming mail and send the
-mail considered to be spam into the group name given by the variable
-@code{spam-split-group}. By default that group name is @samp{spam},
-but you can customize @code{spam-split-group}. Make sure the contents
-of @code{spam-split-group} are an @emph{unqualified} group name, for
-instance in an @code{nnimap} server @samp{your-server} the value
-@samp{spam} will turn out to be @samp{nnimap+your-server:spam}. The
-value @samp{nnimap+server:spam}, therefore, is wrong and will
-actually give you the group
-@samp{nnimap+your-server:nnimap+server:spam} which may or may not
-work depending on your server's tolerance for strange group names.
-
-You can also give @code{spam-split} a parameter,
-e.g. @samp{'spam-use-regex-headers} or @samp{"maybe-spam"}. Why is
-this useful?
-
-Take these split rules (with @code{spam-use-regex-headers} and
-@code{spam-use-blackholes} set):
-
-@example
- nnimap-split-fancy '(|
- (any "ding" "ding")
- (: spam-split)
- ;; default mailbox
- "mail")
-@end example
-
-Now, the problem is that you want all ding messages to make it to the
-ding folder. But that will let obvious spam (for example, spam
-detected by SpamAssassin, and @code{spam-use-regex-headers}) through,
-when it's sent to the ding list. On the other hand, some messages to
-the ding list are from a mail server in the blackhole list, so the
-invocation of @code{spam-split} can't be before the ding rule.
-
-You can let SpamAssassin headers supersede ding rules, but all other
-@code{spam-split} rules (including a second invocation of the
-regex-headers check) will be after the ding rule:
-
-@example
- nnimap-split-fancy '(|
-;;; all spam detected by spam-use-regex-headers goes to "regex-spam"
- (: spam-split "regex-spam" 'spam-use-regex-headers)
- (any "ding" "ding")
-;;; all other spam detected by spam-split goes to spam-split-group
- (: spam-split)
- ;; default mailbox
- "mail")
-@end example
-
-Basically, this lets you invoke specific @code{spam-split} checks
-depending on your particular needs, and to target the results of those
-checks to a particular spam group. You don't have to throw all mail
-into all the spam tests. Another reason why this is nice is that
-messages to mailing lists you have rules for don't have to have
-resource-intensive blackhole checks performed on them. You could also
-specify different spam checks for your nnmail split vs. your nnimap
-split. Go crazy.
-
-You still have to have specific checks such as
-@code{spam-use-regex-headers} set to @code{t}, even if you specifically
-invoke @code{spam-split} with the check. The reason is that when
-loading @file{spam.el}, some conditional loading is done depending on
-what @code{spam-use-xyz} variables you have set.
-
-@emph{Note for IMAP users}
-
-The boolean variable @code{nnimap-split-download-body} needs to be
-set, if you want to split based on the whole message instead of just
-the headers. By default, the nnimap back end will only retrieve the
-message headers. If you use @code{spam-check-bogofilter},
-@code{spam-check-ifile}, or @code{spam-check-stat} (the splitters that
-can benefit from the full message body), you should set this variable.
-It is not set by default because it will slow @acronym{IMAP} down, and
-that is not an appropriate decision to make on behalf of the user.
-
-@xref{Splitting in IMAP}.
-
-@emph{TODO: Currently, spam.el only supports insertion of articles
-into a back end. There is no way to tell spam.el that an article is no
-longer spam or ham.}
-
-@emph{TODO: spam.el needs to provide a uniform way of training all the
-statistical databases. Some have that functionality built-in, others
-don't.}
-
-The following are the methods you can use to control the behavior of
-@code{spam-split} and their corresponding spam and ham processors:
+articles are only expired. The group name is fully qualified, meaning
+that if you see @samp{nntp:servername} before the group name in the
+group buffer then you need it here as well.
+
+Note that you can use multiples destinations per group or regular
+expression! This enables you to send your spam to multiple @emph{spam
+training} groups.
+
+@vindex spam-log-to-registry
+The problem with processing ham and spam is that Gnus doesn't track
+this processing by default. Enable the @code{spam-log-to-registry}
+variable so @code{spam.el} will use @code{gnus-registry.el} to track
+what articles have been processed, and avoid processing articles
+multiple times. Keep in mind that if you limit the number of registry
+entries, this won't work as well as it does without a limit.
+
+@vindex spam-mark-only-unseen-as-spam
+Set this variable if you want only unseen articles in spam groups to
+be marked as spam. By default, it is set. If you set it to nil,
+unread articles will also be marked as spam.
+
+@vindex spam-mark-ham-unread-before-move-from-spam-group
+Set this variable if you want ham to be unmarked before it is moved
+out of the spam group. This is very useful when you use something
+like the tick mark @samp{!} to mark ham - the article will be placed
+in your ham-process-destination, unmarked as if it came fresh from
+the mail server.
+
+@vindex spam-autodetect-recheck-messages
+When autodetecting spam, this variable tells @code{spam.el} whether
+only unseen articles or all unread articles should be checked for
+spam. It is recommended that you leave it off.
+
+@node Spam ELisp Package Configuration Examples
+@subsubsection Spam ELisp Package Configuration Examples
+@cindex spam filtering
+@cindex spam filtering configuration examples
+@cindex spam configuration examples
+@cindex spam
-@menu
-* Blacklists and Whitelists::
-* BBDB Whitelists::
-* Gmane Spam Reporting::
-* Anti-spam Hashcash Payments::
-* Blackholes::
-* Regular Expressions Header Matching::
-* Bogofilter::
-* ifile spam filtering::
-* spam-stat spam filtering::
-* SpamOracle::
-* Extending the spam elisp package::
-@end menu
+@emph{TODO}: add configuration examples with explanations of daily usage
@node Blacklists and Whitelists
@subsubsection Blacklists and Whitelists
added to a group's @code{spam-process} parameter, the senders of
spam-marked articles will be added to the blacklist.
+@emph{WARNING}
+
+Instead of the obsolete
+@code{gnus-group-spam-exit-processor-blacklist}, it is recommended
+that you use @code{'(spam spam-use-blacklist)}. Everything will work
+the same way, we promise.
+
@end defvar
@defvar gnus-group-ham-exit-processor-whitelist
whitelist. Note that this ham processor has no effect in @emph{spam}
or @emph{unclassified} groups.
+@emph{WARNING}
+
+Instead of the obsolete
+@code{gnus-group-ham-exit-processor-whitelist}, it is recommended
+that you use @code{'(ham spam-use-whitelist)}. Everything will work
+the same way, we promise.
+
@end defvar
Blacklists are lists of regular expressions matching addresses you
BBDB. Note that this ham processor has no effect in @emph{spam}
or @emph{unclassified} groups.
+@emph{WARNING}
+
+Instead of the obsolete
+@code{gnus-group-ham-exit-processor-BBDB}, it is recommended
+that you use @code{'(ham spam-use-BBDB)}. Everything will work
+the same way, we promise.
+
@end defvar
@node Gmane Spam Reporting
Gmane can be found at @uref{http://gmane.org}.
+@emph{WARNING}
+
+Instead of the obsolete
+@code{gnus-group-spam-exit-processor-report-gmane}, it is recommended
+that you use @code{'(spam spam-use-gmane)}. Everything will work the
+same way, we promise.
+
@end defvar
@defvar spam-report-gmane-use-article-number
@code{gnus-spam-process-newsgroups} variable. When this symbol is
added to a group's @code{spam-process} parameter, spam-marked articles
will be added to the Bogofilter spam database.
+
+@emph{WARNING}
+
+Instead of the obsolete
+@code{gnus-group-spam-exit-processor-bogofilter}, it is recommended
+that you use @code{'(spam spam-use-bogofilter)}. Everything will work
+the same way, we promise.
@end defvar
@defvar gnus-group-ham-exit-processor-bogofilter
articles in @emph{ham} groups will be added to the Bogofilter database
of non-spam messages. Note that this ham processor has no effect in
@emph{spam} or @emph{unclassified} groups.
+
+@emph{WARNING}
+
+Instead of the obsolete
+@code{gnus-group-ham-exit-processor-bogofilter}, it is recommended
+that you use @code{'(ham spam-use-bogofilter)}. Everything will work
+the same way, we promise.
@end defvar
@defvar spam-bogofilter-database-directory
@code{gnus-spam-process-newsgroups} variable. When this symbol is
added to a group's @code{spam-process} parameter, the spam-marked
articles will be added to the spam-stat database of spam messages.
+
+@emph{WARNING}
+
+Instead of the obsolete
+@code{gnus-group-spam-exit-processor-stat}, it is recommended
+that you use @code{'(spam spam-use-stat)}. Everything will work
+the same way, we promise.
@end defvar
@defvar gnus-group-ham-exit-processor-stat
articles in @emph{ham} groups will be added to the spam-stat database
of non-spam messages. Note that this ham processor has no effect in
@emph{spam} or @emph{unclassified} groups.
+
+@emph{WARNING}
+
+Instead of the obsolete
+@code{gnus-group-ham-exit-processor-stat}, it is recommended
+that you use @code{'(ham spam-use-stat)}. Everything will work
+the same way, we promise.
@end defvar
This enables @file{spam.el} to cooperate with @file{spam-stat.el}.
@code{gnus-spam-process-newsgroups} variable. When this symbol is added
to a group's @code{spam-process} parameter, spam-marked articles will be
sent to SpamOracle as spam samples.
+
+@emph{WARNING}
+
+Instead of the obsolete
+@code{gnus-group-spam-exit-processor-spamoracle}, it is recommended
+that you use @code{'(spam spam-use-spamoracle)}. Everything will work
+the same way, we promise.
@end defvar
@defvar gnus-group-ham-exit-processor-spamoracle
@emph{ham} groups will be sent to the SpamOracle as samples of ham
messages. Note that this ham processor has no effect in @emph{spam} or
@emph{unclassified} groups.
+
+@emph{WARNING}
+
+Instead of the obsolete
+@code{gnus-group-ham-exit-processor-spamoracle}, it is recommended
+that you use @code{'(ham spam-use-spamoracle)}. Everything will work
+the same way, we promise.
@end defvar
-@emph{Example:} These are the Group Parameters of an group that has been
+@emph{Example:} These are the Group Parameters of a group that has been
classified as a ham group, meaning that it should only contain ham
messages.
@example
((spam-contents gnus-group-spam-classification-ham)
- (spam-process
- (gnus-group-spam-exit-processor-spamoracle)))
+ (spam-process ((ham spam-use-spamoracle)
+ (spam spam-use-spamoracle))))
@end example
-For this group the @code{gnus-group-spam-exit-processor-spamoracle} is
-installed. If the group contains spam message (e.g. because SpamOracle
-has not had enough sample messages yet) and the user marks some
-messages as spam messages, these messages will be processed by
-@code{gnus-group-spam-exit-processor-spamoracle}. This processor sends
-the messages to SpamOracle as new samples for spam.
-
-@node Extending the spam elisp package
-@subsubsection Extending the spam elisp package
+For this group the @code{spam-use-spamoracle} is installed for both
+ham and spam processing. If the group contains spam message
+(e.g. because SpamOracle has not had enough sample messages yet) and
+the user marks some messages as spam messages, these messages will be
+processed by SpamOracle. The processor sends the messages to
+SpamOracle as new samples for spam.
+
+@node Extending the Spam ELisp package
+@subsubsection Extending the Spam ELisp package
@cindex spam filtering
@cindex spam elisp package, extending
@cindex extending the spam elisp package
Add
@example
- (spam-use-blackbox . spam-check-blackbox)
+ (spam-use-blackbox . spam-check-blackbox)
@end example
to @code{spam-list-of-checks}.
+Add
+@example
+ (gnus-group-ham-exit-processor-blackbox ham spam-use-blackbox)
+ (gnus-group-spam-exit-processor-blackbox spam spam-use-blackbox)
+@end example
+to @code{spam-list-of-processors}.
+
+Add
+@example
+ (spam-use-blackbox spam-blackbox-register-routine
+ nil
+ spam-blackbox-unregister-routine
+ nil)
+@end example
+to @code{spam-registration-functions}. Write the register/unregister
+routines using the bogofilter register/unregister routines as a
+start, or other restister/unregister routines more appropriate to
+Blackbox.
+
@item
functionality
Write the @code{spam-check-blackbox} function. It should return
-@samp{nil} or @code{spam-split-group}. See the existing
-@code{spam-check-*} functions for examples of what you can do.
+@samp{nil} or @code{spam-split-group}, observing the other
+conventions. See the existing @code{spam-check-*} functions for
+examples of what you can do, and stick to the template unless you
+fully understand the reasons why you aren't.
Make sure to add @code{spam-use-blackbox} to
@code{spam-list-of-statistical-checks} if Blackbox is a statistical
Note you don't have to provide a spam or a ham processor. Only
provide them if Blackbox supports spam or ham processing.
+Also, ham and spam processors are being phased out as single
+variables. Instead the form @code{'(spam spam-use-blackbox)} or
+@code{'(ham spam-use-blackbox)} is favored. For now, spam/ham
+processor variables are still around but they won't be for long.
+
@lisp
-(defvar gnus-group-spam-exit-processor-blackbox "blackbox"
+(defvar gnus-group-spam-exit-processor-blackbox "blackbox-spam"
"The Blackbox summary exit spam processor.
Only applicable to spam groups.")
-(defvar gnus-group-ham-exit-processor-blackbox "blackbox"
+(defvar gnus-group-ham-exit-processor-blackbox "blackbox-ham"
"The whitelist summary exit ham processor.
Only applicable to non-spam (unclassified and ham) groups.")
@end lisp
@item
-functionality
+Gnus parameters
-@lisp
-(defun spam-blackbox-register-spam-routine ()
- (spam-generic-register-routine
- ;; @r{the spam function}
- (lambda (article)
- (let ((from (spam-fetch-field-from-fast article)))
- (when (stringp from)
- (blackbox-do-something-with-this-spammer from))))
- ;; @r{the ham function}
- nil))
-
-(defun spam-blackbox-register-ham-routine ()
- (spam-generic-register-routine
- ;; @r{the spam function}
- nil
- ;; @r{the ham function}
- (lambda (article)
- (let ((from (spam-fetch-field-from-fast article)))
- (when (stringp from)
- (blackbox-do-something-with-this-ham-sender from))))))
-@end lisp
-
-Write the @code{blackbox-do-something-with-this-ham-sender} and
-@code{blackbox-do-something-with-this-spammer} functions. You can add
-more complex code than fetching the message sender, but keep in mind
-that retrieving the whole message takes significantly longer than the
-sender through @code{spam-fetch-field-from-fast}, because the message
-senders are kept in memory by Gnus.
+Add
+@example
+ (const :tag "Spam: Blackbox" (spam spam-use-blackbox))
+ (const :tag "Ham: Blackbox" (ham spam-use-blackbox))
+@end example
+to the @code{spam-process} group parameter in @code{gnus.el}. Make
+sure you do it twice, once for the parameter and once for the
+variable customization.
+
+Add
+@example
+ (variable-item spam-use-blackbox)
+@end example
+to the @code{spam-autodetect-methods} group parameter in
+@code{gnus.el}.
@end enumerate
@lisp
(setq nnmail-split-fancy
`(| (: spam-stat-split-fancy)
- "mail.misc"))
+ "mail.misc"))
@end lisp
@defvar spam-stat-split-fancy-spam-group
@lisp
(setq nnmail-split-fancy
`(| ("Subject" "\\bspam-stat\\b" "mail.emacs")
- (: spam-stat-split-fancy)
- "mail.misc"))
+ (: spam-stat-split-fancy)
+ "mail.misc"))
@end lisp
If you want to filter for spam first, then you must be careful when
(setq nnmail-split-fancy
`(| (: spam-stat-split-fancy)
("Subject" "\\bspam-stat\\b" "mail.emacs")
- "mail.misc"))
+ "mail.misc"))
@end lisp
You can combine this with traditional filtering. Here, we move all
@lisp
(setq nnmail-split-fancy
`(| ("Content-Type" "text/html" "mail.spam.filtered")
- (: spam-stat-split-fancy)
+ (: spam-stat-split-fancy)
("Subject" "\\bspam-stat\\b" "mail.emacs")
- "mail.misc"))
+ "mail.misc"))
@end lisp
XEmacs is distributed as a collection of packages. You should install
whatever packages the Gnus XEmacs package requires. The current
-requirements are @samp{gnus}, @samp{w3}, @samp{mh-e},
-@samp{mailcrypt}, @samp{rmail}, @samp{eterm}, @samp{mail-lib},
-@samp{xemacs-base}, @samp{sh-script} and @samp{fsf-compat}. The
-@samp{misc-games} package is required for Morse decoding.
+requirements are @samp{gnus}, @samp{mail-lib}, @samp{xemacs-base},
+@samp{eterm}, @samp{sh-script}, @samp{net-utils}, @samp{os-utils},
+@samp{dired}, @samp{mh-e}, @samp{sieve}, @samp{ps-print}, @samp{w3},
+@samp{pgg}, @samp{mailcrypt}, @samp{ecrypto}, and @samp{sasl}.
@node History
@itemize @bullet
@item
+@code{gnus-group-read-ephemeral-group} can be called interactively,
+using @kbd{G M}.
+
+@item
In draft groups, @kbd{e} is now bound to @code{gnus-draft-edit-message}.
Use @kbd{B w} for @code{gnus-summary-edit-article} instead.
@lisp
(setq gnus-parameters
'(("mail\\..*"
- (gnus-show-threads nil)
- (gnus-use-scoring nil))
- ("^nnimap:\\(foo.bar\\)$"
- (to-group . "\\1"))))
+ (gnus-show-threads nil)
+ (gnus-use-scoring nil))
+ ("^nnimap:\\(foo.bar\\)$"
+ (to-group . "\\1"))))
@end lisp
@item
The old format like the lines below is obsolete, but still accepted.
@lisp
(header "to" "larsi.*org"
- (Organization "Somewhere, Inc."))
+ (Organization "Somewhere, Inc."))
@end lisp
@item
@lisp
(setq ispell-message-dictionary-alist
'(("^Newsgroups:.*\\bde\\." . "deutsch8")
- (".*" . "default")))
+ (".*" . "default")))
@end lisp
@code{ispell} \e$B$O%$%s%9%H!<%k$5$l$?\e(B @samp{ispell} \e$B%3%^%s%I$K0MB8$7$F$$$^\e(B
@lisp
(setq ispell-message-dictionary-alist
'(("^Newsgroups:.*\\bde\\." . "deutsch8")
- (".*" . "default")))
+ (".*" . "default")))
@end lisp
@code{ispell} depends on having the external @samp{ispell} command