Cron 作业没有获得在 .bashrc 中设置的环境变量

Posted

技术标签:

【中文标题】Cron 作业没有获得在 .bashrc 中设置的环境变量【英文标题】:Cron job does NOT get the environment variables set in .bashrc 【发布时间】:2013-03-11 13:37:51 【问题描述】:

这是我的 cron 工作:

plee@dragon:~$ crontab -l
* * * * * /bin/bash -l -c 'source ~/.bashrc; echo $EDITOR > /tmp/cronjob.test'

~/.bashrc 文件中,我有export EDITOR=vim,但在最终的/tmp/cronjob.test 文件中,它仍然是空的?

那么如何获取环境变量(在.bashrc 文件中设置)并在我的 cron 作业中使用它?

plee@dragon:~$ lsb_release -a
No LSB modules are available.
Distributor ID: Ubuntu
Description:    Ubuntu 12.04 LTS
Release:        12.04
Codename:       precise
plee@dragon:~$ uname -a
Linux dragon 3.2.0-26-generic-pae #41-Ubuntu SMP Thu Jun 14 16:45:14 UTC 2012 i686 i686 i386 GNU/Linux

如果使用这个:

* * * * * /bin/bash -l -c -x 'source ~/.bashrc; echo $EDITOR > /tmp/cronjob.test' 2> /tmp/cron.debug.res

/tmp/cron.debug.res:

...
++ return 0
+ source /home/plee/.bashrc
++ '[' -z '' ']'
++ return
+ echo

顺便说一句,.bashrc 文件是 Ubuntu 12.04 附带的默认文件,除了我添加了一行 export EDITOR=vim

如果我不使用 cron 作业,则直接在命令行上执行此操作:

source .bashrc; echo $EDITOR # Output: vim

【问题讨论】:

如果你 cat ~/.bashrc 进入一个临时文件会发生什么? cat ~/.bashrc 是什么意思?它有一行:export EDITOR=vim。我在问为什么echo 命令没有选择$EDITOR 环境变量。 抱歉不清楚,在cron条目中,不是sourceing文件,而是使用cat确认它可以被cron读取。 是的,可以读取* * * * * /bin/bash -l -c 'cat ~/.bashrc > /tmp/cronjob.test' 我刚刚尝试了一个类似的 cron 命令,它运行良好,可以正确解释 ~ 并从 ~/.bashrc 中回显 shell 变量。这是否表明 ~/.bashrc 中有错误?? 【参考方案1】:

@alex 提供的答案是正确的,但在 Ubuntu 13.10 中,代码已稍作修改。没有 $PS1 变量,但在第 6-9 行有一个代码

case $- in 
   *i*) ;;       
   *) return;; 
esac

只需注释掉返回工作的行。即下面的代码有效

case $- in 
   *i*) ;;       
#   *) return;; 
esac

【讨论】:

如果您不想要此功能,请取出整个 case 声明。【参考方案2】:

source ~/.bashrc 不起作用的原因是您的 ~/.bashrc 上的内容(默认来自 Ubuntu 12.04)。如果您查看它,您将在第 5 行和第 6 行看到以下内容:

# If not running interactively, don't do anything
[ -z "$PS1" ] && return

PS1 变量是为交互式 shell 设置的,因此在通过cron 运行时它不存在,即使您将其作为登录 shell 执行也是如此。 /bin/bash -l -c -x 'source ~/.bashrc; echo $EDITOR > /tmp/cronjob.test'产生的文件内容证实了这一点:

+ source /home/plee/.bashrc
++ '[' -z '' ']'
++ return

要使source ~/.bashrc 起作用,请注释掉检查~/.bashrc 中是否存在PS1 变量的行:

#[ -z "$PS1" ] && return

这将使bash通过cron执行~/.bashrc的全部内容

【讨论】:

或者在source.bashrc文件之前将$PS1设置为任意值;这样您就不必更改.bashrc 这对我有用——我不知道为什么要这样设置,但在尝试了几个小时后似乎已经成功了! 由于某种原因,这对我在 debian 上不起作用。我仍然没有在 cronjobs 中得到我的 ~/.bashrc 此代码存在于文件中是有原因的。正确的解决方案是将应该由非交互式 shell 执行的代码移动到不同的配置文件中。一个常见的安排是将你需要的东西放在cron作业等中的一个单独的文件中,.(又名源;但source命令仅在Bash中可用,不能在sh中使用)根据需要从您的.profile 和/或.bash_profile 和/或.zshrc 和/或cron 作业中提交文件。【参考方案3】:

我刚刚尝试了一个文件.env_setup_rc 文件只有一行export EDITOR=vim,令人惊讶的是它正在工作。

所以我猜.bashrc 中有些东西与 cron 作业 bash 命令冲突。

【讨论】:

以上是关于Cron 作业没有获得在 .bashrc 中设置的环境变量的主要内容,如果未能解决你的问题,请参考以下文章

如何让 CRON 调用正确的路径

如何在 cpanel 中设置 cron 作业

在 windows 的 django 中设置一个 cron 作业

在 Windows 中设置 cron 作业

在 godaddy.com cpanel 中设置 cron 作业

在 Node.js 与 Cron 作业中设置间隔?