🟣 Xcode의 실행 버튼 아래에는 무엇이 있나
앱을 만드는 내내 Xcode의 실행 버튼 하나로 빌드하고 설치했다. 그런데 이 버튼이 실제로 무슨 일을 하는지는 오래 몰랐다. 소스 코드가 어떻게 실제 기기에서 도는 앱이 되고, 왜 아무 기기에나 깔리지 않는지가 불투명했다. 이걸 이해하려면 버튼 한 번으로 뭉뚱그려진 과정을 명령줄에서 손으로 밟아 보는 게 가장 빠르다.
이 장은 실무 배포 자동화가 아니라 ipa 하나가 만들어져 기기에 설치되기까지의 원리를 학습 관점에서 따라간다. 명령줄에서 빌드해 보면 코드 서명이 왜 필요한지, 서드파티 라이브러리가 어떻게 내 앱에 합쳐지는지가 눈에 들어온다. 이 원리를 알면 나중에 배포가 깨졌을 때 어디를 봐야 할지 감이 잡힌다.
🟣 소스에서 ipa까지
Xcode가 실행 버튼 뒤에서 쓰는 도구가 xcodebuild다. 명령줄에서 직접 부를 수 있고, 앱을 만드는 과정은 크게 두 단계로 나뉜다. 먼저 소스를 컴파일해 서명까지 마친 묶음(.xcarchive)을 만들고, 그 묶음을 배포용 형식(.ipa)으로 내보낸다.
# 1단계: 아카이브 생성 (컴파일 + 서명)
xcodebuild archive \
-workspace MyApp.xcworkspace \
-scheme MyApp \
-archivePath build/MyApp.xcarchive
# 2단계: 아카이브를 ipa로 내보내기
xcodebuild -exportArchive \
-archivePath build/MyApp.xcarchive \
-exportOptionsPlist ExportOptions.plist \
-exportPath build/.ipa는 사실 특별한 포맷이 아니다. 앱 번들과 몇 가지 메타데이터를 담은 압축 파일일 뿐이다. 확장자를 바꿔 열어 보면 안에 앱 폴더가 그대로 들어 있다. 신비로워 보이던 배포 산출물이 결국 압축된 폴더라는 걸 확인하면 긴장이 풀린다.
명령이 길고 반복적이라, 이 단계를 Makefile로 묶어 두면 편하다. 실무의 배포 자동화는 여기서 훨씬 더 나아가지만, 원리를 익히는 단계에서는 make archive, make export 정도로 손에 익히는 것만으로 충분하다.
archive:
xcodebuild archive -workspace MyApp.xcworkspace -scheme MyApp \
-archivePath build/MyApp.xcarchive
export:
xcodebuild -exportArchive -archivePath build/MyApp.xcarchive \
-exportOptionsPlist ExportOptions.plist -exportPath build/🟣 왜 아무 기기에나 깔리지 않나
명령줄로 빌드해 보면 서명 문제로 한 번은 막힌다. iOS 앱은 아무 데서나 만든 것을 아무 기기에나 깔 수 없다. 누가 만들었고 어떤 기기에서 돌아도 되는지가 증명돼야 설치된다. 이 증명이 코드 서명이다.
여기엔 두 조각이 필요하다. 하나는 개발자의 신원을 담은 인증서이고, 다른 하나는 이 앱이 어떤 기기와 권한에서 돌아도 되는지를 적은 프로비저닝 프로파일이다. 아카이브를 만들 때 이 둘로 앱에 서명이 박히고, 기기는 설치 시 그 서명을 확인한다. 개발 중에 실기기 테스트가 안 되는 문제는 대개 이 프로파일에 그 기기가 등록돼 있지 않아서 생긴다.
이 구조를 알아 두면 배포 오류 메시지가 덜 무섭다. "서명 실패", "프로파일 불일치" 같은 문구가 나오면, 인증서와 프로파일이라는 두 조각 중 무엇이 어긋났는지를 좁혀 볼 수 있다. 서명의 내부 동작을 깊이 파는 건 다른 자리에서 다루고, 여기서는 배포 흐름 안에서 왜 이 관문이 있는지만 짚는다.
🟣 서드파티는 어떻게 내 앱에 합쳐지나
빌드 명령에 Pods와 .xcworkspace가 나왔다. 이건 서드파티 라이브러리를 붙이는 패키지 관리와 얽혀 있다. 지도, 결제, 분석 도구처럼 직접 만들기 벅찬 기능은 남이 만든 라이브러리를 가져다 쓰는데, 그 라이브러리를 내 프로젝트에 합치는 일을 도구가 대신해 준다. iOS에서 오래 쓰인 것이 CocoaPods다.
CocoaPods는 Podfile에 필요한 라이브러리를 적으면, 각 라이브러리와 그것이 다시 의존하는 라이브러리까지 알맞은 버전으로 받아 온다. 그리고 원래 프로젝트와 받아 온 라이브러리들을 하나로 묶은 .xcworkspace를 만든다. 이때부터는 .xcodeproj가 아니라 이 .xcworkspace를 열어야 한다. 앞의 빌드 명령이 -workspace를 가리킨 이유가 이것이다.
지금은 애플이 만든 Swift Package Manager가 표준으로 자리 잡아 새 프로젝트는 그쪽을 먼저 고른다. 그래도 원리는 같다. 필요한 라이브러리와 그 의존성을 버전에 맞게 모아 내 빌드에 합쳐 준다는 것이다. 도구가 바뀌어도 이 핵심은 변하지 않아서, CocoaPods로 한 번 이해해 두면 다른 도구로 넘어가기 쉽다.
🚀 SDK를 붙일 때 공통으로 보는 것
지도나 결제 같은 서드파티 SDK를 붙일 때는 라이브러리를 받는 것 말고도 매번 반복되는 확인 사항이 있다. 도구가 무엇이든 대체로 같은 항목을 본다.
먼저 SDK가 요구하는 키와 초기화다. 대개 발급받은 키를 Info.plist에 넣고, 앱이 뜰 때 AppDelegate에서 한 번 초기화한다. 1부에서 본 진입 경로가 여기서 다시 쓰인다. 앱에 한 번만 하면 되는 일이라 didFinishLaunching에 두는 것이다.
다음은 권한과 개인정보 문구다. 지도는 위치, 결제는 종종 카메라나 네트워크 권한을 쓴다. iOS는 권한을 쓸 때 사용자에게 이유를 보여 주도록 강제하므로, 그 설명 문구를 Info.plist에 빠뜨리면 앱이 그 자리에서 멈춘다. 마지막으로 SDK가 늘리는 앱 용량과, 심사 때 요구되는 추적 관련 정보다. 특히 결제나 분석 SDK는 데이터 수집 항목을 앱 심사에 정확히 신고해야 한다. 기능을 붙이는 일보다 이 주변 설정에서 시간을 더 쓰게 된다는 걸 알아 두면 일정을 잡을 때 덜 당황한다.
🟣 정리
- Xcode의 실행 버튼은
xcodebuild를 대신 부르는 것이다. 명령줄로 아카이브를 만들고ipa로 내보내 보면 배포 과정이 손에 잡힌다. .ipa는 특별한 포맷이 아니라 앱 번들을 담은 압축 파일이다. 반복되는 빌드 명령은Makefile로 묶어 두면 편하다.- iOS 앱은 코드 서명으로 신원과 허용 기기가 증명돼야 설치된다. 인증서와 프로비저닝 프로파일 두 조각을 알면 서명 오류를 좁혀 볼 수 있다.
CocoaPods는Podfile의 라이브러리와 그 의존성을 버전에 맞게 모아.xcworkspace로 묶는다.Swift Package Manager로 바뀌어도 원리는 같다.- SDK를 붙일 때는 라이브러리 설치보다 키 초기화, 권한 문구, 심사 신고 같은 주변 설정에서 시간이 더 든다. 면접에서 "SDK를 붙이며 겪은 문제"를 물으면 이 지점을 구체적으로 답할 수 있다.
여기까지가 앱을 시작하고, 코드를 나누고, 바깥과 잇고, 데이터를 두고, 세상에 올리는 한 바퀴다. 어떤 앱을 만들든 반복해 마주치는 기본기를 하나의 흐름으로 엮어 봤다. 각 주제의 더 깊은 내부 동작은 애플 플랫폼을 다루는 다른 책에서 이어 간다.