Run Weekly Maintenance at 2 AM Sunday | CronBase
0 2 * * 0 Every Sunday morning at two o'clock.
This cron expression schedules a task to run every Sunday at exactly 2:00 AM. It is widely utilized by system administrators for executing heavy weekly maintenance chores, such as database optimization, full system backups, log archiving, and software updates, during a period when user traffic and system load are typically at their lowest.
- Minute
- 0
- Hour
- 2
- Day of Month
- *
- Month
- *
- Day of Week
- 0
Next 5 Runs
- in 5h 34m
- in 7d 5h
- in 14d 5h
- in 21d 5h
- in 28d 5h
* Tools
Code & Implementations
#!/bin/bash
# System backup script scheduled weekly on Sundays at 2:00 AM via crontab
set -euo pipefail
BACKUP_DIR="/var/backups/weekly"
LOG_FILE="/var/log/weekly_backup.log"
echo "[$(date -u)] Starting weekly system backup..." >> "$LOG_FILE"
# Ensure backup directory exists
mkdir -p "$BACKUP_DIR"
# Perform backup with error handling
if tar -czf "$BACKUP_DIR/backup-$(date +%F).tar.gz" /var/www /etc 2>> "$LOG_FILE"; then
echo "[$(date -u)] Backup completed successfully." >> "$LOG_FILE"
else
echo "[$(date -u)] ERROR: Backup failed!" >> "$LOG_FILE" >&2
exit 1
fi › Setup notes
Add this script to your system and configure it in the user or system-wide crontab using crontab -e with the standard expression.
const cron = require('node-cron');
const { exec } = require('child_process');
// Schedule task to run every Sunday at 2:00 AM
cron.schedule('0 2 * * 0', () => {
console.log('[INFO] Starting weekly database maintenance at:', new Date().toISOString());
exec('/usr/local/bin/db-optimize.sh', (error, stdout, stderr) => {
if (error) {
console.error(`[ERROR] Maintenance failed: ${error.message}`);
return;
}
if (stderr) {
console.warn(`[WARN] Maintenance stderr output: ${stderr}`);
}
console.log(`[SUCCESS] Maintenance output: ${stdout}`);
});
}, {
scheduled: true,
timezone: "UTC"
}); › Setup notes
Install the node-cron package using npm. Run this script in a PM2 or Docker container to keep the Node process running continuously.
import logging
from datetime import datetime
from apscheduler.schedulers.blocking import BlockingScheduler
from apscheduler.triggers.cron import CronTrigger
logging.basicConfig(level=logging.INFO, format='%(asctime)s [%(levelname)s] %(message)s')
def run_weekly_cleanup():
logging.info("Starting weekly data pipeline cleanup process...")
try:
# Simulate cleanup logic
logging.info("Weekly cleanup completed successfully.")
except Exception as e:
logging.error(f"Cleanup failed: {str(e)}")
if __name__ == "__main__":
scheduler = BlockingScheduler()
# Schedule weekly on Sunday at 2:00 AM UTC
trigger = CronTrigger(day_of_week='sun', hour=2, minute=0, timezone='UTC')
scheduler.add_job(run_weekly_cleanup, trigger=trigger)
logging.info("Scheduler started. Waiting for Sunday at 2:00 AM UTC...")
try:
scheduler.start()
except (KeyboardInterrupt, SystemExit):
logging.info("Scheduler stopped manually.") › Setup notes
Install the APScheduler package. Run this script inside a persistent background process or service to ensure the cron trigger fires correctly.
package main
import (
"log"
"os"
"os/signal"
"syscall"
"time"
"github.com/robfig/cron/v3"
)
func main() {
// Use UTC to avoid DST transition issues
nyc, err := time.LoadLocation("UTC")
if err != nil {
log.Fatalf("Failed to load timezone: %v", err)
}
c := cron.New(cron.WithLocation(nyc))
// Schedule for Sunday at 2:00 AM
_, err = c.AddFunc("0 2 * * 0", func() {
log.Println("[INFO] Executing scheduled weekly report generation...")
err := generateWeeklyReports()
if err != nil {
log.Printf("[ERROR] Report generation failed: %v", err)
} else {
log.Println("[SUCCESS] Reports generated successfully.")
}
})
if err != nil {
log.Fatalf("Failed to schedule cron job: %v", err)
}
c.Start()
log.Println("Cron scheduler active. Running weekly at Sunday 2:00 AM UTC.")
sigChan := make(chan os.Signal, 1)
signal.Notify(sigChan, syscall.SIGINT, syscall.SIGTERM)
<-sigChan
c.Stop()
}
func generateWeeklyReports() error {
return nil
} › Setup notes
Initialize a Go module, import the github.com/robfig/cron/v3 package, and run the main executable as a daemon or systemd service.
package com.example.scheduler;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.scheduling.annotation.Scheduled;
import org.springframework.stereotype.Component;
@Component
public class WeeklyMaintenanceScheduler {
private static final Logger logger = LoggerFactory.getLogger(WeeklyMaintenanceScheduler.class);
// Runs every Sunday at 2:00 AM (Spring Cron: seconds, minutes, hours, day of month, month, day of week)
@Scheduled(cron = "0 0 2 * * SUN", zone = "UTC")
public void executeWeeklyTasks() {
logger.info("Initiating scheduled weekly maintenance routine...");
try {
purgeExpiredSessions();
logger.info("Weekly maintenance tasks completed successfully.");
} catch (Exception e) {
logger.error("Error occurred during weekly maintenance: ", e);
}
}
private void purgeExpiredSessions() {
// Business logic
}
} › Setup notes
Enable scheduling in your Spring Boot application using the @EnableScheduling annotation, then place this component in your scanned package paths.
apiVersion: batch/v1
kind: CronJob
metadata:
name: weekly-database-vacuum
namespace: database
spec:
# Runs at 2:00 AM every Sunday
schedule: "0 2 * * 0"
concurrencyPolicy: Forbid
successfulJobsHistoryLimit: 3
failedJobsHistoryLimit: 5
jobTemplate:
spec:
template:
spec:
containers:
- name: postgres-vacuum
image: postgres:15-alpine
command:
- /bin/sh
- -c
- "vacuumdb -U postgres -h db-service -a -z"
env:
- name: PGPASSWORD
valueFrom:
secretKeyRef:
name: db-credentials
key: password
restartPolicy: OnFailure › Setup notes
Apply this manifest using kubectl apply -f cronjob.yaml to deploy a managed weekly task that runs on your Kubernetes cluster.
Last verified:
Monitor this schedule in production
Get alerted the moment this cron job fails, is late, or doesn't run. BetterStack tracks execution, duration, and output — no infrastructure required.
Platform Equivalents
AWS EventBridge
Standard cron expressions often need conversion for AWS EventBridge schedules.
cron(0 2 ? * 0 *) Systemd Timer
OnCalendarSun *-*-* 02:00:00
[Unit]
Description=Timer for cron expression: 0 2 * * 0
[Timer]
OnCalendar=Sun *-*-* 02:00:00
Persistent=true
[Install]
WantedBy=timers.target
Last verified:
Frequently Asked Questions
How does Daylight Saving Time affect a job scheduled for 2:00 AM on Sunday?
In regions observing Daylight Saving Time, the local clock jumps directly from 1:59 AM to 3:00 AM in the spring, which will cause your job to be skipped. In the autumn, the hour repeats, potentially triggering the job twice. To prevent this, always set your system timezone and cron daemon to UTC.
What is the best way to handle long-running tasks that exceed one week?
For tasks that might run longer than seven days, implement locking mechanisms (such as flock in Bash, redis-lock, or Kubernetes concurrencyPolicy: Forbid). This prevents a new instance of the job from starting while the previous week's run is still actively executing.
Can I use '7' instead of '0' for Sunday in this cron expression?
Yes, in standard and POSIX-compliant cron implementations, both 0 and 7 represent Sunday. However, to ensure maximum portability across different systems, platforms, and third-party libraries, using 0 is the widely accepted industry standard.
How can I test or dry-run this Sunday morning schedule immediately?
You can temporarily adjust the cron schedule to run every few minutes for testing, or execute the underlying script/command directly in your terminal. For testing the scheduler logic itself without waiting, use tools like `cron-parser` in Node.js or Python's mock library to simulate time-shifts.
How do I prevent CPU spikes if multiple weekly jobs are scheduled at 2:00 AM?
To avoid resource contention and CPU spikes, stagger your jobs by offsetting the minutes field (e.g., 0 2, 15 2, 30 2) or introduce a randomized sleep delay at the beginning of your script execution (e.g., `sleep $((RANDOM % 300))`).
* Explore
Related expressions you might need
Last verified: