Xamarin Kick-off Project: Create Different Applications with the Same Solution [Part 1/2] - Build Variants
This article is accompanied by an example of a project with Xamarin.Forms, but the solution is also suitable for Xamarin.Android, Xamarin.iOS, and Xamarin.Cross, considering that configurations are made on each platform.
The case will be introduced by explaining the difference between need, decision, and development.
Need
Automate the creation of different applications for the same solution, without making manual changes such as file replacement, and application or package name.
Decision
Taking into account a countless number of posts, the decision was tilted based on how Android handles "flavors" and "build types" in its Gradle archive. That was the starting point for creating all the configurations for the solution.
Development
Android Project
1. Go to the Android project: right-click → Options → Compiler → Configurations
2. Add configurations DebugQa, DebugProd, ReleaseQa, ReleaseProd.
3. Within "Options," choose "Compiler" to set configurations. Take "Debug" and "Release" as a reference because they happen by default.
4. Do the same with "Build" for Android and Package Signature, and save changes.
5. In the folder "Properties," create as many directories as needed for all the applications (in this case, these are dev, QA, and prod). Now, generate an AndroidManifest files.XML archive in each directory. At the moment, just the packages and the app's name vary.
6. Right-click on the project → Edit project file. Next, in each "PropertyGroup," create or modify the <AndroidManifest > tag and <DefineConstants> straight-lines of precompilation.
https://gist.github.com/rodrigotristany/c3d8878b4e6376067c5d9296ed9ba001#file-android-csproj
Follow the same procedure to adjust configurations of "Releases."
Link to Android project
https://github.com/rodrigotristany/flavors/tree/master/flavors
iOS project
1. Right Click on Forms → Options → Build → Configurations.
2. Add the next configurations DebugQa, DebugQa|iPhone, DebugQa|iPhoneSimulator, DebugProd, DebugProd|iPhone, DebugProd|iPhoneSimulator, ReleaseQa, ReleaseQa|iPhone, ReleaseQa|iPhoneSimulator, ReleaseProd, ReleaseProd|iPhone, ReleaseProd|iPhoneSimulator.
3. Go to "Build" and choose "Compiler" to set configurations. Take "Debug" and "Release" as reference because they happen by default.
4. Follow the same procedure for iOS Bundle Signing, iOS Build and iOS Debug.
5. In the root folder, create as many .plist files as needed for all the applications (in this case, dev, QA, prod). They will be Info.plist, Info-qa.plist, and Info-prod.plist. Now, the main differences occur between the "bundleId" and the name of the app.
6. Right click on the project → Edit project file: search for <ItemGroup> that contains Main.cs and add the conditions for the selection of .plist files.
https://gist.github.com/rodrigotristany/85660e334a5d65e1f2969f29c8f0a530#file-ios-csproj
Bear in mind that, as they are logical names, the IDE will only show the file of the selected solution.
Link to iOS project
https://github.com/rodrigotristany/flavors/tree/master/flavors.iOS
Forms Project
1. Right Click on Forms → Options → Build → Configurations.
2. Add the configurations DebugQa, DebugQa|iPhone, DebugQa|iPhoneSimulator, DebugProd, DebugProd|iPhone, DebugProd|iPhoneSimulator, ReleaseQa, ReleaseQa|iPhone, ReleaseQa|iPhoneSimulator, ReleaseProd, ReleaseProd|iPhone, ReleaseProd|iPhoneSimulator.
3. Go to “Build” and choose "Compiler" to set configurations. Take "Debug" and "Release" as a reference because they happen by default.
Link to Forms project
https://github.com/rodrigotristany/flavors/tree/master/flavors
Solution
1. Go to project → Solution Options → Build → Configurations.
2. Add a configuration for each type of compilation. In this case,create DebugQa, DebugQa|iPhone, DebugQa|iPhoneSimulator, DebugProd, DebugProd|iPhone, DebugProd|iPhoneSimulator, which will be set on the basis of Debug configurations, and ReleaseQa, ReleaseQa|iPhone, ReleaseQa|iPhoneSimulator, ReleaseProd, ReleaseProd|iPhone, ReleaseProd|iPhoneSimulator who will take the Release configurations.
3. For each added configuration, set Configuration Mappings.
Summing-up
These steps set the foundations to plan a solution using multiple applications. In the following sections, the precompilation variables will be used, which are created to make decisions, considering selected configurations.