xamarin/Xamarin.Forms

[Bug] binding expression behavior changed in v4.2, StackOverflow exception from bindings that depend on the constructor having completed

Open

#9,272 opened on Jan 21, 2020

View on GitHub
 (4 comments) (1 reaction) (0 assignees)C# (5,644 stars) (1,926 forks)batch import
4.2.0a/binding ⛓a/listviewe/5 :clock5:help wantedi/highi/regressiont/bug :bug:up-for-grabs

Description

Description

I don't think this is an actionable bug, but I wanted to document this in case anyone else encounters the same issue:

We recently upgraded from v4.1.0 to v4.4.0, and started getting a StackOverflow exception.

I bisected the cause down to this pull request in v4.2.0-pre2 "Don't force binding expression applications to queue" #6857

The issue was that one of our binding expressions involved Autofac, where we're resolving a registered element as a side-effect of that same element's constructor via InitializeComponent().

Before, when binding expressions were queued, this worked because in the first iteration the component's construction completed, the Autofac registration was saved, then in the next iteration the previously saved Autofac registration was resolved. Effectively construction, Autofac registration, and Xamarin.Forms element initialization were all separate actions.

After, when now the binding expressions are all executed immediately, the call to the element's constructor is still being executed when the request to Autofac is made, so the registration hasn't been saved yet. Effectively now construction and Xamarin.Forms element initialization happen in the same call-stack, so any code in bindings that depends on the constructor having completed will have different behavior.

I don't think this is a bug because the Xamarin.Forms recommended pattern has always been to call InitializeComponent() in the constructor, but it took me a long time to track down this issue because the change was for this seemingly unrelated bug: "[Bug, CollectionView] SelectionChangedCommand invoked before SelectedItem is set" #6609

Interestingly, that bug still appears to be an issue in v4.4.0 for ListView's at least - We're seeing the SelectedItem is still set to the previous value when the ListView's ItemSelected event is triggered.

Basic Information

  • Version with issue: 4.2.0.618605-pre2
  • Last known good version: 4.2.0.608146-pre1

Workaround

In our case we manually queued updating the Autofac'd property that the binding was dependent on, but the specific workarounds for each scenario will vary.

Contributor guide