如何运行 sudo 命令并加载当前登录用户的环境变量?

如何运行 sudo 命令并加载当前登录用户的环境变量?

我需要运行 ssh sudo 命令。

命令如下:

ssh -i keyfile [email protected]  'sh -v /opt/dir/script'

该脚本包含以下内容:

sudo -E node some.js

我使用 -E 参数的原因是该命令由用户 A 运行正在启动的进程需要从中加载定义

/user/userA/.bashrc

上述命令不会加载在 /user/userA/.bashrc

它确实运行得好像 -E 没有执行任何操作。即所有变量都显示为未定义。

如果我以用户A的身份交互登录到远程计算机并运行相同的命令,即

sudo -E node some.js

变量已正确加载并且我看到了预期的行为。

谁能看到我需要做些什么不同的事情吗?

答案1

您期望 shell 能够获取源代码~/.bashrc,因此我假设 shell 是 Bash。

转折 1:SSH 服务器将 shell 代码传递给非交互式 shell。非交互式 Bash才不是~/.bashrc

转折 2:Bash 尝试确定何时在标准输入连接到网络连接的情况下运行,例如由 SSH 服务器执行时。如果 bash 确定它以这种方式运行,它读取并执行来自的命令~/.bashrc

转折 3:在许多发行版(包括 Ubuntu)中,默认(骨架)~/.bashrc以代码开始,如果 shell 是非交互式的,则返回该代码。实际上,文件的其余部分是未找到来源

我猜你的情况是相关的环境变量是在这段代码之后定义的。代码可能看起来像这样:

# If not running interactively, don't do anything
case $- in
    *i*) ;;
      *) return;;
esac

一个简单的解决方案是移动任务,使其此代码。如果你想移动执行更多操作的命令(例如echo,运行某些操作),那么要非常小心,因为你可能会破坏远程文件传输。阅读为什么要bashrc检查当前shell是否是交互的?如果仅涉及变量,那么你就应该是安全的。

总体环境应该定义为~/.profile而不是在~/.bashrc,但如果您将作业移动到 ,~/.profile那么您将遇到以下情况:~/.profile使用 SSH 时未加载。那么让他们进来也并非不合理~/.bashrc

或者,你可以将它们放在单独的文件中,例如,并从或或其他任何地方~/.special_env获取文件。优点是你可以根据需要获取文件,而不受怪癖和曲折的影响:~/.bashrc~/.profile

ssh -i keyfile [email protected]  '. ~/.special_env; sh -v /opt/dir/script'

相关内容