Docker 容器内定时任务秘诀全解

18 阅读1分钟

Docker 容器内定时任务秘诀全解

容器中的定时任务如何稳定执行?本文适合收藏备查。

核心语法速查

Crontab 基本格式

表达式说明
* * * * *分 时 日 月 周

重要标志

标志说明
-e设置环境变量
-v挂载卷
-d后台运行容器

Dockerfile 示例

FROM ubuntu:20.04
# 安装 cron
RUN apt-get update && apt-get install -y cron

# 添加定时任务脚本
COPY script.sh /script.sh
RUN chmod +x /script.sh

# 添加 crontab 文件
COPY crontab /etc/cron.d/simple-cron

# 赋予 crontab 文件执行权限
RUN chmod 0644 /etc/cron.d/simple-cron

# 应用 crontab 文件更新
RUN crontab /etc/cron.d/simple-cron

# 创建日志文件
RUN touch /var/log/cron.log

# 设置容器启动命令
CMD cron && tail -f /var/log/cron.log

Docker Compose 示例

version: '3'
services:
  cronjob:
    image: your-image
    volumes:
      - ./script.sh:/script.sh
      - ./crontab:/etc/cron.d/simple-cron
    command: ["cron", "-f"]

Crontab 文件示例

# 每分钟执行一次 script.sh
* * * * * root /script.sh >> /var/log/cron.log 2>&1

监控定时任务

工具说明
cron-log定时任务的日志文件
htop实时查看容器内进程

定时任务脚本示例

#!/bin/bash
# 打印当前时间到日志文件
date >> /var/log/cron.log

常见问题

问题解决方法
定时任务不执行确保 cron 服务已启动
定时任务日志为空检查脚本路径和权限
定时任务只执行一次确保 crontab 文件中没有错误
容器重启后定时任务失效使用 docker-composekubernetes 管理定时任务
定时任务在容器内时间不一致设置容器时区与宿主机一致

高级用法

功能说明
@reboot系统启动时执行
@hourly每小时执行
@daily每天执行
@weekly每周执行
@monthly每月执行
@yearly每年执行

Docker 容器内设置时区

FROM ubuntu:20.04
RUN apt-get update && apt-get install -y tzdata
ENV TZ=Asia/Shanghai
RUN ln -snf /usr/share/zoneinfo/$TZ /etc/localtime && echo $TZ > /etc/timezone

持久化日志

version: '3'
services:
  cronjob:
    image: your-image
    volumes:
      - ./script.sh:/script.sh
      - ./crontab:/etc/cron.d/simple-cron
      - ./cron-logs:/var/log
    command: ["cron", "-f"]

使用 Docker Secrets 管理敏感信息

version: '3'
services:
  cronjob:
    image: your-image
    secrets:
      - cron-secret
    command: ["cron", "-f"]

secrets:
  cron-secret:
    file: ./cron-secret.txt
# 读取 Docker Secret
#!/bin/bash
SECRET=$(cat /run/secrets/cron-secret)
echo "Secret: $SECRET" >> /var/log/cron.log

使用环境变量

FROM ubuntu:20.04
RUN apt-get update && apt-get install -y cron

# 设置环境变量
ENV SCRIPT_PATH=/script.sh

# 添加定时任务脚本
COPY script.sh /script.sh
RUN chmod +x /script.sh

# 添加 crontab 文件
COPY crontab /etc/cron.d/simple-cron

# 应用 crontab 文件更新
RUN crontab /etc/cron.d/simple-cron

# 创建日志文件
RUN touch /var/log/cron.log

CMD cron && tail -f /var/log/cron.log

Crontab 文件中使用环境变量

# 使用环境变量
* * * * * root $SCRIPT_PATH >> /var/log/cron.log 2>&1

使用 docker exec 手动执行任务

# 手动执行容器内的定时任务
docker exec -it container_name /script.sh

使用 docker logs 查看日志

# 查看容器的日志
docker logs container_name

使用 docker-compose 管理定时任务

version: '3'
services:
  cronjob:
    image: your-image
    volumes:
      - ./script.sh:/script.sh
      - ./crontab:/etc/cron.d/simple-cron
    command: ["cron", "-f"]
    environment:
      - SCRIPT_PATH=/script.sh

使用 docker-compose 设置时区

