Skip to content

Fix inter-API-level checks #1089

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Closed
jonpryor opened this issue Dec 7, 2017 · 0 comments
Closed

Fix inter-API-level checks #1089

jonpryor opened this issue Dec 7, 2017 · 0 comments
Assignees
Labels
Area: xamarin-android Build Issues building the xamarin-android repo *itself*.
Milestone

Comments

@jonpryor
Copy link
Contributor

jonpryor commented Dec 7, 2017

No description provided.

@jonpryor jonpryor added the Area: xamarin-android Build Issues building the xamarin-android repo *itself*. label Dec 7, 2017
@jonpryor jonpryor self-assigned this Dec 7, 2017
@jonpryor jonpryor added this to the d15-6 milestone Dec 8, 2017
@jonpryor jonpryor modified the milestones: d15-6, d15-7 Jan 4, 2018
jonpryor added a commit to jonpryor/xamarin-android that referenced this issue Jan 18, 2018
Context: dotnet#1089
Context: dotnet#1078
Context: https://jenkins.mono-project.com/view/Xamarin.Android/job/xamarin-android/823/

Commit 8ff139f [broke][0] the [build][1], in a minor way:

[0]: https://jenkins.mono-project.com/view/Xamarin.Android/job/xamarin-android/824/console
[1]: https://jenkins.mono-project.com/view/Xamarin.Android/job/xamarin-android/824/

	# reading extras from: inter-api-extra-v2.3-v4.0.3.txt
	mono --debug /Users/builder/jenkins/workspace/xamarin-android/xamarin-android/bin/BuildDebug/mono-api-html.exe "inter-apis/v2.3/Mono.Android.xml" "inter-apis/v4.0.3/Mono.Android.xml" --ignore-changes-parameter-names --ignore-changes-virtual --ignore-changes-property-setters --ignore-nonbreaking
	<h1>### API BREAK BETWEEN v2.3 and v4.0.3</h1>
	...
	<h2>Namespace Android.Text</h2>
	<!-- start type ClipboardManager --> <div>
	<h3>Type Changed: Android.Text.ClipboardManager</h3>
	<p>Modified properties:</p>
	<pre>
	<div data-is-breaking>	public <span class='added added-breaking-inline'>abstract</span> bool HasText { get; }
	</div><div data-is-breaking>	public <span class='added added-breaking-inline'>abstract</span> Java.Lang.ICharSequence TextFormatted { get; set; }
	</div></pre>
	...

