Cron Expression Builder

Cron Expression for Every Weekday (Mon to Fri): 0 0 * * 1-5

The cron expression 0 0 * * 1-5 runs Monday through Friday. Covers the 1-5 range, MON-FRI aliases, holiday workarounds, and business-hours patterns.

100% client-side. Your data never leaves your browser.

Minute
Hour
Day of Month
Month
Day of Week

At 12:00 AM, Monday through Friday

Next 5 Executions
  • 1.Tue, Jun 9, 2026, 00:00
  • 2.Wed, Jun 10, 2026, 00:00
  • 3.Thu, Jun 11, 2026, 00:00
  • 4.Fri, Jun 12, 2026, 00:00
  • 5.Mon, Jun 15, 2026, 00:00
Quick Reference
*Any value
,List separator
-Range
/Step
1-5Range 1 through 5
*/15Every 15 units

Related Tools

The 0 0 * * 1-5 Expression

The cron expression 0 0 * * 1-5 fires at midnight, Monday through Friday. Field breakdown: minute (0), hour (0), day of month (*), month (*), day of week (1-5). Midnight weekdays is a common base. Most teams adjust the hour field to fit their actual need. The core concept here is the 1-5 range in the day of week field, which is what makes this page worth understanding regardless of what time you set.

The 1-5 Range in the Day of Week Field

Day of week in POSIX cron is the fifth field, and it uses the following numbering:

NumberDay
0Sunday
1Monday
2Tuesday
3Wednesday
4Thursday
5Friday
6Saturday
7Sunday (alias)

The range 1-5 matches Monday through Friday. Saturday (6) and Sunday (0 or 7) are excluded. This is the mechanism behind every “run only on business days” cron expression you will encounter.

MON-FRI Alias

In Vixie cron and most modern implementations, three letter abbreviations work in the day of week field:

0 0 * * MON-FRI    # identical to 0 0 * * 1-5
0 0 * * MON,WED,FRI  # Monday, Wednesday, Friday only
0 0 * * TUE,THU    # Tuesday and Thursday

Named aliases improve readability in shared crontabs. They work in cronie (the default on RHEL/CentOS/Fedora), Vixie cron (Debian/Ubuntu), and most managed cloud schedulers. If portability across minimal or embedded cron implementations matters, use numerics.

Why Weekday Only Schedules Exist

The primary reason is human availability. Automated systems that notify, alert, or deploy should account for whether anyone is around to respond. Common cases:

Business process automation

Invoice generation, report distribution, and data reconciliation jobs that feed into workflows humans act on daily don’t need to run over weekends when the output will sit unread until Monday.

Deployments and alerts

Many teams restrict production deploys to weekdays so that an engineer is available to roll back if something goes wrong. An on call alert at 2 AM Saturday is less useful if the team is unavailable until Monday.

Resource cost

If a job triggers downstream processing, API calls, or external services, running it five days a week instead of seven saves roughly 28% in operational costs on that component.

SLA aligned processing

Jobs tied to business SLAs (payment processing windows, end of day reconciliation, business hour reporting) are inherently weekday only because the underlying SLA is.

Holidays Are Not Handled by Cron

Cron has no awareness of public holidays. A job scheduled with 1-5 will run on Christmas Day and New Year’s Day if they fall on a weekday. If that is a problem, the solution is at the application layer:

#!/bin/bash
# Check holiday list before executing
HOLIDAY_FILE="/etc/holidays.txt"
TODAY=$(date +%Y-%m-%d)

if grep -q "$TODAY" "$HOLIDAY_FILE"; then
  echo "Skipping: $TODAY is a holiday"
  exit 0
fi

# Run the actual job
/opt/jobs/business-report

Maintain the holiday file as part of your infrastructure configuration. Some teams generate it annually from a calendar API (like the Google Calendar API or a country specific public holiday API) and deploy it alongside their crontabs.

Common Weekday Patterns

The 0 0 * * 1-5 base is almost always adjusted. These are the patterns that actually appear in production crontabs:

Daily job at a specific business time:

0 9 * * 1-5    # 9 AM weekdays, morning job before standup
0 6 * * 1-5    # 6 AM weekdays, prep data before business hours start
0 18 * * 1-5   # 6 PM weekdays, end-of-day processing

Interval within business hours:

*/15 9-17 * * 1-5   # every 15 min, 9 AM to 5 PM, weekdays
*/30 8-18 * * 1-5   # every 30 min during extended business hours
0 * 9-17 * * 1-5    # top of every hour during business hours (note: this is a 6-field expression for some implementations)

Multiple fixed times on weekdays:

0 9,12,17 * * 1-5   # 9 AM, noon, and 5 PM weekdays
0 8,16 * * 1-5      # twice daily at shift boundaries

Monday only or Friday only:

0 0 * * 1   # midnight Monday, weekly kickoff job
0 23 * * 5  # 11 PM Friday, end-of-week cleanup before weekend

Interaction Between day of month and day of week

An important cron edge case: if both the day of month field and the day of week field are explicitly set (neither is *), cron runs the job on the union of both constraints, not the intersection.

0 0 15 * 1-5   # runs on the 15th of any month AND on every weekday

This does not mean “weekdays that fall on the 15th.” It means “every weekday plus the 15th of each month.” If you want to restrict execution to a specific combination, you need script level logic, not a more complex cron expression.

With 0 0 * * 1-5, the day of month is *, so this edge case does not apply.

Verifying the Schedule

from croniter import croniter
from datetime import datetime

cron = croniter("0 0 * * 1-5", datetime.now())
for _ in range(7):
    print(cron.get_next(datetime))

Run through 7 iterations and you will see the schedule skips Saturday and Sunday. Use the cron builder on this page to see the next 10 run times interactively.