Python으로 자동화 프로그램을 만들고 macOS의 launchd로 매일 아침 실행되게 등록하면, 시간이 지나면서 이런 생각이 듭니다.

이거 진짜 오늘도 잘 실행된 걸까?

자동화는 사람이 직접 실행하지 않기 때문에 확인 루틴이 필요합니다. 이번 글에서는 launchd로 등록한 프로그램이 잘 돌고 있는지 확인하는 기본 방법을 정리합니다.


launchd가 무엇일까?

launchd는 macOS에 기본으로 들어 있는 자동 실행 관리자입니다.

정해진 시간에 프로그램을 실행하거나, 특정 조건이 되었을 때 작업을 실행할 수 있게 도와줍니다. 쉽게 말하면 macOS 안에 있는 일정 담당자에 가깝습니다.

용어읽는 법의미
launchd런치디macOS 자동 실행 관리자
launchctl런치컨트롤launchd를 다루는 터미널 명령어
load로드자동 실행 설정 등록
unload언로드자동 실행 설정 해제
.plist피리스트launchd 설정 파일

cron처럼 오래전부터 쓰인 스케줄러도 있지만, macOS에서는 launchd를 사용하는 경우가 많습니다.

잠자기 상태였다면 깨어난 뒤 작업이 실행될 수 있습니다. 다만 Mac이 완전히 꺼져 있었거나 설정이 맞지 않으면 기대한 시간에 실행되지 않을 수 있으므로, 로그 확인이 중요합니다.


확인해야 할 것 3가지

자동 실행이 잘 되는지 볼 때는 세 가지를 확인하면 됩니다.

확인 항목확인 방법
오늘 실행됐는지로그 파일 확인
에러가 있었는지에러 로그 확인
등록 상태가 살아 있는지launchctl list 확인

이 세 가지만 보면 대부분의 문제를 빠르게 좁힐 수 있습니다.


로그 파일로 실행 여부 확인하기

자동화 프로그램을 만들 때는 실행 기록을 파일로 남겨두는 것이 좋습니다. 예를 들어 프로젝트 폴더에 log.txt를 남기도록 만들었다면 아래처럼 확인할 수 있습니다.

cd ~/프로젝트/github-curator
cat log.txt

결과를 볼 때는 날짜를 먼저 확인합니다.

로그 상태의미
오늘 날짜 기록이 있음오늘 정상 실행됐을 가능성이 높음
어제 날짜에서 멈춤오늘 실행되지 않았을 가능성이 있음
기록이 전혀 없음로그 경로나 실행 자체를 다시 확인해야 함

전체 로그가 길다면 마지막 부분만 보면 됩니다.

tail -20 log.txt

tail은 파일의 마지막 부분만 보여주는 명령어입니다. -20은 마지막 20줄만 보겠다는 뜻입니다.


에러 로그 확인하기

실행 기록과 별도로 에러 로그도 확인해야 합니다.

cat error.txt

에러 파일이 비어 있다면 보통 문제 없이 실행된 것입니다. 반대로 내용이 있다면 그 안에 실패 원인이 적혀 있을 수 있습니다.

예를 들어 아래 같은 문제가 나올 수 있습니다.

ModuleNotFoundError
Permission denied
FileNotFoundError

이런 메시지가 보이면 자동 실행 자체는 되었지만, 프로그램 내부에서 실패했을 가능성이 큽니다.


launchctl list로 등록 상태 확인하기

launchd에 등록이 살아 있는지도 확인해야 합니다.

launchctl list | grep github-curator

여기서 github-curator는 예시 프로젝트 이름입니다. 실제로는 본인이 .plist에 적어둔 등록 이름 일부를 넣으면 됩니다.

결과가 아래처럼 나온다고 해보겠습니다.

-    0    com.example.github-curator

각 위치의 의미는 다음과 같습니다.

위치예시 값의미
첫 번째-지금 실행 중인 프로세스 ID가 없음
두 번째0마지막 실행이 정상 종료됨
세 번째com.example.github-curator등록된 작업 이름

첫 번째 값이 -인 것은 평소에는 이상하지 않습니다. 매일 아침 잠깐 실행되고 끝나는 작업이라면, 확인하는 순간에는 실행 중이 아닐 수 있습니다.

중요하게 볼 값은 두 번째 숫자입니다. 0이면 마지막 실행이 정상 종료된 것입니다. 다른 숫자가 보이면 실패 상태일 수 있습니다.

아무 결과도 나오지 않으면 등록 이름이 다르거나, 자동 실행 등록이 빠졌을 수 있습니다.


등록 이름을 모를 때 확인하는 방법

등록 이름이 기억나지 않으면 전체 목록을 넓게 검색해볼 수 있습니다.

launchctl list | grep 본인아이디

또는 .plist 파일 안의 Label 값을 확인합니다.

cat ~/Library/LaunchAgents/com.example.github-curator.plist

파일 안에 보통 아래처럼 Label 값이 있습니다.

<key>Label</key>
<string>com.example.github-curator</string>

launchctl startlaunchctl list에서 사용하는 이름은 이 Label 값입니다.


지금 당장 테스트로 실행하기

정해진 시간을 기다리지 않고 바로 실행해보고 싶다면 launchctl start를 사용할 수 있습니다.

launchctl start com.example.github-curator

실행한 뒤에는 로그를 다시 확인합니다.

tail -20 log.txt
cat error.txt

이 순서로 보면 됩니다.

1. launchctl start로 직접 실행
2. log.txt에 기록이 남았는지 확인
3. error.txt에 에러가 생겼는지 확인

테스트 실행이 성공하면 설정이 어느 정도 맞다는 뜻입니다. 다만 정해진 시간 실행까지 확인하려면 다음 예약 시간 이후 로그를 다시 봐야 합니다.


잠깐 끄고 다시 켜기

며칠 동안 자동 실행을 멈추고 싶다면 unload를 사용할 수 있습니다.

launchctl unload ~/Library/LaunchAgents/com.example.github-curator.plist

다시 켜려면 load를 사용합니다.

launchctl load ~/Library/LaunchAgents/com.example.github-curator.plist

unload는 파일을 삭제하는 명령이 아닙니다. 등록을 잠시 내리는 것에 가깝습니다.

그래도 명령어를 실행하기 전에 .plist 파일 경로가 맞는지 꼭 확인하는 편이 좋습니다.


문제가 생겼을 때 보는 순서

자동 실행이 안 된 것처럼 보이면 아래 순서로 확인합니다.

1. log.txt에 오늘 날짜가 있는지 확인합니다.
2. error.txt에 에러 메시지가 있는지 확인합니다.
3. launchctl list에서 등록 이름이 보이는지 확인합니다.
4. launchctl start로 직접 실행해봅니다.
5. .plist 파일 경로와 Label 값을 다시 확인합니다.

이 순서로 보면 “등록이 안 된 문제”인지, “실행은 됐지만 프로그램이 실패한 문제”인지 구분하기 쉽습니다.


정리

launchd로 자동 실행을 걸어두었다면, 가끔은 진짜 실행됐는지 확인해야 합니다.

기본 확인 루틴은 아래 세 가지입니다.

tail -20 log.txt
cat error.txt
launchctl list | grep github-curator

자동화 프로그램은 만들고 끝나는 것이 아닙니다. 사람이 직접 실행하지 않는 만큼, 로그와 등록 상태를 확인하는 습관이 필요합니다.

로그에 오늘 날짜가 있고, 에러 파일이 비어 있고, launchctl list에서 등록 이름이 보인다면 기본 상태는 괜찮다고 볼 수 있습니다.