예제 프로젝트에는 HelloWorld.app 및 Helper.app라는 두 가지 빌드 대상이 있습니다. 우리는 각각에 대한 구성 요소 패키지 를 만들어 제품 아카이브에 결합합니다. .
구성 요소 패키지 는 OS X 설치 프로그램에 의해 설치 될 페이로드 포함되어 있습니다. 구성 요소 패키지는 자체적으로 설치 될 수 있지만 일반적으로 제품 아카이브에 통합됩니다 .
"빌드 및 아카이브"에 성공하면 터미널에서 $ BUILT_PRODUCTS_DIR을 엽니 다.
$ cd ~/Library/Developer/Xcode/DerivedData/.../InstallationBuildProductsLocation
$ pkgbuild --analyze --root ./HelloWorld.app HelloWorldAppComponents.plist
$ pkgbuild --analyze --root ./Helper.app HelperAppComponents.plist
이것은 우리에게 component-plist를 제공합니다. "Component Property List" 섹션에 값 설명이 있습니다. pkgbuild -root 는 구성 요소 패키지를 생성합니다 . 기본 속성을 변경할 필요가없는 경우 --component-plist를 생략 할 수 있습니다 다음 명령에서 매개 변수를 .
productbuild --synthesize 는 배포 정의를 생성 합니다.
$ pkgbuild --root ./HelloWorld.app \
--component-plist HelloWorldAppComponents.plist \
HelloWorld.pkg
$ pkgbuild --root ./Helper.app \
--component-plist HelperAppComponents.plist \
Helper.pkg
$ productbuild --synthesize \
--package HelloWorld.pkg --package Helper.pkg \
Distribution.xml
에서 Distribution.xml 당신은 그래서 제목, 배경, 환영, 추가 정보, 라이센스, 그리고 같은 상황을 타개 할 수 있습니다. 이 명령을 사용 하여 구성 요소 패키지 및 분배 정의를 제품 아카이브로 전환하십시오 .
$ productbuild --distribution ./Distribution.xml \
--package-path . \
./Installer.pkg
가능한 것을 확인하려면 iTunes Installers Distribution.xml을 살펴 보는 것이 좋습니다 . 다음을 사용하여 "Install iTunes.pkg"를 추출 할 수 있습니다.
$ pkgutil --expand "Install iTunes.pkg" "Install iTunes"
함께합시다
일반적으로 프로젝트에는 Distribution.xml, component-plists, resources 및 scripts를 포함하는 Package라는 폴더가 있습니다.
"Generate Package"라는 스크립트 실행 단계를 추가 하십시오.이 패키지는 설치할 때만 스크립트 실행 으로 설정됩니다 .
VERSION=$(defaults read "${BUILT_PRODUCTS_DIR}/${FULL_PRODUCT_NAME}/Contents/Info" CFBundleVersion)
PACKAGE_NAME=`echo "$PRODUCT_NAME" | sed "s/ /_/g"`
TMP1_ARCHIVE="${BUILT_PRODUCTS_DIR}/$PACKAGE_NAME-tmp1.pkg"
TMP2_ARCHIVE="${BUILT_PRODUCTS_DIR}/$PACKAGE_NAME-tmp2"
TMP3_ARCHIVE="${BUILT_PRODUCTS_DIR}/$PACKAGE_NAME-tmp3.pkg"
ARCHIVE_FILENAME="${BUILT_PRODUCTS_DIR}/${PACKAGE_NAME}.pkg"
pkgbuild --root "${INSTALL_ROOT}" \
--component-plist "./Package/HelloWorldAppComponents.plist" \
--scripts "./Package/Scripts" \
--identifier "com.test.pkg.HelloWorld" \
--version "$VERSION" \
--install-location "/" \
"${BUILT_PRODUCTS_DIR}/HelloWorld.pkg"
pkgbuild --root "${BUILT_PRODUCTS_DIR}/Helper.app" \
--component-plist "./Package/HelperAppComponents.plist" \
--identifier "com.test.pkg.Helper" \
--version "$VERSION" \
--install-location "/" \
"${BUILT_PRODUCTS_DIR}/Helper.pkg"
productbuild --distribution "./Package/Distribution.xml" \
--package-path "${BUILT_PRODUCTS_DIR}" \
--resources "./Package/Resources" \
"${TMP1_ARCHIVE}"
pkgutil --expand "${TMP1_ARCHIVE}" "${TMP2_ARCHIVE}"
# Patches and Workarounds
pkgutil --flatten "${TMP2_ARCHIVE}" "${TMP3_ARCHIVE}"
productsign --sign "Developer ID Installer: John Doe" \
"${TMP3_ARCHIVE}" "${ARCHIVE_FILENAME}"
productbuild로 패키지를 생성 한 후 패키지를 변경할 필요가 없으면 pkgutil --expand
및 pkgutil --flatten
단계를 제거 할 수 있습니다. 또한 productsign 을 실행하는 대신 productbuild 에서 --sign paramenter를 사용할 수 있습니다 .
OS X 설치 프로그램 서명
패키지는 개발자 인증서 유틸리티 에서 다운로드 할 수 있는 개발자 ID 설치 프로그램 인증서 로 서명됩니다. .
서명은 pkgbuild , productbuild 또는 productsign--sign "Developer ID Installer: John Doe"
매개 변수로 수행됩니다 .
productbuild 를 사용하여 서명 된 제품 아카이브 를 작성하려는 경우 구성 요소 패키지 에 서명 할 이유가 없습니다 .
모든 방법 : Xcode 아카이브로 패키지 복사
Xcode Archive에 무언가를 복사하기 위해 Run Script Build Phase를 사용할 수 없습니다 . 이를 위해 Scheme Action을 사용해야합니다.
체계를 편집하고 보관을 확장하십시오. 그런 다음 사후 조치를 클릭하고 새 스크립트 실행 조치를 추가 하십시오 .
Xcode 6에서 :
#!/bin/bash
PACKAGES="${ARCHIVE_PATH}/Packages"
PACKAGE_NAME=`echo "$PRODUCT_NAME" | sed "s/ /_/g"`
ARCHIVE_FILENAME="$PACKAGE_NAME.pkg"
PKG="${OBJROOT}/../BuildProductsPath/${CONFIGURATION}/${ARCHIVE_FILENAME}"
if [ -f "${PKG}" ]; then
mkdir "${PACKAGES}"
cp -r "${PKG}" "${PACKAGES}"
fi
Xcode 5에서 PKG
대신 이 값을 사용하십시오.
PKG="${OBJROOT}/ArchiveIntermediates/${TARGET_NAME}/BuildProductsPath/${CONFIGURATION}/${ARCHIVE_FILENAME}"
버전 컨트롤에 Xcode Scheme 정보가 저장되어 있지 않은 경우이 스크립트를 프로젝트에 셸 스크립트로 추가하여 작업 영역에서 사후 조치로 스크립트를 끌어서 조치를 간단하게 복원 할 수 있습니다.
스크립팅
스크립트에는 배포 정의 파일의 JavaScript 와 셸 스크립트 의 두 가지 종류가 있습니다.
WhiteBox-PackageMaker How-to 에서 찾은 Shell Scripts에 대한 가장 좋은 문서 는 이전 패키지 형식 을 나타내 므로주의 깊게 읽으십시오.
추가 자료
알려진 문제 및 해결 방법
대상 선택 창
사용자에게 "이 컴퓨터의 모든 사용자를위한 설치"라는 단일 선택 항목 만있는 대상 선택 옵션이 제공됩니다. 이 옵션은 시각적으로 선택된 것으로 나타나지만 설치를 계속하려면 사용자가 해당 옵션을 클릭해야하므로 혼동을 일으킬 수 있습니다.
Apples 설명서를 사용하는 <domains enable_anywhere ... />
것이 좋지만 이로 인해 Apple이 패키지에서 사용하지 않는 새로운 버그가 많은 Destination Select Pane이 트리거됩니다.
사용 중단을 사용하면 <options rootVolumeOnly="true" />
이전 대상 선택 창이 나타납니다.
현재 사용자의 홈 폴더에 항목을 설치하려고합니다.
짧은 대답 : 시도하지 마십시오!
긴 대답 : 정말; 시도하지 마십시오! 설치 프로그램 문제 및 솔루션 읽기 . 이걸 읽은 후에도 내가 한 일을 알고 있습니까? 나는 그것을 시도하기에 충분히 바보였다. 자신에게 10.7 또는 10.8에서 문제를 해결했다고 확신합니다.
우선 위에서 언급 한 대상 선택 창 버그를 때때로 보았습니다. 그것은 나를 막았어야했지만 무시했습니다. 소프트웨어를 출시 한 후 일주일을 보내지 않으려면 멋진 파란색 선택을 한 번 클릭해야하는 지원 전자 메일에 응답하지 마십시오.
당신은 이제 사용자가 패널을 알아낼 정도로 똑똑하다고 생각하고 있습니까? 홈 폴더 설치에 관한 또 다른 것이 있습니다. 작동하지 않습니다!
나는 다른 OS 버전을 가진 약 10 개의 다른 컴퓨터에서 2 주 동안 테스트했지만 실패하지 않았습니다. 그래서 배송했습니다. 릴리스 후 1 시간 이내에 설치를 할 수 없었던 사용자들의 마음을 사로 잡았습니다. 로그는 수정할 수없는 권한 문제를 암시했습니다.
한 번 더 반복하겠습니다 : 홈 폴더 설치에는 설치 프로그램을 사용하지 않습니다!
Welcome, Read-me, 라이센스 및 결론에 대한 RTFD는에 의해 허용되지 않습니다 productbuild
.
RTFD 파일을 시작한 이후로 이미지가 포함 된 예쁜 시작 화면을 만들기 위해 설치 프로그램이 지원되었지만 productbuild에서는이를 허용하지 않습니다.
해결 방법 : 더미 rtf 파일을 사용하고 이후에 패키지에서 교체하십시오 productbuild
.
참고 : RTFD 파일 내에 Retina 이미지가있을 수도 있습니다. 이를 위해 다중 이미지 tiff 파일을 사용하십시오 tiffutil -cat Welcome.tif Welcome_2x.tif -out FinalWelcome.tif
. 자세한 내용은 .
BundlePostInstallScriptPath 스크립트를 사용하여 설치가 완료되면 애플리케이션 시작 :
#!/bin/bash
LOGGED_IN_USER_ID=`id -u "${USER}"`
if [ "${COMMAND_LINE_INSTALL}" = "" ]
then
/bin/launchctl asuser "${LOGGED_IN_USER_ID}" /usr/bin/open -g PATH_OR_BUNDLE_ID
fi
exit 0
설치 관리자가 아닌 로그인 한 사용자로 앱을 실행해야합니다. 이것은 launchctl asuser uid path로 수행됩니다 . 또한 설치 프로그램 도구 또는 Apple Remote Desktop을 사용 하여 명령 행 설치가 아닌 경우에만 실행합니다 .