BlazorWinFormsApp and BlazorWpfApp throw NullReferenceException when using ExampleJsInterop in .NET 6 Preview 3
See original GitHub issueDescribe the bug
If ExampleJsInterop is called from WinForms or from WPF it throws a NullReferenceException
To Reproduce
In WinForms:
-
open https://github.com/dotnet/aspnetcore/tree/main/src/Components/WebView/Samples/BlazorWinFormsApp
-
Form1.cs
, addWebviewAppShared.ExampleJsInterop exampleJsInterop;
toclass Form1
-
add
exampleJsInterop.Prompt("Hello world!");
tobutton1_Click
-
add
serviceCollection.AddScoped<WebviewAppShared.ExampleJsInterop>();
belowvar serviceCollection = new ServiceCollection();
-
replace
blazorWebView1.Services = serviceCollection.BuildServiceProvider();
withIServiceProvider serviceProvider = serviceCollection.BuildServiceProvider(); blazorWebView1.Services = serviceProvider; exampleJsInterop = serviceProvider.GetRequiredService<WebviewAppShared.ExampleJsInterop>();
-
run app
-
click on
Click to see counter value
In WPF:
-
open https://github.com/dotnet/aspnetcore/tree/main/src/Components/WebView/Samples/BlazorWpfApp
-
MainWindow.xaml.cs
, addWebviewAppShared.ExampleJsInterop exampleJsInterop;
toclass MainWindow
-
add
exampleJsInterop.Prompt("Hello world!");
toButton_Click
-
add
serviceCollection.AddScoped<WebviewAppShared.ExampleJsInterop>();
belowvar serviceCollection = new ServiceCollection();
-
replace
Resources.Add("services", serviceCollection.BuildServiceProvider());
withIServiceProvider serviceProvider = serviceCollection.BuildServiceProvider(); Resources.Add("services", serviceProvider); exampleJsInterop = serviceProvider.GetRequiredService<WebviewAppShared.ExampleJsInterop>();
-
run app
-
click on
Check counter
Exceptions (if any)
System.NullReferenceException: 'Object reference not set to an instance of an object.'
Further technical details
- ASP.NET Core version:
16.10.127.22515
- The IDE (VS / VS Code/ VS4Mac) you’re running on, and its version:
Visual Studio 2019 - Version 16.10.0 Preview 1.0
- Include the output of
dotnet --info
.NET SDK (reflecting any global.json):
Version: 6.0.100-preview.3.21202.5
Commit: aee38a6dd4
Runtime Environment:
OS Name: Windows
OS Version: 6.3.9600
OS Platform: Windows
RID: win81-x64
Base Path: C:\Program Files\dotnet\sdk\6.0.100-preview.3.21202.5\
Host (useful for support):
Version: 6.0.0-preview.3.21201.4
Commit: 236cb21e3c
.NET SDKs installed:
3.1.406 [C:\Program Files\dotnet\sdk]
5.0.200-preview.21077.7 [C:\Program Files\dotnet\sdk]
5.0.201 [C:\Program Files\dotnet\sdk]
6.0.100-preview.3.21202.5 [C:\Program Files\dotnet\sdk]
.NET runtimes installed:
Microsoft.AspNetCore.App 3.1.7 [C:\Program Files\dotnet\shared\Microsoft.AspNe
tCore.App]
Microsoft.AspNetCore.App 3.1.9 [C:\Program Files\dotnet\shared\Microsoft.AspNe
tCore.App]
Microsoft.AspNetCore.App 3.1.12 [C:\Program Files\dotnet\shared\Microsoft.AspN
etCore.App]
Microsoft.AspNetCore.App 3.1.13 [C:\Program Files\dotnet\shared\Microsoft.AspN
etCore.App]
Microsoft.AspNetCore.App 5.0.2 [C:\Program Files\dotnet\shared\Microsoft.AspNe
tCore.App]
Microsoft.AspNetCore.App 5.0.4 [C:\Program Files\dotnet\shared\Microsoft.AspNe
tCore.App]
Microsoft.AspNetCore.App 6.0.0-preview.3.21201.13 [C:\Program Files\dotnet\sha
red\Microsoft.AspNetCore.App]
Microsoft.NETCore.App 3.1.7 [C:\Program Files\dotnet\shared\Microsoft.NETCore.
App]
Microsoft.NETCore.App 3.1.9 [C:\Program Files\dotnet\shared\Microsoft.NETCore.
App]
Microsoft.NETCore.App 3.1.12 [C:\Program Files\dotnet\shared\Microsoft.NETCore
.App]
Microsoft.NETCore.App 3.1.13 [C:\Program Files\dotnet\shared\Microsoft.NETCore
.App]
Microsoft.NETCore.App 5.0.2 [C:\Program Files\dotnet\shared\Microsoft.NETCore.
App]
Microsoft.NETCore.App 5.0.4 [C:\Program Files\dotnet\shared\Microsoft.NETCore.
App]
Microsoft.NETCore.App 6.0.0-preview.3.21201.4 [C:\Program Files\dotnet\shared\
Microsoft.NETCore.App]
Microsoft.WindowsDesktop.App 3.1.9 [C:\Program Files\dotnet\shared\Microsoft.W
indowsDesktop.App]
Microsoft.WindowsDesktop.App 3.1.12 [C:\Program Files\dotnet\shared\Microsoft.
WindowsDesktop.App]
Microsoft.WindowsDesktop.App 3.1.13 [C:\Program Files\dotnet\shared\Microsoft.
WindowsDesktop.App]
Microsoft.WindowsDesktop.App 5.0.2 [C:\Program Files\dotnet\shared\Microsoft.W
indowsDesktop.App]
Microsoft.WindowsDesktop.App 5.0.4 [C:\Program Files\dotnet\shared\Microsoft.W
indowsDesktop.App]
Microsoft.WindowsDesktop.App 6.0.0-preview.3.21201.3 [C:\Program Files\dotnet\
shared\Microsoft.WindowsDesktop.App]
To install additional .NET runtimes or SDKs:
https://aka.ms/dotnet-download
Issue Analytics
- State:
- Created 2 years ago
- Comments:16 (12 by maintainers)
@Eilon The slightly awkward thing is that, each time the page inside the BlazorWebView reloads, we set up a new scope. We have to do that because (for example) you have a new JS context with no pre-existing state so we have to reset everything to do with it. It’s like reloading the page with WebAssembly or Server - those create new DI contexts too.
So given this, if some code outside that system asks for a scope, which scope does it get? One that might become obsolete later if the page is reloaded? Kind of dangerous, but represents the truth about what’s going on.
We could address this simply by exposing some
IServiceProvider? CurrentPageServices { get; set; }
property from WebViewManager whose value may be null (if no page has yet loaded) or may change (if the page navigates) and then trust the developer to understand this and not store a reference to the instance anywhere. TBH this is probably not too bad really.Alternatively we could have some kind of
RunAsync(Func<IServiceProvider, Task>)
method on WebViewManager that’s some kind of combo of “dispatch” and “give me the current service provider” to encourage people to treat it as a transient thing. Not sure people will follow the reasoning though.What do you think?
Turned out to be a non-issue, so this issue doesn’t seem to be related to my changes in JS Interop.