These are "acceptable" API breakage for now, previously not reported
[because the test was broken][6dfb]. The test was fixed on
xamarin-android-api-compatibility/master, but we haven't been able to
merge to that commit yet (PR dotnet#1078).

[6dfb]: xamarin/xamarin-android-api-compatibility@6dfba92

Unfortunately, 8ff139f included a bump to
xamarin-android-api-compatibility/master, thus introducing the
"UNSTABLE" breakage that PR dotnet#1078 encountered.

For now -- until we can properly fix things -- bump to
xamarin-android-api-compatibility/d15-6, which *lacks* the test fixes
on master, and thus will allow the API compatibility checks to pass.
jonpryor added a commit that referenced this issue Jan 18, 2018
Context: #1089
Context: #1078
Context: https://jenkins.mono-project.com/view/Xamarin.Android/job/xamarin-android/823/

Commit 8ff139f [broke][0] the [build][1], in a minor way:

[0]: https://jenkins.mono-project.com/view/Xamarin.Android/job/xamarin-android/824/console
[1]: https://jenkins.mono-project.com/view/Xamarin.Android/job/xamarin-android/824/

	# reading extras from: inter-api-extra-v2.3-v4.0.3.txt
	mono --debug /Users/builder/jenkins/workspace/xamarin-android/xamarin-android/bin/BuildDebug/mono-api-html.exe "inter-apis/v2.3/Mono.Android.xml" "inter-apis/v4.0.3/Mono.Android.xml" --ignore-changes-parameter-names --ignore-changes-virtual --ignore-changes-property-setters --ignore-nonbreaking
	<h1>### API BREAK BETWEEN v2.3 and v4.0.3</h1>
	...
	<h2>Namespace Android.Text</h2>
	<!-- start type ClipboardManager --> <div>
	<h3>Type Changed: Android.Text.ClipboardManager</h3>
	<p>Modified properties:</p>
	<pre>
	<div data-is-breaking>	public <span class='added added-breaking-inline'>abstract</span> bool HasText { get; }
	</div><div data-is-breaking>	public <span class='added added-breaking-inline'>abstract</span> Java.Lang.ICharSequence TextFormatted { get; set; }
	</div></pre>
	...

These are "acceptable" API breakage for now, previously not reported
[because the test was broken][6dfb]. The test was fixed on
xamarin-android-api-compatibility/master, but we haven't been able to
merge to that commit yet (PR #1078).

[6dfb]: xamarin/xamarin-android-api-compatibility@6dfba92

Unfortunately, 8ff139f included a bump to
xamarin-android-api-compatibility/master, thus introducing the
"UNSTABLE" breakage that PR #1078 encountered.

For now -- until we can properly fix things -- bump to
xamarin-android-api-compatibility/d15-6, which *lacks* the test fixes
on master, and thus will allow the API compatibility checks to pass.
jonpryor added a commit to xamarin/xamarin-android-api-compatibility that referenced this issue Feb 22, 2018
Context: dotnet/android#1089

What is the purpose of the xamarin-android-api-compatibility repo?
To ensure that we don't accidentally break API, both for the latest
supported API level, and *between* API level binding assemblies.

How's that working out for us?

It could be better.

Commit e353872 was due to a discovery that `mono-api-html` behavior
had changed: it *used* to emit separate "Removed" and "Added"
declarations whenever a method was changed. Then it started emitting
"Modified" sections, but we weren't aware of this change. The result
was an [accidental API break][pr-771], and a change to start looking
for `data-is-breaking` instead of `>Removed`.

[pr-771]: dotnet/android#771 (comment)

*Then* we learned that `make check-inter-api-level` was broken, due to
bad `test` logic. This was fixed in 6dfba92.

The problem is that xamarin-android has not been able to use
[xamarin-android-api-compatibility/master][pr-1078] since 6dfba92 has
been merged, because it found [inter-API level breakage][inter-break]
that we haven't been able to work around, e.g.:

[pr-1078]: dotnet/android#1078
[inter-break]: dotnet/android#1078 (comment)

	<h3>Type Changed: Android.Preferences.CheckBoxPreference</h3>
	Modified base type: <span class='removed removed-inline removed-breaking-inline'>Android.Preferences.Preference</span> <span class='added '>Android.Preferences.TwoStatePreference</span>

The "obvious" solution would have been to use the existing
`inter-api-extra*` files/mechanism to ignore the changes which kept
`make check-inter-api-level` from succeeding, but `mono-api-html`
didn't provide a mechanism to ignore all of those changes.

Doh!

The fix? [Improve `mono-api-html` so it can ignore more][api-ignore]
API artifacts. (Additionally, improve `mono-api-html` so that we can
"scope" what changes we're ignoring, so that e.g. `mono-api-html -r`
can specify the *type* that the ignore should apply to, and not be
matched against *every member in the assembly*.)

[api-ignore]: mono/mono@de4729f

With that infrastructural change in place, update the
`inter-api-extra*` files so that the acceptable changes are ignored,
thus allowing `make check` to run w/o error on xamarin-android/master.

Additionally:

  * The updated `mono-api-html` supports response files. Update the
    `mono-api-html` invocation to provide the `inter-api-extra*` files as
    response files, instead of `cat`ing the `inter-api-extra*` files.
    Eventually, `mono-api-html` may support comments in response files, which
    would allow us to use them.

  * Update `reference/Mono.Android.xml` for `ChoiceMode`.
    Commit 6874e3f updated `Android.Widget.ListView` to use `ChoiceMode`
    instead of `int` for many of the constants. This was inadvertently
    "reverted"/overwrritten in bb8630a.

  * Add support for a new `$(HTML_OUTPUT_DIR)` make variable. If set,
    `mono-api-html`-generated HTML files will be written into the
    `$(HTML_OUTPUT_DIR)` directory.
jonpryor added a commit to jonpryor/xamarin-android that referenced this issue Feb 22, 2018
Fixes: dotnet#1089

We found that xamarin-android-api-compatibility wasn't *actually*
performing the inter-API-level checks, meaning an important API
compatibility check wasn't being performed.

Bump to xamarin-android-api-compatibility/2c689ef2 so that
inter-API-level checks are properly performed.

Additionally, set `$(HTML_OUTPUT_DIR)` so that `mono-api-html` output
files are written into `bin/Build$(CONFIGURATION)/compatibility`.
This will (hopefully) allow us to use the Jenkins
**Publish HTML reports** Post-build Action to nicely display API
compatibility breakage, without requiring that we read the actual
build log output.
atsushieno pushed a commit that referenced this issue Feb 22, 2018
Fixes: #1089

We found that xamarin-android-api-compatibility wasn't *actually*
performing the inter-API-level checks, meaning an important API
compatibility check wasn't being performed.

Bump to xamarin-android-api-compatibility/2c689ef2 so that
inter-API-level checks are properly performed.

Additionally, set `$(HTML_OUTPUT_DIR)` so that `mono-api-html` output
files are written into `bin/Build$(CONFIGURATION)/compatibility`.
This will (hopefully) allow us to use the Jenkins
**Publish HTML reports** Post-build Action to nicely display API
compatibility breakage, without requiring that we read the actual
build log output.
jonpryor pushed a commit that referenced this issue May 21, 2020
#4643)

Changes: xamarin/monodroid@5849ea1...e795bce

  * xamarin/monodroid@e795bcef3: Bump to xamarin/androidtools@739afe5 (#1095)
  * xamarin/monodroid@97451721c: [tools/msbuild] add $(_AndroidAllowDeltaInstall) (#1089)

Add ***Experimental*** "`.apk` delta installation" support.

*What do we want?!*  Faster `.apk` installs!  (See also PR #4690.)

The question, as ever, is *how* to reduce the time of `.apk` installs,
and what the tradeoffs are.  Fast dev, which removes assemblies from
the `.apk`, is one way to do that; PR #4690 is "fastdev v2", which does
more there.

But for everything else in the `.apk` -- Android Assets, Resources, and
more -- how do we make deploying it faster?

Here is one way.

Android Studio contains an [`installer`][0] utility, built for each
supported Android target platform, which is installed onto the target
device as `/data/local/tmp/.studio/bin/installer`.  `installer` works
in terms of "protocol buffers", and can *in place update* an `.apk`
file installed on the Android target via a "delta" between the
currently installed `.apk` and the "to be installed" `.apk`.
`installer` deals with *just* `.apk` contents, and thus doesn't
special-case Android Assets, Resources, or IL assemblies.

As the `installer` utility is Apache 2 licensed, Xamarin.Android can
redistribute and use the `installer` utility as well.

To use `installer` to deploy `.apk` updates:

 1. Use a Xamarin.Android install which contains `installer`
    integration, e.g. via `make make prepare-external-git-dependencies`
    or via a master AzDO-hosted build.

 2. Install an app:

        msbuild /t:Install samples/HelloWorld/HelloWorld.csproj

 3. Make a change, e.g. by editing
    `samples/HelloWorld/Resources/layout/Main.axml`.

 4. Install the app, enabling use of this new feature:

         msbuild /t:Install samples/HelloWorld/HelloWorld.csproj /p:_AndroidAllowDeltaInstall=True 

     This triggers the following in the code:

     a. Create the `.apk` to deploy, "as normal".

     b. Check to see if `installer` is present on the Android target.
        If not, deploy to `/data/local/tmp/.studio/bin/installer`.         
        This happens optimistically, by trying to start up
	`installer`, looking for certain error codes that indicate the
	installer isn't present, then installing `installer` if needed.

     c. Invoke the target's `installer` to obtain the contents of the
        *currently installed* `.apk` file.

     d. Compute a diff between (4.c) and the `.apk` in (4.a).

     e. Deploy the diff to the Android target.

     f. Invoke `installer` to apply the diff (4.e) to the installed
        `.apk`, updating its contents to that of (4.a).

     g. If this process fails for any reason, a "normal" `adb install`
        is performed.

This new workflow is only performed when:

  * The `$(_AndroidAllowDeltaInstall)` MSBuild Property is True
  * The App is *already deployed* to the Android target.
  * The Android target is running API-24 (Android v7.0) or later.

Some initial Install timing results for step (4), against a Pixel 3a.
Timings are total times, including the build, of which the deploy part
takes on the order of 1.5 - 2.5 sec or so:

| Test                                          |    Normal (s) |     Delta (s) |
|:----------------------------------------------|--------------:|--------------:|
| 18MB APK, fast deploy off, updated 1 assembly |           6.3 |           5.6 |
| 9MB APK, fast deploy on, updated 1 resource   |           5.6 |           5.3 |

[0]: https://android.googlesource.com/platform/tools/base/+/studio-master-dev/deploy/installer
jonpryor pushed a commit that referenced this issue May 26, 2020
#4643)

Changes: https://github.com/xamarin/monodroid/compare/52312f241428fc78f4d15baaa80b56f85a180427...8d51d0af0572db1583a8ab5ec095bec3046ae476

  * xamarin/monodroid@8d51d0af0: Bump to xamarin/androidtools/d16-7@767cfdfe (#1095)
  * xamarin/monodroid@a0fcae82e: [tools/msbuild] add $(_AndroidAllowDeltaInstall) (#1089)
  * xamarin/monodroid@781e564e5: [tests] Fix build from xamarin-android (#1093)

Add ***Experimental*** "`.apk` delta installation" support.

*What do we want?!*  Faster `.apk` installs!  (See also PR #4690.)

The question, as ever, is *how* to reduce the time of `.apk` installs,
and what the tradeoffs are.  Fast dev, which removes assemblies from
the `.apk`, is one way to do that; PR #4690 is "fastdev v2", which does
more there.

But for everything else in the `.apk` -- Android Assets, Resources, and
more -- how do we make deploying it faster?

Here is one way.

Android Studio contains an [`installer`][0] utility, built for each
supported Android target platform, which is installed onto the target
device as `/data/local/tmp/.studio/bin/installer`.  `installer` works
in terms of "protocol buffers", and can *in place update* an `.apk`
file installed on the Android target via a "delta" between the
currently installed `.apk` and the "to be installed" `.apk`.
`installer` deals with *just* `.apk` contents, and thus doesn't
special-case Android Assets, Resources, or IL assemblies.

As the `installer` utility is Apache 2 licensed, Xamarin.Android can
redistribute and use the `installer` utility as well.

To use `installer` to deploy `.apk` updates:

 1. Use a Xamarin.Android install which contains `installer`
    integration, e.g. via `make make prepare-external-git-dependencies`
    or via a master AzDO-hosted build.

 2. Install an app:

        msbuild /t:Install samples/HelloWorld/HelloWorld.csproj

 3. Make a change, e.g. by editing
    `samples/HelloWorld/Resources/layout/Main.axml`.

 4. Install the app, enabling use of this new feature:

         msbuild /t:Install samples/HelloWorld/HelloWorld.csproj /p:_AndroidAllowDeltaInstall=True

     This triggers the following in the code:

     a. Create the `.apk` to deploy, "as normal".

     b. Check to see if `installer` is present on the Android target.
        If not, deploy to `/data/local/tmp/.studio/bin/installer`.
        This happens optimistically, by trying to start up
	`installer`, looking for certain error codes that indicate the
	installer isn't present, then installing `installer` if needed.

     c. Invoke the target's `installer` to obtain the contents of the
        *currently installed* `.apk` file.

     d. Compute a diff between (4.c) and the `.apk` in (4.a).

     e. Deploy the diff to the Android target.

     f. Invoke `installer` to apply the diff (4.e) to the installed
        `.apk`, updating its contents to that of (4.a).

     g. If this process fails for any reason, a "normal" `adb install`
        is performed.

This new workflow is only performed when:

  * The `$(_AndroidAllowDeltaInstall)` MSBuild Property is True
  * The App is *already deployed* to the Android target.
  * The Android target is running API-24 (Android v7.0) or later.

Some initial Install timing results for step (4), against a Pixel 3a.
Timings are total times, including the build, of which the deploy part
takes on the order of 1.5 - 2.5 sec or so:

| Test                                          |    Normal (s) |     Delta (s) |
|:----------------------------------------------|--------------:|--------------:|
| 18MB APK, fast deploy off, updated 1 assembly |           6.3 |           5.6 |
| 9MB APK, fast deploy on, updated 1 resource   |           5.6 |           5.3 |

[0]: https://android.googlesource.com/platform/tools/base/+/studio-master-dev/deploy/installer
@ghost ghost locked as resolved and limited conversation to collaborators Jun 9, 2022
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
Area: xamarin-android Build Issues building the xamarin-android repo *itself*.
Projects
None yet
Development

No branches or pull requests

1 participant