-(defun notmuch-show-mm-display-part-inline (part content-type)
- "Use the mm-decode/mm-view functions to display a part inline, if possible."
- (let ((handle (mm-make-handle nil (list content-type))))
- (if (and (mm-inlinable-p handle)
- (mm-inlined-p handle))
- (progn
- (insert (with-temp-buffer
- (let ((display-buffer (current-buffer)))
- (with-temp-buffer
- (let ((work-buffer (current-buffer)))
- (insert (plist-get part :content))
- (set-buffer display-buffer)
- (mm-display-part (mm-make-handle work-buffer
- (list content-type)))
- (buffer-string))))))
- t)))
- nil)
-
-(defun notmuch-show-insert-part-text/plain (part content-type nth depth declared-type)
+(defun notmuch-show-save-part (message-id nth &optional filename)
+ (with-temp-buffer
+ ;; Always acquires the part via `notmuch part', even if it is
+ ;; available in the JSON output.
+ (insert (notmuch-show-get-bodypart-internal message-id nth))
+ (let ((file (read-file-name
+ "Filename to save as: "
+ (or mailcap-download-directory "~/")
+ nil nil
+ filename))
+ (require-final-newline nil)
+ (coding-system-for-write 'no-conversion))
+ (write-region (point-min) (point-max) file))))
+
+(defun notmuch-show-mm-display-part-inline (msg part content-type content)
+ "Use the mm-decode/mm-view functions to display a part in the
+current buffer, if possible."
+ (let ((display-buffer (current-buffer)))
+ (with-temp-buffer
+ (insert content)
+ (let ((handle (mm-make-handle (current-buffer) (list content-type))))
+ (set-buffer display-buffer)
+ (if (and (mm-inlinable-p handle)
+ (mm-inlined-p handle))
+ (progn
+ (mm-display-part handle)
+ t)
+ nil)))))
+
+(defun notmuch-show-insert-part-multipart/alternative (msg part content-type nth depth declared-type)
+ (let ((inner-parts (plist-get part :content)))
+ (notmuch-show-insert-part-header nth declared-type content-type nil)
+ ;; In most cases, multipart/alternative is used to provide both
+ ;; text/plain and text/html (or multipart/related with text/html
+ ;; and image/*) parts. We might allow the user to express a
+ ;; preference about which part to show, but for the moment we just
+ ;; choose the first. This is usually the text/plain part.
+ (notmuch-show-insert-bodypart msg (car inner-parts) depth)
+ (mapc (lambda (inner-part)
+ (let ((inner-type (concat (plist-get inner-part :content-type) " (not shown)")))
+ (notmuch-show-insert-part-header (plist-get inner-part :id) inner-type inner-type nil)))
+ (cdr inner-parts)))
+ t)
+
+(defun notmuch-show-insert-part-multipart/* (msg part content-type nth depth declared-type)
+ (let ((inner-parts (plist-get part :content)))
+ (notmuch-show-insert-part-header nth declared-type content-type nil)
+ ;; Show all of the parts.
+ (mapc (lambda (inner-part)
+ (notmuch-show-insert-bodypart msg inner-part depth))
+ inner-parts))
+ t)
+
+(defun notmuch-show-insert-part-message/rfc822 (msg part content-type nth depth declared-type)
+ (let* ((message-part (plist-get part :content))
+ (inner-parts (plist-get message-part :content)))
+ (notmuch-show-insert-part-header nth declared-type content-type nil)
+ ;; Override `notmuch-message-headers' to force `From' to be
+ ;; displayed.
+ (let ((notmuch-message-headers '("From" "Subject" "To" "Cc" "Date")))
+ (notmuch-show-insert-headers (plist-get part :headers)))
+ ;; Blank line after headers to be compatible with the normal
+ ;; message display.
+ (insert "\n")
+
+ ;; Show all of the parts.
+ (mapc (lambda (inner-part)
+ (notmuch-show-insert-bodypart msg inner-part depth))
+ inner-parts))
+ t)
+
+(defun notmuch-show-insert-part-text/plain (msg part content-type nth depth declared-type)