Best practice for setting CFBundleVersion automatically

With the newest releases of iOS and iTunesConnect, Apple is more and more restrictive about what´s happening in your CFBundleVersion of your Extensions.


I tried to fiddle around with Run Script Build Phases, such as this:


#!/bin/sh
INFOPLIST_EXT="${TARGET_BUILD_DIR}/${INFOPLIST_PATH}"
echo "Extension writing to $INFOPLIST_EXT"
PLISTCMD="Set :CFBundleVersion $(git rev-list --all|wc -l)"
echo -n "$INFOPLIST_EXT" \
| xargs -0 /usr/libexec/PlistBuddy -c "$PLISTCMD"


However, this seems to work for some types of Extensions (WatchKit), but for some others it doesn´t (Today Widget). In my cases, I seem to access the $TARGET_BUILD_DIR before there´s content in it. Using $BUILT_PRODUCTS_DIR delivers the same error.


Extension writing to /Users/marc/Library/Developer/Xcode/DerivedData/MyApp-focpnqzzpnqsfyaqwwocwpujmhmh/Build/Intermediates/ArchiveIntermediates/MyApp/IntermediateBuildFilesPath/UninstalledProducts/TopNewsWidget.appex/Info.plist
Set: Entry, ":CFBundleVersion", Does Not Exist
File Doesn't Exist, Will Create: /Users/marc/Library/Developer/Xcode/DerivedData/MyApp-focpnqzzpnqsfyaqwwocwpujmhmh/Build/Intermediates/ArchiveIntermediates/MyApp/IntermediateBuildFilesPath/UninstalledProducts/TopNewsWidget.appex/Info.plist
Command /bin/sh failed with exit code 1


So now I´m asking: what is the best practice for setting the CFBundleVersion automatically across all my Extensions? If Apple forces this for all developers, there should be an official way to do this across all extensions!

I don´t want to use agvtool, as this requires a separate step in the build process, modifes the Info.plists (which then are marked as modified by the SCM) etc.


What is the lifecycle of a build, when are which directories filled with build products?


Cheers,

Marc

I generally do this with a custom build setting. Put the version number in that build setting and then reference it from your various Info.plist's via $(MY_BUILD_SETTING_NAME).


Share and Enjoy

--

Quinn "The Eskimo!"

Apple Developer Relations, Developer Technical Support, Core OS/Hardware

This does not work when you use a tool to generate the build number. I have also used a build phase, but the WatchKit app extension does not have any build phases. Why do we need to set it manually, if it is required to be the same as the app?


/Lars

This does not work when you use a tool to generate the build number.

Surely that would depend on your tool, no?

Why do we need to set it manually, if it is required to be the same as the app?

Indeed. I totally agree that Xcode should make this easier and I encourage you to file a bug to that effect.

Please post your bug number, just for the record.

Share and Enjoy

Quinn "The Eskimo!"
Apple Developer Relations, Developer Technical Support, Core OS/Hardware

let myEmail = "eskimo" + "1@apple.com"

Maybe I should be a little more explicit 🙂 We do not enter the build number in our settings manually. We have a tool that calculates the build number during the build process (e.g. number of GIT commits or the current build number on the build server). We do not want to make our source code checkout dirty, so the build number is updated in the build output, instead of in the project settings. And that is why build setting parameter does not work in our case. I hope that explaines it better.


I have reported a bug:

Bug number 21790470


/Lars

Also submitted a bug: 22948948

While Apple tries to get its stuff together, I found the following solution (or better, workaround):

http://stackoverflow.com/questions/32974815/how-do-i-keep-the-cfbundleversion-of-all-my-targets-watchkitapp-watchkitextens

Best practice for setting CFBundleVersion automatically
 
 
Q