Created
March 19, 2016 18:35
-
-
Save curiositycasualty/7002462b37eabf3a4e0d to your computer and use it in GitHub Desktop.
Install Xcode SDK major releases from Xcode 6.1.1 - 7.2.1 into a host's Xcode.app
This file contains hidden or 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
#!/usr/bin/env bash | |
PREFIX='./xcodes' | |
DMGs=(xcode_6.1.1.dmg | |
Xcode_6.2.dmg | |
Xcode_6.3.2.dmg | |
Xcode_6.4.dmg | |
Xcode_7.0.1.dmg | |
Xcode_7.1.1.dmg | |
Xcode_7.2.1.dmg) | |
# DISCLAIMER: These are not official checksums from Apple, | |
# just ones I've generated from my dropbox copy of the DMGs. | |
url_611="https://www.dropbox.com/s/f0fgbj43wbgmukh/xcode_6.1.1.dmg?dl=0" | |
md5_611="00773faa3ddc9a0b7b94bab8496aa522" | |
url_62="https://www.dropbox.com/s/kv711z3c2x76vvw/Xcode_6.2.dmg?dl=0" | |
md5_62="fe4c6c99182668cf14bfa5703bedeed6" | |
url_632="https://www.dropbox.com/s/amnisaibwfpr6jw/Xcode_6.3.2.dmg?dl=0" | |
md5_632="a61d18cc7abf5de83f24ae7dc4ee281a" | |
url_64="https://www.dropbox.com/s/m8pq8rfgz3y58d9/Xcode_6.4.dmg?dl=0" | |
md5_64="fc57760b91df8d45ee57ba80436e49a9" | |
url_701="https://www.dropbox.com/s/xiqafaa99wkwxr7/Xcode_7.0.1.dmg?dl=0" | |
md5_701="3702b5291ed8127781158eb6a79d03cb" | |
url_711="https://www.dropbox.com/s/cwpsd42f57szcsw/Xcode_7.1.1.dmg?dl=0" | |
md5_711="25e4af4f0a0251e08446cd51485041f1" | |
url_721="https://www.dropbox.com/s/6gsm40zdt9i519k/Xcode_7.2.1.dmg?dl=0" | |
md5_721="e9c6ec03fd269cb2802180800fb7fb0e" | |
# | |
# preflight() | |
# | |
# Make sure we have an Xcode.app on the host and all the DMGs | |
# we are expecting before we do any heavy lifting. | |
# | |
function preflight() { | |
echo "INFO: Starting preflight check." | |
# is first xcode installed? | |
if [ -d "/Applications/Xcode.app" ]; then | |
# do you have all the DMGs? | |
declare -a missing | |
for dmg in "${DMGs[@]}"; do | |
if [ ! -s "${PREFIX}/${dmg}" ]; then | |
missing=(${missing[@]} $dmg) | |
fi | |
done | |
if [[ ! -z ${missing[@]} ]]; then | |
echo "ERR: Preflight check failed: Missing some DMGs" | |
echo "ERR: Missing: ${missing[@]}" | |
exit 255 | |
fi | |
else | |
echo "ERR: Preflight check failed: No base Xcode detected." | |
echo "ERR: Please install the most recent Xcode via the App Store." | |
exit 256 | |
fi | |
echo "INFO: Preflight check passed!" | |
} | |
# | |
# main() | |
# | |
# Where all the pieces come together except the preflight check. | |
# | |
function main() { | |
attach-all | |
copy-all "iPhoneOS" | |
copy-all "iPhoneSimulator" | |
detach-all | |
} | |
# | |
# copy-all() | |
# | |
# Given a platform ("iPhoneOS", "AppleTVOS", etc.) copy all | |
# the files from that Xcode's version into the host's Xcode.app. | |
# | |
# Also renames the host's Xcode.app's version of said platform | |
# SDK and removes the symlinking to the latest version. | |
# | |
function copy-all() { | |
if [ -z "${@}" ]; then | |
echo "ERR: Which SDK to consolidate not specified." | |
exit 255 | |
fi | |
platform="$1" | |
base="/Applications/Xcode.app/Contents/Developer/Platforms/${platform}.platform/Developer/SDKs" | |
echo "INFO: Removing latest symlink and moving original into place." | |
sym="$(find ${base} -type l -maxdepth 1)" | |
name="${sym##*/}" | |
sudo rm -rfv $sym | |
sudo mv -v "${base}/${platform}.sdk" "${sym}" | |
echo "INFO: Copying ${platform} SDKs" | |
for SDK in /Volumes/dmg.*/Xcode.app/Contents/Developer/Platforms/${platform}*/Developer/SDKs/${platform}*[0-9]*.sdk; do | |
name="${SDK##*/}" | |
real="${SDK%%${platform}[0-9]*}${platform}.sdk" | |
sudo rsync -a --ignore-existing "$real" "${base}/${name}" & | |
done | |
for pid in $(jobs -p); do | |
wait $pid | |
done | |
echo | |
} | |
# | |
# attach() | |
# | |
# Attach a single .DMG file to a path matching the pattern: | |
# /Volumes/dmg.[a-zA-Z0-9]{6} (per the "-mountrandom" flag). | |
# Close any resultant Finder.app windows with the title "Xcode." | |
# | |
# Does not handle EULAs. Will verify if DMG specified is | |
# already attached, but will not attach duplicates of the | |
# same DMG. | |
# | |
function attach() { | |
dmg="${PREFIX}/$1" | |
path="$(hdiutil attach "${dmg}" -mountrandom "/Volumes" | grep Volumes | awk '{ print substr($0, index($0,$3)) }')" | |
while ( ( osascript -e 'tell application "Finder" to close Finder window "Xcode"' 2>&1 ) > /dev/null ); do | |
sleep 1 | |
done | |
echo "$path" | |
} | |
# | |
# attach-all() | |
# | |
# Loop through $DMGs and attach() each. | |
# | |
function attach-all() { | |
for dmg in "${DMGs[@]}"; do | |
path="$(attach "$dmg")" | |
version="${dmg//[^0-9.]}" | |
version="${version%%.}" | |
echo -e "${dmg} (${version})\t:\t${path}" | |
done | |
} | |
# | |
# detach() | |
# | |
# Detach a single attached volume specified by path. | |
# | |
function detach() { | |
path="$1" | |
echo "INFO: Detaching ${path}..." | |
if (hdiutil detach "$path" 2>&1 > /dev/null); then | |
echo "INFO: Success!" | |
else | |
echo "ERR: Failure. :(" | |
fi | |
} | |
# | |
# detach-all() | |
# | |
# Detach all attached volumes that resemble the pattern: | |
# /Volumes/dmg.[a-zA-Z0-9]{6} | |
# | |
function detach-all() { | |
echo "INFO: Detaching all Xcode DMGs from /Volumes/dmg.*" | |
for dmg in /Volumes/dmg.*; do | |
detach "$dmg" | |
done | |
} | |
preflight | |
main |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment