Subject: Re: bug#64516: [PATCH] docview: Only enable imenu when supported

From: Tassilo Horn <[email-masked]>
Date: Tue, 18 Jul 2023 21:14:35 +0200

Morgan Smith <[email-masked]> writes:

Hi Morgan,

>> my reasoning was to have an explanation in the *Messages* buffer for
>> people who ask themselves "where the heck is the Outline menu item"?
>
> I didn't think of users using the toolbar.

I've heared there are three of them.  But we are talking about the menu
bar of which there are a good dozen users. :-)

> I think you can go ahead and use the patch you sent a couple emails
> back.  I'm happy with that one.

Alright, I've amended your patch with my slight modifications.  Eli,
feel free to "git am" it where you see fit.  It should apply both on
master and on emacs-29.

Thanks,
Tassilo
>From 2a297bc4c1de575f45fa7fdb9e2b9ea2f23294a2 Mon Sep 17 00:00:00 2001
From: Morgan Smith <[email-masked]>
Date: Tue, 11 Jul 2023 14:08:24 -0400
Subject: [PATCH] docview: imenu: check return value of 'mutool'

While 'mutool' supports many filetypes, 'mutool show' only supports
PDF files.  This would lead to cryptic imenu errors when opening other
file types (like EPUB) since we would parse the error output.  During
my testing this caused 'imenu--index-alist' to have a value of '(nil).

* lisp/doc-view.el (doc-view--pdf-outline): Error when 'mutool'
returns an error.  Use 'call-process' to get the return value and
remove the call to 'shell-quote-argument' as 'call-process' doesn't
want any escapes.
(doc-view-mode): Handle possible error from 'doc-view-imenu-setup'.
(doc-view-imenu-enabled): Remove superfluous (and ... t).
(doc-view-imenu-setup): Remove check for mutool already ensured by
'doc-view-imenu-enabled' being non-nil.
---
 lisp/doc-view.el | 16 +++++++++++-----
 1 file changed, 11 insertions(+), 5 deletions(-)

diff --git a/lisp/doc-view.el b/lisp/doc-view.el
index b14655fb274..847601872f5 100644
--- a/lisp/doc-view.el
+++ b/lisp/doc-view.el
@@ -147,6 +147,8 @@
 (require 'filenotify)
 (eval-when-compile (require 'subr-x))
 
+(autoload 'imenu-unavailable-error "imenu")
+
 ;;;; Customization Options
 
 (defgroup doc-view nil
@@ -214,7 +216,7 @@ doc-view-mupdf-use-svg
   :type 'boolean
   :version "30.1")
 
-(defcustom doc-view-imenu-enabled (and (executable-find "mutool") t)
+(defcustom doc-view-imenu-enabled (executable-find "mutool")
   "Whether to generate an imenu outline when \"mutool\" is available."
   :type 'boolean
   :version "29.1")
@@ -1910,9 +1912,10 @@ doc-view--pdf-outline
   (let ((fn (or file-name (buffer-file-name))))
     (when fn
       (let ((outline nil)
-            (fn (shell-quote-argument (expand-file-name fn))))
+            (fn (expand-file-name fn)))
         (with-temp-buffer
-          (insert (shell-command-to-string (format "mutool show %s outline" fn)))
+          (unless (= 0 (call-process "mutool" nil (current-buffer) nil "show" fn "outline"))
+            (imenu-unavailable-error "Unable to create imenu index using `mutool'"))
           (goto-char (point-min))
           (while (re-search-forward doc-view--outline-rx nil t)
             (push `((level . ,(length (match-string 1)))
@@ -1961,7 +1964,7 @@ doc-view-imenu-index
 
 (defun doc-view-imenu-setup ()
   "Set up local state in the current buffer for imenu, if needed."
-  (when (and doc-view-imenu-enabled (executable-find "mutool"))
+  (when doc-view-imenu-enabled
     (setq-local imenu-create-index-function #'doc-view-imenu-index
                 imenu-submenus-on-top nil
                 imenu-sort-function nil
@@ -2236,7 +2239,10 @@ doc-view-mode
     (setq mode-name "DocView"
 	  buffer-read-only t
 	  major-mode 'doc-view-mode)
-    (doc-view-imenu-setup)
+    (condition-case imenu-error
+        (doc-view-imenu-setup)
+      (imenu-unavailable (message "imenu support unavailable: %s"
+                                  (cadr imenu-error))))
     (doc-view-initiate-display)
     ;; Switch off view-mode explicitly, because doc-view-mode is the
     ;; canonical view mode for PDF/PS/DVI files.  This could be
-- 
2.41.0