Question

I am developing an iOS-application which is supposed to be branded to different customers. The issue at hand is that I need two versions of the application (one with orange theme and one with red theme) installed at the same time. What would be the best approach for accomplishing this?

Was it helpful?

Solution

You will simply need to use two different bundle-identifiers. This can be set in the info.plist: CFBundleIdentifier. You may want to setup different target or schemes that use different versions of the info.plist.

OTHER TIPS

I prefer to do this without maintaining two separate plist files, by post-processing the plist file in a custom "Pre-actions" build script for the "Archive" operation.

This helps to avoid problems where someone forgets to update both plist files when changing something.

I use this mechanism for building test versions of the app which I can upload to TestFlight so that my testers can have both the live version and the current test version installed simultaneously.

(note: Although this script goes in the "Pre-actions" section, it's really a post-processing step because it happens after XCode has done all of the variable substitution into the plist file)

To set this up (these instructions are for XCode 5.0.1), duplicate your existing scheme and call it something appropriate.

Select "Edit scheme", and expand the "Archive" item in the left tab. This should give you "Pre-actions", "Archive" and "Post-actions" sub-items. Click on the "Pre-actions" one, and then in the right tab, click on the '+' at the bottom to add a new "Run Script Action".

I use Ruby for my build scripts, so I enter "/usr/bin/ruby" in the "Shell" box at the top, but you can obviously do the same thing in bash or similar.

Select your project in the "Provide build settings from..." dropdown.

Then you can paste in some variant of the following code in the box at the bottom (or put it in a file, and drag the file to the box):

def changeBundle(file)
    oldId = `/usr/libexec/Plistbuddy -c "print :CFBundleIdentifier" #{file}`.strip
    system("/usr/libexec/PlistBuddy -c \"Set :CFBundleIdentifier #{oldId}_test\" #{file}")

    oldName = `/usr/libexec/Plistbuddy -c "print :CFBundleDisplayName" #{file}`.strip
    system("/usr/libexec/PlistBuddy -c \"Set :CFBundleDisplayName #{oldName}-Test\" #{file}")
end

changeBundle("#{ENV['CODESIGNING_FOLDER_PATH']}/Info.plist")

This updates the CFBundleIdentifier (adding '_test'), and the CFBundleDisplayName (adding '-Test') so that the apps are visibly different. Customise to make whatever changes you require.

The reason that the code to change the file is in a function is so that it's easy to make the same change to several plist files if you need to.

You don't need to do that in this case (because you probably just want to change what goes into the output archive file), but some of my other build scripts update version numbers automatically, and I want those changes to be checked into git. If you need to do that sort of thing, you can modify the source plist file as well by adding this at the bottom:

changeBundle("#{ENV['PROJECT_DIR']}/#{ENV['INFOPLIST_FILE']}")

Setting up two differents targets for the same project. Then, in each target you define pre-processor macros that you use in your code to distinguish between the versions of your app. For example you can have:

if (FREE_VERSION == true) {
    ...
}
else {
    ...
}

You have to create two targets with a different bundle identifier for each target.

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top