在我的项目中,我们有一个为一些环境变量设置默认值的 shell 脚本。当我尝试运行时rinari-console
,我收到一个错误,因为该脚本尚未获得来源。有没有办法确保 rinari 来源它,以便在 rails 控制台启动时,所有变量都具有所需的值?
4 回答
好吧,我一直在思考这个问题。我提出了两种可能的解决方案:
通过包装器在 Emacs 外部
这个解决方案有点笨拙,但它应该可以工作。
您可以创建一个包装脚本,例如“emacs-wrapper.sh”:
#!/bin/sh
set -a
. YOUR-SCRIPT.sh
emacs
如果您启动 ./emacs-wrapper.sh,将获取 YOUR-SCRIPT.sh,然后启动 Emacs。通过这种方式,Emacs 将可以看到相同的环境。在我的机器上测试这种方法,我能够(getenv "var") YOUR-SCRIPT.sh 中定义的所有变量
更好:在 Emcas 中通过 shell-command
这是 IMO 一个更好的解决方案,因为它完全在 Emacs 中运行。调用 shell-command-to-string 以获取您的 YOUR-SCRIPT.sh。最后,它还会转储该进程的环境。随后将其添加到 Emacs 自己的进程环境中:
;; defadvice is optional, you could also just call source-script directly
(defadvice rinari-console (before init-environment activate)
(source-script "/PATH/TO/YOUR-SCRIPT.sh"))
(defun source-script (script)
(let ((env (extract-environment script)))
(mapc 'import-environment-variable (split-string env "\n"))))
(defun extract-environment (script)
(shell-command-to-string (format "set -a; . %s > /dev/null 2>&1; env" script)))
(defun import-environment-variable (variable-assignment)
(when (not (or (null variable-assignment) (string= "" variable-assignment)))
(let* ((key-value-pair (split-string variable-assignment "="))
(key (car key-value-pair))
(value (cadr key-value-pair)))
(setenv key value))))
我也在我的机器上验证了这种方法。在 YOUR-SCRIPT 中定义的所有变量也在 Emacs 中定义。
我设法用包装器做你想做的事。假设您在~/test
. Rinari 将尝试irb
通过执行命令来启动~/test/script/console
。我创建了一个名为~/test/script/console.sh
:
#!/bin/sh
. ~/test/script/env.sh
~/test/script/console
包装器获取包含环境变量的脚本,然后执行常规命令。
该文件~/test/script/env.sh
包含:
export TEST=test
现在要使用该包装器,请rinari-mode
使用前缀参数调用并将 aC-u M-x rinari-mode
添加.sh
到建议命令的末尾。TEST
将设置环境变量。
然后,您可以创建一个.sh
自动添加的宏。
我不使用 rinari,所以可能有更好的方法来做到这一点,但原则上你可以在运行实际的 rinari-console 命令之前运行“YOUR-SCRIPT.sh”。
(defadvice rinari-console (before run-my-script activate)
(shell-command "YOUR-SCRIPT.sh"))
另见:http ://www.gnu.org/software/emacs/manual/html_node/elisp/Advising-Functions.html
好吧,如果您想获取脚本,是否可以执行与 tkf 建议的非常相似的操作:
(defadvice rinari-console (before run-my-script activate)
(shell-command ". YOUR-SCRIPT.sh"))