让 emacsclient 支持 --funcall

emacsclient 只有 -e/--eval,却没 --funcall,不像 emacs 是都有的,这导致从调用函数有点儿麻烦,需要自己加引号和括号,而在命令行输入它们实在是不方便:

$ emacsclient -e '(kill-emacs)'
$ emacsclient -e '(emacs-version)'
$ emacsclient -e '(magit-status)'

所以我写一个 Shell 函数 ec 来支持 --funcall:

ec () {
    for arg in "[email protected]"; do
        shift
        case "$arg" in
            --fun*) func=starts && set -- "[email protected]" "--eval" ;;
            -*) func=ends && set -- "[email protected]" "$arg" ;;
            *) if [[ "$func" == starts ]]; then
                   set -- "[email protected]" "($arg)"
               else
                   set -- "[email protected]" "$arg"
               fi
        esac
    done
    emacsclient "[email protected]"
}

然后就可以用

$ ec --funcall kill-emacs
$ ec --funcall emacs-version
$ ec --funcall magit-status

这样就不用手动输入括号了。

1 个赞

:joy: 是不是有点太hacky了

其实吧,大多数脚本语言都可以做到类似功能。 我选择用 NewLisp。

不清楚是不是 Shell 语法的关系。方法本身是非常清楚的,就是把 --funcall 换成 --eval,再把后面的参数加上括号:

emacsclient --eval 1 2 --funcall version pwd -e 3

=>

emacsclient --eval 1 2 --eval '(version)' '(pwd)' -e 3

我原来尝试过修改 emacsclient.c 的,但是 C 语言知识非常有限,只能做到处理一个参数,不能像上面的 Shell 函数那样支持任意数量的参数,暂时就放弃了。