Skip to content
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

WASM MSAL Configuration Not Correctly Supported #1453

Open
SeanC2222 opened this issue Apr 22, 2024 · 1 comment
Open

WASM MSAL Configuration Not Correctly Supported #1453

SeanC2222 opened this issue Apr 22, 2024 · 1 comment
Labels
input needed When an issue requires input or suggestions

Comments

@SeanC2222
Copy link

Describe the bug

In the MSAL backed Blazor WASM authentication packages, there exists an overloaded class the RemoteAuthenticationService.

This service implements the AuthenticationStateProvider and an IRemoteAuthenticationService<>.

The DI for this package abuses this a bit by casting the configured AuthenticationStateProvider to it's alternate interface form.

This doesn't play nicely with BUnit's configuration which simply adds a singleton definition for AuthenticationStateProvider for the Fake that doesn't implement both the interface and abstract class.

Example:
Testing this component:

Any component where the host program uses MSAL:

With this test:
Requires Package Reference:

    <PackageReference Include="Microsoft.Authentication.WebAssembly.Msal" Version="8.0.3" />
public class TestClass : Bunit.TestContext
{

    [Fact]
    public void Broken()
    {
        var authContext = this.AddTestAuthorization();

        this.Services.AddMsalAuthentication(options => { });

        // Demo to simply show the DI demand of a component
        var throws = this.Services.GetService<IRemoteAuthenticationService<RemoteAuthenticationState>>();
    }
}

Results in this output:

 TestClass.Broken
   Source: TestMe.cs line 9
   Duration: 949 ms

  Message: 
System.InvalidCastException : Unable to cast object of type 'Bunit.TestDoubles.FakeAuthenticationStateProvider' to type 'Microsoft.AspNetCore.Components.WebAssembly.Authentication.IRemoteAuthenticationService`1[Microsoft.AspNetCore.Components.WebAssembly.Authentication.RemoteAuthenticationState]'.

  Stack Trace: 
<>c__1`1.<AddAuthenticationStateProvider>b__1_0(IServiceProvider sp)
CallSiteRuntimeResolver.VisitFactory(FactoryCallSite factoryCallSite, RuntimeResolverContext context)
CallSiteVisitor`2.VisitCallSiteMain(ServiceCallSite callSite, TArgument argument)
CallSiteRuntimeResolver.VisitCache(ServiceCallSite callSite, RuntimeResolverContext context, ServiceProviderEngineScope serviceProviderEngine, RuntimeResolverLock lockType)
CallSiteRuntimeResolver.VisitScopeCache(ServiceCallSite callSite, RuntimeResolverContext context)
CallSiteVisitor`2.VisitCallSite(ServiceCallSite callSite, TArgument argument)
CallSiteRuntimeResolver.Resolve(ServiceCallSite callSite, ServiceProviderEngineScope scope)
<>c__DisplayClass2_0.<RealizeService>b__0(ServiceProviderEngineScope scope)
ServiceProvider.GetService(ServiceIdentifier serviceIdentifier, ServiceProviderEngineScope serviceProviderEngineScope)
ServiceProviderEngineScope.GetService(Type serviceType)
TestServiceProvider.GetServiceInternal(Type serviceType) line 159
TestServiceProvider.GetService(Type serviceType) line 151
TestServiceProvider.GetService[TService]() line 141
TestClass.Broken() line 15
RuntimeMethodHandle.InvokeMethod(Object target, Void** arguments, Signature sig, Boolean isConstructor)
MethodBaseInvoker.InvokeWithNoArgs(Object obj, BindingFlags invokeAttr)

Expected behavior:

Not triggering the cast error.

Version info:

  • bUnit version:
  • .NET Runtime and Blazor version:
  • OS type and version:

Additional context:

We're wrapping the BUnit FakeAuthenticationStateProvider in an extra layer that implements both the AuthenticationStateProvider and the IRemoteAuthenticationService which is working, but it also requires us taking the BUnit implementation out of the DI and sticking ours in based on this little insight. Not ideal.

Not sure what the right answer is for BUnit as BUnit targets all Blazor, and this is a WASM specific problem.

@egil
Copy link
Member

egil commented Apr 22, 2024

Thanks for reporting this. My initial take is that we won't be taking a dependency on an 3rd party package to implement a base type or interface from that.

However, I am open to adding to our fake Auth API in (non-breeding way) to enable your scenario in a way that feels natural.

Do you have any suggestions in this regard?

@egil egil added the input needed When an issue requires input or suggestions label May 3, 2024
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
input needed When an issue requires input or suggestions
Projects
None yet
Development

No branches or pull requests

2 participants