TECH NOTE · DESKTOP AI PET
애플 개발자 계정 없이 만든 macOS 앱은 손상됐다는 경고가 뜹니다. 애드혹 서명과 격리 속성 해제로 배포한 방법을 정리했습니다.
앱은 깨지지 않았는데 안 열린다
애플 개발자 계정 없이 만든 macOS 앱을 남에게 보내면, 받은 사람 화면에는 “손상되었기 때문에 열 수 없습니다”가 뜬다. 앱이 실제로 손상된 게 아니다. 다운로드한 파일에 붙는 격리 속성 때문이다.
이 프로젝트는 연 99달러짜리 개발자 계정 없이 데스크톱 앱을 배포하고 있다. 그래서 이 문제를 정면으로 만났고, 결국 “터미널 한 줄을 안내한다”로 정리했다. 이 글은 그 과정을 다룬다.
무엇이 막고 있나
macOS는 인터넷에서 받은 파일에 com.apple.quarantine이라는 확장 속성을 붙인다. Gatekeeper가 이걸 보고 서명과 공증 상태를 확인한다.
여기서 세 단계가 있다.
| 상태 | 사용자가 보는 것 |
|---|---|
| 개발자 서명 + 공증 완료 | 그냥 열린다 |
| 개발자 서명만 있음 | 경고 후 우클릭 열기로 통과 |
| 애드혹 서명 (개발자 계정 없음) | “손상되었기 때문에 열 수 없습니다” |
세 번째가 우리 상황이다. 문구가 “확인되지 않은 개발자”가 아니라 “손상”이라 오해를 부른다. 받은 사람은 파일이 깨졌다고 생각하고 다시 받는다. 다시 받아도 똑같다.
애드혹 서명은 무엇인가
앱에 서명이 아예 없는 건 아니다. codesign -dv --verbose=2 뒤에 앱 경로를 붙여 확인해 보면, 배포하는 앱에서 Signature=adhoc이 보인다. 애플 인증서 없이 로컬에서 붙인 서명이다. 앱 안의 파일이 바뀌지 않았다는 것은 보장하지만, 누가 만들었는지는 보장하지 않는다. Gatekeeper가 요구하는 건 후자다.
애드혹 서명을 굳이 하는 이유가 있다. 서명이 아예 없으면 arm64 macOS에서는 실행 자체가 막히는 경우가 있다. 그래서 배포 전에 애드혹으로 서명하고 다시 압축하는 단계를 거쳤다.
결국 터미널 한 줄을 안내했다
받는 쪽에서 격리 속성을 지우는 방법이 있다.
xattr -cr ~/Downloads/DesktopAIPet.app && open ~/Downloads/DesktopAIPet.app
xattr -cr이 확장 속성을 재귀적으로 지운다. 격리 표시가 사라지면 Gatekeeper가 막지 않는다.
다운로드 페이지에 이 명령을 그대로 넣고, “앱이 깨진 것이 아니라 다운로드 파일에 붙는 격리 때문”이라는 설명을 함께 적었다. 압축을 어디에 풀었느냐에 따라 경로가 달라져서, 경로가 헷갈리면 xattr -cr 까지만 치고 파일을 터미널로 끌어다 놓으면 된다는 안내도 붙였다.
안내가 여러 번 바뀌었다
한 번에 정리되지 않았다. 배포 저장소 커밋을 보면 같은 문제를 여러 번 손봤다.
- 애드혹 서명으로 다시 패키징하고 zip 체크섬을 갱신
- “처음 열 때” 도우미를 안내에 추가하고 체크섬을 다시 갱신
- 터미널
xattr방법을 문서화 - 압축을 푼 폴더 밖으로 앱을 옮길 필요가 없다는 점을 명시
- 업데이트 URL 수정으로 다시 빌드하고 체크섬을 또 갱신
우클릭 열기부터 안내했는데 애드혹 서명에서는 그 경로가 잘 통하지 않았다. 결국 터미널 명령이 가장 확실했다.
체크섬을 매번 갱신해야 한다
앱을 다시 패키징할 때마다 zip 파일의 해시가 바뀐다. 다운로드 페이지에 체크섬을 적어두면 사용자가 파일 무결성을 확인할 수 있는데, 재패키징하고 갱신을 잊으면 오히려 “파일이 변조됐다”는 신호가 된다.
위 커밋 목록에 “체크섬 갱신”이 세 번 나오는 게 그래서다. 서명하고, 압축하고, 해시 내고, 페이지에 반영하는 순서가 매번 붙는다.
무엇을 감수한 것인가
정리하면 이런 거래다.
| 선택 | 비용 | 사용자 경험 |
|---|---|---|
| 개발자 계정 + 공증 | 연 99달러, 공증 절차 | 그냥 열린다 |
| 애드혹 서명 + 안내 | 0원 | 터미널 한 줄이 필요하다 |
받는 사람에게 터미널을 열게 하는 건 분명한 마찰이다. 기술에 익숙하지 않은 사용자에게는 그 자체가 벽이다.
다만 이 앱은 아직 초기 버전이고 받는 사람 범위가 좁다. 사용자층이 넓어지면 계정을 사는 쪽이 맞다고 본다. 지금은 “무료로 만들어 무료로 나눠주는” 단계라 비용을 안 쓰는 쪽을 골랐다.
같이 나오는 질문
우클릭으로 열기는 왜 안 되나
개발자 서명은 있는데 공증만 없는 경우에는 그 방법이 통한다. 애드혹 서명은 서명자를 확인할 수 없어서 그 경로가 잘 열리지 않는다. 그래서 격리 속성을 지우는 쪽으로 갔다.
`xattr -cr`은 안전한가
그 파일에 붙은 확장 속성을 지우는 명령이라, 대상 경로를 정확히 지정하는 게 중요하다. 앱 하나를 가리키는 것과 홈 디렉터리 전체를 가리키는 것은 전혀 다른 이야기다. 안내할 때 경로를 앱까지 붙여서 적은 이유다.
공증까지 하면 무엇이 달라지나
사용자가 아무것도 하지 않아도 된다. 대신 계정 비용과 공증 절차가 붙고, 빌드할 때마다 애플 서버에 올려 검사를 받는 단계가 추가된다.
다음에 볼 건 이 프로젝트를 만드는 동안 어떤 AI 도구를 언제 썼는지 추적한 이야기다. 기억이 아니라 커밋 기록으로 확인하면 다른 그림이 나온다.

핑백: 서명 없이 macOS 앱 배포하기 - Bluecafe Blog