Skip to content

Stable Updates 20250618 #1159

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

Open
wants to merge 21 commits into
base: main
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
21 commits
Select commit Hold shift + click to select a range
325b6be
Stable Updates 20250610
jonathanpeppers Jun 10, 2025
4cf8252
Merge branch 'main' into dev/peppers/20250610
jonathanpeppers Jun 12, 2025
7cb828b
Update config.json
jonathanpeppers Jun 18, 2025
c3b39ac
Merge branch 'main' into dev/peppers/20250610
jonathanpeppers Jun 18, 2025
ce33e14
Update config.json
jonathanpeppers Jun 18, 2025
15dffdc
Update more files
jonathanpeppers Jun 19, 2025
ccbb8c6
published-namespaces.txt
jonathanpeppers Jun 19, 2025
e6c2be8
Ad missing `androidx.window`
jonathanpeppers Jun 19, 2025
62c2400
Update Extensions.cs
jonathanpeppers Jun 19, 2025
04f726b
Update files
jonathanpeppers Jun 19, 2025
4cb0efc
Fix AndroidX.WebKit.ChromiumLibBoundary
jonathanpeppers Jun 19, 2025
3bd7f24
Fix AndroidX.Wear.ProtoLayout.Expression.DynamicDataMap
jonathanpeppers Jun 19, 2025
9dc2b5a
Move troubleshooting to bottom
jonathanpeppers Jun 19, 2025
88df3d6
Fix Xamarin.GoogleAndroid.Libraries.Places.Widget.Listener.IPredictio…
jonathanpeppers Jun 19, 2025
e9e6f2a
Update AndroidX.WebKit.ChromiumLibBoundary.IWebViewBuilderBoundaryInt…
jonathanpeppers Jun 19, 2025
2c4eb08
Fix androidx.wear.protolayout.protolayout
jonathanpeppers Jun 19, 2025
ff38d95
Downgrade com.google.auto.value.auto-value
jonathanpeppers Jun 19, 2025
b30200c
"Freeze" com.google.auto.value.auto-value
jonathanpeppers Jun 19, 2025
e015970
Fixes from @DevronB
jonathanpeppers Jun 19, 2025
30e41fe
Update development-tips.md
jonathanpeppers Jun 19, 2025
3efc484
Fix io.grpc.grpc-api
jonathanpeppers Jun 20, 2025
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1,783 changes: 749 additions & 1,034 deletions cgmanifest.json

Large diffs are not rendered by default.

635 changes: 326 additions & 309 deletions config.json

Large diffs are not rendered by default.

1,306 changes: 642 additions & 664 deletions docs/artifact-list-with-versions.md

Large diffs are not rendered by default.

1,012 changes: 495 additions & 517 deletions docs/artifact-list.md

Large diffs are not rendered by default.

187 changes: 187 additions & 0 deletions docs/development-tips.md
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,43 @@

This is a collection of tasks you might want to do in this repository, and how to do them.

## Updating Packages

Initially, run:

```bash
dotnet cake -t:update-config
```

Which will lookup Java Maven dependencies and update the `config.json` file
with the latest versions.

To update other files in the repo, run:

```bash
dotnet cake utilities.cake -t=generate-component-governance
dotnet cake utilities.cake -t=generate-namespace-file
dotnet cake utilities.cake -t=list-artifacts
```

For PR descriptions, run:

```bash
dotnet cake utilities.cake -t=api-diff-markdown-info-pr
```

This outputs a bunch of lines like this, you can copy/paste into your PR description:

```md
========================================
api-diff-markdown-info-pr
========================================
1. `androidx.appcompat:appcompat` - 1.7.0 -> 1.7.1
2. `androidx.appcompat:appcompatresources` - 1.7.0 -> 1.7.1
3. `androidx.autofill:autofill` - 1.1.0 -> 1.3.0
4. `androidx.compose.animation:animation` - 1.7.8 -> 1.8.3
```

