infra
Platform

모듈 맵

[Linux] Cron과 systemd timer 자동화

0 / 20 완료

펼치기

Linux-master · 17 / 20

[Linux] Cron과 systemd timer 자동화

crontab과 systemd timer로 반복 작업을 자동화하고, 실행 로그를 확인하여 자동화 누락을 방지합니다

🚨INCIDENT ALERT
HIGH

3개월 전에 설정해둔 DB 백업 cron이 어느 시점부터 조용히 실패하고 있었습니다. 장애가 나서 복구하려는데 백업 파일이 없습니다. 로그를 보니 cron은 실행을 시도했지만 스크립트가 에러를 냈고, 아무도 몰랐습니다. 자동화는 실행만 되면 끝이 아닙니다 — 실패했을 때 알 수 있어야 하고, 로그가 남아야 하고, 다음에 재시도할 수 있어야 진짜 자동화입니다.

Cron과 systemd timer 자동화

백업 스크립트를 매일 돌리고, 인증서를 자동 갱신하고, 오래된 로그를 정리하는 것 — 전부 사람이 기억해서 하면 언젠가 빠뜨립니다. 자동화의 첫걸음은 작업 스케줄러를 제대로 쓰는 것입니다.


이번 챕터에서 배울 것

crontab은 간단하고 빠릅니다. systemd timer는 로그와 실패 감지가 필요할 때 씁니다. 둘 다 알아두면 상황에 맞게 선택할 수 있습니다.

  • 1crontab 문법과 자주 쓰는 패턴
  • 2cron 환경 트러블슈팅 — PATH, 환경변수, 로그 확인
  • 3systemd timer — .timer + .service 유닛 구성
  • 4OnCalendar, OnBootSec, Persistent 옵션
  • 5실무 자동화 예제 — 백업, 인증서 갱신, 정리 작업
실습 환경 준비

💡개념

crontab 문법 — 핵심 패턴

분  시  일  월  요일  명령
*   *   *   *   *    /path/to/command

특수 문자:
*   — 모든 값
,   — 여러 값 (1,3,5)
-   — 범위 (1-5)
/   — 간격 (*/10 = 10마다)
로컬 터미널
# crontab 편집
crontab -e

# 자주 쓰는 패턴
0 2 * * *          # 매일 새벽 2시
0 2 * * 0          # 매주 일요일 새벽 2시
0 2 1 * *          # 매월 1일 새벽 2시
*/10 * * * *       # 10분마다
0 9-18 * * 1-5     # 월~금, 9~18시 매 정시
0 2 * * * /usr/local/bin/daily-backup.sh >> /var/log/backup.log 2>&1

# 특수 문자열 (단축어)
@reboot            # 부팅 시 1회
@daily             # = 0 0 * * *
@weekly            # = 0 0 * * 0
@monthly           # = 0 0 1 * *
@reboot /usr/local/bin/startup-init.sh
로컬 터미널
# cron 실행 로그 확인
grep CRON /var/log/syslog | tail -20
# 또는
journalctl -u cron --since today

💡개념

systemd timer — .timer + .service 구성

systemd timer는 두 파일로 구성됩니다:

  1. .service — 실제 실행할 명령
  2. .timer — 스케줄 정의
로컬 터미널
# /etc/systemd/system/daily-backup.service
[Unit]
Description=Daily Backup Job
After=network.target

[Service]
Type=oneshot
ExecStart=/usr/local/bin/daily-backup.sh
User=root
StandardOutput=journal
StandardError=journal
로컬 터미널
# /etc/systemd/system/daily-backup.timer
[Unit]
Description=Run daily-backup.service every day at 02:00

[Timer]
OnCalendar=*-*-* 02:00:00    # 매일 02:00
Persistent=true               # 실행 누락 시 부팅 후 즉시 실행
AccuracySec=1min              # 1분 오차 허용 (기본 1분)

[Install]
WantedBy=timers.target
서버 터미널
# 활성화 및 시작
sudo systemctl daemon-reload
sudo systemctl enable --now daily-backup.timer

# 상태 확인
systemctl status daily-backup.timer
systemctl list-timers                   # 전체 timer 목록과 다음 실행 시각

# 로그 확인
journalctl -u daily-backup.service      # 실행 이력
journalctl -u daily-backup.service -n 20 --no-pager

💡개념

OnCalendar 시간 표현식

로컬 터미널
# 자주 쓰는 OnCalendar 표현
OnCalendar=daily                 # 매일 00:00:00
OnCalendar=weekly                # 매주 월요일 00:00:00
OnCalendar=monthly               # 매월 1일 00:00:00
OnCalendar=hourly                # 매 정시

