Mercurial > emacs
comparison lisp/gnus/gnus-cache.el @ 85712:a3c27999decb
Update Gnus to No Gnus 0.7 from the Gnus CVS trunk
Revision: emacs@sv.gnu.org/emacs--devo--0--patch-911
author | Miles Bader <miles@gnu.org> |
---|---|
date | Sun, 28 Oct 2007 09:18:39 +0000 |
parents | 24202b793a08 |
children | 781256628613 880960b70474 |
comparison
equal
deleted
inserted
replaced
85711:b6f5dc84b2e1 | 85712:a3c27999decb |
---|---|
28 ;;; Code: | 28 ;;; Code: |
29 | 29 |
30 (eval-when-compile (require 'cl)) | 30 (eval-when-compile (require 'cl)) |
31 | 31 |
32 (require 'gnus) | 32 (require 'gnus) |
33 (require 'gnus-int) | |
34 (require 'gnus-range) | |
35 (require 'gnus-start) | |
36 (eval-when-compile | 33 (eval-when-compile |
37 (if (not (fboundp 'gnus-agent-load-alist)) | 34 (unless (fboundp 'gnus-agent-load-alist) |
38 (defun gnus-agent-load-alist (group))) | 35 (defun gnus-agent-load-alist (group))) |
39 (require 'gnus-sum)) | 36 (require 'gnus-sum)) |
40 | 37 |
41 (defcustom gnus-cache-active-file | 38 (defcustom gnus-cache-active-file |
42 (expand-file-name "active" gnus-cache-directory) | 39 (expand-file-name "active" gnus-cache-directory) |
90 | 87 |
91 (defvar gnus-cache-removable-articles nil) | 88 (defvar gnus-cache-removable-articles nil) |
92 (defvar gnus-cache-buffer nil) | 89 (defvar gnus-cache-buffer nil) |
93 (defvar gnus-cache-active-hashtb nil) | 90 (defvar gnus-cache-active-hashtb nil) |
94 (defvar gnus-cache-active-altered nil) | 91 (defvar gnus-cache-active-altered nil) |
92 (defvar gnus-cache-total-fetched-hashtb nil) | |
95 | 93 |
96 (eval-and-compile | 94 (eval-and-compile |
97 (autoload 'nnml-generate-nov-databases-1 "nnml") | 95 (autoload 'nnml-generate-nov-databases-1 "nnml") |
98 (autoload 'nnvirtual-find-group-art "nnvirtual")) | 96 (autoload 'nnvirtual-find-group-art "nnvirtual")) |
99 | 97 |
131 (if (> (buffer-size) 0) | 129 (if (> (buffer-size) 0) |
132 ;; Non-empty overview, write it to a file. | 130 ;; Non-empty overview, write it to a file. |
133 (let ((coding-system-for-write | 131 (let ((coding-system-for-write |
134 gnus-cache-overview-coding-system)) | 132 gnus-cache-overview-coding-system)) |
135 (gnus-write-buffer overview-file)) | 133 (gnus-write-buffer overview-file)) |
136 ;; Empty overview file, remove it | 134 (let ((file-name-coding-system nnmail-pathname-coding-system)) |
137 (when (file-exists-p overview-file) | 135 ;; Empty overview file, remove it |
138 (delete-file overview-file)) | 136 (when (file-exists-p overview-file) |
139 ;; If possible, remove group's cache subdirectory. | 137 (delete-file overview-file)) |
140 (condition-case nil | 138 ;; If possible, remove group's cache subdirectory. |
141 ;; FIXME: we can detect the error type and warn the user | 139 (condition-case nil |
142 ;; of any inconsistencies (articles w/o nov entries?). | 140 ;; FIXME: we can detect the error type and warn the user |
143 ;; for now, just be conservative...delete only if safe -- sj | 141 ;; of any inconsistencies (articles w/o nov entries?). |
144 (delete-directory (file-name-directory overview-file)) | 142 ;; for now, just be conservative...delete only if safe -- sj |
145 (error nil))))) | 143 (delete-directory (file-name-directory overview-file)) |
144 (error)))) | |
145 | |
146 (gnus-cache-update-overview-total-fetched-for | |
147 (car gnus-cache-buffer) overview-file))) | |
146 ;; Kill the buffer -- it's either unmodified or saved. | 148 ;; Kill the buffer -- it's either unmodified or saved. |
147 (gnus-kill-buffer buffer) | 149 (gnus-kill-buffer buffer) |
148 (setq gnus-cache-buffer nil)))) | 150 (setq gnus-cache-buffer nil)))) |
149 | 151 |
150 (defun gnus-cache-possibly-enter-article | 152 (defun gnus-cache-possibly-enter-article |
151 (group article ticked dormant unread &optional force) | 153 (group article ticked dormant unread &optional force) |
152 (when (and (or force (not (eq gnus-use-cache 'passive))) | 154 (when (and (or force (not (eq gnus-use-cache 'passive))) |
153 (numberp article) | 155 (numberp article) |
154 (> article 0)) ; This might be a dummy article. | 156 (> article 0)) ; This might be a dummy article. |
155 (let ((number article) file headers) | 157 (let ((number article) |
158 file headers lines-chars | |
159 (file-name-coding-system nnmail-pathname-coding-system)) | |
156 ;; If this is a virtual group, we find the real group. | 160 ;; If this is a virtual group, we find the real group. |
157 (when (gnus-virtual-group-p group) | 161 (when (gnus-virtual-group-p group) |
158 (let ((result (nnvirtual-find-group-art | 162 (let ((result (nnvirtual-find-group-art |
159 (gnus-group-real-name group) article))) | 163 (gnus-group-real-name group) article))) |
160 (setq group (car result) | 164 (setq group (car result) |
178 (let ((gnus-use-cache nil) | 182 (let ((gnus-use-cache nil) |
179 (gnus-article-decode-hook nil)) | 183 (gnus-article-decode-hook nil)) |
180 (gnus-request-article-this-buffer number group)) | 184 (gnus-request-article-this-buffer number group)) |
181 (when (> (buffer-size) 0) | 185 (when (> (buffer-size) 0) |
182 (let ((coding-system-for-write gnus-cache-coding-system)) | 186 (let ((coding-system-for-write gnus-cache-coding-system)) |
183 (gnus-write-buffer file)) | 187 (gnus-write-buffer file) |
188 (gnus-cache-update-file-total-fetched-for group file)) | |
189 (setq lines-chars (nnheader-get-lines-and-char)) | |
184 (nnheader-remove-body) | 190 (nnheader-remove-body) |
185 (setq headers (nnheader-parse-naked-head)) | 191 (setq headers (nnheader-parse-naked-head)) |
186 (mail-header-set-number headers number) | 192 (mail-header-set-number headers number) |
193 (mail-header-set-lines headers (car lines-chars)) | |
194 (mail-header-set-chars headers (cadr lines-chars)) | |
187 (gnus-cache-change-buffer group) | 195 (gnus-cache-change-buffer group) |
188 (set-buffer (cdr gnus-cache-buffer)) | 196 (set-buffer (cdr gnus-cache-buffer)) |
189 (goto-char (point-max)) | 197 (goto-char (point-max)) |
190 (forward-line -1) | 198 (forward-line -1) |
191 (while (condition-case () | 199 (while (condition-case () |
234 (setq gnus-cache-removable-articles nil))) | 242 (setq gnus-cache-removable-articles nil))) |
235 | 243 |
236 (defun gnus-cache-possibly-remove-articles-1 () | 244 (defun gnus-cache-possibly-remove-articles-1 () |
237 "Possibly remove some of the removable articles." | 245 "Possibly remove some of the removable articles." |
238 (when (gnus-cache-fully-p gnus-newsgroup-name) | 246 (when (gnus-cache-fully-p gnus-newsgroup-name) |
239 (let ((articles gnus-cache-removable-articles) | 247 (let ((cache-articles gnus-newsgroup-cached)) |
240 (cache-articles gnus-newsgroup-cached) | |
241 article) | |
242 (gnus-cache-change-buffer gnus-newsgroup-name) | 248 (gnus-cache-change-buffer gnus-newsgroup-name) |
243 (while articles | 249 (dolist (article gnus-cache-removable-articles) |
244 (when (memq (setq article (pop articles)) cache-articles) | 250 (when (memq article cache-articles) |
245 ;; The article was in the cache, so we see whether we are | 251 ;; The article was in the cache, so we see whether we are |
246 ;; supposed to remove it from the cache. | 252 ;; supposed to remove it from the cache. |
247 (gnus-cache-possibly-remove-article | 253 (gnus-cache-possibly-remove-article |
248 article (memq article gnus-newsgroup-marked) | 254 article (memq article gnus-newsgroup-marked) |
249 (memq article gnus-newsgroup-dormant) | 255 (memq article gnus-newsgroup-dormant) |
254 (gnus-cache-save-buffers))) | 260 (gnus-cache-save-buffers))) |
255 | 261 |
256 (defun gnus-cache-request-article (article group) | 262 (defun gnus-cache-request-article (article group) |
257 "Retrieve ARTICLE in GROUP from the cache." | 263 "Retrieve ARTICLE in GROUP from the cache." |
258 (let ((file (gnus-cache-file-name group article)) | 264 (let ((file (gnus-cache-file-name group article)) |
259 (buffer-read-only nil)) | 265 (buffer-read-only nil) |
266 (file-name-coding-system nnmail-pathname-coding-system)) | |
260 (when (file-exists-p file) | 267 (when (file-exists-p file) |
261 (erase-buffer) | 268 (erase-buffer) |
262 (gnus-kill-all-overlays) | 269 (gnus-kill-all-overlays) |
263 (let ((coding-system-for-read gnus-cache-coding-system)) | 270 (let ((coding-system-for-read gnus-cache-coding-system)) |
264 (insert-file-contents file)) | 271 (insert-file-contents file)) |
283 ;; the normal way. | 290 ;; the normal way. |
284 (let ((gnus-use-cache nil)) | 291 (let ((gnus-use-cache nil)) |
285 (gnus-retrieve-headers articles group fetch-old)) | 292 (gnus-retrieve-headers articles group fetch-old)) |
286 (let ((uncached-articles (gnus-sorted-difference articles cached)) | 293 (let ((uncached-articles (gnus-sorted-difference articles cached)) |
287 (cache-file (gnus-cache-file-name group ".overview")) | 294 (cache-file (gnus-cache-file-name group ".overview")) |
288 type) | 295 type |
296 (file-name-coding-system nnmail-pathname-coding-system)) | |
289 ;; We first retrieve all the headers that we don't have in | 297 ;; We first retrieve all the headers that we don't have in |
290 ;; the cache. | 298 ;; the cache. |
291 (let ((gnus-use-cache nil)) | 299 (let ((gnus-use-cache nil)) |
292 (when uncached-articles | 300 (when uncached-articles |
293 (setq type (and articles | 301 (setq type (and articles |
323 (defun gnus-cache-enter-article (&optional n) | 331 (defun gnus-cache-enter-article (&optional n) |
324 "Enter the next N articles into the cache. | 332 "Enter the next N articles into the cache. |
325 If not given a prefix, use the process marked articles instead. | 333 If not given a prefix, use the process marked articles instead. |
326 Returns the list of articles entered." | 334 Returns the list of articles entered." |
327 (interactive "P") | 335 (interactive "P") |
328 (let ((articles (gnus-summary-work-articles n)) | 336 (let (out) |
329 article out) | 337 (dolist (article (gnus-summary-work-articles n)) |
330 (while (setq article (pop articles)) | |
331 (gnus-summary-remove-process-mark article) | 338 (gnus-summary-remove-process-mark article) |
332 (if (natnump article) | 339 (if (natnump article) |
333 (when (gnus-cache-possibly-enter-article | 340 (when (gnus-cache-possibly-enter-article |
334 gnus-newsgroup-name article | 341 gnus-newsgroup-name article |
335 nil nil nil t) | 342 nil nil nil t) |
346 "Remove the next N articles from the cache. | 353 "Remove the next N articles from the cache. |
347 If not given a prefix, use the process marked articles instead. | 354 If not given a prefix, use the process marked articles instead. |
348 Returns the list of articles removed." | 355 Returns the list of articles removed." |
349 (interactive "P") | 356 (interactive "P") |
350 (gnus-cache-change-buffer gnus-newsgroup-name) | 357 (gnus-cache-change-buffer gnus-newsgroup-name) |
351 (let ((articles (gnus-summary-work-articles n)) | 358 (let (out) |
352 article out) | 359 (dolist (article (gnus-summary-work-articles n)) |
353 (while articles | |
354 (setq article (pop articles)) | |
355 (gnus-summary-remove-process-mark article) | 360 (gnus-summary-remove-process-mark article) |
356 (when (gnus-cache-possibly-remove-article article nil nil nil t) | 361 (when (gnus-cache-possibly-remove-article article nil nil nil t) |
357 (when gnus-newsgroup-agentized | 362 (when gnus-newsgroup-agentized |
358 (let ((alist (gnus-agent-load-alist gnus-newsgroup-name))) | 363 (let ((alist (gnus-agent-load-alist gnus-newsgroup-name))) |
359 (unless (cdr (assoc article alist)) | 364 (unless (cdr (assoc article alist)) |
405 (cons group | 410 (cons group |
406 (set-buffer (gnus-get-buffer-create | 411 (set-buffer (gnus-get-buffer-create |
407 " *gnus-cache-overview*")))) | 412 " *gnus-cache-overview*")))) |
408 ;; Insert the contents of this group's cache overview. | 413 ;; Insert the contents of this group's cache overview. |
409 (erase-buffer) | 414 (erase-buffer) |
410 (let ((file (gnus-cache-file-name group ".overview"))) | 415 (let ((file (gnus-cache-file-name group ".overview")) |
416 (file-name-coding-system nnmail-pathname-coding-system)) | |
411 (when (file-exists-p file) | 417 (when (file-exists-p file) |
412 (nnheader-insert-file-contents file))) | 418 (nnheader-insert-file-contents file))) |
413 ;; We have a fresh (empty/just loaded) buffer, | 419 ;; We have a fresh (empty/just loaded) buffer, |
414 ;; mark it as unmodified to save a redundant write later. | 420 ;; mark it as unmodified to save a redundant write later. |
415 (set-buffer-modified-p nil)))) | 421 (set-buffer-modified-p nil)))) |
419 (or (and ticked (memq 'ticked class)) | 425 (or (and ticked (memq 'ticked class)) |
420 (and dormant (memq 'dormant class)) | 426 (and dormant (memq 'dormant class)) |
421 (and unread (memq 'unread class)) | 427 (and unread (memq 'unread class)) |
422 (and (not unread) (not ticked) (not dormant) (memq 'read class)))) | 428 (and (not unread) (not ticked) (not dormant) (memq 'read class)))) |
423 | 429 |
430 (defvar gnus-cache-decoded-group-names nil | |
431 "Alist of original group names and decoded group names. | |
432 Decoding is done according to `gnus-group-name-charset-method-alist' | |
433 or `gnus-group-name-charset-group-alist'.") | |
434 | |
435 (defvar gnus-cache-unified-group-names nil | |
436 "Alist of unified decoded group names and original group names. | |
437 A group name is decoded according to | |
438 `gnus-group-name-charset-method-alist' or | |
439 `gnus-group-name-charset-group-alist' first, and is encoded and | |
440 decoded again according to `nnmail-pathname-coding-system', | |
441 `file-name-coding-system', or `default-file-name-coding-system'. | |
442 | |
443 It is used when asking for a original group name from a cache | |
444 directory name, in which non-ASCII characters might have been unified | |
445 into the ones of a certain charset particularly if the `utf-8' coding | |
446 system for example was used.") | |
447 | |
448 (defun gnus-cache-decoded-group-name (group) | |
449 "Return a decoded group name of GROUP." | |
450 (or (cdr (assoc group gnus-cache-decoded-group-names)) | |
451 (let ((decoded (gnus-group-decoded-name group)) | |
452 (coding (or nnmail-pathname-coding-system | |
453 (and (boundp 'file-name-coding-system) | |
454 file-name-coding-system) | |
455 (and (boundp 'default-file-name-coding-system) | |
456 default-file-name-coding-system)))) | |
457 (push (cons group decoded) gnus-cache-decoded-group-names) | |
458 (push (cons (mm-decode-coding-string | |
459 (mm-encode-coding-string decoded coding) | |
460 coding) | |
461 group) | |
462 gnus-cache-unified-group-names) | |
463 decoded))) | |
464 | |
424 (defun gnus-cache-file-name (group article) | 465 (defun gnus-cache-file-name (group article) |
425 (setq group (gnus-group-decoded-name group)) | 466 (setq group (gnus-cache-decoded-group-name group)) |
426 (expand-file-name | 467 (expand-file-name |
427 (if (stringp article) article (int-to-string article)) | 468 (if (stringp article) article (int-to-string article)) |
428 (file-name-as-directory | 469 (file-name-as-directory |
429 (expand-file-name | 470 (expand-file-name |
430 (nnheader-translate-file-chars | 471 (nnheader-translate-file-chars |
453 (defun gnus-cache-possibly-remove-article (article ticked dormant unread | 494 (defun gnus-cache-possibly-remove-article (article ticked dormant unread |
454 &optional force) | 495 &optional force) |
455 "Possibly remove ARTICLE from the cache." | 496 "Possibly remove ARTICLE from the cache." |
456 (let ((group gnus-newsgroup-name) | 497 (let ((group gnus-newsgroup-name) |
457 (number article) | 498 (number article) |
458 file) | 499 file |
500 (file-name-coding-system nnmail-pathname-coding-system)) | |
459 ;; If this is a virtual group, we find the real group. | 501 ;; If this is a virtual group, we find the real group. |
460 (when (gnus-virtual-group-p group) | 502 (when (gnus-virtual-group-p group) |
461 (let ((result (nnvirtual-find-group-art | 503 (let ((result (nnvirtual-find-group-art |
462 (gnus-group-real-name group) article))) | 504 (gnus-group-real-name group) article))) |
463 (setq group (car result) | 505 (setq group (car result) |
466 (when (and (file-exists-p file) | 508 (when (and (file-exists-p file) |
467 (or force | 509 (or force |
468 (gnus-cache-member-of-class | 510 (gnus-cache-member-of-class |
469 gnus-cache-remove-articles ticked dormant unread))) | 511 gnus-cache-remove-articles ticked dormant unread))) |
470 (save-excursion | 512 (save-excursion |
513 (gnus-cache-update-file-total-fetched-for group file t) | |
471 (delete-file file) | 514 (delete-file file) |
515 | |
472 (set-buffer (cdr gnus-cache-buffer)) | 516 (set-buffer (cdr gnus-cache-buffer)) |
473 (goto-char (point-min)) | 517 (goto-char (point-min)) |
474 (when (or (looking-at (concat (int-to-string number) "\t")) | 518 (when (or (looking-at (concat (int-to-string number) "\t")) |
475 (search-forward (concat "\n" (int-to-string number) "\t") | 519 (search-forward (concat "\n" (int-to-string number) "\t") |
476 (point-max) t)) | 520 (point-max) t)) |
477 (gnus-delete-line))) | 521 (gnus-delete-line))) |
478 (unless (setq gnus-newsgroup-cached | 522 (unless (setq gnus-newsgroup-cached |
479 (delq article gnus-newsgroup-cached)) | 523 (delq article gnus-newsgroup-cached)) |
480 (gnus-sethash gnus-newsgroup-name nil gnus-cache-active-hashtb) | 524 (gnus-sethash gnus-newsgroup-name nil gnus-cache-active-hashtb) |
481 (setq gnus-cache-active-altered t)) | 525 (setq gnus-cache-active-altered t)) |
482 (gnus-summary-update-secondary-mark article) | 526 (gnus-summary-update-secondary-mark article) |
483 t))) | 527 t))) |
484 | 528 |
485 (defun gnus-cache-articles-in-group (group) | 529 (defun gnus-cache-articles-in-group (group) |
486 "Return a sorted list of cached articles in GROUP." | 530 "Return a sorted list of cached articles in GROUP." |
487 (let ((dir (file-name-directory (gnus-cache-file-name group 1))) | 531 (let ((dir (file-name-directory (gnus-cache-file-name group 1))) |
488 articles) | 532 articles |
533 (file-name-coding-system nnmail-pathname-coding-system)) | |
489 (when (file-exists-p dir) | 534 (when (file-exists-p dir) |
490 (setq articles | 535 (setq articles |
491 (sort (mapcar (lambda (name) (string-to-number name)) | 536 (sort (mapcar (lambda (name) (string-to-number name)) |
492 (directory-files dir nil "^[0-9]+$" t)) | 537 (directory-files dir nil "^[0-9]+$" t)) |
493 '<)) | 538 '<)) |
506 beg end) | 551 beg end) |
507 (gnus-cache-save-buffers) | 552 (gnus-cache-save-buffers) |
508 (save-excursion | 553 (save-excursion |
509 (set-buffer cache-buf) | 554 (set-buffer cache-buf) |
510 (erase-buffer) | 555 (erase-buffer) |
511 (let ((coding-system-for-read | 556 (let ((coding-system-for-read gnus-cache-overview-coding-system) |
512 gnus-cache-overview-coding-system)) | 557 (file-name-coding-system nnmail-pathname-coding-system)) |
513 (insert-file-contents | 558 (insert-file-contents |
514 (or file (gnus-cache-file-name group ".overview")))) | 559 (or file (gnus-cache-file-name group ".overview")))) |
515 (goto-char (point-min)) | 560 (goto-char (point-min)) |
516 (insert "\n") | 561 (insert "\n") |
517 (goto-char (point-min))) | 562 (goto-char (point-min))) |
523 (forward-line 1)) | 568 (forward-line 1)) |
524 (beginning-of-line) | 569 (beginning-of-line) |
525 (set-buffer cache-buf) | 570 (set-buffer cache-buf) |
526 (if (search-forward (concat "\n" (int-to-string (car cached)) "\t") | 571 (if (search-forward (concat "\n" (int-to-string (car cached)) "\t") |
527 nil t) | 572 nil t) |
528 (setq beg (gnus-point-at-bol) | 573 (setq beg (point-at-bol) |
529 end (progn (end-of-line) (point))) | 574 end (progn (end-of-line) (point))) |
530 (setq beg nil)) | 575 (setq beg nil)) |
531 (set-buffer nntp-server-buffer) | 576 (set-buffer nntp-server-buffer) |
532 (when beg | 577 (when beg |
533 (insert-buffer-substring cache-buf beg end) | 578 (insert-buffer-substring cache-buf beg end) |
535 (setq cached (cdr cached))) | 580 (setq cached (cdr cached))) |
536 (kill-buffer cache-buf))) | 581 (kill-buffer cache-buf))) |
537 | 582 |
538 (defun gnus-cache-braid-heads (group cached) | 583 (defun gnus-cache-braid-heads (group cached) |
539 (let ((cache-buf (gnus-get-buffer-create " *gnus-cache*"))) | 584 (let ((cache-buf (gnus-get-buffer-create " *gnus-cache*"))) |
540 (save-excursion | 585 (with-current-buffer cache-buf |
541 (set-buffer cache-buf) | |
542 (erase-buffer)) | 586 (erase-buffer)) |
543 (set-buffer nntp-server-buffer) | 587 (set-buffer nntp-server-buffer) |
544 (goto-char (point-min)) | 588 (goto-char (point-min)) |
545 (while cached | 589 (dolist (entry cached) |
546 (while (and (not (eobp)) | 590 (while (and (not (eobp)) |
547 (looking-at "2.. +\\([0-9]+\\) ") | 591 (looking-at "2.. +\\([0-9]+\\) ") |
548 (< (progn (goto-char (match-beginning 1)) | 592 (< (progn (goto-char (match-beginning 1)) |
549 (read (current-buffer))) | 593 (read (current-buffer))) |
550 (car cached))) | 594 entry)) |
551 (search-forward "\n.\n" nil 'move)) | 595 (search-forward "\n.\n" nil 'move)) |
552 (beginning-of-line) | 596 (beginning-of-line) |
553 (set-buffer cache-buf) | 597 (set-buffer cache-buf) |
554 (erase-buffer) | 598 (erase-buffer) |
555 (let ((coding-system-for-read | 599 (let ((coding-system-for-read gnus-cache-coding-system) |
556 gnus-cache-coding-system)) | 600 (file-name-coding-system nnmail-pathname-coding-system)) |
557 (insert-file-contents (gnus-cache-file-name group (car cached)))) | 601 (insert-file-contents (gnus-cache-file-name group entry))) |
558 (goto-char (point-min)) | 602 (goto-char (point-min)) |
559 (insert "220 ") | 603 (insert "220 ") |
560 (princ (car cached) (current-buffer)) | 604 (princ (car cached) (current-buffer)) |
561 (insert " Article retrieved.\n") | 605 (insert " Article retrieved.\n") |
562 (search-forward "\n\n" nil 'move) | 606 (search-forward "\n\n" nil 'move) |
563 (delete-region (point) (point-max)) | 607 (delete-region (point) (point-max)) |
564 (forward-char -1) | 608 (forward-char -1) |
565 (insert ".") | 609 (insert ".") |
566 (set-buffer nntp-server-buffer) | 610 (set-buffer nntp-server-buffer) |
567 (insert-buffer-substring cache-buf) | 611 (insert-buffer-substring cache-buf)) |
568 (setq cached (cdr cached))) | |
569 (kill-buffer cache-buf))) | 612 (kill-buffer cache-buf))) |
570 | 613 |
571 ;;;###autoload | 614 ;;;###autoload |
572 (defun gnus-jog-cache () | 615 (defun gnus-jog-cache () |
573 "Go through all groups and put the articles into the cache. | 616 "Go through all groups and put the articles into the cache. |
659 (defun gnus-cache-generate-active (&optional directory) | 702 (defun gnus-cache-generate-active (&optional directory) |
660 "Generate the cache active file." | 703 "Generate the cache active file." |
661 (interactive) | 704 (interactive) |
662 (let* ((top (null directory)) | 705 (let* ((top (null directory)) |
663 (directory (expand-file-name (or directory gnus-cache-directory))) | 706 (directory (expand-file-name (or directory gnus-cache-directory))) |
707 (file-name-coding-system nnmail-pathname-coding-system) | |
664 (files (directory-files directory 'full)) | 708 (files (directory-files directory 'full)) |
665 (group | 709 (group |
666 (if top | 710 (if top |
667 "" | 711 "" |
668 (string-match | 712 (string-match |
684 (if (string-match "^[0-9]+$" (file-name-nondirectory (car files))) | 728 (if (string-match "^[0-9]+$" (file-name-nondirectory (car files))) |
685 (push (string-to-number (file-name-nondirectory (pop files))) nums) | 729 (push (string-to-number (file-name-nondirectory (pop files))) nums) |
686 (push (pop files) alphs))) | 730 (push (pop files) alphs))) |
687 ;; If we have nums, then this is probably a valid group. | 731 ;; If we have nums, then this is probably a valid group. |
688 (when (setq nums (sort nums '<)) | 732 (when (setq nums (sort nums '<)) |
689 (gnus-sethash group (cons (car nums) (gnus-last-element nums)) | 733 ;; Use non-decoded group name. |
734 ;; FIXME: this is kind of a workaround. The active file should | |
735 ;; be updated at the time articles are cached. It will make | |
736 ;; `gnus-cache-unified-group-names' needless. | |
737 (gnus-sethash (or (cdr (assoc group gnus-cache-unified-group-names)) | |
738 group) | |
739 (cons (car nums) (gnus-last-element nums)) | |
690 gnus-cache-active-hashtb)) | 740 gnus-cache-active-hashtb)) |
691 ;; Go through all the other files. | 741 ;; Go through all the other files. |
692 (while alphs | 742 (dolist (file alphs) |
693 (when (and (file-directory-p (car alphs)) | 743 (when (and (file-directory-p file) |
694 (not (string-match "^\\." | 744 (not (string-match "^\\." |
695 (file-name-nondirectory (car alphs))))) | 745 (file-name-nondirectory file)))) |
696 ;; We descend directories. | 746 ;; We descend directories. |
697 (gnus-cache-generate-active (car alphs))) | 747 (gnus-cache-generate-active file))) |
698 (setq alphs (cdr alphs))) | |
699 ;; Write the new active file. | 748 ;; Write the new active file. |
700 (when top | 749 (when top |
701 (gnus-cache-write-active t) | 750 (gnus-cache-write-active t) |
702 (gnus-message 5 "Generating the cache active file...done")))) | 751 (gnus-message 5 "Generating the cache active file...done")))) |
703 | 752 |
706 "Generate NOV files recursively starting in DIR." | 755 "Generate NOV files recursively starting in DIR." |
707 (interactive (list gnus-cache-directory)) | 756 (interactive (list gnus-cache-directory)) |
708 (gnus-cache-close) | 757 (gnus-cache-close) |
709 (let ((nnml-generate-active-function 'identity)) | 758 (let ((nnml-generate-active-function 'identity)) |
710 (nnml-generate-nov-databases-1 dir)) | 759 (nnml-generate-nov-databases-1 dir)) |
760 | |
761 (setq gnus-cache-total-fetched-hashtb nil) | |
762 | |
711 (gnus-cache-open)) | 763 (gnus-cache-open)) |
712 | 764 |
713 (defun gnus-cache-move-cache (dir) | 765 (defun gnus-cache-move-cache (dir) |
714 "Move the cache tree to somewhere else." | 766 "Move the cache tree to somewhere else." |
715 (interactive "FMove the cache tree to: ") | 767 (interactive "FMove the cache tree to: ") |
734 Always updates the cache, even when disabled, as the old cache | 786 Always updates the cache, even when disabled, as the old cache |
735 files would corrupt Gnus when the cache was next enabled. It | 787 files would corrupt Gnus when the cache was next enabled. It |
736 depends on the caller to determine whether group renaming is | 788 depends on the caller to determine whether group renaming is |
737 supported." | 789 supported." |
738 (let ((old-dir (gnus-cache-file-name old-group "")) | 790 (let ((old-dir (gnus-cache-file-name old-group "")) |
739 (new-dir (gnus-cache-file-name new-group ""))) | 791 (new-dir (gnus-cache-file-name new-group "")) |
792 (file-name-coding-system nnmail-pathname-coding-system)) | |
740 (gnus-rename-file old-dir new-dir t)) | 793 (gnus-rename-file old-dir new-dir t)) |
794 | |
795 (gnus-cache-rename-group-total-fetched-for old-group new-group) | |
741 | 796 |
742 (let ((no-save gnus-cache-active-hashtb)) | 797 (let ((no-save gnus-cache-active-hashtb)) |
743 (unless gnus-cache-active-hashtb | 798 (unless gnus-cache-active-hashtb |
744 (gnus-cache-read-active)) | 799 (gnus-cache-read-active)) |
745 (let* ((old-group-hash-value | 800 (let* ((old-group-hash-value |
760 "Delete GROUP from the cache. | 815 "Delete GROUP from the cache. |
761 Always updates the cache, even when disabled, as the old cache | 816 Always updates the cache, even when disabled, as the old cache |
762 files would corrupt gnus when the cache was next enabled. | 817 files would corrupt gnus when the cache was next enabled. |
763 Depends upon the caller to determine whether group deletion is | 818 Depends upon the caller to determine whether group deletion is |
764 supported." | 819 supported." |
765 (let ((dir (gnus-cache-file-name group ""))) | 820 (let ((dir (gnus-cache-file-name group "")) |
821 (file-name-coding-system nnmail-pathname-coding-system)) | |
766 (gnus-delete-directory dir)) | 822 (gnus-delete-directory dir)) |
823 | |
824 (gnus-cache-delete-group-total-fetched-for group) | |
767 | 825 |
768 (let ((no-save gnus-cache-active-hashtb)) | 826 (let ((no-save gnus-cache-active-hashtb)) |
769 (unless gnus-cache-active-hashtb | 827 (unless gnus-cache-active-hashtb |
770 (gnus-cache-read-active)) | 828 (gnus-cache-read-active)) |
771 (let* ((group-hash-value (gnus-gethash group gnus-cache-active-hashtb))) | 829 (let* ((group-hash-value (gnus-gethash group gnus-cache-active-hashtb))) |
773 | 831 |
774 (if no-save | 832 (if no-save |
775 (setq gnus-cache-active-altered group-hash-value) | 833 (setq gnus-cache-active-altered group-hash-value) |
776 (gnus-cache-write-active group-hash-value))))) | 834 (gnus-cache-write-active group-hash-value))))) |
777 | 835 |
836 (defvar gnus-cache-inhibit-update-total-fetched-for nil) | |
837 (defvar gnus-cache-need-update-total-fetched-for nil) | |
838 | |
839 (defmacro gnus-cache-with-refreshed-group (group &rest body) | |
840 `(prog1 (let ((gnus-cache-inhibit-update-total-fetched-for t)) | |
841 ,@body) | |
842 (when (and gnus-cache-need-update-total-fetched-for | |
843 (not gnus-cache-inhibit-update-total-fetched-for)) | |
844 (save-excursion | |
845 (set-buffer gnus-group-buffer) | |
846 (setq gnus-cache-need-update-total-fetched-for nil) | |
847 (gnus-group-update-group ,group t))))) | |
848 | |
849 (defun gnus-cache-update-file-total-fetched-for (group file &optional subtract) | |
850 (when gnus-cache-total-fetched-hashtb | |
851 (gnus-cache-with-refreshed-group | |
852 group | |
853 (let* ((entry (or (gnus-gethash group gnus-cache-total-fetched-hashtb) | |
854 (gnus-sethash group (make-vector 2 0) | |
855 gnus-cache-total-fetched-hashtb))) | |
856 size) | |
857 | |
858 (if file | |
859 (setq size (or (nth 7 (file-attributes file)) 0)) | |
860 (let* ((file-name-coding-system nnmail-pathname-coding-system) | |
861 (files (directory-files (gnus-cache-file-name group "") | |
862 t nil t)) | |
863 file attrs) | |
864 (setq size 0.0) | |
865 (while (setq file (pop files)) | |
866 (setq attrs (file-attributes file)) | |
867 (unless (nth 0 attrs) | |
868 (incf size (float (nth 7 attrs))))))) | |
869 | |
870 (setq gnus-cache-need-update-total-fetched-for t) | |
871 | |
872 (incf (nth 1 entry) (if subtract (- size) size)))))) | |
873 | |
874 (defun gnus-cache-update-overview-total-fetched-for (group file) | |
875 (when gnus-cache-total-fetched-hashtb | |
876 (gnus-cache-with-refreshed-group | |
877 group | |
878 (let* ((entry (or (gnus-gethash group gnus-cache-total-fetched-hashtb) | |
879 (gnus-sethash group (make-list 2 0) | |
880 gnus-cache-total-fetched-hashtb))) | |
881 (file-name-coding-system nnmail-pathname-coding-system) | |
882 (size (or (nth 7 (file-attributes | |
883 (or file | |
884 (gnus-cache-file-name group ".overview")))) | |
885 0))) | |
886 (setq gnus-cache-need-update-total-fetched-for t) | |
887 (setf (nth 0 entry) size))))) | |
888 | |
889 (defun gnus-cache-rename-group-total-fetched-for (old-group new-group) | |
890 "Record of disk space used by OLD-GROUP now associated with NEW-GROUP." | |
891 (when gnus-cache-total-fetched-hashtb | |
892 (let ((entry (gnus-gethash old-group gnus-cache-total-fetched-hashtb))) | |
893 (gnus-sethash new-group entry gnus-cache-total-fetched-hashtb) | |
894 (gnus-sethash old-group nil gnus-cache-total-fetched-hashtb)))) | |
895 | |
896 (defun gnus-cache-delete-group-total-fetched-for (group) | |
897 "Delete record of disk space used by GROUP being deleted." | |
898 (when gnus-cache-total-fetched-hashtb | |
899 (gnus-sethash group nil gnus-cache-total-fetched-hashtb))) | |
900 | |
901 (defun gnus-cache-total-fetched-for (group &optional no-inhibit) | |
902 "Get total disk space used by the cache for the specified GROUP." | |
903 (unless (equal group "dummy.group") | |
904 (unless gnus-cache-total-fetched-hashtb | |
905 (setq gnus-cache-total-fetched-hashtb (gnus-make-hashtable 1024))) | |
906 | |
907 (let* ((entry (gnus-gethash group gnus-cache-total-fetched-hashtb))) | |
908 (if entry | |
909 (apply '+ entry) | |
910 (let ((gnus-cache-inhibit-update-total-fetched-for (not no-inhibit))) | |
911 (+ | |
912 (gnus-cache-update-overview-total-fetched-for group nil) | |
913 (gnus-cache-update-file-total-fetched-for group nil))))))) | |
914 | |
778 (provide 'gnus-cache) | 915 (provide 'gnus-cache) |
779 | 916 |
780 ;;; arch-tag: 05a79442-8c58-4e65-bd0a-3cbb1b89a33a | 917 ;;; arch-tag: 05a79442-8c58-4e65-bd0a-3cbb1b89a33a |
781 ;;; gnus-cache.el ends here | 918 ;;; gnus-cache.el ends here |