studio - xamarin build targets




Is it possible to specify package name dynamically during build? (3)

I'd like to deploy both Debug and Release builds to my device at the same time. I can do this if I manually change the package name in the manifest before I build, e.g. change

<manifest xmlns:android="http://schemas.android.com/apk/res/android" 
          package="my.package">

to

<manifest xmlns:android="http://schemas.android.com/apk/res/android" 
          package="my.packageDEBUG">

However, I'd like to do this automatically when I'm building the solution. If I do a Debug build, it'll build with package="my.packageDEBUG" in the manifest.

Is this possible, and if so, how?


According to this question on Xamarin's forum you can change the Packaging Properties and specify different AndroidManifest.xml files for each build.

In the droid.csproj file add the <AndroidManifest> tag like so, for each build configuration:

  <PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Debug|AnyCPU' ">
    ...
    <AndroidManifest>Properties\AndroidManifestDbg.xml</AndroidManifest>
    ...

Here's the Xamarin's documentation on it.


I have achieved a solution with steps below:

  1. In my Visual Studio Solution, in Droid project, I have created an folder "Customers" and into this folder I have created two child folders (each one for a customer "CustomerA" and "CustomerB")
  2. Into customer folders I have put the images, resx,... files that I would like to change for each customer.
  3. In the root structure of project, I have created a PowerShell script (.ps1) and I have written this code:

    param ([string] $ProjectDir, [string] $SolutionDir, [string] $SolutionName)
    
    Write-Host "ProjectDir --> " $ProjectDir
    Write-Host "SolutionDir -->" $SolutionDir
    Write-Host "SolutionName --> " $SolutionName
    
    $PathCustomerFileName = $SolutionDir + $SolutionName + "\" + $SolutionName + "\CustomerTarget.txt"
    
    Write-Host "PathCustomerFileName --> " $PathCustomerFileName
    
    $ConfigurationName = Get-Content $SolutionDir$SolutionName"\"$SolutionName"\CustomerTarget.txt"
    
    $CorrectCustomerName = "CustomerA","CustomerB" -Contains $ConfigurationName
    
    If ($ConfigurationName.length -gt 0 -And $CorrectCustomerName) {
    
        $Origin = $ProjectDir + "\Customers\" + $ConfigurationName + ""
        $Destination = $ProjectDir + "\Resources"
    
        robocopy $Origin $Destination /S
    
    } else {
        Write-Host "[ERROR] Error copying customer resources. Check ShellScript params and " $PathCustomerFileName " content file."
    }
    

It copies the files from specific customer folder to "Resources" folder project.

  1. I have gone to properties on project: double click over "Properties" -> Compilation Events --> Pre-build and I have set this call:

    PowerShell -File "$(ProjectDir)GetCustomerResources.ps1" $(ProjectDir) $(SolutionDir) $(SolutionName)

  2. This previous steps, I have done them in each platform project (Android, iOS, ...).

  3. Then, I have added in the "Portable" project a "CustomerTarget.txt" file, where his content would be "CustomerA" or "CustomerB".

  4. Rebuild the solution, and that's all!

How to target a Xamarin PCL application for multiple customers?

Unfortunately this is not supported by Visual Studio.

But there is a third solution. You could create another project and add all (static) files as link to the project. With this, you don't have to switch between configurations or branches, you just select the project.

To add a file as link, you must right click on the folder -> add -> existing files -> select the files from original project -> on "add" click the arrow and select "add as link" (or somehow similar)

If you rather want to do it by configuration I would suggest reading this question.