OnCalendar=*-*-* 02:00:00       # 매일 02:00
OnCalendar=Mon *-*-* 03:00:00   # 매주 월요일 03:00
OnCalendar=*-*-01 00:00:00      # 매월 1일 자정
OnCalendar=Sat,Sun 10:00:00     # 주말 10시

# 표현식 검증 (실행 전 확인 필수)
systemd-analyze calendar '*-*-* 02:00:00'
#   Original form: *-*-* 02:00:00
#  Normalized form: *-*-* 02:00:00
#     Next elapse: Wed 2026-04-15 02:00:00 KST
#        (in UTC): Tue 2026-04-14 17:00:00 UTC
#        From now: 11h left

# 특수 옵션
OnBootSec=5min                   # 부팅 후 5분 뒤 1회 실행
OnUnitActiveSec=1h               # 마지막 실행 후 1시간마다
Persistent=true                  # 시스템이 꺼져있어 놓친 실행을 부팅 후 즉시 실행

로컬 터미널
# 수동 실행: OK
$ /usr/local/bin/daily-backup.sh
백업 완료

# cron 실행 후 로그 확인
$ grep CRON /var/log/syslog
Apr 14 02:00:01 server CRON[12345]: (root) CMD (/usr/local/bin/daily-backup.sh)
# 하지만 백업 파일이 없음...

원인 1: PATH 차이

로컬 터미널
# 스크립트 상단에 PATH 명시
#!/bin/bash
PATH=/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin

# 또는 crontab 상단에 추가
$ crontab -e
PATH=/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin
0 2 * * * /usr/local/bin/daily-backup.sh

원인 2: 환경변수 누락 (AWS CLI, DB 패스워드 등)

로컬 터미널
# 스크립트에서 직접 환경변수 파일 로드
#!/bin/bash
source /etc/environment
source /home/ubuntu/.env.backup
# 이제 $AWS_ACCESS_KEY_ID 등 사용 가능

원인 3: 출력 리다이렉션 없어서 에러를 못 봄

로컬 터미널
# 표준출력 + 에러 모두 로그로
0 2 * * * /usr/local/bin/daily-backup.sh >> /var/log/backup.log 2>&1
💼
실무 맥락
현업 패턴

실무 자동화 패턴

패턴 1: Let's Encrypt 자동 갱신 (certbot timer 확인)

서버 터미널
# Ubuntu에서 certbot 설치 시 자동 생성됨
systemctl status certbot.timer
systemctl list-timers | grep certbot

# 없으면 직접 생성
# /etc/systemd/system/certbot-renew.service
[Unit]
Description=Certbot Renewal

[Service]
Type=oneshot
ExecStart=/usr/bin/certbot renew --quiet --deploy-hook "systemctl reload nginx"
로컬 터미널
# /etc/systemd/system/certbot-renew.timer
[Unit]
Description=Certbot Renewal Timer

[Timer]
OnCalendar=*-*-* 03:00:00
OnCalendar=*-*-* 15:00:00   # 하루 2회 (Let's Encrypt 권장)
Persistent=true
RandomizedDelaySec=1h        # 서버 몰림 방지

[Install]
WantedBy=timers.target

패턴 2: 오래된 파일 정리 (임시파일, 로그)

로컬 터미널
# /etc/systemd/system/cleanup-tmp.service
[Service]
Type=oneshot
ExecStart=/bin/bash -c 'find /tmp -mtime +7 -delete && find /var/log/app -name "*.log.*" -mtime +30 -delete'

패턴 3: DB 덤프 자동화

로컬 터미널
# /etc/systemd/system/mysql-backup.service
[Service]
Type=oneshot
User=backup
EnvironmentFile=/etc/backup.env   # MYSQL_PASS 등 환경변수
ExecStart=/usr/local/bin/mysql-backup.sh

# timer: 매일 새벽 1시
OnCalendar=*-*-* 01:00:00

언제 crontab, 언제 systemd timer?

상황추천
간단한 1줄 명령, 빠르게 추가crontab
실행 실패 감지가 중요systemd timer
journalctl로 이력 조회 필요systemd timer
부팅 후 누락 실행 보장 필요systemd timer (Persistent=true)
기존 systemd 서비스와 연동systemd timer

지식 확인

퀴즈 — 4문제

Q1

crontab에서 '0 2 * * 1-5'의 의미는?

Q2

systemd timer가 crontab보다 유리한 상황은?

Q3

crontab 작업이 수동 실행은 되는데 cron으로는 안 된다. 가장 흔한 원인은?

Q4

systemd timer의 OnCalendar=weekly 는 언제 실행되는가?

0 / 4 답변

이것도 배워보세요

linux-master중급 · 75
[Linux] Ansible 입문 — 인프라 자동화
Linux-master 트랙 계속