Alpine: "service `crond' does not exist"
Asked Answered
P

2

5

I'm trying to run an Node 12.13.0 Alpine Docker container that runs a script every 15 minutes. According to Alpine's wiki cron section, I should be able to just add a RUN task in the Dockerfile to run crond as a service via:

rc-service crond start && rc-update add crond

This however returns an error:

rc-service: service `crond' does not exist

Running a separate Docker container just to run the cron task against this Docker container is NOT an option. This container is already extremely lightweight, and doesn't do much.

Here is my Dockerfile:

FROM node:12.13.0-alpine

RUN apk add --no-cache tini openrc

WORKDIR /opt/app

COPY script.sh /etc/periodic/15min/

RUN chmod a+x /etc/periodic/15min/script.sh

RUN rc-service crond start && rc-update add crond

COPY . .

RUN chmod a+x startup.sh

ENTRYPOINT ["/sbin/tini", "--"]

CMD ["./startup.sh"]

Any help here would be appreciated.

Prem answered 27/10, 2019 at 8:27 Comment(2)
As a general rule, init scripts don't work in Docker: nothing actually runs them, and there isn't usually a proper init system. (tini in your example is a lightweight init that handles signals and reaps zombies but otherwise just runs a single child process.) "A separate container" or "the host cron" are the standard answers here.Leralerch
@DavidMaze I'm not sure what part of the problem you're specifically referring to. You seem to be addressing two separate issues: my use of tini, and me trying to setup a cron task. In my "startup" script, crond is what I'm using tini to take control over in case of sigterms. I'm handling sigterms directly in my node app's code.Prem
P
7

The issue was that some Alpine Docker containers come without the busybox-initscripts package installed. After installing this, crond is running as a service. One other hiccup I ran into is that run-parts, the command the executes the files in the /etc/periodic folders expects there to be no extension, so I stripped that, and everything is working now.

The working Dockerfile looks like this:

FROM node:12.13.0-alpine

RUN apk upgrade --available

RUN apk add --no-cache tini openrc busybox-initscripts

WORKDIR /opt/app

COPY runScraper /etc/periodic/15min/

RUN chmod a+x /etc/periodic/15min/runScraper

COPY . .

RUN chmod a+x startup

ENTRYPOINT ["/sbin/tini", "--"]

CMD ["./startup"]
Prem answered 27/10, 2019 at 9:46 Comment(7)
I think you forgot to add RUN rc-service crond start && rc-update add crond to this Dockerfile version. Didn't you?Haema
The busybox-initscripts takes care of loading that, and should run after installing the package. I think crond, and a lot of other supporting libraries were stripped from this specific image. If memory serves correctly, busybox-initscripts was the recommended way to install/load crond onto a bare Alpine image at the time.Prem
@ClarkBrent I'm scratching my head on this for two days now. I have tried many things and just found your answer here. I tried this, but this still doesn't seem to work. I see you install 'busybox-initscripts', but at what line are these initscripts then being executed? Is it in your startup script?Scythia
@Scythia All the scripts in the busybox-initscripts package (Including crond) should start immediately after being installed by apk. The startup shell script just ran a small node app. As for actually creating a cronjob, I just made another shell script with the commands I needed, and put it in the one of the /etc/periodic folders, and made it executable.Prem
@ClarkBrent Hmm ok thanks. It's weird, but in my case cron won't start that way. (That is on PHP alpine image, so maybe "something" is different there)Scythia
@Scythia see my posted answer, I faced the exact same issue as you just now, it seems now you need to explicitly create a file for it to still start, even though openrc is installed and activated "crond" via busybox-initscripts.Sarinasarine
Thanks, I'll try that once I get to it.Scythia
S
0

Alpine might've changed how things work since the last solution was published, now it just reports back:

 # rc-service crond start
 * You are attempting to run an openrc service on a
 * system which openrc did not boot.
 * You may be inside a chroot or you may have used
 * another initialization system to boot this system.
 * In this situation, you will get unpredictable results!
 * If you really want to do this, issue the following command:
 * touch /run/openrc/softlevel
 * ERROR: syslog failed to start
 * ERROR: cannot start crond as syslog would not start

Failing silently during the installation of "busybox-initscripts" which activates it automatically.

The important bit being:

touch /run/openrc/softlevel

which makes it work, note that you still need the rest of the previous solution installed, that is "openrc" and "busybox-initscripts".

Sarinasarine answered 9/7, 2021 at 16:22 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.