Cron 和 virtualenv

2025-02-14 09:50:00
admin
原创
45
摘要:问题描述:我正在尝试从 cron 运行 Django 管理命令。我正在使用 virtualenv 来保持我的项目处于沙盒状态。我在这里和其他地方看到过一些示例,它们展示了在 virtualenv 中运行管理命令,例如:0 3 * * * source /home/user/project/env/bin/ac...

问题描述:

我正在尝试从 cron 运行 Django 管理命令。我正在使用 virtualenv 来保持我的项目处于沙盒状态。

我在这里和其他地方看到过一些示例,它们展示了在 virtualenv 中运行管理命令,例如:

0 3 * * * source /home/user/project/env/bin/activate && /home/user/project/manage.py command arg

但是,尽管 syslog 显示任务应该启动时的条目,但该任务实际上从未运行(脚本的日志文件为空)。如果我从 shell 手动运行该行,它会按预期工作。

我目前能够通过 cron 运行命令的唯一方法是将命令分解并将它们放入愚蠢的 bash 包装器脚本中:

#!/bin/sh
source /home/user/project/env/bin/activate
cd /home/user/project/
./manage.py command arg

编辑:

ars 提出了一个可行的命令组合:

0 3 * * * cd /home/user/project && /home/user/project/env/bin/python /home/user/project/manage.py command arg

至少就我的情况而言,调用 virtualenv 的 activate 脚本没有任何作用。这有效,所以继续演示。


解决方案 1:

您应该能够通过python在虚拟环境中使用来执行此操作:

/home/my/virtual/bin/python /home/my/project/manage.py command arg

编辑:如果你的 django 项目不在 PYTHONPATH 中,那么你需要切换到正确的目录:

cd /home/my/project && /home/my/virtual/bin/python ...

您还可以尝试从 cron 记录失败:

cd /home/my/project && /home/my/virtual/bin/python /home/my/project/manage.py > /tmp/cronlog.txt 2>&1

manage.py另一件可以尝试的事情是在脚本的最顶部进行相同的更改:

#!/home/my/virtual/bin/python

解决方案 2:

从 cronfile运行source将不起作用,因为 cron 使用/bin/sh其默认 shell,它不支持source。您需要将 SHELL 环境变量设置为/bin/bash

SHELL=/bin/bash
*/10 * * * * root source /path/to/virtualenv/bin/activate && /path/to/build/manage.py some_command > /dev/null

由于没有记录错误详细信息,因此很难发现失败的原因/var/log/syslog。最好将自己设置为 root,这样您就可以通过电子邮件收到任何 cron 错误。只需将自己添加到/etc/aliases并运行即可sendmail -bi

更多信息请访问:http:
//codeinthehole.com/archives/43-Running-django-cronjobs-within-a-virtualenv.html

上面的链接改为:
https: //codeinthehole.com/tips/running-django-cronjobs-within-a-virtualenv/

解决方案 3:

对于第 n 个答案,我感到很抱歉,但是我检查了答案,确实有更简单、更整洁的答案。

长话短说

在你的 cron 中使用 venv 的 python 二进制文件:

0 3 * * * /home/user/project/env/bin/python /home/user/project/manage.py 

长话短说

当我们想要使用特定虚拟环境(即二进制文件和模块)的 python 配置设置当前 shell 时,我们会激活虚拟环境。

这与使用当前 shell 有关:在当前 shell 上执行多个 python 命令,而无需引用 venv 的完整 python 路径。

在 cron 或甚至 bash 框架中,哪个值可以激活环境?此外,我在一些答案中读到了一些参考,bash而不是sh或仍然定义一个包装器来调用 Python 代码。但我们为什么要为这些烦恼呢?

我再说一遍,只管去做:

0 3 * * * /home/user/project/env/bin/python /home/user/project/manage.py 

该文件证实:

您不需要特别激活环境;激活只是将虚拟环境的二进制目录添加到您的路径中,这样“python”就会调用虚拟环境的 Python 解释器,您可以运行已安装的脚本而无需使用其完整路径。但是,虚拟环境中安装的所有脚本都应该无需激活即可运行,并自动与虚拟环境的 Python 一起运行。

解决方案 4:

不要再看了:

0 3 * * * /usr/bin/env bash -c 'cd /home/user/project && source /home/user/project/env/bin/activate && ./manage.py command arg' > /dev/null 2>&1

通用方法:

* * * * * /usr/bin/env bash -c 'YOUR_COMMAND_HERE' > /dev/null 2>&1

这样做的好处是你不需要将SHELLcrontab 的变量从sh更改为bash

解决方案 5:

使用虚拟环境时运行 python cron 作业的唯一正确方法是激活环境,然后执行环境的 python 来运行代码。

