애플 공식 문서는 웹훅 전달 상태를 Success, Pending, Failed로 구분합니다. 공식 웹훅 관리 안내에 따라 설정하되, Webhook은 알림과 작업 시작에 사용하고 최종 판단은 서버 기록과 API 또는 화면으로 확인해야 합니다. 원격 맥이 빌드와 업로드를 담당하고, 서버가 이벤트 ID·버전·빌드 번호를 연결하는 구조가 가장 안전합니다.
이 글은 다음 사용자에게 맞습니다.
- 업로드 뒤 처리 중, 실패, 완료 알림을 자동으로 받고 싶은 독립 개발자
- 원격 맥의 빌드·업로드·콜백·재시도를 하나의 흐름으로 관리하는 운영자
- 여러 사람이 같은 출시 상태를 확인해야 하는 소규모 팀
먼저 정할 것: 어떤 상태를 자동화할까
App Store Connect Webhooks를 연결하기 전에 “무엇을 알릴지”와 “무엇을 자동 실행할지”를 나눠야 합니다. 업로드가 끝났다는 사실과 TestFlight에서 실제로 테스트할 수 있다는 사실은 같지 않습니다.
애플의 이벤트 설명에 맞춰 다음처럼 분리하면 오판을 줄일 수 있습니다.
| 상태 영역 | 확인하려는 결과 | 권장 동작 |
|---|---|---|
| 빌드 업로드 상태 | 바이너리가 애플 쪽으로 전달되었는지 | 서버에 기록하고 운영자에게 알림 |
| 베타 빌드 상태 | TestFlight에서 테스트 가능한 상태인지 | API 또는 화면으로 재확인한 뒤 테스터 안내 |
| 앱 버전 상태 | 심사 제출, 대기, 출시와 관련된 현재 단계 | 자동 변경보다 사람의 확인을 우선 |
| TestFlight 피드백 | 테스터가 남긴 오류와 의견 | 알림과 이슈 등록으로 연결 |
BUILD_UPLOAD_STATE_UPDATED 같은 이벤트는 흐름을 시작하는 신호입니다. 그러나 이벤트 하나만 보고 재업로드, 빌드 삭제, 출시 단계 변경을 실행하면 안 됩니다. 이벤트 ID, 앱 식별자, 버전 번호, 빌드 번호, 수신 시각을 함께 저장하고 같은 이벤트가 다시 들어와도 업무 동작은 한 번만 실행해야 합니다.
주의: “전송 성공”은 Transporter 또는 업로드 단계의 결과일 수 있습니다. 애플의 처리 완료와 TestFlight 사용 가능 여부는 별도로 확인해야 합니다. 빌드 상태의 의미는 [공식 빌드 업로드 상태 문서](https://developer.apple.com/help/app-store-connect/reference/app-uploads/build-upload-statuses?utm_source=openai)에서 확인합니다.
첫 단계: App Store Connect Webhooks를 설정하기
계정과 앱 범위를 먼저 확인합니다
App Store Connect의 Users and Access, Integrations, Webhooks 메뉴에서 사용할 팀과 앱 범위를 확인합니다. 계정 전체의 모든 앱을 자동으로 듣는다고 가정하지 말고, 설정 화면에서 선택한 앱 범위를 기록해 두어야 합니다.
여러 앱을 운영한다면 앱마다 웹훅을 따로 만들지, 하나의 수신 서버에서 앱 식별자로 분기할지 결정합니다. 이 선택은 이벤트 수신 방식보다 운영 권한과 장애 격리에 더 큰 영향을 줍니다.
수신 주소와 비밀값을 분리합니다
Payload URL은 외부에서 접근할 수 있어야 합니다. 수신 서버는 요청을 받은 즉시 원본 본문과 헤더를 보관하고 빠르게 응답해야 합니다. 긴 처리나 API 조회를 요청 수신 과정에 넣으면 네트워크 지연이 전달 실패로 이어질 수 있습니다.
설정에는 다음 값을 사용합니다.
- Payload URL:
https://<your-domain>/<webhook-path> - Secret:
<WEBHOOK_SECRET> - 앱 식별자:
<APP_ID> - 버전 번호:
<VERSION> - 빌드 번호:
<BUILD_NUMBER>
이벤트 선택은 운영 목적에 맞춥니다
처음부터 모든 이벤트를 받을 필요는 없습니다. 독립 개발자는 빌드 업로드와 베타 빌드 상태부터 시작하고, 팀 운영에서 앱 버전 상태와 TestFlight 피드백이 필요할 때 확장하는 편이 낫습니다.
공식 이벤트 유형 문서에 없는 유형을 추정해 자동화하지 마십시오. 애플이 공식적으로 제공하는 이벤트와 자체 시스템에서 추론한 상태를 구분해야 합니다.
두 번째 단계: 콜백을 받고 중복을 막기
수신 서버의 처리 순서는 다음과 같이 고정합니다.
- 원본 요청 본문과 수신 시각을 먼저 저장합니다.
- 요청의 출처와 서명 또는 비밀값 검증을 수행합니다.
- 이벤트 ID가 이미 처리되었는지 조회합니다.
- 이벤트 유형을 앱 식별자, 버전 번호, 빌드 번호와 연결합니다.
- 업무 큐에 알림이나 후속 확인 작업을 등록합니다.
- 처리 결과와 검증 실패 이유를 별도로 기록합니다.
| 검증 항목 | 통과할 때 | 실패할 때 |
|---|---|---|
| 이벤트 ID | 새 업무 기록 생성 | 기존 결과만 반환 |
| 앱 식별자 | 대상 앱과 연결 | 수동 확인 대기 |
| 버전·빌드 번호 | 원격 맥 작업과 연결 | 업로드 기록과 대조 |
| 이벤트 상태 | 알림 또는 확인 작업 실행 | 자동 배포 중단 |
| 원본 요청 | 감사 로그에 보관 | 접근 로그와 함께 격리 |
세 번째 단계: 원격 맥의 업로드를 상태 흐름에 연결하기
원격 맥에서 수행하는 작업을 하나의 성공으로 묶지 마십시오. 다음 단계는 서로 다른 실패 원인을 가집니다.
Archive 시작 → Export 완료 → 바이너리 업로드 → 애플 처리 중 → 처리 완료 또는 실패 → TestFlight 확인 가능
따라서 내부 상태도 이 흐름에 맞춰 나누는 것이 좋습니다.
started: 아카이브 작업이 시작됨uploaded: 바이너리 전송이 끝남processing: 애플 처리를 기다림processed: 빌드 상태를 다시 확인함failed: 업로드나 처리 실패manual_review: 자동 연결 또는 상태 확인이 불가능함
App Store Connect Webhooks로 빌드 업로드 완료 알림을 받는 방법을 찾는 경우에도 같은 원칙을 적용해야 합니다. 웹훅 수신은 시작 신호이고, 실제 완료 판정은 연결된 빌드 상태 조회가 담당합니다.
네 번째 단계: 실패한 전달과 중복 알림을 복구하기
웹훅 전달이 Pending 또는 Failed가 되면 먼저 수신 서버의 네트워크와 응답 기록을 확인합니다. 일시적인 네트워크 오류나 서버 오류는 재시도 대상이 될 수 있지만, 잘못된 서명, 누락된 앱 연결, 유효하지 않은 바이너리 같은 업무 오류는 같은 요청을 반복해도 해결되지 않습니다.
애플은 웹훅 관리 화면에서 최근 전달 기록과 이벤트 상세 내용을 확인하고, 일부 전달을 다시 보낼 수 있도록 안내합니다. 공식 관리 문서의 재전송 기능을 사용하더라도 서버의 멱등 처리는 그대로 유지해야 합니다.
복구 순서는 다음과 같습니다.
- 전달 상세에서 이벤트 ID와 실패 원인을 확인합니다.
- 수신 서버가 원본 요청을 저장했는지 확인합니다.
- 네트워크 또는 임시 서버 오류인지 업무 오류인지 분류합니다.
- 복구 가능한 오류만 전달 재시도를 사용합니다.
- 이벤트를 다시 받아도 기존 업무 동작이 중복되지 않는지 확인합니다.
- 최종 빌드 상태는 API나 App Store Connect 화면으로 확인합니다.
경험상 가장 위험한 자동화는 “콜백을 받으면 다시 업로드한다”는 규칙입니다. 업로드는 이미 끝났지만 처리만 지연된 경우 중복 빌드와 혼란스러운 출시 기록을 만들 수 있으므로, 재업로드는 사람이 실패 원인을 확인한 뒤 결정해야 합니다.
다섯 번째 단계: 첫 실제 출시로 검증하기
처음부터 운영 앱 전체에 적용하지 말고, 한 번의 탈감작된 테스트 빌드로 아래 흐름을 검증합니다.
- 원격 맥의 아카이브와 내보내기 로그가 남는지 확인합니다.
- 업로드 결과와 이벤트 ID를 같은 작업 기록에 연결합니다.
- 앱 식별자, 버전 번호, 빌드 번호가 서로 일치하는지 확인합니다.
- 처리 중 상태가 즉시 완료로 바뀌지 않는지 확인합니다.
- 동일 이벤트 재전송이 업무 동작을 한 번만 만드는지 확인합니다.
- 전달 실패 뒤 재시도와 수동 확인이 가능한지 확인합니다.
- 로그에서 Secret, JWT, API 키와 전체 Payload가 노출되지 않는지 점검합니다.
- 서버 기록과 App Store Connect 화면의 최종 상태가 일치하는지 대조합니다.
장기 운영: API와 원격 맥의 역할을 나누기
App Store Connect Webhooks는 API와 함께 사용하는 편이 좋습니다. 웹훅만 사용하면 전달 실패나 순서 뒤바뀜을 보정하기 어렵고, API만 주기적으로 조회하면 불필요한 요청과 지연이 생깁니다.
| 구성 | 장점 | 한계 | 적합한 경우 |
|---|---|---|---|
| 웹훅만 사용 | 이벤트를 빠르게 감지 | 누락·중복·최종 상태 보정이 약함 | 단순 알림 |
| API만 사용 | 현재 상태를 직접 확인 | 계속 조회하는 운영 부담 | 보정 조회 |
| 웹훅과 API 조합 | 이벤트 감지와 최종 확인을 분리 | 서버와 기록 설계가 필요함 | 지속 출시와 팀 운영 |
| 원격 맥에서 화면을 계속 확인 | 초기 구성이 쉬움 | 세션 종료, 권한, 화면 상태에 취약함 | 임시 수동 작업 |
상시 빌드와 업로드를 맡길 별도 환경이 없다면 MACGPU의 원격 맥 환경을 검토할 수 있습니다. 다만 이미 안정적인 자체 빌드 머신이 있고 물리 장비 접근이나 장기 고정 부하가 필요하다면 직접 구매하거나 기존 인프라를 유지하는 편이 더 적합할 수 있습니다.
마무리: 상태 감시는 서버에, 실행은 원격 맥에
이 구성에서 가장 중요한 경계는 간단합니다. 원격 맥은 아카이브와 업로드를 실행하고, Webhook은 변화를 알리며, 서버는 이벤트를 저장하고, API 또는 App Store Connect 화면은 최종 상태를 확인합니다.
로컬 맥만으로 운영하면 장비가 꺼졌을 때 업로드가 멈추고, 화면 폴링은 세션 단절과 오판에 취약하며, 별도 빌드 서버를 직접 관리하면 권한·디스크·업데이트·복구 작업이 계속 발생합니다. 이런 부담 때문에 상시 실행되는 macOS 환경이 필요하지만 장비를 바로 구매하고 싶지 않다면, MACGPU의 맥 대여 구성을 확인해 볼 수 있습니다. 단기 출시 검증이나 지속적인 원격 맥 업로드처럼 사용 기간이 분명한 경우에 특히 현실적인 선택입니다.