From: teranisi Date: Wed, 2 Apr 2003 08:15:19 +0000 (+0000) Subject: Synch up with main trunk and following: X-Git-Tag: elmo-mark-restart~64 X-Git-Url: http://git.chise.org/gitweb/?a=commitdiff_plain;h=76d29ada5aaadf0eb05c8e9d157abd6638808cde;p=elisp%2Fwanderlust.git Synch up with main trunk and following: * wl-summary.el (wl-summary-rescan): Follow the changes in wl-score API. (wl-summary-sync-update): Ditto. * wl-score.el (wl-score-get-score-alist): Changed argument. (wl-summary-rescore-msgs): Likewise. (wl-summary-score-headers): Likewise. (wl-score-headers): Likewise; Use elmo-folder-do-each-message-entity, etc. (wl-summary-score-effect): Follow the changes above. (wl-summary-rescore): Ditto. (wl-score-get-latest-msgs): Follow the changes in elmo-msgdb API. (wl-score-get-overview): Abolish. * wl-summary.el (wl-summary-default-from): Follow the API change in elmo-msgdb. (wl-summary-count-unread): Ditto. (wl-summary-detect-mark-position): Ditto. (wl-summary-overview-entity-compare-by-date): Ditto. (wl-summary-overview-entity-compare-by-number): Ditto. (wl-summary-overview-entity-compare-by-from): Ditto. (wl-summary-overview-entity-compare-by-subject): Ditto. (wl-summary-get-list-info): Ditto. (wl-summary-rescan): Ditto. (wl-summary-jump-to-msg-by-message-id): Ditto. (wl-summary-sync-update): Ditto; Removed comment. (wl-summary-insert-thread-entity): Renamed to wl-summary-insert-thread. (wl-summary-insert-message): Use wl-summary-insert (wl-summary-insert-sequential): Changed argument msgdb to folder. (wl-summary-insert-headers): Changed argument overview to folder. (wl-summary-search-by-subject): Likewise. (wl-summary-insert-thread): Renamed from wl-summary-insert-thread-entity and changed argument msgdb to folder. * wl-folder.el (wl-folder-check-one-entity): Treat elmo-imap4-bye-error too. * wl-fldmgr.el (wl-add-entity-sub): Use elmo-string-member instead of wl-string-member. * elmo.el (elmo-folder-list-messages): Redefine as a luna method. (elmo-folder-list-message-entities): New API. (elmo-message-entity): Ditto. (elmo-message-entity-parent): Ditto. (elmo-folder-do-each-message-entity): Ditto. (elmo-message-entity-number): Ditto. (elmo-message-entity-field): Ditto. (elmo-message-entity-set-field): Ditto. (elmo-folder-count-flags): Ditto. (elmo-folder-length): Ditto. * elmo-util.el (elmo-get-hash-val): Check whether hashtable is nil or not. * elmo-msgdb.el (elmo-msgdb-list-messages): New function. (elmo-msgdb-count-marks): Abolish. (elmo-msgdb-make-entity): Ditto. (elmo-msgdb-do-each-entity): Ditto. (elmo-msgdb-message-entity): New inline function. (elmo-msgdb-message-entity-field): Ditto. (elmo-msgdb-message-entity-set-field): Ditto. (elmo-msgdb-make-message-entity): New function. --- diff --git a/doc/TODO b/doc/TODO index 7ad2308..ff68dd0 100644 --- a/doc/TODO +++ b/doc/TODO @@ -16,5 +16,4 @@ ** organize optional setting for pipe folders to download messages at once when one checks new messages ** support for rfc2192, rfc2193, rfc2221 (managing imap referral) -** improve folder name completion for complex ones (multi,filter,pipe) ** putting codes in order diff --git a/doc/TODO.ja b/doc/TODO.ja index 7d76aa1..203280d 100644 --- a/doc/TODO.ja +++ b/doc/TODO.ja @@ -17,5 +17,4 @@ ** パイプフォルダに、新規メールチェック時にダウンロードまでやってしまう オプションを設ける ** rfc2192, rfc2193, rfc2221 (imap referral の処理) への対応 -** フォルダ名の補完をうまくやる(マルチ、フィルタ、パイプフォルダ) ** コードの整理 diff --git a/elmo/ChangeLog b/elmo/ChangeLog index bc97007..300b089 100644 --- a/elmo/ChangeLog +++ b/elmo/ChangeLog @@ -1,3 +1,28 @@ +2003-04-02 Yuuichi Teranishi + + * elmo.el (elmo-folder-list-messages): Redefine as a luna method. + (elmo-folder-list-message-entities): New API. + (elmo-message-entity): Ditto. + (elmo-message-entity-parent): Ditto. + (elmo-folder-do-each-message-entity): Ditto. + (elmo-message-entity-number): Ditto. + (elmo-message-entity-field): Ditto. + (elmo-message-entity-set-field): Ditto. + (elmo-folder-count-flags): Ditto. + (elmo-folder-length): Ditto. + + * elmo-util.el (elmo-get-hash-val): Check whether hashtable is nil or + not. + + * elmo-msgdb.el (elmo-msgdb-list-messages): New function. + (elmo-msgdb-count-marks): Abolish. + (elmo-msgdb-make-entity): Ditto. + (elmo-msgdb-do-each-entity): Ditto. + (elmo-msgdb-message-entity): New inline function. + (elmo-msgdb-message-entity-field): Ditto. + (elmo-msgdb-message-entity-set-field): Ditto. + (elmo-msgdb-make-message-entity): New function. + 2003-03-25 Yuuichi Teranishi * elmo.el (elmo-folder-append-buffer): Changed argument from unread @@ -38,6 +63,26 @@ (elmo-msgdb-get-field-value): Abolish. (elmo-msgdb-overview-get-entity-by-number): Ditto. +2003-03-30 Yoichi NAKAYAMA + + * elmo.el (elmo-folder-delete): Confirm deletion here, return t if + the folder has been deleted successfully. + * elmo-imap4.el (elmo-folder-delete): Ditto. + * elmo-archive.el (elmo-folder-delete): Ditto. + * elmo-localdir.el (elmo-folder-delete): Ditto. + * elmo-maildir.el (elmo-folder-delete): Ditto. + +2003-03-27 Tetsurou Okazaki + + * elmo-util.el (elmo-string-member-ignore-case): New function. + * elmo-imap4.el (elmo-imap4-response-get-selectable-mailbox-list): Use it. + (elmo-imap4-fetch-callback-1-subr): Likewise. + +2003-03-27 Kimura Fuyuki + + * elmo-imap4.el (elmo-imap4-response-get-selectable-mailbox-list): Fix + the case of the name attribute "\Noselect". + 2003-02-16 Yoichi NAKAYAMA * elmo.el (elmo-folder-rename-internal): New method to cause error. diff --git a/elmo/elmo-archive.el b/elmo/elmo-archive.el index eb94d29..2fb1c3c 100644 --- a/elmo/elmo-archive.el +++ b/elmo/elmo-archive.el @@ -447,12 +447,20 @@ TYPE specifies the archiver's symbol." (delete-file dummy))) )))) -(luna-define-method elmo-folder-delete :before ((folder elmo-archive-folder)) - (let ((arc (elmo-archive-get-archive-name folder))) - (if (not (file-exists-p arc)) - (error "No such file: %s" arc) - (delete-file arc) - t))) +(luna-define-method elmo-folder-delete ((folder elmo-archive-folder)) + (let ((msgs (and (elmo-folder-exists-p folder) + (elmo-folder-list-messages folder)))) + (when (yes-or-no-p (format "%sDelete msgdb and substance of \"%s\"? " + (if (> (length msgs) 0) + (format "%d msg(s) exists. " (length msgs)) + "") + (elmo-folder-name-internal folder))) + (let ((arc (elmo-archive-get-archive-name folder))) + (if (not (file-exists-p arc)) + (error "No such file: %s" arc) + (delete-file arc)) + (elmo-msgdb-delete-path folder) + t)))) (luna-define-method elmo-folder-rename-internal ((folder elmo-archive-folder) new-folder) diff --git a/elmo/elmo-imap4.el b/elmo/elmo-imap4.el index e998989..4ed7762 100644 --- a/elmo/elmo-imap4.el +++ b/elmo/elmo-imap4.el @@ -607,7 +607,7 @@ BUFFER must be a single-byte buffer." (mapcar (lambda (entry) (if (and (eq 'list (car entry)) - (not (member "\\NoSelect" (nth 1 (nth 1 entry))))) + (not (elmo-string-member-ignore-case "\\Noselect" (nth 1 (nth 1 entry))))) (car (nth 1 entry)))) response))) @@ -776,11 +776,11 @@ If CHOP-LENGTH is not specified, message set is not chopped." (let* ((use-flag (cdr app-data)) (app-data (car app-data)) mark) - (if (member "\\Flagged" flags) + (if (elmo-string-member-ignore-case "\\Flagged" flags) (elmo-msgdb-global-mark-set (car entity) elmo-msgdb-important-mark)) (if (setq mark (elmo-msgdb-global-mark-get (car entity))) - (unless (member "\\Seen" flags) + (unless (elmo-string-member-ignore-case "\\Seen" flags) (setq elmo-imap4-seen-messages (cons (elmo-msgdb-overview-entity-get-number entity) @@ -788,16 +788,18 @@ If CHOP-LENGTH is not specified, message set is not chopped." (setq mark (or (if (elmo-file-cache-status (elmo-file-cache-get (car entity))) ;; cached. - (if (member "\\Answered" flags) + (if (elmo-string-member-ignore-case + "\\Answered" flags) elmo-msgdb-answered-cached-mark (if (and use-flag (member "\\Seen" flags)) nil elmo-msgdb-unread-cached-mark)) - (if (member "\\Answered" flags) + (if (elmo-string-member-ignore-case "\\Answered" flags) elmo-msgdb-answered-uncached-mark (if (and use-flag - (member "\\Seen" flags)) + (elmo-string-member-ignore-case + "\\Seen" flags)) (if elmo-imap4-use-cache elmo-msgdb-read-uncached-mark) elmo-msgdb-new-mark)))))) @@ -1983,18 +1985,25 @@ Return nil if no complete line has arrived." (luna-define-method elmo-folder-writable-p ((folder elmo-imap4-folder)) t) -(luna-define-method elmo-folder-delete :before ((folder elmo-imap4-folder)) - (let ((session (elmo-imap4-get-session folder)) - msgs) - (when (elmo-imap4-folder-mailbox-internal folder) - (when (setq msgs (elmo-folder-list-messages folder)) - (elmo-folder-delete-messages folder msgs)) - (elmo-imap4-send-command-wait session "close") - (elmo-imap4-send-command-wait - session - (list "delete " - (elmo-imap4-mailbox - (elmo-imap4-folder-mailbox-internal folder))))))) +(luna-define-method elmo-folder-delete ((folder elmo-imap4-folder)) + (let ((msgs (and (elmo-folder-exists-p folder) + (elmo-folder-list-messages folder)))) + (when (yes-or-no-p (format "%sDelete msgdb and substance of \"%s\"? " + (if (> (length msgs) 0) + (format "%d msg(s) exists. " (length msgs)) + "") + (elmo-folder-name-internal folder))) + (let ((session (elmo-imap4-get-session folder))) + (when (elmo-imap4-folder-mailbox-internal folder) + (when msgs (elmo-folder-delete-messages folder msgs)) + (elmo-imap4-send-command-wait session "close") + (elmo-imap4-send-command-wait + session + (list "delete " + (elmo-imap4-mailbox + (elmo-imap4-folder-mailbox-internal folder)))))) + (elmo-msgdb-delete-path folder) + t))) (luna-define-method elmo-folder-rename-internal ((folder elmo-imap4-folder) new-folder) diff --git a/elmo/elmo-localdir.el b/elmo/elmo-localdir.el index 9df24d0..0a75990 100644 --- a/elmo/elmo-localdir.el +++ b/elmo/elmo-localdir.el @@ -292,11 +292,19 @@ (elmo-make-directory dir)) t))) -(luna-define-method elmo-folder-delete :before ((folder elmo-localdir-folder)) - (let ((dir (elmo-localdir-folder-directory-internal folder))) - (if (not (file-directory-p dir)) - (error "No such directory: %s" dir) - (elmo-delete-match-files dir "[0-9]+" t) +(luna-define-method elmo-folder-delete ((folder elmo-localdir-folder)) + (let ((msgs (and (elmo-folder-exists-p folder) + (elmo-folder-list-messages folder)))) + (when (yes-or-no-p (format "%sDelete msgdb and substance of \"%s\"? " + (if (> (length msgs) 0) + (format "%d msg(s) exists. " (length msgs)) + "") + (elmo-folder-name-internal folder))) + (let ((dir (elmo-localdir-folder-directory-internal folder))) + (if (not (file-directory-p dir)) + (error "No such directory: %s" dir) + (elmo-delete-match-files dir "[0-9]+" t))) + (elmo-msgdb-delete-path folder) t))) (luna-define-method elmo-folder-rename-internal ((folder elmo-localdir-folder) diff --git a/elmo/elmo-maildir.el b/elmo/elmo-maildir.el index 7b58ec4..151a232 100644 --- a/elmo/elmo-maildir.el +++ b/elmo/elmo-maildir.el @@ -474,22 +474,30 @@ file name for maildir directories." t) (error)))) -(luna-define-method elmo-folder-delete :before ((folder elmo-maildir-folder)) - (let ((basedir (elmo-maildir-folder-directory-internal folder))) - (condition-case nil - (let ((tmp-files (directory-files - (expand-file-name "tmp" basedir) - t "[^.].*"))) - ;; Delete files in tmp. - (dolist (file tmp-files) - (delete-file file)) - (dolist (dir '("new" "cur" "tmp" ".")) - (setq dir (expand-file-name dir basedir)) - (if (not (file-directory-p dir)) - (error nil) - (elmo-delete-directory dir t))) - t) - (error nil)))) +(luna-define-method elmo-folder-delete ((folder elmo-maildir-folder)) + (let ((msgs (and (elmo-folder-exists-p folder) + (elmo-folder-list-messages folder)))) + (when (yes-or-no-p (format "%sDelete msgdb and substance of \"%s\"? " + (if (> (length msgs) 0) + (format "%d msg(s) exists. " (length msgs)) + "") + (elmo-folder-name-internal folder))) + (let ((basedir (elmo-maildir-folder-directory-internal folder))) + (condition-case nil + (let ((tmp-files (directory-files + (expand-file-name "tmp" basedir) + t "[^.].*"))) + ;; Delete files in tmp. + (dolist (file tmp-files) + (delete-file file)) + (dolist (dir '("new" "cur" "tmp" ".")) + (setq dir (expand-file-name dir basedir)) + (if (not (file-directory-p dir)) + (error nil) + (elmo-delete-directory dir t)))) + (error nil))) + (elmo-msgdb-delete-path folder) + t))) (luna-define-method elmo-folder-rename-internal ((folder elmo-maildir-folder) new-folder) diff --git a/elmo/elmo-msgdb.el b/elmo/elmo-msgdb.el index 40c45de..0a7e183 100644 --- a/elmo/elmo-msgdb.el +++ b/elmo/elmo-msgdb.el @@ -92,6 +92,9 @@ ;; elmo-msgdb-delete-msgs MSGDB NUMBERS ;; elmo-msgdb-sort-by-date MSGDB +;;; +;; LIST-OF-NUMBERS elmo-msgdb-list-messages MSGDB + ;; elmo-flag-table-load ;; elmo-flag-table-set ;; elmo-flag-table-get @@ -118,6 +121,9 @@ ;; elmo-msgdb-seen-save DIR OBJ ;; elmo-msgdb-overview-save DIR OBJ +;; elmo-msgdb-message-entity MSGDB KEY + +;;; Abolish ;; elmo-msgdb-overview-entity-get-references ENTITY ;; elmo-msgdb-overview-entity-set-references ENTITY ;; elmo-msgdb-get-parent-entity ENTITY MSGDB @@ -178,6 +184,10 @@ (elmo-msgdb-make-index msgdb) msgdb)) +(defun elmo-msgdb-list-messages (msgdb) + "List message numbers in the MSGDB." + (mapcar 'car (elmo-msgdb-get-number-alist msgdb))) + (defsubst elmo-msgdb-get-mark (msgdb number) "Get mark string from MSGDB which corresponds to the message with NUMBER." (cadr (elmo-get-hash-val (format "#%d" number) @@ -355,20 +365,6 @@ FLAG is a symbol which is one of the following: elmo-msgdb-unread-uncached-mark elmo-msgdb-read-uncached-mark)))) -(defsubst elmo-msgdb-count-marks (msgdb) - (let ((new 0) - (unreads 0) - (answered 0)) - (dolist (elem (elmo-msgdb-get-mark-alist msgdb)) - (cond - ((string= (cadr elem) elmo-msgdb-new-mark) - (incf new)) - ((member (cadr elem) (elmo-msgdb-unread-marks)) - (incf unreads)) - ((member (cadr elem) (elmo-msgdb-answered-marks)) - (incf answered)))) - (list new unreads answered))) - (defsubst elmo-msgdb-get-number (msgdb message-id) "Get number of the message which corrensponds to MESSAGE-ID from MSGDB." (elmo-msgdb-overview-entity-get-number @@ -452,19 +448,6 @@ content of MSGDB is changed." (message "Sorting...done") (list overview (nth 1 msgdb)(nth 2 msgdb)))) -(defun elmo-msgdb-make-entity (&rest args) - "Make an msgdb entity." - (cons (plist-get args :message-id) - (vector (plist-get args :number) - (plist-get args :references) - (plist-get args :from) - (plist-get args :subject) - (plist-get args :date) - (plist-get args :to) - (plist-get args :cc) - (plist-get args :size) - (plist-get args :extra)))) - ;;; (defsubst elmo-msgdb-append-element (list element) (if list @@ -973,6 +956,62 @@ Return CONDITION itself if no entity exists in msgdb." (and entity (aset (cdr entity) 8 extra)) entity) +;;; New APIs +(defsubst elmo-msgdb-message-entity (msgdb key) + (elmo-get-hash-val + (cond ((stringp key) key) + ((numberp key) (format "#%d" key))) + (elmo-msgdb-get-entity-hashtb msgdb))) + +(defun elmo-msgdb-make-message-entity (&rest args) + "Make an message entity." + (cons (plist-get args :message-id) + (vector (plist-get args :number) + (plist-get args :references) + (plist-get args :from) + (plist-get args :subject) + (plist-get args :date) + (plist-get args :to) + (plist-get args :cc) + (plist-get args :size) + (plist-get args :extra)))) + +(defsubst elmo-msgdb-message-entity-field (entity field &optional decode) + (and entity + (if (not decode) + (case field + (to (aref (cdr entity) 5)) + (cc (aref (cdr entity) 6)) + (date (aref (cdr entity) 4)) + (subject (aref (cdr entity) 3)) + (from (aref (cdr entity) 2)) + (message-id (car entity)) + (references (aref (cdr entity) 1)) + (size (aref (cdr entity) 7)) + (t (cdr (assoc (symbol-name field) (aref (cdr entity) 8))))) + (elmo-msgdb-get-decoded-cache + (elmo-msgdb-message-entity-field entity field))))) + +(defsubst elmo-msgdb-message-entity-set-field (entity field value) + (and entity + (case field + (to (aset (cdr entity) 5 value)) + (cc (aset (cdr entity) 6 value)) + (date (aset (cdr entity) 4 value)) + (subject (aset (cdr entity) 3 value)) + (from (aset (cdr entity) 2 value)) + (message-id (setcar entity value)) + (references (aset (cdr entity) 1 value)) + (size (aset (cdr entity) 7 value)) + (t + (let ((extras (and entity (aref (cdr entity) 8))) + extra) + (if (setq extra (assoc field extras)) + (setcdr extra value) + (aset (cdr entity) 8 (cons (cons (symbol-name field) + value) extras)))))))) + +;;; (defun elmo-msgdb-overview-get-entity (id msgdb) (when id (let ((ht (elmo-msgdb-get-entity-hashtb msgdb))) @@ -1303,13 +1342,6 @@ Return the updated INDEX." (setq matched (cons (car elem) matched)))))) matched)) -(put 'elmo-msgdb-do-each-entity 'lisp-indent-function '1) -(def-edebug-spec elmo-msgdb-do-each-entity - ((symbolp form &rest form) &rest form)) -(defmacro elmo-msgdb-do-each-entity (spec &rest form) - `(dolist (,(car spec) (elmo-msgdb-get-overview ,(car (cdr spec)))) - ,@form)) - (require 'product) (product-provide (provide 'elmo-msgdb) (require 'elmo-version)) diff --git a/elmo/elmo-util.el b/elmo/elmo-util.el index 4f019e2..309a424 100644 --- a/elmo/elmo-util.el +++ b/elmo/elmo-util.el @@ -948,6 +948,7 @@ the directory becomes empty after deletion." (defmacro elmo-get-hash-val (string hashtable) `(and (stringp ,string) + ,hashtable (let ((sym (intern-soft ,string ,hashtable))) (if (boundp sym) (symbol-value sym))))) @@ -1264,7 +1265,6 @@ But if optional argument AUTO is non-nil, DEFAULT is returned." (y-or-n-p prompt))) (defun elmo-string-member (string slist) - "Return t if STRING is a member of the SLIST." (catch 'found (while slist (if (and (stringp (car slist)) @@ -1272,6 +1272,25 @@ But if optional argument AUTO is non-nil, DEFAULT is returned." (throw 'found t)) (setq slist (cdr slist))))) +(cond ((fboundp 'member-ignore-case) + (defalias 'elmo-string-member-ignore-case 'member-ignore-case)) + ((fboundp 'compare-strings) + (defun elmo-string-member-ignore-case (elt list) + "Like `member', but ignores differences in case and text representation. +ELT must be a string. Upper-case and lower-case letters are treated as equal. +Unibyte strings are converted to multibyte for comparison." + (while (and list (not (eq t (compare-strings elt 0 nil (car list) 0 nil t)))) + (setq list (cdr list))) + list)) + (t + (defun elmo-string-member-ignore-case (elt list) + "Like `member', but ignores differences in case and text representation. +ELT must be a string. Upper-case and lower-case letters are treated as equal." + (let ((str (downcase elt))) + (while (and list (not (string= str (downcase (car list))))) + (setq list (cdr list))) + list)))) + (defun elmo-string-match-member (str list &optional case-ignore) (let ((case-fold-search case-ignore)) (catch 'member diff --git a/elmo/elmo.el b/elmo/elmo.el index 22c1ad5..d357233 100644 --- a/elmo/elmo.el +++ b/elmo/elmo.el @@ -147,14 +147,15 @@ If optional argument NON-PERSISTENT is non-nil, the folder msgdb is not saved." (save-match-data (elmo-folder-send folder 'elmo-folder-initialize name)))) +;; Note that this function is for internal use only. (luna-define-generic elmo-folder-msgdb (folder) - "Return the msgdb of FOLDER (on-demand loading).") + "Return the msgdb of FOLDER (on-demand loading). +\(For internal use only.\)") (luna-define-method elmo-folder-msgdb ((folder elmo-folder)) (or (elmo-folder-msgdb-internal folder) (elmo-folder-set-msgdb-internal folder (elmo-msgdb-load folder)))) - (luna-define-generic elmo-folder-open (folder &optional load-msgdb) "Open and setup (load saved status) FOLDER. If optional LOAD-MSGDB is non-nil, msgdb is loaded. @@ -196,8 +197,8 @@ If optional KEEP-KILLED is non-nil, killed-list is not cleared.") If optional NUMBERS is set, it is used as current NUMBERS. Otherwise, saved status for folder is used for comparison. Return value is cons cell or list: - - a cons cell (NEWS . MESSAGES) - - a list (RECENT UNSEEN MESSAGES) ; RECENT means NEWS, UNSEEN means UNREAD.") + - a cons cell (new . all) + - a list (new unread all)") (luna-define-generic elmo-folder-status (folder) "Returns a cons cell of (MAX-NUMBER . MESSAGES) in the FOLDER.") @@ -205,10 +206,13 @@ Return value is cons cell or list: (luna-define-generic elmo-folder-reserve-status-p (folder) "If non-nil, the folder should not close folder after `elmo-folder-status'.") -(defun elmo-folder-list-messages (folder &optional visible-only in-msgdb) +(luna-define-generic elmo-folder-list-messages (folder &optional visible-only + in-msgdb) "Return a list of message numbers contained in FOLDER. If optional VISIBLE-ONLY is non-nil, killed messages are not listed. -If second optional IN-MSGDB is non-nil, only messages in the msgdb are listed." +If second optional IN-MSGDB is non-nil, only messages in the msgdb are listed.") +(luna-define-method elmo-folder-list-messages ((folder elmo-folder) + &optional visible-only in-msgdb) (let ((list (if in-msgdb t (elmo-folder-list-messages-internal folder visible-only)))) @@ -216,9 +220,7 @@ If second optional IN-MSGDB is non-nil, only messages in the msgdb are listed." (if (listp list) list ;; Use current list. - (mapcar - 'car - (elmo-msgdb-get-number-alist (elmo-folder-msgdb folder)))) + (elmo-msgdb-list-messages (elmo-folder-msgdb folder))) (elmo-folder-killed-list-internal folder)))) (luna-define-generic elmo-folder-list-unreads (folder) @@ -726,7 +728,10 @@ Return a cons cell of (NUMBER-CROSSPOSTS . NEW-MARK-ALIST).") nil) ; default is not writable. (luna-define-method elmo-folder-delete ((folder elmo-folder)) - (elmo-msgdb-delete-path folder)) + (when (yes-or-no-p (format "Delete msgdb of \"%s\"? " + (elmo-folder-name-internal folder))) + (elmo-msgdb-delete-path folder) + t)) (luna-define-method elmo-folder-rename ((folder elmo-folder) new-name) (let* ((new-folder (elmo-make-folder new-name))) @@ -739,11 +744,6 @@ Return a cons cell of (NUMBER-CROSSPOSTS . NEW-MARK-ALIST).") (elmo-folder-send folder 'elmo-folder-rename-internal new-folder) (elmo-msgdb-rename-path folder new-folder))) -(luna-define-method elmo-folder-rename-internal ((folder elmo-folder) - new-folder) - (error "Cannot rename %s folder" - (symbol-name (elmo-folder-type-internal folder)))) - (defsubst elmo-folder-search-fast (folder condition numbers) (when (and numbers (vectorp condition) @@ -1142,6 +1142,76 @@ If CACHED is t, message is set as cached." (elmo-message-use-cache-p folder number)) (elmo-folder-set-mark-modified-internal folder t))) +;;; APIs for message-entity +(luna-define-generic elmo-folder-list-message-entities (folder) + "Return the all list of message-entity structure of FOLDER.") + +(luna-define-method elmo-folder-list-message-entities ((folder elmo-folder)) + (elmo-msgdb-get-overview (elmo-folder-msgdb folder))) + +(luna-define-generic elmo-message-entity (folder key) + "Return the message-entity structure which matches to the KEY. +KEY is a number or a string. +A number is for message number in the FOLDER. +A string is for message-d of the message.") + +(luna-define-method elmo-message-entity ((folder elmo-folder) key) + (elmo-msgdb-message-entity (elmo-folder-msgdb folder) key)) + +(luna-define-generic elmo-message-entity-parent (folder entity) + "Return the parent message-entity structure in the FOLDER. +ENTITY is the message-entity to get the parent.") + +(luna-define-method elmo-message-entity-parent ((folder elmo-folder) entity) + (elmo-msgdb-get-parent-entity entity (elmo-folder-msgdb folder))) + +(put 'elmo-folder-do-each-message-entity 'lisp-indent-function '1) +(def-edebug-spec elmo-folder-do-each-message-entity + ((symbolp form &rest form) &rest form)) + +(defmacro elmo-folder-do-each-message-entity (spec &rest form) + "Iterator for message entity in the folder. +\(elmo-folder-do-each-message-entity \(entity folder\) + ... do the process using entity... +\)" + `(dolist (,(car spec) (elmo-folder-list-message-entities ,(car (cdr spec)))) + ,@form)) + +(defmacro elmo-message-entity-number (entity) + `(elmo-msgdb-overview-entity-get-number ,entity)) + +(defun elmo-message-entity-field (entity field &optional decode) + "Get message entity field value. +ENTITY is the message entity structure obtained by `elmo-message-entity'. +FIELD is the symbol of the field name. +if optional DECODE is non-nil, returned value is decoded." + (elmo-msgdb-message-entity-field entity field decode)) + +(defun elmo-message-entity-set-field (entity field value) + "Set message entity field value. +ENTITY is the message entity structure. +FIELD is the symbol of the field name. +VALUE is the field value (raw)." + (elmo-msgdb-message-entity-set-field entity field value)) + +(luna-define-generic elmo-folder-count-flags (folder) + "Count flagged message number in the msgdb of the FOLDER. +Return a list of numbers (`new' `unread' `answered')") + +(luna-define-method elmo-folder-count-flags ((folder elmo-folder)) + (let ((new 0) + (unreads 0) + (answered 0)) + (dolist (elem (elmo-msgdb-get-mark-alist (elmo-folder-msgdb folder))) + (cond + ((string= (cadr elem) elmo-msgdb-new-mark) + (incf new)) + ((member (cadr elem) (elmo-msgdb-unread-marks)) + (incf unreads)) + ((member (cadr elem) (elmo-msgdb-answered-marks)) + (incf answered)))) + (list new unreads answered))) + (defun elmo-message-set-flag (folder number flag) "Set message flag. FOLDER is a ELMO folder structure. @@ -1469,6 +1539,12 @@ If update process is interrupted, return nil." (elmo-msgdb-get-number-alist (elmo-folder-msgdb folder)))) +(luna-define-generic elmo-folder-length (folder) + "Return number of messages in the FOLDER.") + +(luna-define-method elmo-folder-length ((folder elmo-folder)) + (elmo-msgdb-length (elmo-folder-msgdb folder))) + (defun elmo-msgdb-load (folder &optional silent) (unless silent (message "Loading msgdb for %s..." (elmo-folder-name-internal folder))) @@ -1567,6 +1643,11 @@ Return a hashtable for newsgroups." (funcall func nil))) (setq types (cdr types))))) +(luna-define-method elmo-folder-rename-internal ((folder elmo-folder) + new-folder) + (error "Cannot rename %s folder" + (symbol-name (elmo-folder-type-internal folder)))) + ;;; Define folders. (elmo-define-folder ?% 'imap4) diff --git a/wl/ChangeLog b/wl/ChangeLog index 5c1bba5..ed7c40d 100644 --- a/wl/ChangeLog +++ b/wl/ChangeLog @@ -1,3 +1,45 @@ +2003-04-02 Yuuichi Teranishi + + * wl-summary.el (wl-summary-rescan): Follow the changes in wl-score + API. + (wl-summary-sync-update): Ditto. + + * wl-score.el (wl-score-get-score-alist): Changed argument. + (wl-summary-rescore-msgs): Likewise. + (wl-summary-score-headers): Likewise. + (wl-score-headers): Likewise; + Use elmo-folder-do-each-message-entity, etc. + (wl-summary-score-effect): Follow the changes above. + (wl-summary-rescore): Ditto. + (wl-score-get-latest-msgs): Follow the changes in elmo-msgdb API. + (wl-score-get-overview): Abolish. + + * wl-summary.el (wl-summary-default-from): Follow the API change in + elmo-msgdb. + (wl-summary-count-unread): Ditto. + (wl-summary-detect-mark-position): Ditto. + (wl-summary-overview-entity-compare-by-date): Ditto. + (wl-summary-overview-entity-compare-by-number): Ditto. + (wl-summary-overview-entity-compare-by-from): Ditto. + (wl-summary-overview-entity-compare-by-subject): Ditto. + (wl-summary-get-list-info): Ditto. + (wl-summary-rescan): Ditto. + (wl-summary-jump-to-msg-by-message-id): Ditto. + (wl-summary-sync-update): Ditto; Removed comment. + (wl-summary-insert-thread-entity): Renamed to wl-summary-insert-thread. + (wl-summary-insert-message): Use wl-summary-insert + (wl-summary-insert-sequential): Changed argument msgdb to folder. + (wl-summary-insert-headers): Changed argument overview to folder. + (wl-summary-search-by-subject): Likewise. + (wl-summary-insert-thread): Renamed from + wl-summary-insert-thread-entity and changed argument msgdb to folder. + + * wl-folder.el (wl-folder-check-one-entity): Treat elmo-imap4-bye-error + too. + + * wl-fldmgr.el (wl-add-entity-sub): Use elmo-string-member instead of + wl-string-member. + 2003-03-25 Yuuichi Teranishi * wl-draft.el (wl-draft-do-fcc): Follow the changes in @@ -22,6 +64,20 @@ (wl-summary-redisplay-internal): If msgdb flag is already read, just update the mark on buffer. +2003-03-30 Yoichi NAKAYAMA + + * wl-fldmgr.el (wl-fldmgr-delete): Move confirmation to elmo side, + cut visible folder when elmo-folder-delete returns non-nil value. + +2003-03-30 Yoichi NAKAYAMA + + * wl-draft.el (wl-draft-send-confirm): Display more info (advised + by Kenichi OKADA ). + +2003-03-28 Yoichi NAKAYAMA + + * wl-folder.el (wl-folder-open-all): Fix to get proper entity. + 2003-03-19 Yoichi NAKAYAMA * wl-fldmgr.el (wl-fldmgr-sort, wl-fldmgr-access-display-all): diff --git a/wl/wl-draft.el b/wl/wl-draft.el index 74368a6..5ef768c 100644 --- a/wl/wl-draft.el +++ b/wl/wl-draft.el @@ -1272,7 +1272,7 @@ This variable is valid when `wl-interactive-send' has non-nil value." (goto-char (point-min)) ; to show recipients in header (catch 'done (while t - (message "Send current draft? ") + (message "Send current draft? ") (setq answer (let ((cursor-in-echo-area t)) (read-char))) (cond ((or (eq answer ?y) diff --git a/wl/wl-fldmgr.el b/wl/wl-fldmgr.el index 7da121f..caced28 100644 --- a/wl/wl-fldmgr.el +++ b/wl/wl-fldmgr.el @@ -387,11 +387,11 @@ return value is diffs '(-new -unread -all)." (cond ((stringp (car new2)) ;; folder (cond - ((wl-string-member (car new2) flist) + ((elmo-string-member (car new2) flist) (and errmes (message "%s: already exists" (car new2))) (throw 'success nil)) ((and access - (not (wl-string-member (car new2) unsubscribes))) + (not (elmo-string-member (car new2) unsubscribes))) (and errmes (message "%s: not access group folder" (car new2))) (throw 'success nil)))) (t ;; group @@ -850,15 +850,8 @@ return value is diffs '(-new -unread -all)." (let* ((inhibit-read-only t) (tmp (wl-fldmgr-get-path-from-buffer)) (entity (elmo-string (nth 4 tmp))) - (folder (wl-folder-get-elmo-folder entity)) - (msgs (and (elmo-folder-exists-p folder) - (elmo-folder-list-messages folder)))) - (when (yes-or-no-p (format "%sDo you really want to delete \"%s\"? " - (if (> (length msgs) 0) - (format "%d msg(s) exists. " (length msgs)) - "") - entity)) - (elmo-folder-delete folder) + (folder (wl-folder-get-elmo-folder entity))) + (when (elmo-folder-delete folder) (wl-fldmgr-cut tmp nil t))))) (defun wl-fldmgr-rename () diff --git a/wl/wl-folder.el b/wl/wl-folder.el index 7e759f9..7d1de74 100644 --- a/wl/wl-folder.el +++ b/wl/wl-folder.el @@ -825,8 +825,10 @@ Optional argument ARG is repeart count." (elmo-folder-diff folder))) (error ;; maybe not exist folder. - (if (and (not (memq 'elmo-open-error - (get (car err) 'error-conditions))) + (if (and (not (or (memq 'elmo-open-error + (get (car err) 'error-conditions)) + (memq 'elmo-imap4-bye-error + (get (car err) 'error-conditions)))) (not (elmo-folder-exists-p folder))) (wl-folder-create-subr folder) (signal (car err) (cdr err)))))) @@ -2505,7 +2507,7 @@ Use `wl-subscribed-mailing-list'." (save-excursion (goto-char (point-min)) (while (re-search-forward - "^\\([ ]*\\)\\[\\([+]\\)\\]\\(.+\\):[-0-9-]+/[0-9-]+/[0-9-]+\n" + "^\\([ ]*\\)\\[\\([+]\\)\\]\\(.+\\):[-0-9-]+/[0-9-]+/[0-9-]+$" nil t) (setq indent (wl-match-buffer 1)) (setq name (wl-folder-get-entity-from-buffer)) @@ -2514,7 +2516,7 @@ Use `wl-subscribed-mailing-list'." wl-folder-entity)) ;; insert as opened (setcdr (assoc (car entity) wl-folder-group-alist) t) - (forward-line -1) + (beginning-of-line) (wl-folder-insert-entity indent entity) (delete-region (save-excursion (beginning-of-line) (point)) diff --git a/wl/wl-score.el b/wl/wl-score.el index a3eb67b..f940cb1 100644 --- a/wl/wl-score.el +++ b/wl/wl-score.el @@ -340,7 +340,7 @@ Set `wl-score-cache' nil." (defun wl-score-get-score-files (score-alist folder) (let ((files (wl-get-assoc-list-value - score-alist folder + score-alist (elmo-folder-name-internal folder) (if (not wl-score-folder-alist-matchone) 'all-list))) fl f) (while (setq f (wl-pop files)) @@ -352,11 +352,12 @@ Set `wl-score-cache' nil." (list f))))) fl)) -(defun wl-score-get-score-alist (&optional folder) +(defun wl-score-get-score-alist () (interactive) - (let* ((fld (or folder (wl-summary-buffer-folder-name))) - (score-alist (reverse - (wl-score-get-score-files wl-score-folder-alist fld))) + (let* ((score-alist (reverse + (wl-score-get-score-files + wl-score-folder-alist + wl-summary-buffer-elmo-folder))) alist scores) (setq wl-current-score-file nil) (unless (and wl-score-default-file @@ -390,32 +391,29 @@ Set `wl-score-cache' nil." (setq score-alist (cdr score-alist))) scores)) -(defun wl-score-headers (scores &optional msgdb force-msgs not-add) +(defun wl-score-headers (scores &optional force-msgs not-add) (let* ((elmo-mime-charset wl-summary-buffer-mime-charset) + (folder wl-summary-buffer-elmo-folder) (now (wl-day-number (current-time-string))) (expire (and wl-score-expiry-days (- now wl-score-expiry-days))) - (overview (elmo-msgdb-get-overview - (or msgdb (wl-summary-buffer-msgdb)))) - (mark-alist (elmo-msgdb-get-mark-alist - (or msgdb (wl-summary-buffer-msgdb)))) (wl-score-stop-add-entry not-add) entries news new num entry ov header) (setq wl-scores-messages nil) (message "Scoring...") - ;; Create messages, an alist of the form `(OVERVIEW . SCORE)'. - (while (setq ov (pop overview)) + ;; Create messages, an alist of the form `(ENTITY . SCORE)'. + (elmo-folder-do-each-message-entity (entity folder) (when (and (not (assq (setq num - (elmo-msgdb-overview-entity-get-number ov)) + (elmo-message-entity-number entity)) wl-summary-scored)) (or (memq num force-msgs) - (member (cadr (assq num mark-alist)) + (member (elmo-message-mark folder num) wl-summary-score-marks))) (setq wl-scores-messages - (cons (cons ov (or wl-summary-default-score 0)) + (cons (cons entity (or wl-summary-default-score 0)) wl-scores-messages)))) (save-excursion @@ -786,8 +784,8 @@ Set `wl-score-cache' nil." (< expire (setq day (wl-day-number - (elmo-msgdb-overview-entity-get-date - (car art))))))) + (elmo-message-entity-field + (car art) 'date)))))) (when (setq new (wl-score-add-followups (car art) score all-scores alist thread day)) @@ -930,8 +928,9 @@ Set `wl-score-cache' nil." (wl-summary-buffer-msgdb)))) msgs) (if (not expire) - (mapcar 'car (elmo-msgdb-get-number-alist - (wl-summary-buffer-msgdb))) ;; all messages + (elmo-folder-list-messages wl-summary-buffer-elmo-folder + nil t) + ;; XXX What's this? (catch 'break (while roverview (if (< (wl-day-number @@ -939,22 +938,18 @@ Set `wl-score-cache' nil." expire) (throw 'break t)) (wl-push (elmo-msgdb-overview-entity-get-number (car roverview)) - msgs) + msgs) (setq roverview (cdr roverview)))) msgs))) -(defsubst wl-score-get-overview () - (let ((num (wl-summary-message-number))) - (if num - (assoc (cdr (assq num (elmo-msgdb-get-number-alist - (wl-summary-buffer-msgdb)))) - (elmo-msgdb-get-overview (wl-summary-buffer-msgdb)))))) - (defun wl-score-get-header (header &optional extra) (let ((index (nth 2 (assoc header wl-score-header-index))) (decode (nth 3 (assoc header wl-score-header-index)))) (if index - (wl-score-ov-entity-get (wl-score-get-overview) index extra decode)))) + (wl-score-ov-entity-get + (elmo-message-entity wl-summary-buffer-elmo-folder + (wl-summary-message-number)) + index extra decode)))) (defun wl-score-kill-help-buffer () (when (get-buffer "*Score Help*") @@ -1144,8 +1139,8 @@ Set `wl-score-cache' nil." (cond ((string= header "followup") (if wl-score-auto-make-followup-entry (let ((wl-score-make-followup t)) - (wl-score-headers scores nil (wl-score-get-latest-msgs))) - (wl-score-headers scores nil + (wl-score-headers scores (wl-score-get-latest-msgs))) + (wl-score-headers scores (if (eq wl-summary-buffer-view 'thread) (wl-thread-get-children-msgs (wl-summary-message-number)) @@ -1155,7 +1150,7 @@ Set `wl-score-cache' nil." "references" (cdr (assoc "references" (car scores)))))) ((string= header "thread") - (wl-score-headers scores nil + (wl-score-headers scores (if (eq wl-summary-buffer-view 'thread) (wl-thread-get-children-msgs (wl-summary-message-number)) @@ -1165,18 +1160,16 @@ Set `wl-score-cache' nil." ;; remove parent (cdr (cdaar scores))))) (t - (wl-score-headers scores nil + (wl-score-headers scores (list (wl-summary-message-number))))) (wl-summary-score-update-all-lines t))) -(defun wl-summary-rescore-msgs (number-alist) - (mapcar - 'car - (nthcdr - (max (- (length number-alist) - wl-summary-rescore-partial-threshold) - 0) - number-alist))) +(defun wl-summary-rescore-msgs (numbers) + (nthcdr + (max (- (length numbers) + wl-summary-rescore-partial-threshold) + 0) + numbers)) (defun wl-summary-rescore (&optional arg) "Redo the entire scoring process in the current summary." @@ -1186,8 +1179,7 @@ Set `wl-score-cache' nil." (setq wl-score-cache nil) (setq wl-summary-scored nil) (setq number-alist (elmo-msgdb-get-number-alist (wl-summary-buffer-msgdb))) - (wl-summary-score-headers nil (wl-summary-buffer-msgdb) - (unless arg + (wl-summary-score-headers (unless arg (wl-summary-rescore-msgs number-alist))) (setq expunged (wl-summary-score-update-all-lines t)) (if expunged @@ -1195,12 +1187,11 @@ Set `wl-score-cache' nil." (set-buffer-modified-p nil))) ;; optional argument force-msgs is added by teranisi. -(defun wl-summary-score-headers (&optional folder msgdb force-msgs not-add) +(defun wl-summary-score-headers (&optional force-msgs not-add) "Do scoring if scoring is required." - (let ((scores (wl-score-get-score-alist - (or folder (wl-summary-buffer-folder-name))))) + (let ((scores (wl-score-get-score-alist))) (when scores - (wl-score-headers scores msgdb force-msgs not-add)))) + (wl-score-headers scores force-msgs not-add)))) (defun wl-summary-score-update-all-lines (&optional update) (let* ((alist wl-summary-scored) diff --git a/wl/wl-summary.el b/wl/wl-summary.el index 6559bd0..1cae974 100644 --- a/wl/wl-summary.el +++ b/wl/wl-summary.el @@ -218,8 +218,8 @@ See also variable `wl-use-petname'." (wl-summary-buffer-folder-name)) (wl-address-user-mail-address-p from) (cond - ((and (setq tos (elmo-msgdb-overview-entity-get-to - wl-message-entity)) + ((and (setq tos (elmo-message-entity-field + wl-message-entity 'to t)) (not (string= "" tos))) (setq retval (concat "To:" @@ -237,8 +237,8 @@ See also variable `wl-use-petname'." to)))) (wl-parse-addresses tos) ",")))) - ((setq ng (elmo-msgdb-overview-entity-get-extra-field - wl-message-entity "newsgroups")) + ((setq ng (elmo-message-entity-field + wl-message-entity 'newsgroups)) (setq retval (concat "Ng:" ng))))) (if wl-use-petname (setq retval (or (funcall wl-summary-get-petname-function from) @@ -568,7 +568,7 @@ See also variable `wl-use-petname'." (wl-summary-redisplay))) (defun wl-summary-count-unread () - (let ((lst (elmo-msgdb-count-marks (wl-summary-buffer-msgdb)))) + (let ((lst (elmo-folder-count-flags wl-summary-buffer-elmo-folder))) (if (eq major-mode 'wl-summary-mode) (setq wl-summary-buffer-new-count (car lst) wl-summary-buffer-unread-count (nth 1 lst) @@ -712,7 +712,7 @@ you." wl-summary-buffer-line-formatter formatter) (insert (wl-summary-create-line - (elmo-msgdb-make-entity + (elmo-msgdb-make-message-entity :number 10000 :from "foo" :subject "bar" @@ -828,74 +828,67 @@ Entering Folder mode calls the value of `wl-summary-mode-hook'." ;; of system internal to accord facilities for the Emacs variants. (run-hooks 'wl-summary-mode-hook)) +;;; (defun wl-summary-overview-entity-compare-by-date (x y) "Compare entity X and Y by date." (condition-case nil (string< (timezone-make-date-sortable - (elmo-msgdb-overview-entity-get-date x)) + (elmo-message-entity-field x 'date)) (timezone-make-date-sortable - (elmo-msgdb-overview-entity-get-date y))) + (elmo-message-entity-field y 'date))) (error))) ;; ignore error. (defun wl-summary-overview-entity-compare-by-number (x y) "Compare entity X and Y by number." (< - (elmo-msgdb-overview-entity-get-number x) - (elmo-msgdb-overview-entity-get-number y))) + (elmo-message-entity-number x) + (elmo-message-entity-number y))) (defun wl-summary-overview-entity-compare-by-from (x y) "Compare entity X and Y by from." (string< (wl-address-header-extract-address - (or (elmo-msgdb-overview-entity-get-from-no-decode x) + (or (elmo-message-entity-field x 'from) wl-summary-no-from-message)) (wl-address-header-extract-address - (or (elmo-msgdb-overview-entity-get-from-no-decode y) + (or (elmo-message-entity-field y 'from) wl-summary-no-from-message)))) (defun wl-summary-overview-entity-compare-by-subject (x y) "Compare entity X and Y by subject." - (string< (elmo-msgdb-overview-entity-get-subject-no-decode x) - (elmo-msgdb-overview-entity-get-subject-no-decode y))) + (string< (elmo-message-entity-field x 'subject) + (elmo-message-entity-field y 'subject))) (defun wl-summary-get-list-info (entity) "Returns (\"ML-name\" . ML-count) of ENTITY." (let (sequence ml-name ml-count subject return-path delivered-to mailing-list) - (setq sequence (elmo-msgdb-overview-entity-get-extra-field - entity "x-sequence") - ml-name (or (elmo-msgdb-overview-entity-get-extra-field - entity "x-ml-name") + (setq sequence (elmo-message-entity-field entity 'x-sequence) + ml-name (or (elmo-message-entity-field entity 'x-ml-name) (and sequence (car (split-string sequence " ")))) - ml-count (or (elmo-msgdb-overview-entity-get-extra-field - entity "x-mail-count") - (elmo-msgdb-overview-entity-get-extra-field - entity "x-ml-count") + ml-count (or (elmo-message-entity-field entity 'x-mail-count) + (elmo-message-entity-field entity 'x-ml-count) (and sequence (cadr (split-string sequence " "))))) - (and (setq subject (elmo-msgdb-overview-entity-get-subject - entity)) + (and (setq subject (elmo-message-entity-field entity 'subject t)) (setq subject (elmo-delete-char ?\n subject)) (string-match "^\\s(\\(\\S)+\\)[ :]\\([0-9]+\\)\\s)[ \t]*" subject) (progn (or ml-name (setq ml-name (match-string 1 subject))) (or ml-count (setq ml-count (match-string 2 subject))))) (and (setq return-path - (elmo-msgdb-overview-entity-get-extra-field - entity "return-path")) + (elmo-message-entity-field entity 'return-path)) (string-match "^<\\([^@>]+\\)-return-\\([0-9]+\\)-" return-path) (progn (or ml-name (setq ml-name (match-string 1 return-path))) (or ml-count (setq ml-count (match-string 2 return-path))))) (and (setq delivered-to - (elmo-msgdb-overview-entity-get-extra-field - entity "delivered-to")) + (elmo-message-entity-field entity 'delivered-to)) (string-match "^mailing list \\([^@]+\\)@" delivered-to) (or ml-name (setq ml-name (match-string 1 delivered-to)))) (and (setq mailing-list - (elmo-msgdb-overview-entity-get-extra-field - entity "mailing-list")) + (elmo-message-entity-field entity 'mailing-list)) (string-match "\\(^\\|; \\)contact \\([^@]+\\)-[^-@]+@" mailing-list) ; *-help@, *-owner@, etc. (or ml-name (setq ml-name (match-string 2 mailing-list)))) (cons (and ml-name (car (split-string ml-name " "))) @@ -932,45 +925,45 @@ Entering Folder mode calls the value of `wl-summary-mode-hook'." (defun wl-summary-rescan (&optional sort-by) "Rescan current folder without updating." (interactive) - (let* ((cur-buf (current-buffer)) - (msgdb (wl-summary-buffer-msgdb)) - (overview (elmo-msgdb-get-overview msgdb)) - (number-alist (elmo-msgdb-get-number-alist msgdb)) - (elmo-mime-charset wl-summary-buffer-mime-charset) - i percent num - gc-message entity - curp - (inhibit-read-only t) - (buffer-read-only nil) - expunged) + (let ((elmo-mime-charset wl-summary-buffer-mime-charset) + i percent num + gc-message entity + curp + (inhibit-read-only t) + (buffer-read-only nil) + numbers expunged) (erase-buffer) (message "Re-scanning...") (setq i 0) - (setq num (length overview)) + (setq num (length wl-summary-buffer-number-list)) + (setq numbers wl-summary-buffer-number-list) (when sort-by (message "Sorting by %s..." sort-by) - (setq overview - (sort overview - (intern (format "wl-summary-overview-entity-compare-by-%s" - sort-by)))) - (message "Sorting by %s...done" sort-by) - (elmo-msgdb-set-overview (wl-summary-buffer-msgdb) - overview)) - (setq curp overview) - (set-buffer cur-buf) - (setq wl-thread-entity-hashtb (elmo-make-hash (* (length overview) 2))) - (setq wl-thread-entity-list nil) - (setq wl-thread-entities nil) - (setq wl-summary-buffer-number-list nil) - (setq wl-summary-buffer-target-mark-list nil) - (setq wl-summary-buffer-refile-list nil) - (setq wl-summary-buffer-delete-list nil) - (setq wl-summary-delayed-update nil) + (setq numbers + (sort wl-summary-buffer-number-list + (lambda (x y) + (funcall + (intern (format "wl-summary-overview-entity-compare-by-%s" + sort-by)) + (elmo-message-entity wl-summary-buffer-elmo-folder x) + (elmo-message-entity wl-summary-buffer-elmo-folder y))))) + (message "Sorting by %s...done" sort-by)) + (setq wl-thread-entity-hashtb (elmo-make-hash (* num 2)) + wl-thread-entity-list nil + wl-thread-entities nil + wl-summary-buffer-number-list nil + wl-summary-buffer-target-mark-list nil + wl-summary-buffer-refile-list nil + wl-summary-buffer-delete-list nil + wl-summary-delayed-update nil) (elmo-kill-buffer wl-summary-search-buf-name) - (while curp - (setq entity (car curp)) - (wl-summary-insert-message entity msgdb nil) - (setq curp (cdr curp)) + (while numbers + (setq entity (elmo-message-entity wl-summary-buffer-elmo-folder + (car numbers))) + (wl-summary-insert-message entity + wl-summary-buffer-elmo-folder + nil) + (setq numbers (cdr numbers)) (when (> num elmo-display-progress-threshold) (setq i (+ i 1)) (if (or (zerop (% i 5)) (= i num)) @@ -984,10 +977,10 @@ Entering Folder mode calls the value of `wl-summary-mode-hook'." (elmo-msgdb-overview-entity-get-number (cdar wl-summary-delayed-update))) (wl-summary-insert-message - (cdar wl-summary-delayed-update) msgdb nil t) + (cdar wl-summary-delayed-update) + wl-summary-buffer-elmo-folder nil t) (setq wl-summary-delayed-update (cdr wl-summary-delayed-update)))) (message "Constructing summary structure...done") - (set-buffer cur-buf) (if (eq wl-summary-buffer-view 'thread) (progn (message "Inserting thread...") @@ -995,8 +988,8 @@ Entering Folder mode calls the value of `wl-summary-mode-hook'." (message "Inserting thread...done"))) (when wl-use-scoring (setq wl-summary-scored nil) - (wl-summary-score-headers nil msgdb - (wl-summary-rescore-msgs number-alist) + (wl-summary-score-headers (wl-summary-rescore-msgs + wl-summary-buffer-number-list) t) (when (and wl-summary-scored (setq expunged (wl-summary-score-update-all-lines))) @@ -1734,6 +1727,7 @@ If ARG is non-nil, checking is omitted." (msgs2 msgs) (len (length msgs)) (i 0) + (deleting-info (or deleting-info "Deleting...")) update-list) (elmo-kill-buffer wl-summary-search-buf-name) (while msgs @@ -1751,8 +1745,7 @@ If ARG is non-nil, checking is omitted." (delete-char 1) ; delete '\n' (setq wl-summary-buffer-number-list (delq (car msgs) wl-summary-buffer-number-list))))) - (when (and deleting-info - (> len elmo-display-progress-threshold)) + (when (> len elmo-display-progress-threshold) (setq i (1+ i)) (if (or (zerop (% i 5)) (= i len)) (elmo-display-progress @@ -1760,9 +1753,9 @@ If ARG is non-nil, checking is omitted." (/ (* i 100) len)))) (setq msgs (cdr msgs))) (when (eq wl-summary-buffer-view 'thread) - (wl-thread-update-line-msgs (elmo-uniq-list update-list) - (unless deleting-info 'no-msg)) + (wl-thread-update-line-msgs (elmo-uniq-list update-list)) (wl-thread-cleanup-symbols msgs2)) + (message (concat deleting-info "done")) (wl-summary-count-unread) (wl-summary-update-modeline) (wl-folder-update-unread @@ -1824,7 +1817,7 @@ If ARG is non-nil, checking is omitted." (defun wl-summary-insert-message (&rest args) (if (eq wl-summary-buffer-view 'thread) - (apply 'wl-summary-insert-thread-entity args) + (apply 'wl-summary-insert-thread args) (apply 'wl-summary-insert-sequential args))) (defun wl-summary-sort () @@ -1924,13 +1917,6 @@ If ARG is non-nil, checking is omitted." (progn ;; Setup sync-all (if sync-all (wl-summary-sync-all-init)) -; (if (and has-nntp -; (elmo-nntp-max-number-precedes-list-active-p)) - ;; XXX this does not work correctly in rare case. -; (setq delete-list -; (wl-summary-delete-canceled-msgs-from-list -; delete-list -; (wl-summary-buffer-msgdb)))) (setq diff (elmo-list-diff (elmo-folder-list-messages folder 'visible-only @@ -1940,67 +1926,55 @@ If ARG is non-nil, checking is omitted." (setq delete-list (cadr diff)) (when delete-list - (wl-summary-delete-messages-on-buffer - delete-list "Deleting...") - (message "Deleting...done")) + (wl-summary-delete-messages-on-buffer delete-list)) (wl-summary-update-status-marks) - (setq curp append-list) - (setq num (length curp)) - (when append-list - (setq i 0) - - ;; set these value for append-message-func - (setq overview (elmo-msgdb-get-overview - (elmo-folder-msgdb folder))) - (setq number-alist (elmo-msgdb-get-number-alist - (elmo-folder-msgdb folder))) - - (setq wl-summary-delayed-update nil) - (elmo-kill-buffer wl-summary-search-buf-name) - (while curp - (setq entity (elmo-msgdb-overview-get-entity - (car curp) (elmo-folder-msgdb folder))) + (setq num (length append-list)) + (setq i 0) + (setq wl-summary-delayed-update nil) + (elmo-kill-buffer wl-summary-search-buf-name) + (dolist (number append-list) + (setq entity (elmo-message-entity folder number)) + (when (setq update-thread + (wl-summary-insert-message + entity folder + (not sync-all))) + (wl-append update-top-list update-thread)) + (if elmo-use-database + (elmo-database-msgid-put + (car entity) (elmo-folder-name-internal folder) + (elmo-msgdb-overview-entity-get-number entity))) + (when (> num elmo-display-progress-threshold) + (setq i (+ i 1)) + (if (or (zerop (% i 5)) (= i num)) + (elmo-display-progress + 'wl-summary-sync-update + (if (eq wl-summary-buffer-view 'thread) + "Making thread..." + "Inserting message...") + (/ (* i 100) num))))) + (when wl-summary-delayed-update + (while wl-summary-delayed-update + (message "Parent (%d) of message %d is no entity" + (caar wl-summary-delayed-update) + (elmo-msgdb-overview-entity-get-number + (cdar wl-summary-delayed-update))) (when (setq update-thread (wl-summary-insert-message - entity (elmo-folder-msgdb folder) - (not sync-all))) + (cdar wl-summary-delayed-update) + wl-summary-buffer-elmo-folder + (not sync-all) t)) (wl-append update-top-list update-thread)) - (if elmo-use-database - (elmo-database-msgid-put - (car entity) (elmo-folder-name-internal folder) - (elmo-msgdb-overview-entity-get-number entity))) - (setq curp (cdr curp)) - (when (> num elmo-display-progress-threshold) - (setq i (+ i 1)) - (if (or (zerop (% i 5)) (= i num)) - (elmo-display-progress - 'wl-summary-sync-update - (if (eq wl-summary-buffer-view 'thread) - "Making thread..." - "Inserting message...") - (/ (* i 100) num))))) - (when wl-summary-delayed-update - (while wl-summary-delayed-update - (message "Parent (%d) of message %d is no entity" - (caar wl-summary-delayed-update) - (elmo-msgdb-overview-entity-get-number - (cdar wl-summary-delayed-update))) - (when (setq update-thread - (wl-summary-insert-message - (cdar wl-summary-delayed-update) - (elmo-folder-msgdb folder) - (not sync-all) t)) - (wl-append update-top-list update-thread)) - (setq wl-summary-delayed-update - (cdr wl-summary-delayed-update)))) - (when (and (eq wl-summary-buffer-view 'thread) - update-top-list) - (wl-thread-update-indent-string-thread - (elmo-uniq-list update-top-list))) - (message (if (eq wl-summary-buffer-view 'thread) - "Making thread...done" - "Inserting message...done"))) - (wl-summary-set-message-modified) + (setq wl-summary-delayed-update + (cdr wl-summary-delayed-update)))) + (when (and (eq wl-summary-buffer-view 'thread) + update-top-list) + (wl-thread-update-indent-string-thread + (elmo-uniq-list update-top-list))) + (message (if (eq wl-summary-buffer-view 'thread) + "Making thread...done" + "Inserting message...done")) + (when (or delete-list append-list) + (wl-summary-set-message-modified)) (when (and sync-all (eq wl-summary-buffer-view 'thread)) (elmo-kill-buffer wl-summary-search-buf-name) (message "Inserting message...") @@ -2024,8 +1998,7 @@ If ARG is non-nil, checking is omitted." ;; scoring (when wl-use-scoring (setq wl-summary-scored nil) - (wl-summary-score-headers nil (wl-summary-buffer-msgdb) - (and sync-all + (wl-summary-score-headers (and sync-all (wl-summary-rescore-msgs number-alist)) sync-all) (when (and wl-summary-scored @@ -2574,19 +2547,19 @@ If ARG, without confirm." (ignore-errors (run-hooks 'wl-summary-line-inserted-hook))) -(defun wl-summary-insert-sequential (entity msgdb &rest args) +(defun wl-summary-insert-sequential (entity folder &rest args) (let ((inhibit-read-only t) buffer-read-only) (goto-char (point-max)) (wl-summary-insert-line (wl-summary-create-line entity nil nil - (elmo-msgdb-get-mark - msgdb - (elmo-msgdb-overview-entity-get-number + (elmo-message-mark + folder + (elmo-message-entity-number entity)))) (setq wl-summary-buffer-number-list (wl-append wl-summary-buffer-number-list - (list (elmo-msgdb-overview-entity-get-number entity)))) + (list (elmo-message-entity-number entity)))) nil)) (defun wl-summary-default-subject-filter (subject) @@ -2608,14 +2581,15 @@ If ARG, without confirm." (` (elmo-get-hash-val (format "#%d" (wl-count-lines)) wl-summary-alike-hashtb))) -(defun wl-summary-insert-headers (overview func mime-decode) - (let (ov this last alike) +(defun wl-summary-insert-headers (folder func mime-decode) + (let ((entities (elmo-folder-list-message-entities folder)) + ov this last alike) (buffer-disable-undo (current-buffer)) (make-local-variable 'wl-summary-alike-hashtb) - (setq wl-summary-alike-hashtb (elmo-make-hash (* (length overview) 2))) + (setq wl-summary-alike-hashtb (elmo-make-hash (* (length entities) 2))) (when mime-decode (elmo-set-buffer-multibyte default-enable-multibyte-characters)) - (while (setq ov (pop overview)) + (while (setq ov (pop entities)) (setq this (funcall func ov)) (and this (setq this (std11-unfold-string this))) (if (equal last this) @@ -2635,7 +2609,7 @@ If ARG, without confirm." (eword-decode-region (point-min) (point-max)))) (run-hooks 'wl-summary-insert-headers-hook))) -(defun wl-summary-search-by-subject (entity overview) +(defun wl-summary-search-by-subject (entity folder) (let ((summary-buf (current-buffer)) (buf (get-buffer-create wl-summary-search-buf-name)) (folder-name (wl-summary-buffer-folder-name)) @@ -2647,15 +2621,16 @@ If ARG, without confirm." (setq wl-summary-search-buf-folder-name folder-name) (message "Creating subject cache...") (wl-summary-insert-headers - overview + folder (function (lambda (x) (funcall wl-summary-subject-filter-function - (elmo-msgdb-overview-entity-get-subject-no-decode x)))) + (elmo-message-entity-field x 'subject)))) t) (message "Creating subject cache...done")) (setq match (funcall wl-summary-subject-filter-function - (elmo-msgdb-overview-entity-get-subject entity))) + (elmo-message-entity-field entity 'subject + 'decode))) (if (string= match "") (setq match "\n")) (goto-char (point-max)) @@ -2671,50 +2646,45 @@ If ARG, without confirm." ;; the first element of found-entity list exists on ;; thread tree. (wl-thread-get-entity - (elmo-msgdb-overview-entity-get-number - (car founds))) + (elmo-message-entity-number (car founds))) ;; message id is not same as myself. (not (string= - (elmo-msgdb-overview-entity-get-id entity) - (elmo-msgdb-overview-entity-get-id (car founds)))) + (elmo-message-entity-field entity 'message-id) + (elmo-message-entity-field (car founds) + 'message-id))) ;; not a descendant. (not (wl-thread-descendant-p - (elmo-msgdb-overview-entity-get-number entity) - (elmo-msgdb-overview-entity-get-number - (car founds))))) + (elmo-message-entity-number entity) + (elmo-message-entity-number (car founds))))) (setq result (car founds) founds nil)) (setq founds (cdr founds)))))) result)))) -(defun wl-summary-insert-thread-entity (entity msgdb update - &optional force-insert) - (let* ((overview (elmo-msgdb-get-overview msgdb)) - this-id - parent-entity - parent-number - (case-fold-search t) - (depth 0) relatives anumber - cur number overview2 cur-entity linked retval delayed-entity - update-list entity-stack) +(defun wl-summary-insert-thread (entity folder update + &optional force-insert) + (let ((case-fold-search t) + (depth 0) + this-id parent-entity parent-number relatives anumber + cur number cur-entity linked retval delayed-entity + update-list entity-stack) (while entity - (setq this-id (elmo-msgdb-overview-entity-get-id entity) + (setq this-id (elmo-message-entity-field entity 'message-id) parent-entity - (elmo-msgdb-get-parent-entity entity msgdb) - parent-number (elmo-msgdb-overview-entity-get-number - parent-entity)) - (setq number (elmo-msgdb-overview-entity-get-number entity)) + (elmo-message-entity-parent folder entity) + parent-number (elmo-message-entity-number parent-entity)) + (setq number (elmo-message-entity-number entity)) (setq cur entity) ;; If thread loop detected, set parent as nil. (while cur (setq anumber - (elmo-msgdb-overview-entity-get-number - (setq cur (elmo-msgdb-get-parent-entity cur msgdb)))) + (elmo-message-entity-number + (setq cur (elmo-message-entity-parent folder cur)))) (if (memq anumber relatives) (setq parent-number nil cur nil)) (setq relatives (cons - (elmo-msgdb-overview-entity-get-number cur) + (elmo-message-entity-number cur) relatives))) (if (and parent-number (not (wl-thread-get-entity parent-number)) @@ -2730,21 +2700,21 @@ If ARG, without confirm." (string-match wl-summary-search-parent-by-subject-regexp (elmo-msgdb-overview-entity-get-subject entity))) - (let ((found (wl-summary-search-by-subject entity overview))) + (let ((found (wl-summary-search-by-subject entity folder))) (when (and found (not (member found wl-summary-delayed-update))) (setq parent-entity found) (setq parent-number - (elmo-msgdb-overview-entity-get-number parent-entity)) + (elmo-message-entity-number parent-entity)) (setq linked t)))) ;; If subject is change, divide thread. (if (and parent-number wl-summary-divide-thread-when-subject-changed (not (wl-summary-subject-equal - (or (elmo-msgdb-overview-entity-get-subject - entity) "") - (or (elmo-msgdb-overview-entity-get-subject - parent-entity) "")))) + (or (elmo-message-entity-field entity + 'subject t) "") + (or (elmo-message-entity-field parent-entity + 'subject t) "")))) (setq parent-number nil)) (setq retval (wl-thread-insert-message entity @@ -3895,7 +3865,6 @@ If ARG, exit virtual folder." (let ((inhibit-read-only t) (buffer-read-only nil) (folder wl-summary-buffer-elmo-folder) - (msgdb (wl-summary-buffer-msgdb)) (case-fold-search nil) number-list mark visible new-mark) (setq number-list (or (and (numberp number-or-numbers) @@ -4602,13 +4571,10 @@ Return t if message exists." (interactive) (let* ((original (wl-summary-message-number)) (msgid (elmo-string (or id (read-from-minibuffer "Message-ID: ")))) - (number-alist (elmo-msgdb-get-number-alist (wl-summary-buffer-msgdb))) + (entity (elmo-message-entity wl-summary-buffer-elmo-folder msgid)) msg otherfld schar - (errmsg - (format "No message with id \"%s\" in the folder." msgid))) - (if (setq msg (car (rassoc msgid number-alist))) -;;; (wl-summary-jump-to-msg-internal -;;; (wl-summary-buffer-folder-name) msg 'no-sync) + (errmsg (format "No message with id \"%s\" in the folder." msgid))) + (if (setq msg (elmo-message-entity-number entity)) (progn (wl-thread-jump-to-msg msg) t)