version: '3'
services:
  cronjob:
    image: your-image
    volumes:
      - /etc/localtime:/etc/localtime:ro
      - /etc/timezone:/etc/timezone:ro
    command: ["cron", "-f"]

使用 Kubernetes 管理定时任务

apiVersion: batch/v1
kind: CronJob
metadata:
  name: cronjob-example
spec:
  schedule: "*/1 * * * *"
  jobTemplate:
    spec:
      template:
        spec:
          containers:
          - name: cronjob-container
            image: your-image
            args:
            - /script.sh
            volumeMounts:
            - name: script-volume
              mountPath: /script.sh
          volumes:
          - name: script-volume
            configMap:
              name: script-config
          restartPolicy: OnFailure

Kubernetes ConfigMap 示例

apiVersion: v1
kind: ConfigMap
metadata:
  name: script-config
data:
  script.sh: |
    #!/bin/bash
    date >> /var/log/cron.log

使用 docker events 监控容器事件

# 监控容器事件
docker events --filter 'event=start' --filter 'event=stop'

使用 docker stats 查看容器资源使用情况

# 查看容器资源使用情况
docker stats

定时任务的容错处理

问题解决方法
定时任务失败不重试使用 cronMAILTO 配置发送邮件报警
定时任务在容器中部分执行检查脚本是否完整执行
定时任务依赖的服务未启动确保依赖的服务在定时任务前启动

使用 cronMAILTO 配置发送邮件报警

# 发送邮件报警
MAILTO=admin@example.com
* * * * * root /script.sh >> /var/log/cron.log 2>&1

使用 docker 命令查看容器内的 cron 任务

# 查看容器内的 cron 任务
docker exec container_name crontab -l

使用 docker 命令编辑容器内的 cron 任务

# 编辑容器内的 cron 任务
docker exec -it container_name crontab -e

使用 docker 命令删除容器内的 cron 任务

# 删除容器内的 cron 任务
docker exec -it container_name crontab -r

定时任务脚本中的错误处理

#!/bin/bash
# 错误处理
set -e
date >> /var/log/cron.log
echo "Task completed" >> /var/log/cron.log

使用 docker 命令重启容器

# 重启容器
docker restart container_name

使用 docker-compose 重启容器

# 重启容器
docker-compose restart service_name

使用 docker 命令停止容器

# 停止容器
docker stop container_name

使用 docker-compose 停止容器

# 停止容器
docker-compose stop service_name

使用 docker 命令删除容器

# 删除容器
docker rm container_name

使用 docker-compose 删除容器

# 删除容器
docker-compose rm service_name

使用 docker 命令构建镜像

# 构建镜像
docker build -t your-image .

使用 docker-compose 构建镜像

# 构建镜像
docker-compose build

使用 docker 命令运行容器

# 运行容器
docker run -d --name container_name your-image

使用 docker-compose 运行容器

# 运行容器
docker-compose up -d

使用 docker 命令查看容器状态

# 查看容器状态
docker ps -a

使用 docker-compose 查看容器状态

# 查看容器状态
docker-compose ps

使用 docker 命令进入容器

# 进入容器
docker exec -it container_name /bin/bash

使用 docker-compose 进入容器

# 进入容器
docker-compose exec service_name /bin/bash

使用 docker 命令查看容器日志

# 查看容器日志
docker logs container_name

使用 docker-compose 查看容器日志

# 查看容器日志
docker-compose logs service_name

定时任务中的环境变量

环境变量说明
PATH系统路径
SHELL默认 shell
HOME家目录
USER当前用户
TZ时区

容器化定时任务的最佳实践

  • 使用 cron 服务管理定时任务
  • 设置容器时区与宿主机一致
  • 持久化日志文件
  • 使用 dockerdocker-compose 管理容器

生成 Cron 表达式

如果你对 Cron 表达式的生成感到困扰,可以使用 Hey CronCron 表达式生成器。输入中文描述,自动生成标准的 Cron 表达式,省时省力。

其他实用工具

  • 正则表达式生成器:快速生成和测试正则表达式
  • 中英互译:便捷的在线翻译工具
  • JSON 格式化:格式化 JSON 数据,便于阅读和调试
  • Base64 编码解码:在线 Base64 编解码工具
  • 时间戳转换:方便的时间戳与日期互转工具
  • JWT 解析:解析 JWT 令牌,查看其内容

Hey Cron 不仅提供 Cron 表达式生成器,还有多种实用工具,助你高效开发和调试。