一种方法是activate_this在你的 Python 脚本中使用虚拟环境,请参阅:http://virtualenv.readthedocs.org/en/latest/userguide.html#using-virtualenv-without-bin-python

另一个解决方案是回显完整的命令,包括激活环境并将其导入/bin/bash。请考虑以下方法/etc/crontab

***** root echo 'source /env/bin/activate; python /your/script' | /bin/bash

解决方案 6:

不用处理特定于虚拟环境的 shebang,只需将其添加PATH到 crontab 即可。

从激活的虚拟环境运行这三个命令,python 脚本就可以正常工作:

$ echo "PATH=$PATH" > myserver.cron
$ crontab -l >> myserver.cron
$ crontab myserver.cron

crontab 的第一行现在应如下所示:

PATH=/home/me/virtualenv/bin:/usr/bin:/bin:  # [etc...]

解决方案 7:

这是一个简单的方法,使 crontab 命令与常规命令非常相似(在 Ubuntu 18.04 中测试)。需要记住的一些关键注意事项:

  • 您可以使用.命令代替source。 (crontabsh默认使用 ,而不是bash,因此它没有source。)

  • ~$variables在 crontab 命令中扩展。(只有 crontab 环境语句不进行变量扩展。)

如果您有文件,则以下是示例~/myproject/main.py

* * * * * cd ~/myproject && . .venv/bin/activate && python main.py > /tmp/out1 2>&1

您也可以直接调用venv目录中的具体路径python,那么就不需要调用了activate

* * * * * ~/myproject/.venv/bin/python ~/myproject/main.py > /tmp/out2 2>&1

缺点是你需要指定两次项目路径,这会使维护变得更加棘手。为了避免这种情况,你可以使用 shell 变量,这样你只需指定一次项目路径:

* * * * * project_dir=~/myproject ; $project_dir/.venv/bin/python $project_dir/main.py > /tmp/out3 2>&1

解决方案 8:

对我来说最好的解决方案是

  • 使用 venv bin/ 目录中的 python 二进制文件

  • 设置 python 路径以包含 venv 模块目录。

man python提到在 shell 中$PYTHONPATH或在 python 中使用sys.path

其他答案提到了使用 shell 执行此操作的想法。从 python 中,将以下几行添加到我的脚本中允许我直接从 cron 成功运行它。

import sys
sys.path.insert(0,'/path/to/venv/lib/python3.3/site-packages');

以下是它在交互式会话中的表现——

Python 3.3.2+ (default, Feb 28 2014, 00:52:16) 
[GCC 4.8.1] on linux
Type "help", "copyright", "credits" or "license" for more information.

>>> import sys

>>> sys.path
['', '/usr/lib/python3.3', '/usr/lib/python3.3/plat-x86_64-linux-gnu', '/usr/lib/python3.3/lib-dynload']

>>> import requests
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
ImportError: No module named 'requests'   

>>> sys.path.insert(0,'/path/to/venv/modules/');

>>> import requests
>>>

解决方案 9:

我想添加这一点,因为我花了一些时间解决这个问题,但没有找到在 cron 和 virtualenv 中组合使用变量的答案。所以也许这会对某些人有所帮助。

PATH=/usr/local/sbin:/usr/local/bin:/sbin:/bin:/usr/sbin:/usr/bin
DIR_SMTH="cd /smth"
VENV=". venv/bin/activate"
CMD="some_python_bin do_something"
# m h  dom mon dow   command
0 * * * * $DIR_SMTH && $VENV && $CMD -k2 some_target >> /tmp/crontest.log 2>&1

当配置如下时,它不能很好地工作

DIR_SMTH="cd /smth && . venv/bin/activate"

感谢@davidwinterbottom、@reed-sandberg和@mkb给出正确的指导。接受的答案实际上工作正常,直到您的 python 需要运行一个脚本,而该脚本必须从 venv/bin 目录运行另一个 python 二进制文件。

解决方案 10:

如果您使用 Python 并使用 Conda 虚拟环境,其中 Python 脚本包含 shebang #!/usr/bin/env python,则以下工作有效:

* * * * * cd /home/user/project && /home/user/anaconda3/envs/envname/bin/python script.py 2>&1

此外,如果您想捕获脚本中的任何输出(例如打印、错误等),您可以使用以下命令:

* * * * * cd /home/user/project && /home/user/anaconda3/envs/envname/bin/python script.py >> /home/user/folder/script_name.log 2>&1

解决方案 11:

我遇到了同样的问题,花了很多时间解决这个问题。这里的解决方案都对我没用,所以我分享一下对我有用的方法:

  1. 打开一个新文件“pick_name.sh”,在项目目录中打开它。

  2. 在“pick_name.sh”文件中,写入并保存以下行:

#!/bin/bash
source /YOUR_VIRTUAL_ENV_PATH/bin/activate
export PYTHONPATH="${PYTHONPATH}:/PATH_TO_CUSTOM_MODULE_YOU_CREATED**OPTIONAL**"
export PYTHONPATH="${PYTHONPATH}:/PATH_TO_ANOTHER_CUSTOM_MODULE_YOU_CREATED**OPTIONAL**"
cd /PATH_TO_DIR_STORING_FILE_NAME.PY
python file_name.py
  1. 转到 /var/spool/cron/crontabs(或您的 cron 管理文件所在的位置)并打开“root”文件。

  2. 将这些行添加到 crontab 文件夹内的根文件中:

# m h  dom mon dow   command
* * * * * /PATH_TO_DIR_WHERE_PICK_NAME.SH_SITS/pick_name.sh >> /YOUR_PROJECT_DIR/cron_output.txt 2>&1

笔记:

  • 此命令(第 4 节)将运行“pick_name.sh”文件。在此示例中,它每分钟运行一次,因此请确保根据您的需要进行更改。它将所有日志写入名为“cron_ouput”​​的日志文件。无需事先创建该文件,它将自动创建。

  • 确保将所有路径(我用大写字母书写)替换为您的路径。

  • 您可以更改文件名,如果是这样,请确保按照我的说明在所有情况下都进行更改,以避免出现错误。

  • 如果您想要添加另一个 py 文件以通过 cron 运行,则需要将其添加到“pick_nam.sh”文件*而不是 cron。只需在“pick_nam.sh”中复制第 2 节的行,但不包含“#!/bin/bash”部分。然后,每次 cron 运行“pick_name.sh”时,它都会运行您在其中指定的所有文件。

  • 确保在更改后重新启动 cron,这可以节省我大量的调试时间,使用此命令:

systemctl restart cron

解决方案 12:

python 脚本