## Tagging and Releasing

When ready to release, tag a commit such as:
Expand Down Expand Up @@ -55,6 +92,156 @@ Then I released the package using the [AndroidX Push NuGet.org
pipeline][androidx-pipeline] and selected the appropriate branch by
selecting a specific build via `Resources > AndroidX`.

## Troubleshooting

This is an example list of problems and how to fix them.

### Example 1

```log
generated\androidx.webkit.webkit\obj\Debug\net8.0-android\generated\src\AndroidX.WebKit.ChromiumLibBoundary.IWebViewBuilderBoundaryInterface.cs(202,89):
error CS0535: 'WebViewBuilderBoundaryInterfaceConfig' does not implement interface member 'IConsumer.Accept(Object?)'
[generated\androidx.webkit.webkit\androidx.webkit.webkit.csproj]
```

In this case, the `WebViewBuilderBoundaryInterfaceConfig` class has:

```csharp
// Metadata.xml XPath method reference: path="/api/package[@name='org.chromium.support_lib_boundary']/class[@name='WebViewBuilderBoundaryInterface.Config']/method[@name='accept' and count(parameter)=1 and parameter[1][@type='java.util.function.BiConsumer<java.lang.Integer, java.lang.Object>']]"
[Register ("accept", "(Ljava/util/function/BiConsumer;)V", "GetAccept_Ljava_util_function_BiConsumer_Handler")]
public virtual unsafe void Accept (global::Java.Util.Functions.IBiConsumer? chromiumConfig)
```

Java can change the type of parameters on methods in type inheritance, while C# does *not* allow this.

In C#, the `IConsumer` interface requires:

```csharp
public virtual unsafe void Accept (global::Java.Lang.Object? chromiumConfig)
```

To fix this, I added `source\androidx.webkit\webkit\Additions\AndroidX.WebKit.ChromiumLibBoundary.IWebViewBuilderBoundaryInterface.cs`:

```csharp
namespace AndroidX.WebKit.ChromiumLibBoundary;

public partial class WebViewBuilderBoundaryInterfaceConfig
{
public virtual unsafe void Accept (Java.Lang.Object? chromiumConfig)
{
this.Accept ((Java.Util.Functions.IBiConsumer?) chromiumConfig);
}
}
```

### Example 2

```log
generated\androidx.wear.protolayout.protolayout-expression\obj\Release\net8.0-android\generated\src\AndroidX.Wear.ProtoLayout.Expression.DynamicDataMap.cs(136,44): error CS0111: Type 'DynamicDataMap' already defines a member called 'Get' with the same parameter types
generated\androidx.wear.protolayout.protolayout-expression\obj\Release\net8.0-android\generated\src\AndroidX.Wear.ProtoLayout.Expression.DynamicDataMap.cs(151,42): error CS0111: Type 'DynamicDataMap' already defines a member called 'Get' with the same parameter types
generated\androidx.wear.protolayout.protolayout-expression\obj\Release\net8.0-android\generated\src\AndroidX.Wear.ProtoLayout.Expression.DynamicDataMap.cs(166,44): error CS0111: Type 'DynamicDataMap' already defines a member called 'Get' with the same parameter types
generated\androidx.wear.protolayout.protolayout-expression\obj\Release\net8.0-android\generated\src\AndroidX.Wear.ProtoLayout.Expression.DynamicDataMap.cs(181,25): error CS0111: Type 'DynamicDataMap' already defines a member called 'Get' with the same parameter types
generated\androidx.wear.protolayout.protolayout-expression\obj\Release\net8.0-android\generated\src\AndroidX.Wear.ProtoLayout.Expression.DynamicDataMap.cs(196,45): error CS0111: Type 'DynamicDataMap' already defines a member called 'Get' with the same parameter types
generated\androidx.wear.protolayout.protolayout-expression\obj\Release\net8.0-android\generated\src\AndroidX.Wear.ProtoLayout.Expression.DynamicDataMap.cs(211,44): error CS0111: Type 'DynamicDataMap' already defines a member called 'Get' with the same parameter types
```

