Skip to content

Commit

Permalink
[Xamarin.Android.Build.Tasks] Add Support for AndroidManifest.xml ove…
Browse files Browse the repository at this point in the history
…rlays (#5325)

Fixes #5312

The manifest merger tool supports providing additional AndroidManifest.xml
files which will `overlay` on top of the final file. This commit adds a
new Build Action `AndroidManifestOverlay` which can be used to provide
these files to the manifest merger.

Users can now use these overlay files to alter the manifest during
build time. This can be for adding new permissions or even removing
ones that are not needed. It will also allow for different manifest
files to be generated for debug/release configurations. This can be
done by conditionally including `overlay` files depending on the
`$(Configuration)`.

```
<ItemGroup>
  <AndroidManifestOverlay Include="DebugPermissions.xml" Condition=" '$(Configuration)' == 'Debug' " />
</ItemGroup>
```
  • Loading branch information
dellis1972 authored Nov 27, 2020
1 parent a3d4d19 commit d794534
Show file tree
Hide file tree
Showing 3 changed files with 59 additions and 0 deletions.
30 changes: 30 additions & 0 deletions Documentation/guides/building-apps/build-items.md
Original file line number Diff line number Diff line change
Expand Up @@ -86,6 +86,36 @@ which tests to enable and disable.
See the [lint documentation](https://developer.android.com/studio/write/lint)
for more details.

## AndroidManifestOverlay

The build action `AndroidManifestOverlay` can be used to provide additional
`AndroidManifest.xml` files to the [Manifest Merger]([~/android/deploy-test/building-apps/build-properties.md#](https://developer.android.com/studio/build/manifest-merge)) tool.
Files with this build action will be passed to the Manifest Merger along with
the main `AndroidManifest.xml` file and any additional manifest files from
references. These will then be merged into the final manifest.

You can use this build action to provide additional changes and settings to
your app depending on your build configuration. For example if you need to
have a specific permission only while debugging, you can use the overlay to
inject that permission when debugging. For example given the following
overlay file contents

```
<manifest xmlns:android="http://schemas.android.com/apk/res/android">
<uses-permission android:name="android.permission.CAMERA" />
</manifest>
```

you can use the following to add this for a debug build.

```
<ItemGroup>
<AndroidManifestOverlay Include="DebugPermissions.xml" Condition=" '$(Configuration)' == 'Debug' " />
</ItemGroup>
```

Introduced in Xamarin.Android 11.2

## AndroidNativeLibrary

[Native libraries](~/android/platform/native-libraries.md)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -150,6 +150,33 @@ public void CheckElementReOrdering ([Values (true, false)] bool useAapt2)
}
}

[Test]
public void OverlayManifestTest ()
{
var proj = new XamarinAndroidApplicationProject () {
IsRelease = true,
ManifestMerger = "manifestmerger.jar",
};
proj.AndroidManifest = @"<?xml version=""1.0"" encoding=""utf-8""?>
<manifest xmlns:android=""http://schemas.android.com/apk/res/android"" xmlns:tools=""http://schemas.android.com/tools"" android:versionCode=""1"" android:versionName=""1.0"" package=""foo.foo"">
<application android:label=""foo"">
</application>
</manifest>";
proj.OtherBuildItems.Add (new BuildItem ("AndroidManifestOverlay", "ManifestOverlay.xml") {
TextContent = () => @"<?xml version=""1.0"" encoding=""utf-8""?>
<manifest xmlns:android=""http://schemas.android.com/apk/res/android"">
<uses-permission android:name=""android.permission.CAMERA"" />
</manifest>
"
});
using (var b = CreateApkBuilder ("temp/OverlayManifestTest", cleanupAfterSuccessfulBuild: true, cleanupOnDispose: false)) {
Assert.IsTrue (b.Build (proj), "Build should have succeeded.");
var manifestFile = Path.Combine (Root, b.ProjectDirectory, proj.IntermediateOutputPath, "android", "AndroidManifest.xml");
var text = File.ReadAllText (manifestFile);
StringAssert.Contains ("android.permission.CAMERA", text, $"{manifestFile} should contain 'android.permission.CAMERA'");
}
}

[Test]
public void RemovePermissionTest ()
{
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -171,6 +171,7 @@ Copyright (C) 2011-2012 Xamarin. All rights reserved.
<AvailableItemName Include="MultiDexMainDexList" />
<AvailableItemName Include="ProguardConfiguration" />
<AvailableItemName Include="ProjectReference" />
<AvailableItemName Include="AndroidManifestOverlay" />
</ItemGroup>

<!-- Version/fx properties -->
Expand Down Expand Up @@ -1442,6 +1443,7 @@ because xbuild doesn't support framework reference assemblies.
OutputManifestFile="$(IntermediateOutputPath)android\AndroidManifest.xml"
LibraryManifestFiles="@(ExtractedManifestDocuments)"
ManifestPlaceholders="$(AndroidManifestPlaceholders)"
ManifestOverlayFiles="@(AndroidManifestOverlay)"
/>
<ItemGroup>
<FileWrites Include="$(IntermediateOutputPath)android\AndroidManifest.xml" />
Expand Down

0 comments on commit d794534

Please sign in to comment.