클로드 코드 자동 실행의 실제 함정
사람 없이 정해진 시각에 클로드 코드를 돌리고, 결과를 저장소나 PR로 받아보려는 분에게 맞는 글입니다. 터미널에서 한 번 잘 실행된 명령이라도 자동 실행에 넣으면 같은 조건으로 움직이지 않습니다.
저희는 macOS의 launchd로 매일 오전 10시 30분에 셸 스크립트를 실행합니다. 스크립트는 블로그별 에이전트를 병렬로 띄우며, 12편이 PR로 올라오기까지 26~36분이 걸립니다. 이 흐름도 처음부터 한 번에 안정되지 않았고, 자동화 안에는 눈에 잘 보이지 않는 함정이 있었습니다.
먼저 결론부터
- 헤드리스 실행은 아래처럼 시작하며, 사용할 도구와 세션 아이디를 함께 지정해 두면 나중에 세션을 되살릴 수 있습니다.
claude -p "지시문"
- launchd에서 실행되는 셸은 터미널과 다르므로, 스크립트 위치와 PATH, 실제 바이너리 경로를 직접 확인해야 합니다.
- macOS가 보호하는 바탕화면 폴더에 스크립트를 두면 launchd가 읽지 못하므로, 홈 아래 다른 폴더에 두고 바탕화면에는 링크만 두는 편이 안전합니다.
- Git push는 자동 실행 환경에서 다른 계정 자격증명을 쓸 수 있으므로, PR을 올릴 계정을 따로 확인해야 합니다.
- 맥 전원이 꺼진 동안 놓친 launchd 일정은 실행되지 않으므로, 그날 작업이 사라졌는지 확인할 장치가 필요합니다.
- 자동화 결과는 되돌릴 수 있는 곳에 내놓고, 깨끗하지 않은 작업 폴더와 재현되지 않는 멈춤까지 로그로 추적해야 합니다.
사람 없는 실행은 다른 환경이다
터미널의 성공만으로는 부족합니다.
직접 확인한 운영 환경에서는 같은 맥에서 같은 명령을 썼어도, 터미널 앱이 물려 준 경로와 권한, 로그인한 계정의 자격증명은 launchd가 셸 스크립트를 실행할 때 그대로 따라오지 않았으며, 이 차이가 작업 시작 자체를 막거나 마지막 push 단계만 실패하게 만들었습니다.
그래서 실행 조건을 따로 봤습니다.
헤드리스 작업의 출발점은 다음 명령입니다. 사용할 도구를 명시하고 세션 아이디를 붙여 두면, 나중에 이어서 처리할 여지도 남습니다. 다만 자동 실행의 안정성은 이 한 줄보다 스크립트를 둘 환경에서 갈립니다.
claude -p "지시문"
작업 위치와 경로
바탕화면은 편한 위치였습니다. 하지만 macOS는 바탕화면을 보호 영역으로 잡고 있었고, 바탕화면에 둔 스크립트를 launchd가 읽지 못했습니다. 스크립트는 홈 아래 다른 폴더로 옮겼으며, 바탕화면에는 링크만 남겼습니다.
PATH도 터미널에서처럼 넘어오지 않았습니다.
터미널에서는 되던 명령이 launchd에서는 없는 명령이 되었고, 터미널 앱이 설치한 래퍼를 호출한 경우에는 자동 실행 환경이 기대한 실행 파일을 찾지 못했으므로, 스크립트 안에서 PATH를 직접 지정하고 래퍼 대신 실제 바이너리 경로를 사용해야 했습니다.
다음 명령으로 후보를 먼저 확인할 수 있습니다.
which -a claude
결과가 두 줄 이상이면 앞의 경로가 잡힌다는 뜻입니다. 자동화 스크립트에는 그 경로가 어떤 실행 파일인지 분명히 적어 두는 편이 좋습니다.
계정과 전원 상태
Git 자격증명도 별도 문제였습니다. 이 맥에는 회사 계정 자격증명이 저장돼 있었고, 자동 실행이 그 계정을 사용하면서 개인 저장소 push가 거부됐습니다. 개인 계정 자격증명을 따로 붙여 해결했습니다.
전원 상태는 더 단순합니다.
launchd는 잠자기 중 놓친 일정은 맥이 깨어나면 실행합니다. 반면 전원이 꺼져 있던 동안 놓친 일정은 실행하지 않습니다. 저희는 이 차이 때문에 하루치 작업이 통째로 날아간 일을 직접 겪었습니다.
따라서 매일 실행만 믿기보다, 실행 뒤에 PR이 실제로 열렸는지 확인할 방법을 함께 두는 편이 낫습니다. 꺼져 있던 날의 공백은 다음 날 작업이 대신 메우지 않습니다.
멈춤을 처리하는 기준
안전장치는 작업을 보호하지만, 조용한 중단도 만듭니다. 저희 스크립트는 작업 폴더가 깨끗하지 않으면 해당 저장소를 건너뜁니다.
어느 날에는 에이전트가 글을 모두 쓴 뒤 커밋 직전에 죽었고 파일만 남았는데, 다음 날 배치는 그 변경 사항을 보고 시작하지 않았으며, 로그에는 한 줄만 남고 알림은 없어서 문제가 생긴 시점보다 한참 뒤에야 작업이 멈춘 이유를 확인했습니다.
이 기준은 유지했습니다. 대신 결과를 어디에 내놓을지부터 정했습니다. 에이전트는 PR만 열고, 사람은 내용을 확인한 뒤 머지합니다. 잘못된 결과도 되돌릴 수 있습니다.
재현하지 못한 정지
해결하지 못한 사례도 있습니다.
어느 날 에이전트 다섯 개가 세 시간 동안 CPU를 3초만 쓰고 멈춰 있었습니다. 화면에 막는 창은 없었고, 같은 명령을 터미널에서 실행하면 바로 응답했습니다. 다음 날에는 정상이었으며 재현하지 못했습니다.
이 사례는 원인을 단정하지 않습니다. 자동 실행이 멈췄을 때 오류 메시지만 찾으면 놓치는 상태가 있다는 기록으로 남겨 두고, 실행 시간과 CPU 사용 상태, 로그를 함께 보게 만들었습니다.
마무리
다음 작업은 작은 저장소 하나에 일정을 붙이고, 스크립트 위치와 실제 claude 경로, Git 계정을 먼저 확인하는 일입니다. 이후에는 의도적으로 작업 폴더에 변경 파일을 남겨 두고, 안전장치가 어떤 로그를 남기며 어떻게 건너뛰는지도 확인해 두면 좋습니다.
여기서 확인한 문제들은 공식 문서의 명령 사용법만으로 드러나지 않습니다. 문서는 명령이 실행되는 방식을 설명하지만, 보호 폴더의 권한, 로컬 계정 자격증명, 전원 상태, 재현되지 않은 정지처럼 각 맥의 자동 실행 환경에서 생기는 일은 실제로 돌려 봐야 드러납니다.