Java you can have multiple methods with the same name, parameters, and *different* return type. C# does not allow this.

So, in this case, I renamed the five methods in C#, so for example:

```csharp
// Metadata.xml XPath method reference: path="/api/package[@name='androidx.wear.protolayout.expression']/class[@name='DynamicDataMap']/method[@name='get' and count(parameter)=1 and parameter[1][@type='androidx.wear.protolayout.expression.DynamicDataKey<androidx.wear.protolayout.expression.DynamicBuilders.DynamicBool>']]"
[Register ("get", "(Landroidx/wear/protolayout/expression/DynamicDataKey;)Ljava/lang/Boolean;", "")]
public unsafe global::Java.Lang.Boolean? Get (global::AndroidX.Wear.ProtoLayout.Expression.DynamicDataKey key)
{
const string __id = "get.(Landroidx/wear/protolayout/expression/DynamicDataKey;)Ljava/lang/Boolean;";
try {
JniArgumentValue* __args = stackalloc JniArgumentValue [1];
__args [0] = new JniArgumentValue ((key == null) ? IntPtr.Zero : ((global::Java.Lang.Object) key).Handle);
var __rm = _members.InstanceMethods.InvokeNonvirtualObjectMethod (__id, this, __args);
return global::Java.Lang.Object.GetObject<global::Java.Lang.Boolean> (__rm.Handle, JniHandleOwnership.TransferLocalRef);
} finally {
global::System.GC.KeepAlive (key);
}
}
```

You can rename this to `GetBoolean` in `source\androidx.wear.protolayout\protolayout-expression\Transforms\Metadata.xml`, such as:

```xml
<attr
path="/api/package[@name='androidx.wear.protolayout.expression']/class[@name='DynamicDataMap']/method[@name='get' and count(parameter)=1 and parameter[1][@type='androidx.wear.protolayout.expression.DynamicDataKey&lt;androidx.wear.protolayout.expression.DynamicBuilders.DynamicBool&gt;']]"
name="managedName"
>
GetBoolean
</attr>
```

I did this for all five methods.

### Example 3

```log
generated\com.google.android.libraries.places.places\obj\Release\net8.0-android\generated\src\Xamarin.GoogleAndroid.Libraries.Places.Widget.Listener.IPredictionSelectionListener.cs(136,10): error CS0111: Type 'ErrorEventArgs' already defines a member called 'ErrorEventArgs' with the same parameter types
```

This means that more than C# `EventArgs` type is being generated for
two Java callback methods with the same name, in the same namespace.

To solve this, I added to `source\com.google.android.libraries.places\places\Transforms\Metadata.xml`:

```xml
<attr
path="/api/package[@name='com.google.android.libraries.places.widget.listener']/interface[@name='PredictionSelectionListener']/method[@name='onError' and count(parameter)=1 and parameter[1][@type='com.google.android.gms.common.api.Status']]"
name="argsType"
>
PredictionSelectionEventArgs
</attr>
```

### Example 4

```log
generated\io.grpc.grpc-api\obj\Debug\net8.0-android\generated\src\Xamarin.Grpc.LongGaugeMetricInstrument.cs(20,84):
error CS0738: 'LongGaugeMetricInstrument' does not implement interface member 'IMetricInstrument.OptionalLabelKeys'. 'LongGaugeMetricInstrument.OptionalLabelKeys' cannot implement 'IMetricInstrument.OptionalLabelKeys' because it does not have the matching return type of 'IList<string>'.
generated\io.grpc.grpc-api\obj\Debug\net8.0-android\generated\src\Xamarin.Grpc.LongGaugeMetricInstrument.cs(20,84):
error CS0738: 'LongGaugeMetricInstrument' does not implement interface member 'IMetricInstrument.RequiredLabelKeys'. 'LongGaugeMetricInstrument.RequiredLabelKeys' cannot implement 'IMetricInstrument.RequiredLabelKeys' because it does not have the matching return type of 'IList<string>'.
```

