Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Run a shell script before build in Xcode

I need to adjust my build and version number for my project before build/archiving.
I tried multiple things, but so far to no avail.

I added a target with the script to update the numbers and added that as first dependency to my main target. But because I have multiple dependencies as I have extensions in my app and all dependencies are executed by Xcode in parallel (or at least in random order) this does not work.

I added a pre-action to my scheme with the same result. Xcode is not waiting for my pre-action to complete before continuing with the build (I added a sleep 100 to test).

As I'm altering build numbers it is crucial that the script can complete before anything else is started, but there is also one more side-effect: The build even stops due to the fact that the plist files have been altered while building the related target.

What makes it more difficult is, that I would like to use agvtools to set my version & build number. This obviously starts background processes that are out of my control to alter the plists.

Disclaimer: I have searched for other answers, didn't help.

like image 410
dogsgod Avatar asked Apr 04 '15 20:04

dogsgod


People also ask

How do I run a shell script in Xcode?

If you have an existing shell script file, drag it onto the Shell text field to copy the script there. You may use any of the available shell environments to execute your script, and you can change the execution shell by changing the shell command above your script code.

How do I create a .sh file in Xcode?

In Terminal, make the shell script an executable by running chmod +x $filename.sh . Add code to your custom build script — including a shebang in the first line; for example #!/bin/sh — and add it to your Git repository. Xcode Cloud runs it automatically when it starts the next build.

How do I compile and run a script in one step Swift?

Compiling your Swift file and executing it from Xcode is as easy as doing it from the terminal. All you need to do is define a New Run Script Phase and add the commands you executed on the terminal into it. From the Project navigator, select the project file.


2 Answers

agvtools just does not work in an Xcode build. It will always stop the build. What works fine is PlistBuddy, although the setup is not as nice and neat.

I added a Pre-Action to the build in my main scheme to call a new target in my project:

xcodebuild -project "${SRCROOT}/MAIN_APP.xcodeproj" -scheme BuildNumberPreProcess

In the target BuildNumberPreProcess I have a Run Script:

VERSION=$(head -n 1 version.txt)
BUILD=`git rev-list $(git rev-parse --abbrev-ref HEAD) | wc -l | awk '{ print $1 }'`

echo "${VERSION} (${BUILD})"

SCRIPT="${SRCROOT}/CLIENT/Supporting Files/set-version-in-plist.sh"

"${SCRIPT}" "${SRCROOT}/MAIN_APP/Supporting Files/Info.plist" ${VERSION} ${BUILD}
"${SCRIPT}" "${SRCROOT}/EXTENSION/Info.plist" ${VERSION} ${BUILD}
...

set-version-in-plist.h:

#!/bin/sh

#  set-version-in-plist.sh
#
# usage:
# set-version-in-plist LIST VERSION BUILD
# LIST:      Info.plist path & name
# VERSION:   version number xxx.xxx.xxx
# BUILD:     build number xxxxx
#

# Location of PlistBuddy
PLISTBUDDY="/usr/libexec/PlistBuddy"

echo "$1: $2 ($3)"

${PLISTBUDDY} -c "Set :CFBundleShortVersionString $2" "$1";
${PLISTBUDDY} -c "Set :CFBundleVersion $3" "$1";
like image 104
dogsgod Avatar answered Sep 28 '22 17:09

dogsgod


Xcode has command line tools for build/archiving: https://developer.apple.com/library/ios/technotes/tn2339/_index.html

So, you can write shell script that at first runs your script for adjusting build/version number and then runs xcode build/archive as command line tool.

like image 39
ITemius Avatar answered Sep 28 '22 17:09

ITemius