Synch with Oort Gnus.
authoryamaoka <yamaoka>
Sat, 11 Jan 2003 05:31:24 +0000 (05:31 +0000)
committeryamaoka <yamaoka>
Sat, 11 Jan 2003 05:31:24 +0000 (05:31 +0000)
lisp/ChangeLog
lisp/gnus-art.el
lisp/gnus-cite.el
lisp/gnus-fun.el
lisp/gnus-score.el
lisp/gnus.el
texi/ChangeLog
texi/gnus-ja.texi
texi/gnus.texi

index d930374..995ce95 100644 (file)
@@ -1,3 +1,18 @@
+2003-01-10  Lars Magne Ingebrigtsen  <larsi@gnus.org>
+
+       * gnus-cite.el (gnus-cite-delete-overlays): Protect against
+       errors when deleting overlays.
+
+       * gnus-score.el (gnus-score-followup): Allow tracing.
+
+       * gnus-art.el (gnus-treat-display-face): New variable.
+       (article-display-face): New command.
+
+       * gnus-fun.el (gnus-face-from-file): New function.
+       (gnus-convert-face-to-png): Ditto.
+
+       * gnus-art.el (gnus-ignored-headers): Added Face.
+
 2003-01-10  Simon Josefsson  <jas@extundo.com>
 
        * nndraft.el (nndraft-request-group): Avoid crash in
        db parameter only if it's set
        (spam-ifile-register-with-ifile): ditto
 
+2003-01-09  Alex Schroeder  <alex@emacswiki.org>
+
+       * spam-stat.el (spam-stat-save): Set spam-stat-ngood and
+       spam-stat-nbad before creating the hash table.
+       (spam-stat-reset): Set spam-stat-ngood and spam-stat-nbad to 0.
+       Changed copyright statement to FSF.
+
 2002-01-09  Kevin Greiner  <kgreiner@xpediantsolutions.com>
 
        * gnus-agent.el (gnus-agent-catchup): Do not mark cached nor
index 4e784ff..1853644 100644 (file)
      "^X-Request-PGP:" "^X-Fingerprint:" "^X-WRIEnvto:" "^X-WRIEnvfrom:"
      "^X-Virus-Scanned:" "^X-Delivery-Agent:" "^Posted-Date:" "^X-Gateway:"
      "^X-Local-Origin:" "^X-Local-Destination:" "^X-UserInfo1:"
-     "^X-Received-Date:" "^X-Hashcash:")
+     "^X-Received-Date:" "^X-Hashcash:" "^Face:")
   "*All headers that start with this regexp will be hidden.
 This variable can also be a list of regexps of headers to be ignored.
 If `gnus-visible-headers' is non-nil, this variable will be ignored."
@@ -1224,6 +1224,24 @@ even if you are using Emacs 21+.  It has no effect on XEmacs."
   "Internal variable used to say whether `smiley-mule' is loaded (whether
 smiley functions are not overridden by `smiley').")
 
+(defcustom gnus-treat-display-face
+  (and (not noninteractive)
+       (or (and (fboundp 'image-type-available-p)
+               (image-type-available-p 'png))
+          (and (featurep 'xemacs)
+               (featurep 'png)))
+       'head)
+  "Display Face headers.
+Valid values are nil, t, `head', `last', an integer or a predicate.
+See Info node `(gnus)Customizing Articles' and Info node
+`(gnus)X-Face' for details."
+  :group 'gnus-article-treat
+  :version "21.1"
+  :link '(custom-manual "(gnus)Customizing Articles")
+  :link '(custom-manual "(gnus)X-Face")
+  :type gnus-article-treat-head-custom)
+(put 'gnus-treat-display-xface 'highlight t)
+
 (defcustom gnus-treat-display-grey-xface
   (and (not noninteractive)
        (or (featurep 'xemacs)
@@ -1433,6 +1451,7 @@ It is a string, such as \"PGP\". If nil, ask user."
     (gnus-treat-date-original gnus-article-date-original)
     (gnus-treat-date-user-defined gnus-article-date-user)
     (gnus-treat-date-iso8601 gnus-article-date-iso8601)
+    (gnus-treat-display-face gnus-article-display-face)
     (gnus-treat-hide-headers gnus-article-maybe-hide-headers)
     (gnus-treat-hide-boring-headers gnus-article-hide-boring-headers)
     (gnus-treat-hide-signature gnus-article-hide-signature)
@@ -2044,6 +2063,28 @@ unfolded."
         (forward-line 1)
         (point))))))
 
