Emacs shell scripts-как поместить начальные параметры в скрипт?

вдохновленный вопросом переполнения стека idomatic пакетная обработка текста в Emacs? Я опробовал сценарий оболочки Emacs со следующим заголовком:

#!/usr/bin/emacs --script 

Я поместил в него код Emacs Lisp и сохранил его как textfile rcat.

поскольку опция --script не предотвращает загрузку файла запуска сайта, у меня было много

Loading /etc/emacs/site-start.d/20apel.el (source)...
Loading /etc/emacs23/site-start.d/35elib-startup.el (source)...
Loading /etc/emacs23/site-start.d/50auctex.el (source)...

сообщения в оболочке Bash (stdout). Я могу предотвратить это, позвонив

rcat --no-site-file

или

rcat -Q

но не путем изменения заголовка в скрипте:

 #!/usr/bin/emacs --script --no-site-file

есть ли способ передать дополнительные параметры Emacs внутри такого файла сценария вместо того, чтобы делать это позже в командной строке?

3 ответов


вы всегда можете изменить #!/usr/bin/emacs что-то вроде #!/home/thorsten/bin/emacs-no-site-file, и установлено, что:

#!/bin/sh
exec /usr/bin/emacs --no-site-file "$@"

Если это не работает для вас, или если вы хотите, чтобы ваш скрипт был портативным, то см. ответ Жиля ниже для более надежного (и немного фанки :) подхода.


многие варианты unix допускают только один аргумент для программы в строке shebang. Печально, но это правда. Если вы используете #!/usr/bin/env emacs чтобы не зависеть от местоположения emacs исполняемый файл, вы не можете передать аргумент вообще.

цепочки скриптов - это возможность на некоторых системах, но это тоже не поддерживается везде.

вы можете пройти проверенный временем маршрут написания сценария полиглота: сценарий, который является как сценарием оболочки, так и Emacs Lisp скрипт (например, Perl if $running_under_some_shell, например). Конечно, выглядит банально, но работает.

комментарии Elisp начинаются с ;, который в оболочке разделяющей две команды. Таким образом, мы можем использовать ; затем следует инструкция оболочки для переключения на Emacs, с фактическим кодом Lisp, начинающимся на следующей строке. Большинство оболочек не любят пустую команду, поэтому нам нужно найти что-то, что и оболочка, и Emacs рассматривают как no-op, чтобы поставить перед ;. Оболочка нет команды :; вы можете писать ":" Что касается оболочки, и Emacs анализирует это как константу на верхнем уровне, которая также является no-op.

#! /bin/sh
":"; exec emacs --no-site-file --script "" -- "$@" # -*-emacs-lisp-*-
(print (+ 2 2))

Если вы запускаете emacs в режиме скрипта, я бы рекомендовал сбросить переменную " argv "до нуля в конце вашего скрипта, иначе emacs попытается интерпретировать" argv " после завершения скрипта.

предположим, у вас есть файл с именем "test-emacs-script.el " со следующим содержанием:

#!/usr/bin/emacs --script
(print argv)
(setq argv nil)

попробуйте запустить этот скрипт как "./ тест-emacs-скрипт.эль -а". Если вы запустите этот скрипт без сброса " argv "(последняя строка в скрипте), то вывод будет быть:

("-a")
Unknown option `-a'

сброс "argv" избавляется от сообщения об ошибке" неизвестный параметр"