-
-
Save voxels/0ec095d567bcb0bc30a7c80122b17396 to your computer and use it in GitHub Desktop.
This run script will build the iphoneos and iphonesimulator schemes and then combine them into a single framework using the lipo tool (including all the Swift module architectures). This version works with Cocoapods, merging simulator and device architectures for intermediate libraries as well. To use this script, go to Product > Scheme > Edit S…
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
# This XCode scheme archive post-action script combines the device and iOS simulator frameworks into a single binary | |
# so that the encapsulated library can be run in both contexts. PLEASE NOTE: the iOS Simulator framework must be REMOVED | |
# before submitting this binary to the app store | |
# Source: https://gist.github.com/voxels/0ec095d567bcb0bc30a7c80122b17396 | |
# Based on: https://gist.github.com/atsepkov/1673c2d899470270e3eb313912aafc6f | |
# Resources: | |
# - https://developer.apple.com/library/content/technotes/tn2215/_index.html | |
# - https://pewpewthespells.com/blog/buildsettings.html | |
# WARNING: | |
# In order to submit this combined framework to the app store, an additional build script must be inserted | |
# into the adopting XCode project so that the iOS simulator binary is removed | |
# An example of this additional build script is located at: https://gist.github.com/voxels/2ab56e3bcda4a9a70053751f9d7ed5fa | |
# This script copies the unmodified iphoneos build product into ${SRCROOT}/archive/iphoneos/latest directory | |
BUILD_NUMBER=$(date +%Y%m%d%H%M) | |
exec > /tmp/${PROJECT_NAME}_post_archive_$BUILD_NUMBER.log 2>&1 | |
UNIVERSAL_OUTPUTFOLDER=${BUILD_DIR}/${CONFIGURATION}-universal | |
if [ "true" == ${ALREADYINVOKED:-false} ] | |
then | |
echo "RECURSION: Detected, stopping" | |
else | |
export ALREADYINVOKED="true" | |
# make sure the output directory exists | |
mkdir -p "${UNIVERSAL_OUTPUTFOLDER}" | |
echo "Building for iPhoneSimulator" | |
xcodebuild -workspace "${WORKSPACE_PATH}" -scheme "${SCHEME_NAME}" -configuration ${CONFIGURATION} -sdk iphonesimulator -destination 'platform=iOS Simulator,name=iPhone 6' ONLY_ACTIVE_ARCH=NO ARCHS='arm7 arm64 x86_64' BUILD_DIR="${BUILD_DIR}" BUILD_ROOT="${BUILD_ROOT}" ENABLE_BITCODE=YES OTHER_CFLAGS="-fembed-bitcode" BITCODE_GENERATION_MODE=bitcode clean build | |
# Step 1. Copy the framework structure (from iphoneos build) to the universal folder | |
echo "Copying to output folder" | |
cp -R "${ARCHIVE_PRODUCTS_PATH}${INSTALL_PATH}/${FULL_PRODUCT_NAME}" "${UNIVERSAL_OUTPUTFOLDER}/" | |
mkdir -p "${SRCROOT}/archive/iphoneos/latest/${FULL_PRODUCT_NAME}" | |
cp -Rf "${ARCHIVE_PRODUCTS_PATH}${INSTALL_PATH}/${FULL_PRODUCT_NAME}" "${SRCROOT}/archive/iphoneos/latest/${FULL_PRODUCT_NAME}" | |
# Step 2. Copy Swift modules from iphonesimulator build (if it exists) to the copied framework directory | |
SIMULATOR_SWIFT_MODULES_DIR="${BUILD_DIR}/${CONFIGURATION}-iphonesimulator/${PROJECT_NAME}.framework/Modules/${PROJECT_NAME}.swiftmodule/." | |
if [ -d "${SIMULATOR_SWIFT_MODULES_DIR}" ]; then | |
cp -R "${SIMULATOR_SWIFT_MODULES_DIR}" "${UNIVERSAL_OUTPUTFOLDER}/${PROJECT_NAME}.framework/Modules/${PROJECT_NAME}.swiftmodule" | |
fi | |
# Step 3. Create universal binary file using lipo and place the combined executable in the copied framework directory | |
echo "Combining executables" | |
lipo -create -output "${UNIVERSAL_OUTPUTFOLDER}/${EXECUTABLE_PATH}" "${BUILD_DIR}/${CONFIGURATION}-iphonesimulator/${EXECUTABLE_PATH}" "${ARCHIVE_PRODUCTS_PATH}${INSTALL_PATH}/${EXECUTABLE_PATH}" | |
# Step 4. Create universal binaries for embedded frameworks | |
for SUB_FRAMEWORK in $( ls "${UNIVERSAL_OUTPUTFOLDER}/${PROJECT_NAME}.framework/Frameworks" ); do | |
BINARY_NAME="${SUB_FRAMEWORK%.*}" | |
lipo -create -output "${UNIVERSAL_OUTPUTFOLDER}/${PROJECT_NAME}.framework/Frameworks/${SUB_FRAMEWORK}/${BINARY_NAME}" "${BUILD_DIR}/${CONFIGURATION}-iphonesimulator/${SUB_FRAMEWORK}/${BINARY_NAME}" "${ARCHIVE_PRODUCTS_PATH}${INSTALL_PATH}/${PROJECT_NAME}.framework/Frameworks/${SUB_FRAMEWORK}/${BINARY_NAME}" | |
done | |
# Step 5. Convenience step to copy the framework to the project's directory | |
echo "Copying from: ${UNIVERSAL_OUTPUTFOLDER}/${FULL_PRODUCT_NAME}" | |
echo "Copying to project dir: ${ARCHIVE_PRODUCTS_PATH}${INSTALL_PATH}" | |
yes | cp -Rf "${UNIVERSAL_OUTPUTFOLDER}/${FULL_PRODUCT_NAME}" "${ARCHIVE_PRODUCTS_PATH}${INSTALL_PATH}" | |
echo "Copying to archive dir: ${SRCROOT}/archive/universal/latest/${FULL_PRODUCT_NAME}" | |
mkdir -p "${SRCROOT}/archive/universal/latest/${FULL_PRODUCT_NAME}" | |
yes | cp -Rf "${UNIVERSAL_OUTPUTFOLDER}/${FULL_PRODUCT_NAME}" "${SRCROOT}/archive/latest/${FULL_PRODUCT_NAME}" | |
fi |
exec > /tmp/${PROJECT_NAME}_post_archive_$BUILD_NUMBER.log 2>&1
This line sets the output for the build steps logs
WIP, leaving this for now because ${ARCHIVE_PRODUCTS_PATH}${INSTALL_PATH}/${PROJECT_NAME}
is incorrect. Not using:
Building fat binaries in Xcode without lipo scripts
Using:
https://medium.com/@filippotosetto/how-to-create-a-carthage-framework-8d9d65f98ac2
Distributing closed source frameworks with CocoaPods and Carthage
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Thanks to atsepkov