+(defun article-display-face ()
+  "Display any Face headers in the header."
+  (interactive)
+  (gnus-with-article-headers
+    (let ((face nil))
+      (save-excursion
+       (when (gnus-buffer-live-p gnus-original-article-buffer)
+         (set-buffer gnus-original-article-buffer)
+         (setq face (message-fetch-field "face"))))
+      (when face
+       (let ((png (gnus-convert-face-to-png face))
+             image)
+         (when png
+           (setq image (gnus-create-image png 'png t))
+           (gnus-article-goto-header "from")
+           (when (bobp)
+             (insert "From: [no `from' set]\n")
+             (forward-char -17))
+           (gnus-add-wash-type 'face)
+           (gnus-add-image 'face image)
+           (gnus-put-image image)))))))
+
 (defun article-display-x-face (&optional force)
   "Look for an X-Face header and display it if present."
   (interactive (list 'force))
@@ -3527,6 +3568,7 @@ If variable `gnus-use-long-file-name' is non-nil, it is
      article-remove-cr
      article-remove-leading-whitespace
      article-display-x-face
+     article-display-face
      article-de-quoted-unreadable
      article-de-base64-unreadable
      article-decode-HZ
index 927abba..ca999e0 100644 (file)
@@ -672,7 +672,8 @@ See also the documentation for `gnus-article-highlight-citation'."
              (and (>= (gnus-overlay-end overlay) (point-min))
                   (<= (gnus-overlay-end overlay) (point-max))))
       (setq gnus-cite-overlay-list (delete overlay gnus-cite-overlay-list))
-      (gnus-delete-overlay overlay))))
+      (ignore-errors
+       (gnus-delete-overlay overlay)))))
 
 (defun gnus-cite-parse-wrapper ()
   ;; Wrap chopped gnus-cite-parse.
index fa2b54f..1ee48ce 100644 (file)
   :group 'gnus-fun
   :type 'string)
 
+(defcustom gnus-convert-image-to-face-command "djpeg %s | ppmnorm | pnmscale -width 48 -height 48 | ppmquant %d | pnmtopng"
+  "Command for converting a GIF to an X-Face."
+  :group 'gnus-fun
+  :type 'string)
+
 (defun gnus-shell-command-to-string (command)
   "Like `shell-command-to-string' except not mingling ERROR."
   (with-output-to-string
@@ -74,6 +79,45 @@ Output to the current buffer, replace text, and don't mingle error."
      (format gnus-convert-image-to-x-face-command
             (shell-quote-argument file)))))
 
+(defun gnus-face-from-file (file)
+  "Return an Face header based on an image file."
+  (interactive "fImage file name:" )
+  (when (file-exists-p file)
+    (let ((done nil)
+         (attempt "")
+         (quant 16))
+      (while (and (not done)
+                 (> quant 1))
+       (setq attempt
+             (gnus-shell-command-to-string
+              (format gnus-convert-image-to-face-command
+                      (shell-quote-argument file)
+                      quant)))
+       (if (> (length attempt) 740)
+           (progn
+             (setq quant (- quant 2))
+             (message "Length %d; trying quant %d"
+                      (length attempt) quant))
+         (setq done t)))
+      (if done
+         (mm-with-unibyte-buffer       
+           (insert attempt)
+           (base64-encode-region (point-min) (point-max))
+           (goto-char (point-min))
+           (forward-line 1)
+           (while (not (eobp))
+             (insert " ")
+             (forward-line 1))
+           (buffer-string))
+       nil))))
+
+;;;###autoload
+(defun gnus-convert-face-to-png (face)
+  (mm-with-unibyte-buffer
+    (insert face)
+    (base64-decode-region (point-min) (point-max))
+    (buffer-string)))
+
 (defun gnus-convert-image-to-gray-x-face (file depth)
   (let* ((mapfile (mm-make-temp-file (expand-file-name "gnus."
                                                       mm-tmp-directory)))
index f3582ac..087871e 100644 (file)
@@ -1866,6 +1866,11 @@ score in `gnus-newsgroup-scored' by SCORE."
                ;; Found a match, update scores.
                (while (setq art (pop arts))
                  (setcdr art (+ score (cdr art)))
+                 (when trace
+                   (push (cons
+                          (car-safe (rassq alist gnus-score-cache))
+                          kill)
+                         gnus-score-trace))
                  (when (setq new (gnus-score-add-followups
                                   (car art) score all-scores thread))
                    (push new news)))))
index cf7bdbd..db2405d 100644 (file)
@@ -2388,7 +2388,8 @@ gnus-newsrc-hashtb should be kept so that both hold the same information.")
      ("gnus-demon" :interactive t
       gnus-demon-init gnus-demon-cancel)
      ("gnus-fun" gnus-convert-gray-x-face-to-xpm gnus-display-x-face-in-from
-      gnus-convert-image-to-gray-x-face)
+      gnus-convert-image-to-gray-x-face gnus-convert-face-to-png
+      gnus-face-from-file)
      ("gnus-salt" gnus-highlight-selected-tree gnus-possibly-generate-tree
       gnus-tree-open gnus-tree-close gnus-carpal-setup-buffer)
      ("gnus-nocem" gnus-nocem-scan-groups gnus-nocem-close
index 59b835b..3f686d8 100644 (file)
@@ -1,3 +1,10 @@
+2003-01-10  Alex Schroeder  <alex@emacswiki.org>
+
+       * gnus.texi (Creating a spam-stat dictionary): Explain how using
+       the Gnus Agent with nnimap might work to do this.
+       (Splitting mail using spam-stat): Use nnimap-split-fancy if you
+       use the nnimap back end.
+
 2003-01-10  Katsumi Yamaoka  <yamaoka@jpl.org>
 
        * gnus.texi (Filtering Spam Using spam.el): Trivial fix.
index 1e91529..b53dcdf 100644 (file)
@@ -21468,6 +21468,12 @@ nnml \e$B%P%C%/%(%s%I$O0lDL$N%a!<%k$K$D$-0l$D$N%U%!%$%k$G!"$9$Y$F$N%a!<%k$r\e(B
 \e$B>o\e(B @samp{nnml:mail.misc} \e$B%0%k!<%W$KBP1~\e(B) \e$B$KBP$7\e(B
 \e$B$F\e(B @code{spam-stat-process-non-spam-directory} \e$B$r8F$V$G$7$g$&!#\e(B
 
+\e$B$"$J$?$,\e(B IMAP \e$B$r;H$C$F$$$k$J$i%a!<%k$r%m!<%+%k$K$O;}$C$F$$$J$$$N$G!"$=$l\e(B
+\e$B$OF0$+$J$$$G$7$g$&!#0l$D$N2r7h:v$O!"\e(Bgnus \e$B%(!<%8%'%s%H$G5-;v$r%-%c%C%7%e\e(B
+\e$B$9$k$3$H$G$9!#$=$&$9$l$P\e(B @code{spam-stat-process-spam-directory} \e$B$H$7\e(B
+\e$B$F\e(B @file{"~/News/agent/nnimap/mail.yourisp.com/personal_spam"} \e$B$N$h$&$J\e(B
+\e$B$b$N$,;H$($^$9!#\e(B@xref{Agent as Cache}\e$B!#\e(B
+
 @defvar spam-stat
 \e$B$3$NJQ?t$O$9$Y$F$NE}7W$N%O%C%7%e%F!<%V%k\e(B -- \e$B2f!9$,<-=q$H8@$C$F$$$k$b\e(B
 \e$B$N\e(B -- \e$B$r;}$A$^$9!#$3$N%O%C%7%e%F!<%V%k$O!"APJ}$N%3%l%/%7%g%s$N$9$Y$F$NC1\e(B
@@ -21515,9 +21521,13 @@ nnml \e$B%P%C%/%(%s%I$O0lDL$N%a!<%k$K$D$-0l$D$N%U%!%$%k$G!"$9$Y$F$N%a!<%k$r\e(B
 \e$B$3$l$OI,MW$J\e(B gnus \e$B$N%3!<%I$H$"$J$?$,:n$C$?<-=q$r\e(B load \e$B$7$^$9!#\e(B
 
 \e$B<!$K!"FC5iJ,3d$N5,B'$rE,9g$5$;$kI,MW$,$"$j$^$9\e(B: \e$B$I$&$d$C\e(B
-\e$B$F\e(B @code{spam-stat} \e$B$r;H$&$+$r7h$a$F2<$5$$!#$G\e(B
-\e$B$O\e(B @samp{mail.misc} \e$B$H\e(B @samp{mail.spam} \e$B$NFs$D$N%0%k!<%W$@$1$,$"$k:G$bC1\e(B
-\e$B=c$J;vNc$G$O$I$&$J$k$+!#0J2<$N<0$O%a!<%k$,\e(B spam \e$B$G$"$k$+!"$^$?$O$=$l\e(B
+\e$B$F\e(B @code{spam-stat} \e$B$r;H$&$+$r7h$a$F2<$5$$!#0J2<$NNc$O\e(B nnml \e$B%P%C%/%(%s%I\e(B
+\e$BMQ$G$9!#\e(Bnnimap \e$B%P%C%/%(%s%I$G$b$^$C$?$/F1MM$KF0:n$7$^$9!#C1\e(B
+\e$B$K\e(B @code{nnmail-split-fancy} \e$B$NBe$o$j$K\e(B @code{nnimap-split-fancy} \e$B$r;H$C\e(B
+\e$B$F2<$5$$!#\e(B
+
+\e$B$G$O\e(B @samp{mail.misc} \e$B$H\e(B @samp{mail.spam} \e$B$NFs$D$N%0%k!<%W$@$1$,$"$k:G$b\e(B
+\e$BC1=c$J;vNc$G$O$I$&$J$k$+!#0J2<$N<0$O%a!<%k$,\e(B spam \e$B$G$"$k$+!"$^$?$O$=$l\e(B
 \e$B$,\e(B @samp{mail.misc} \e$B$K9T$/$Y$-$@$H8@$C$F$$$^$9!#$b$7\e(B spam \e$B$@$C$?\e(B
 \e$B$i\e(B @code{spam-stat-split-fancy} \e$B$O\e(B @samp{mail.spam} \e$B$rJV$7$^$9!#\e(B
 
index 8162bb0..a6abec7 100644 (file)
@@ -21939,6 +21939,12 @@ the the group @samp{nnml:mail.spam}), and you would call
 @file{~/Mail/mail/misc} (this usually corresponds the the group
 @samp{nnml:mail.misc}).
 
+When you are using IMAP, you won't have the mails available locally,
+so that will not work.  One solution is to use the Gnus Agent to cache
+the articles.  Then you can use directories such as
+@file{"~/News/agent/nnimap/mail.yourisp.com/personal_spam"} for
+@code{spam-stat-process-spam-directory}.  @xref{Agent as Cache}.
+
 @defvar spam-stat
 This variable holds the hash-table with all the statistics -- the
 dictionary we have been talking about.  For every word in either
@@ -21989,10 +21995,14 @@ This will load the necessary Gnus code, and the dictionary you
 created.
 
 Next, you need to adapt your fancy splitting rules:  You need to
-determine how to use @code{spam-stat}.  In the simplest case, you only have
-two groups, @samp{mail.misc} and @samp{mail.spam}.  The following expression says
-that mail is either spam or it should go into @samp{mail.misc}.  If it is
-spam, then @code{spam-stat-split-fancy} will return @samp{mail.spam}.
+determine how to use @code{spam-stat}.  The following examples are for
+the nnml back end.  Using the nnimap back end works just as well.  Just
+use @code{nnimap-split-fancy} instead of @code{nnmail-split-fancy}.
+
+In the simplest case, you only have two groups, @samp{mail.misc} and
+@samp{mail.spam}.  The following expression says that mail is either
+spam or it should go into @samp{mail.misc}.  If it is spam, then
+@code{spam-stat-split-fancy} will return @samp{mail.spam}.
 
 @example
 (setq nnmail-split-fancy