DEV Community

James Candan
James Candan

Posted on • Updated on

Cron with Lando

Update Feb 28, 2020: It turns out that cron runs within it's own limited environment. See below for more details.

In Laravel, we want the following cron configuration to fire the framework's scheduler. Place this in a file somewhere within your project code base. I went with resources/config/cron.txt.

* * * * * php /app/artisan schedule:run

Note: The cron daemon was designed in such a way that it does NOT execute commands within your normal shell environment. That means your $PATH will not match your container's, and your php.ini memory limit may not be set. That said, we need to supply the full path from within the Lando container to php. Typically, this will be /usr/local/bin/php. In that case, use the following:

* * * * * /usr/local/bin/php -d memory_limit=-1 /app/artisan schedule:run

Next, we need to get cron installed. You'll want to perform this as root during build.

    build_as_root:
      - apt-get update -y
      - apt-get install cron -y

Now, we're ready to fire the cron service. Because cron services all users in a system, it must be started with root priviliges.

    run_as_root:
      - service cron start

Here we are, born to be kings; we're the princes of the the universe.

Oh, sorry, off on a tangent. Okay, we can now store our cron config with crontab.

    run:
      - crontab /app/resources/config/cron.txt

Put this altogether, and you will have arrived.

name: my-project
recipe: laravel
config:
  webroot: public
services:
  appserver:
    build_as_root:
      - apt-get update -y
      - apt-get install cron -y
    run_as_root:
      - service cron start
    run:
      - crontab /app/resources/config/cron.txt

Check that things have gone as planned.

$ lando ssh
www-data@ba70770a45a1:/app$ service cron status
[ ok ] cron is running.
www-data@ba70770a45a1:/app$ crontab -l
* * * * * php /app/artisan schedule:run
www-data@ba70770a45a1:/app$ 

Enjoy.

Top comments (4)

Collapse
 
djboris88 profile image
Boris Đemrovski

Thank you! Very useful and easy to set up.

Collapse
 
djboris88 profile image
Boris Đemrovski

Actually, it doesn't start automatically after lando is restarted... :( I have to ssh manually and run service cron start for it to work after appservice restarts.

Collapse
 
djboris88 profile image
Boris Đemrovski

Ok, I managed to do it.

Here is @jcandan 's script but updated with an additional step:

appserver:
    build_as_root:
      - apt-get update -y
      - apt-get install cron -y
      - cp -f /app/.lando/docker-php-entrypoint.sh /usr/local/bin/docker-php-entrypoint
    run_as_root:
      - service cron start
    run:
      - crontab /app/resources/config/cron.txt

The only thing added is the command to copy a changed docker entrypoint bash script to the usual place. And here is the content of the changed entrypoint script:

#!/bin/sh
service cron start

set -e

# first arg is `-f` or `--some-option`
if [ "${1#-}" != "$1" ]; then
        set -- apache2-foreground "$@"
fi

exec "$@"

Here I only added service cron start, the rest was already there in the original entrypoint bash script. I actually used the same combo for getting the supervisor to work, for Laravel queue workers.

Collapse
 
parijke profile image
Paul Rijke

Great tip. Implemented it immediately