At first, I thought I could do something like:

```xml
<attr
path="/api/package[@name='io.grpc']/class[@name='LongGaugeMetricInstrument']/method[@name='getOptionalLabelKeys' and count(parameter)=0]"
name="managedReturn"
>
System.Collections.IList&gt;System.String&lt;
</attr>
```

But this results in the error:

```log
BINDINGSGENERATOR : error BG0000: System.ArgumentOutOfRangeException: length ('-15') must be a non-negative value. (Parameter 'length')
```

So, I'm not sure we support putting generic types in the `managedReturn` value.

So instead, I used a C# additions and an explicit interface implementation:

```csharp
using System.Collections.Generic;

namespace Xamarin.Grpc;

public partial class LongGaugeMetricInstrument
{
IList<string>? IMetricInstrument.OptionalLabelKeys => (IList<string>?) OptionalLabelKeys;

IList<string>? IMetricInstrument.RequiredLabelKeys => (IList<string>?) RequiredLabelKeys;
}
```

[1118]: https://github.com/dotnet/android-libraries/pull/1118
[androidx.security]: https://github.com/dotnet/android-libraries/tree/androidx.security
[androidx-pipeline]: https://devdiv.visualstudio.com/DevDiv/_build?definitionId=25324
49 changes: 4 additions & 45 deletions published-namespaces.txt
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,7 @@ Android.Gms.Ads.Preload
Android.Gms.Ads.Query
Android.Gms.Ads.Rewarded
Android.Gms.Ads.RewardedInterstitial
Android.Gms.Ads.Search
Android.Gms.Analytics
Android.Gms.Analytics.Ecommerce
Android.Gms.AppIndex
Expand Down Expand Up @@ -490,8 +491,6 @@ AndroidX.Legacy.Content
AndroidX.Legacy.Widget
AndroidX.Lifecycle
AndroidX.Lifecycle.Compose
AndroidX.Lifecycle.Internal
AndroidX.Lifecycle.Serialization
AndroidX.Lifecycle.ViewModels
AndroidX.Lifecycle.ViewModels.Compose
AndroidX.Lifecycle.ViewModels.Internal
Expand Down Expand Up @@ -597,9 +596,7 @@ AndroidX.MediaRouter.App
AndroidX.MediaRouter.Media
AndroidX.Navigation
AndroidX.Navigation.Compose
AndroidX.Navigation.Compose.Internal
AndroidX.Navigation.Fragment
AndroidX.Navigation.Internal
AndroidX.Navigation.Serialization
AndroidX.Navigation.UI
AndroidX.Paging
Expand Down Expand Up @@ -632,31 +629,20 @@ AndroidX.RecyclerView.Selection
AndroidX.RecyclerView.Widget
AndroidX.ResourceInspection.Annotation
AndroidX.Room
AndroidX.Room.Concurrent
AndroidX.Room.Coroutines
AndroidX.Room.Driver
AndroidX.Room.Guava
AndroidX.Room.Migration
AndroidX.Room.Paging
AndroidX.Room.RxJava3
AndroidX.Room.Util
AndroidX.SavedState
AndroidX.SavedState.Compose
AndroidX.SavedState.Compose.Serialization.Serializers
AndroidX.SavedState.Internal
AndroidX.SavedState.Serialization
AndroidX.SavedState.Serialization.Serializers
AndroidX.Security.Crypto
AndroidX.Slice
AndroidX.Slice.Builders
AndroidX.Slice.Compat
AndroidX.Slice.Core
AndroidX.Slice.Widget
AndroidX.SlidingPaneLayout.Widget
AndroidX.Sqlite
AndroidX.Sqlite.Db
AndroidX.Sqlite.Db.Framework
AndroidX.Sqlite.Driver
AndroidX.Sqlite.Util
AndroidX.Startup
AndroidX.SwipeRefreshLayout.Widget
Expand Down Expand Up @@ -1000,33 +986,15 @@ Google.Ads.InteractiveMedia.V3.Impl.Data
Google.Ads.Mediation
Google.Ads.Mediation.Admob
Google.Ads.Nonagon.Util.Logging.Csi
Google.Android.Gms.Ads
Google.Android.Gms.Ads.AdManager
Google.Android.Gms.Ads.AppOpen
Google.Android.Gms.Ads.Formats
Google.Android.Gms.Ads.H5
Google.Android.Gms.Ads.Initialization
Google.Android.Gms.Ads.Internal.Offline.Buffering
Google.Android.Gms.Ads.Internal.Util.Client
Google.Android.Gms.Ads.Interstitial
Google.Android.Gms.Ads.Mediation
Google.Android.Gms.Ads.Mediation.CustomEvent
Google.Android.Gms.Ads.Mediation.Rtb
Google.Android.Gms.Ads.NativeAd
Google.Android.Gms.Ads.Nonagon.SignalGeneration
Google.Android.Gms.Ads.Preload
Google.Android.Gms.Ads.Query
Google.Android.Gms.Ads.Rewarded
Google.Android.Gms.Ads.RewardedInterstitial
Google.Android.Gms.Common.SignatureVerification
Google.Android.Gms.IdentityCredentials
Google.Android.Gms.IdentityCredentials.Internal
Google.Android.Gms.IdentityCredentials.Provider
Google.Android.Gms.Maps.Internal
Google.Android.Gms.RecaptchaBase
Google.Android.Libraries.AppActions.Service
Google.Android.Libraries.Places.Api.Auth
Google.Android.Libraries.Places.Widget.Internal.AutoComplete.UI
Google.Android.Material.Animation
Google.Android.Material.AppBar
Google.Android.Material.Badge
Expand Down Expand Up @@ -1085,23 +1053,13 @@ Google.Android.Material.Transition
Google.Android.Material.Transition.Platform
Google.AndroidLibraries.BarHopper
Google.Api
Google.Apphosting.DataStore.Testing
Google.Assistant.AppActions.Suggestions
Google.Assistant.AppActions.Suggestions.Client
Google.Assistant.AppActions.Widgets
Google.Assistant.AppActions.Widgets.PinAppWidget
Google.AutoValue.Annotations
Google.AutoValue.Extension
Google.AutoValue.Extension.Memoized.Processor
Google.AutoValue.Extension.Serializable
Google.AutoValue.Extension.Serializable.Processor
Google.AutoValue.Extension.Serializable.Serializer
Google.AutoValue.Extension.Serializable.Serializer.Impl
Google.AutoValue.Extension.Serializable.Serializer.Interfaces
Google.AutoValue.Extension.Serializable.Serializer.Runtime
Google.AutoValue.Extension.ToPrettyString
Google.AutoValue.Extension.ToPrettyString.Processor
Google.AutoValue.Processor
Google.Cloud.Audit
Google.Cloud.Datastore.Core.Number
Google.Common.Util.Concurrent
Expand Down Expand Up @@ -1171,8 +1129,6 @@ Kotlin.Collections.Jdk8
Kotlin.Collections.Unsigned
Kotlin.Comparisons
Kotlin.Concurrent
Kotlin.Concurrent.Atomics
Kotlin.Concurrent.Internal
Kotlin.Contracts
Kotlin.Coroutines
Kotlin.Coroutines.Cancellation
Expand Down Expand Up @@ -1497,7 +1453,9 @@ Xamarin.Google.MLKit.Vision.MediaPipe.Segmentation
Xamarin.Google.MLKit.Vision.MediaPipe.Utils
Xamarin.Google.MLKit.Vision.Objects
Xamarin.Google.MLKit.Vision.Objects.Custom
Xamarin.Google.MLKit.Vision.Objects.Custom.Internal
Xamarin.Google.MLKit.Vision.Objects.Defaults
Xamarin.Google.MLKit.Vision.Objects.Defaults.Internal
Xamarin.Google.MLKit.Vision.Objects.Internal
Xamarin.Google.MLKit.Vision.Pose
Xamarin.Google.MLKit.Vision.Pose.Accurate
Expand Down Expand Up @@ -1533,6 +1491,7 @@ Xamarin.GoogleAndroid.TV.Ads
Xamarin.GoogleAndroid.TV.Ads.Controls
Xamarin.Grpc
Xamarin.Grpc.Android
Xamarin.Grpc.Core.InProcess
Xamarin.Grpc.Core.Internal
Xamarin.Grpc.Core.Util
Xamarin.Grpc.OkHttp
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,48 @@
>
Java.Lang.Object
</attr>
<attr
path="/api/package[@name='androidx.wear.protolayout.expression']/class[@name='DynamicDataMap']/method[@name='get' and count(parameter)=1 and parameter[1][@type='androidx.wear.protolayout.expression.DynamicDataKey&lt;androidx.wear.protolayout.expression.DynamicBuilders.DynamicColor&gt;']]"
name="managedName"
>
GetColor
</attr>
<attr
path="/api/package[@name='androidx.wear.protolayout.expression']/class[@name='DynamicDataMap']/method[@name='get' and count(parameter)=1 and parameter[1][@type='androidx.wear.protolayout.expression.DynamicDataKey&lt;androidx.wear.protolayout.expression.DynamicBuilders.DynamicBool&gt;']]"
name="managedName"
>
GetBoolean
</attr>
<attr
path="/api/package[@name='androidx.wear.protolayout.expression']/class[@name='DynamicDataMap']/method[@name='get' and count(parameter)=1 and parameter[1][@type='androidx.wear.protolayout.expression.DynamicDataKey&lt;androidx.wear.protolayout.expression.DynamicBuilders.DynamicFloat&gt;']]"
name="managedName"
>
GetFloat
</attr>
<attr
path="/api/package[@name='androidx.wear.protolayout.expression']/class[@name='DynamicDataMap']/method[@name='get' and count(parameter)=1 and parameter[1][@type='androidx.wear.protolayout.expression.DynamicDataKey&lt;androidx.wear.protolayout.expression.DynamicBuilders.DynamicInt32&gt;']]"
name="managedName"
>
GetInteger
</attr>
<attr
path="/api/package[@name='androidx.wear.protolayout.expression']/class[@name='DynamicDataMap']/method[@name='get' and count(parameter)=1 and parameter[1][@type='androidx.wear.protolayout.expression.DynamicDataKey&lt;androidx.wear.protolayout.expression.DynamicBuilders.DynamicString&gt;']]"
name="managedName"
>
GetString
</attr>
<attr
path="/api/package[@name='androidx.wear.protolayout.expression']/class[@name='DynamicDataMap']/method[@name='get' and count(parameter)=1 and parameter[1][@type='androidx.wear.protolayout.expression.DynamicDataKey&lt;androidx.wear.protolayout.expression.DynamicBuilders.DynamicDuration&gt;']]"
name="managedName"
>
GetDuration
</attr>
<attr
path="/api/package[@name='androidx.wear.protolayout.expression']/class[@name='DynamicDataMap']/method[@name='get' and count(parameter)=1 and parameter[1][@type='androidx.wear.protolayout.expression.DynamicDataKey&lt;androidx.wear.protolayout.expression.DynamicBuilders.DynamicInstant&gt;']]"
name="managedName"
>
GetInstant
</attr>

<remove-node
path="/api/package[@name='androidx.wear.protolayout.expression']/interface[@name='DynamicBuilders.DynamicZonedDateTime']"
Expand Down
Loading