生产环境下的Docker中django_crontab无法工作

3
我将为您翻译与IT技术相关的内容。以下是需要翻译的文本:

我正在尝试使用django_crontab每天运行两次计划脚本。我已在Ubuntu 18上进行了本地测试,它可以正常工作。然而,当我尝试在服务器上运行它(Python Docker镜像,在远程Ubuntu服务器上运行Django项目)时,什么也没有发生。 这是我的代码:

setting.py:

INSTALLED_APPS = (
.
.
    'django_crontab',
.
.
.
)

RONJOBS = [
    ('0 9,21 * * *', 'appname.folder.file.start')
]

我通过以下方式执行了cron:

$ python manage.py crontab add .

并查看活动作业:

$ python manage.py crontab show
f95300a5599dc7687ac79ab51c8bb33c -> ('0 9,21 * * *', 'appname.folder.file.start')


def start():
  logger.info(" process begins!")
  do_something()

注意:'start'函数已在生产服务器上测试过并且运行良好。

我还尝试通过在setting.py中添加路径来映射cronjob日志:

('0 9,21 * * *', 'appname.folder.file.start','>> /Logs/crontab.log')

但是文件crontab.log没有被创建。

有什么建议吗?谢谢!

5个回答

10

我遇到了同样的问题,以下是我采取的解决方法:

  • 在容器中安装了cron
  • 将命令service cron start添加到Dockerfile中的CMD中。
  • 将命令python manage.py crontab add添加到Dockerfile中的CMD中。

启动容器后,我使用python manage.py crontab showcrontab -l命令检查了cronjobs是否已创建,在这两种情况下,我都可以看到cronjobs。

我再次测试了它,并且它正在工作。我使用了以下:

docker-compose
command: bash -c "service cron start && python manage.py crontab add && gunicorn serv.wsgi:application --bind 0.0.0.0:8000 --timeout 600 --workers 5" 或来自Django的开发服务器。python manage.py runserver 0:8000

Dockerfile

FROM  python:3.9

RUN apt-get -y update

# Install cron.
RUN apt-get install -y cron && touch /var/log/cron.log

WORKDIR /app
COPY ./docker/python/django/requirements.txt /app/

RUN pip install -r requirements.txt

COPY ./app/ /app/```

2
虽然这不是一个完整的答案,但它提供了一个解决问题的方法,因此在这里保留是有用的。 - joanis
@Glarx的回答对我有用,但我遇到了一个问题,我通过在docker-compose文件中添加时区来解决它,因为我的容器时区比本地机器晚5个小时。请确保您的本地机器时区和容器时区相同。 - undefined

3
Django-crontab 依赖于 cron daemon 运行, 但许多 Docker 镜像并没有安装它或以其他方式启动它。这是 init 程序的职责之一,而大部分镜像都剥离了该功能。
你检查了 cron 的状态吗?我在生产环境中也遇到过相同的情况,后来发现是这个问题导致的。
首先运行 crontab -l 命令确认 cronjob 是否已正确安装,这可能取决于应用程序运行的用户,因此您可能需要为该命令添加其他选项。
如果 crontab 已安装,请通过运行 service cron status 命令检查 cron daemon 的状态。 如果未启动,请运行 service cron start 命令并检查此后是否可以正常使用 cron 任务。您应该将此操作添加到您的启动脚本中。

感谢您的评论。Crontab已安装并且状态正常运行,不幸的是,这并不是问题所在。 - Daniel Ben Zaken

1

我不知道这个问题是否已经解决,但是我有同样的问题,而且这个 Docker 文件对我有效:

FROM python:3.9-bullseye

RUN pip install --upgrade pip

RUN apt-get update && apt-get install ffmpeg libsm6 libxext6  -y

RUN apt-get install -y cron
RUN service cron start

COPY ./requirements.txt .
RUN pip install -r requirements.txt


COPY . /app

WORKDIR /app

ENV PORT 8080

RUN python3 manage.py crontab add
RUN service cron start 

CMD cron;gunicorn --bind :$PORT --workers 3 --timeout 300 usertest.wsgi:application

嗨,请添加有用的解释。只有代码答案很可能会被删除... 请阅读如何回答 - pierpy

0

如果您在生产环境中使用环境变量,可能会出现cronjob无法访问的情况。以下信息可能有所帮助,

如果您使用的是Ubuntu >=18.0,请尝试进行以下更改。 我假设您已经成功地将django-crontab集成到了您的django应用程序中。现在,通过ssh访问您的服务器并键入“crontab -e”,您将在此处定义您的cronjobs。在您的cronjob上方添加您的环境变量。请查看以下几行以了解如何使其对您的问题有意义-

DB_NAME = "your database name"
DB_USER = "User"
DB_PASSWORD = "password"
SECRET_KEY = "************************"

*/1 * * * * /home/sms/sms/env/bin/python /home/sms/sms/sms- 
backend/website/manage.py crontab run 446aeeebac8c8f82d9e01bb662dc9b21 >> 
/tmp/scheduled_job.log # django>

希望你能摆脱它。


0
django_crontab添加到settings.py文件中的INSTALLED_APPS中 CRONJOBS = [ ('5 * * * *', 'attendance.cron.print_message', '>> /var/log/cron.log 2>&1'), ]
这是我的DockerFile
FROM python:3.9
ENV PYTHONUNBUFFERED=1
RUN apt-get update \
&& apt-get install gcc -y \
&& apt-get clean \
&& apt-get install gunicorn3 -y \
#&& apt-get install python3.9-dev -y \
&& apt-get install libcurl4-gnutls-dev librtmp-dev -y \
&& apt-get install libnss3 libnss3-dev iputils-ping  -y \
&& apt-get install -y cron && touch /var/log/cron.log
RUN touch /var/log/attendance_system.log
WORKDIR /attendance_system
COPY requirements.txt /attendance_system/
RUN pip install -r requirements.txt
COPY . /attendance_system/

RUN chmod +x common_commands.sh
RUN bash common_commands.sh

EXPOSE 8000
EXPOSE 8001

这是我的common_commands.sh文件。
#!bin/bash

crontab -r                        # remove exist one
python manage.py crontab add      # add

exec "$@"

这是我的网络容器:
web:
    container_name: attendance_system
    build: .
    command: bash -c "service cron start  && daphne -b 0.0.0.0 -p 8000 AttendanceSystem.asgi:application"
    #    command: python manage.py runserver 0.0.0.0:8000
    volumes:
      - .:/attendance_system
    ports:
      - "8000:8000"
    environment:
      - TZ=Asia/Karachi
    depends_on:
      - db
      - redis

请注意:
- 请将文件名设置为您正在使用的项目名称,使用 asgi 而不是 wsgi。 - 确保 Web 容器应该运行在该容器中,并检查 Python 和容器的日期时间。
命令:
sudo docker-compose exec -it **container_name or ID** /bin/bash
python
from datetime import datetime
print(datetime.now())    

如果没有设置,则打印将显示您本地机器的当前日期和时间,如果没有,则将docker容器的时区设置为我在Web容器中设置的时区。

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接