from datetime import datetime                                                                                                                                                                
import boto   # check wheather its taking the virtualenv or not                                                                                                                                                                        
import sys                                                                                                                                                                                   
param1=sys.argv[1]     #Param                                                                                                                                                                                                                                                                                                                                                                    
myFile = open('appendtxt.txt', 'a')                                                                                                                                                      
myFile.write('
Accessed on ' + param1+str(datetime.now())) 

Cron 命令

 */1 * * * *  cd /Workspace/testcron/ && /Workspace/testcron/venvcron/bin/python3  /Workspace/testcron/testcronwithparam.py param  

在上面的命令中

  • /1 * - 每隔一分钟执行一次

  • cd /Workspace/testcron/ -python 脚本的路径

  • /Workspace/testcron/venvcron/bin/python3 - Virtualenv 路径

  • Workspace/testcron/testcronwithparam.py - 文件路径

  • param - 参数

解决方案 13:

我在 Django 项目中添加了以下脚本manage.sh,它会获取虚拟环境,然后使用manage.py您传递给它的任何参数运行该脚本。它使得在虚拟环境(cron、systemd 单元,基本上任何地方)内运行命令变得非常容易:

#! /bin/bash

# this is a convenience script that first sources the venv (assumed to be in
# ../venv) and then executes manage.py with whatever arguments you supply the
# script with. this is useful if you need to execute the manage.py from
# somewhere where the venv isn't sourced (e.g. system scripts)

# get the script's location
DIR="$( cd "$( dirname "${BASH_SOURCE[0]}" )" >/dev/null 2>&1 && pwd )"

# source venv <- UPDATE THE PATH HERE WITH YOUR VENV's PATH
source $DIR/../venv/bin/activate

# run manage.py script
$DIR/manage.py "$@"

然后在你的 cron 条目中运行:

0 3 * * * /home/user/project/manage.sh command arg

只需记住你需要使manage.sh脚本可执行

解决方案 14:

在 venv 中添加 Python 安装的路径,但不要激活环境。

* * * * * /HDD1/shritam_kumar/VENOM/venv/bin/python /HDD1/shritam_kumar/Projects/Voelkner-DE/schedule_product_BA.py

就这么简单。

解决方案 15:

由于 cron 在其自己的最小sh环境中执行,因此我在虚拟环境中运行 Python 脚本的操作如下:

* * * * * . ~/.bash_profile; . ~/path/to/venv/bin/activate; python ~/path/to/script.py

(注意:如果. ~/.bash_profile对您不起作用,请尝试. ~/.bashrc. ~/.profile取决于您的服务器如何设置。)

这将加载您的bashshell 环境,然后激活您的 Python 虚拟环境,本质上让您使用与您测试脚本相同的设置。

无需在 crontab 中定义环境变量,也无需修改现有的脚本。

解决方案 16:

如果你和我一样是 MacOS 用户,你可以在 /var/mail/{username} 文件中检查 crontab 错误消息。像这样

tail /var/mail/{username}

如果出现“操作不允许”错误,也许您必须将 cron 添加到完全磁盘访问应用程序(安全和隐私 > 隐私 > 完全磁盘访问应用程序/执行程序)。

然后点击+按钮,进入/usr/sbin,双击cron文件,就会修复“不允许”的错误,详细步骤

这是我的代码:

0 19 * * * cd /Users/user/Desktop/Project && source /Users/user/Desktop/Project/venv/bin/activate && python command arg

解决方案 17:

我发现这对我有用(通用):

* * * * * cd /home/user/project && /home/user/project/.venv/bin/python /home/user/project/project.py  >> /home/user/project/project.log 2>&1

笔记:

  • 在项目目录中创建一个日志文件 project.log(故障排除)

  • 假设 .venv 已经创建

  • 假定这些条目也存在于 crontab 文件中:

SHELL=/bin/bash PATH=/sbin:/bin:/usr/sbin:/usr/bin

解决方案 18:

对于我来说,这是一个非常有效的解决方案。

source /root/miniconda3/etc/profile.d/conda.sh && \nconda activate <your_env> && \npython <your_application> &

我在 Ubuntu 18.04.3 LTS 上使用带有 Conda 版本 4.7.12 的 miniconda。

我能够将上述内容放入脚本中并通过 crontab 运行它,不会出现任何问题。

解决方案 19:

这也适用于 crontab -e

* */5 * * * cd /home/project && sudo /home/project/venv/bin/python scripte.py

解决方案 20:

我遇到了同样的问题:

我编写了一个自定义 django 命令来检查 geodjango 多边形内的 geodjango 位置坐标,但在自动运行该任务时遇到了麻烦,但是使用此命令与 crontab 对我有用:

* * * * * ./home/project/locations/locations.sh >> /var/log/locations.log 2>&1
相关推荐
  政府信创国产化的10大政策解读一、信创国产化的背景与意义信创国产化,即信息技术应用创新国产化,是当前中国信息技术领域的一个重要发展方向。其核心在于通过自主研发和创新,实现信息技术应用的自主可控,减少对外部技术的依赖,并规避潜在的技术制裁和风险。随着全球信息技术竞争的加剧,以及某些国家对中国在科技领域的打压,信创国产化显...
工程项目管理   1590  
  为什么项目管理通常仍然耗时且低效?您是否还在反复更新电子表格、淹没在便利贴中并参加每周更新会议?这确实是耗费时间和精力。借助软件工具的帮助,您可以一目了然地全面了解您的项目。如今,国内外有足够多优秀的项目管理软件可以帮助您掌控每个项目。什么是项目管理软件?项目管理软件是广泛行业用于项目规划、资源分配和调度的软件。它使项...
项目管理软件   1361  
  信创产品在政府采购中的占比分析随着信息技术的飞速发展以及国家对信息安全重视程度的不断提高,信创产业应运而生并迅速崛起。信创,即信息技术应用创新,旨在实现信息技术领域的自主可控,减少对国外技术的依赖,保障国家信息安全。政府采购作为推动信创产业发展的重要力量,其对信创产品的采购占比情况备受关注。这不仅关系到信创产业的发展前...
信创和国产化的区别   18  
  信创,即信息技术应用创新产业,旨在实现信息技术领域的自主可控,摆脱对国外技术的依赖。近年来,国货国用信创发展势头迅猛,在诸多领域取得了显著成果。这一发展趋势对科技创新产生了深远的推动作用,不仅提升了我国在信息技术领域的自主创新能力,还为经济社会的数字化转型提供了坚实支撑。信创推动核心技术突破信创产业的发展促使企业和科研...
信创工作   18  
  信创技术,即信息技术应用创新产业,旨在实现信息技术领域的自主可控与安全可靠。近年来,信创技术发展迅猛,对中小企业产生了深远的影响,带来了诸多不可忽视的价值。在数字化转型的浪潮中,中小企业面临着激烈的市场竞争和复杂多变的环境,信创技术的出现为它们提供了新的发展机遇和支撑。信创技术对中小企业的影响技术架构变革信创技术促使中...
信创国产化   19  
热门文章
项目管理软件有哪些?
云禅道AD
禅道项目管理软件

云端的项目管理软件

尊享禅道项目软件收费版功能

无需维护,随时随地协同办公

内置subversion和git源码管理

每天备份,随时转为私有部署

免费试用