我正在尝试解决在当前和父目录dired-do-shell-command
和!
'上无法调用.
(绑定到..
)的限制。堆栈跟踪粘贴在底部。
我可以定义以下建议来绕过这个错误:
(defadvice dired-get-filename (before h-no-error-if-not-filep activate)
(ad-set-arg 1 t))
但是这会影响对dired-get-filename
的所有调用。我希望它只在堆栈为dired-do-shell-command -> dired-get-marked-files -> dired-get-filename
时触发。
我能想到的唯一方法如下
(with-output-to-string (backtrace))
中的匹配项
有更好的方法吗?我想我正在寻找访问当前堆栈跟踪作为数据结构而不是来自(backtrace)
的字符串
Debugger entered--Lisp error: (error "Cannot operate on `.' or `..'")
signal(error ("Cannot operate on `.' or `..'"))
error("Cannot operate on `.' or `..'")
dired-get-filename(t)
dired-get-marked-files(t nil)
(let ((files (dired-get-marked-files t current-prefix-arg))) (list (dired-read-shell-command (concat "! on " "%s: ") current-prefix-arg files) current-prefix-arg files))
call-interactively(dired-do-shell-command nil nil)
答案 0 :(得分:2)
我希望将dired-do-shell-command
复制到my:dired-do-shell-command
,然后从那里调用my:dired-get-marked-files
,它会使用第三个参数t调用dired-get-filename
。
这样我可以复制/粘贴两个函数,但是我可以通过建议常用函数来减少副作用。
答案 1 :(得分:2)
您可以通过backtrace-frame
一次访问一个图层的堆栈跟踪。但这真的是在推动黑客攻击。我们还建议您M-x report-emacs-bug
要求!
使用.
和..
。
答案 2 :(得分:1)
以列表的形式访问堆栈会很棒,但不幸的是,这似乎无法从elisp中访问。 (编辑:啊,我是盲人; backtrace-frame
提供了这个,我甚至没有看过它。感谢Stefan。)
第二种选择(使用额外建议和标记变量)的类似方法是根据外部建议启用或禁用内部建议。这是一个例子:
答案 3 :(得分:1)
绝对提交功能请求。
但是你的意思是你可以自己制作my:dired-do-shell-command
“复制任何代码”,只需使用flet
重新绑定dired-get-filename
你的功能。这接近@ oleg的解决方案。
在此question:
中也进行了讨论此代码未经测试,但您明白了。
(eval-when-compile (require 'cl))
(defun my:dired-do-shell-command (&rest args)
(interactive)
(let ((old-func (symbol-function 'dired-get-filename)))
(flet ((dired-get-filename (&rest args)
(let ((file (funcall old-func 'verbatim)))
(if (memberq file '("." ".."))
(if (car args)
file
(expand-file-name file default-directory))
(apply old-func args)))))
(apply 'dired-do-shell-command args))))
Emacs黑客滥用defadvice
太多了。它可怕地混淆了一些事情
并且只应作为最后的解决方案保留。
答案 4 :(得分:1)
使用this-command
变量:
(defadvice dired-get-filename (before h-no-error-if-not-filep activate)
(when (equal this-command 'dired-do-shell-command)
(ad-set-arg 1 t)))