How to run cron jobs in Docker containers?
1 Overview
As system administrators, we always encounter the need to schedule tasks. We can cron
achieve this by serving in the Linux system . In addition, we can in the container systemcron
Now, this tutorial will clarify that in the Docker container cron
in the first method, we embed the cron
service in the docker image, and the other method will explain how to install the scheduling service in the container.
2. Cron service - use Dockerfile
method
Dockerfile
Building an image is one of the easiest ways to create a container image. So, what should we do? Basically, it Dockerfile
is a simple text file that contains a set of instructions for building an image. We need to provide scheduling tasks, cron
detailed information, and slave Dockerfile
cron
services.
2.1. WritingDockerfile
Let's take a quick look at an example:
$ tree . ├── Dockerfile └── get_date.sh 0 directories, 2 files
Dockerfile
FROM
Start with the first line of command, which will get the requested image from the configured registry. In our example, the default registry configuration is DockerHub
. Then MAINTAINER
, it is metadata used to capture author information. ADD
The instruction get_date.sh
copies the script from the image build path of the host to the target path of the image.
After copying the script to the build image, the RUN
instructions will grant executable permissions. Not only that- RUN
instructions help to execute any shell command as a new image layer above the current layer and submit the result. RUN
Update the apt
repository and cron
it is still crontab
cron
scheduling in the image .
Finally, we will use the CMD
commandcron
$ cat Dockerfile # Dockerfile to create image with cron services FROM ubuntu:latest MAINTAINER baeldung.com # Add the script to the Docker Image ADD get_date.sh /root/get_date.sh # Give execution rights on the cron scripts RUN chmod 0644 /root/get_date.sh #Install Cron RUN apt-get update RUN apt-get -y install cron # Add the cron job RUN crontab -l | { cat; echo "* * * * * bash /root/get_date.sh"; } | crontab - # Run the command on container startup CMD cron
2.2. Build and run cron image
Once Dockerfile
ready, we can use docker build
commands to build the image. The dot (.) instructs the Docker engine to Dockerfile
Dockerfile
create a docker layer from each instruction given on the current path to form the final build image . The typical build output looks like this:
$ docker build . Sending build context to Docker daemon 3.072kB Step 1/8 : FROM ubuntu:latest ---> ba6acccedd29 Step 2/8 : MAINTAINER baeldung.com ---> Using cache ---> e6b3946b2382 Step 3/8 : ADD get_date.sh /root/get_date.sh ---> 4976f058d428 Step 4/8 : RUN chmod 0644 /root/get_date.sh ---> Running in 423a4e9adbab Removing intermediate container 423a4e9adbab ---> 76d972a082ba Step 5/8 : RUN apt-get update ---> Running in badc0d84f6ff Get:1 http://security.ubuntu.com/ubuntu focal-security InRelease [114 kB] ... ... output truncated ... ... Removing intermediate container badc0d84f6ff ---> edb8a19b891c Step 6/8 : RUN apt-get -y install cron ---> Running in efd9b8a67d98 Reading package lists... Building dependency tree... ... ... output truncated ... ... Done. invoke-rc.d: could not determine current runlevel invoke-rc.d: policy-rc.d denied execution of start. Removing intermediate container efd9b8a67d98 ---> 2b80000d32a1 Step 7/8 : RUN crontab -l | { cat; echo "* * * * * bash /root/get_date.sh"; } | crontab - ---> Running in 1bdd3e0cc877 no crontab for root Removing intermediate container 1bdd3e0cc877 ---> aa7c82aa7c11 Step 8/8 : CMD cron ---> Running in cf2d44873b36 Removing intermediate container cf2d44873b36 ---> 8cee091ca87d Successfully built 8cee091ca87d
Since we have cron
pre-installed the service into the image and embedded the task crontab
, when we run the container cron
or, we can use the docker run
command to start the container. Subsequently, the docker run
-it
"option helps to enter the container through the bash prompt.
The following figure shows the script cron
in the container get_date.sh
:
$ docker run -it 8cee091ca87d /bin/bash [email protected]:/# [email protected]:/# date Mon Nov 15 14:30:21 UTC 2021 [email protected]:/# ls -ltrh ~/date.out ls: cannot access '/root/date.out': No such file or directory [email protected]:/# ls -ltrh /root/get_date.sh -rw-r--r-- 1 root root 18 Nov 15 14:20 /root/get_date.sh [email protected]:/# crontab -l * * * * * bash /root/get_date.sh [email protected]:/# ls -ltrh ~/date.out -rw-r--r-- 1 root root 29 Nov 15 14:31 /root/date.out [email protected]:/# cat /root/date.out Mon Nov 15 14:31:01 UTC 2021
3. Cron service-real-time container method
Or, we can work in a Docker container cron
cron
. So, what is the modus operandi?
Let's docker run
quickly run a command using commands. ubuntu
Usually, the container is a lightweight operating system and does not include cron
services as its default package.
Therefore, we need to ** enter the container's interactive shell and use the apt
repository command cron
** service:
$ docker run -it ubuntu:latest /bin/bash Unable to find image 'ubuntu:latest' locally latest: Pulling from library/ubuntu 7b1a6ab2e44d: Pull complete Digest: sha256:626ffe58f6e7566e00254b638eb7e0f3b11d4da9675088f4781a50ae288f3322 Status: Downloaded newer image for ubuntu:latest root:/# root:/# which cron root:/# apt update -y Get:1 http://archive.ubuntu.com/ubuntu focal InRelease [265 kB] ... ... output truncated ... ... All packages are up to date. root:/# apt upgrade -y ... ... output truncated ... ... root:/# apt install cron vim -y Reading package lists... Done ... ... output truncated ... ... Done. invoke-rc.d: could not determine current runlevel invoke-rc.d: policy-rc.d denied execution of start. [email protected]:/# which cron /usr/sbin/cron $ docker cp get_data.sh 77483fc20fc9: /root/get_date.sh
We can use the get_date.sh
docker cp
command to copy get_date.sh from the host to the container. crontab -e
Use the vi
editor to edit cron
the cron
configuration below to run the script every minute. In addition, output a timestamp indicating the execution of the script:
root:/# export EDITOR=vi [email protected]:/# crontab -e * * * * * bash /root/get_date.sh root:/# date Mon Nov 17 11:15:21 UTC 2021 root:/# ls -ltrh ~/date.out ls: cannot access '/root/date.out': No such file or directory root:/# ls -ltrh /root/get_date.sh -rw-r--r-- 1 root root 18 Nov 17 11:09 /root/get_date.sh root:/# ls -ltrh ~/date.out -rw-r--r-- 1 root root 29 Nov 17 11:16 /root/date.out root:/# cat /root/date.out Mon Nov 17 11:16:01 UTC 2021
4 Conclusion
All in all, we have explored the cron
specific details of the assignment. The method ofcron
using Dockerfile is tocron
automatically execute scripts for service and task scheduling configuration.
Although it cron
can be installed and configured in a running container, it is only a runtime construct unless we use a docker commit
construct image.
In addition, depending on our usage, both options have their advantages.
0 Comments