Run Jobs on the Last Day of the Month | CronBase

cron expression Standard
$ 0 0 L * *

At midnight on the last day of every month

The `0 0 L * *` cron schedule executes a task once a month at midnight on the very last day of the month, regardless of whether that month has twenty-eight, twenty-nine, thirty, or thirty-one days. It is ideal for monthly billing cycles, data archiving, and generating financial reports.

Minute
0
Hour
0
Day of Month
L
Month
*
Day of Week
*

* Tools

Code & Implementations

nodejs
// Node.js implementation using standard cron pattern.
// Since many Node libraries lack native 'L' support, we schedule
// daily for the end of the month and evaluate programmatically.
const cron = require('node-cron');

function isLastDayOfMonth() {
    const today = new Date();
    const tomorrow = new Date(today);
    tomorrow.setDate(today.getDate() + 1);
    return tomorrow.getDate() === 1;
}

// Runs daily at midnight from the 28th to the 31st
cron.schedule('0 0 28-31 * *', () => {
    if (!isLastDayOfMonth()) {
        return;
    }
    console.log('Executing end-of-month database reconciliation...');
    try {
        // Execute production business logic here
    } catch (error) {
        console.error('Failed to run monthly job:', error);
    }
});
Setup notes

Install node-cron using npm install node-cron, then run this script as a persistent background process using PM2 or Docker.

Partner UptimeRobot

Keep this cron job monitored 24/7

UptimeRobot alerts you the moment a scheduled job stops responding. Free plan monitors up to 50 endpoints — no credit card required.

Platform Equivalents

Systemd Timer

OnCalendar*-*-* 00:00:00

my-task.timer
[Unit]
Description=Timer for cron expression: 0 0 L * *

[Timer]
OnCalendar=*-*-* 00:00:00
Persistent=true

[Install]
WantedBy=timers.target

Frequently Asked Questions

Does standard Linux crontab natively support the 'L' character?

No, standard Vixie cron and standard Linux crontabs do not natively support the 'L' character. Schedulers like Quartz, AWS EventBridge, and systemd-timers support it, but for standard crontab, you must run a daily script at month-end and check if tomorrow is the first.

How does this expression handle leap years in February?

If the underlying scheduler natively supports the 'L' character, it dynamically calculates leap years, running on February 29th during a leap year and February 28th otherwise. If using a daily fallback wrapper, the date utility calculates this automatically.

What timezone should I use when scheduling end-of-month jobs?

Always configure your cron daemon or orchestrator to run in Coordinated Universal Time (UTC). Using local timezones can cause your job to run twice or be skipped entirely during Daylight Saving Time (DST) transitions at month-end.

How can I prevent database locking during heavy monthly aggregations?

Avoid running heavy queries directly on your primary transactional database. Offload the data to a read-replica, use batching with small limit/offset chunks, or stream the data to an asynchronous processing queue to prevent performance degradation.

What is the best way to test a job scheduled with 'L'?

Since 'L' only occurs once a month, test your script logic by temporarily changing the cron schedule to run every minute in a staging environment, or mock the system clock in your application code to verify the date-evaluation logic.

* Explore

Related expressions you might need

Was this helpful?

Last verified: