.NET 8 Blazor Interactive WebAssembly HttpClient 和身份问题

问题描述 投票:0回答:1

这就是我创建项目的方式

Solution creation

到目前为止我已经:

  • 为项目添加了角色,他们正在研究FE和BE,例如我已经将特定用户添加到角色中,如果用户有角色,则在 FE 上渲染内容,如果用户有角色,则可以直接访问 BE 端点 = 浏览器发送请求,这样就可以了。

我的问题是 HttpClient 或 HttpClientFactory 注册,到目前为止我所做的:

  • 我已将控制器添加到BE项目中
  • 我添加了HttpClient服务注册(但是这次必须添加到BE中——由于交互性......)

我的下一步是使用 HTTP 通信的通用解决方案,例如就我而言,我已经编写了自己的,但是让我们以 refit 为例,如何注册 refit 并在 FE 中使用它?

问题是,在客户端,由于交互性,你不能像以前一样注册它,因为它必须在 BE 上

builder.Services.AddHttpClient("WebAPI", client =>
    client.BaseAddress = new Uri(builder.HostEnvironment.BaseAddress)

现在怎么办?我的场景非常复杂,这就是我想要实现的目标:

  • 我想要BE API
  • 我想要 FE WebAssembly
  • 我想要一个用 Razor 组件编写的新身份实现
  • 我想在 FE 上使用 HttpClientFactory 实现通用 HttpClient,以便从 BE 访问数据
  • 我想保留身份验证和授权,并让用户仅访问他们拥有角色的部分,但这也必须包含在 HttpClient 中
  • 稍后,我想添加更多应用程序,例如.NET MAUI 使用我现有的 API。

最后,我确实阅读了很多有关渲染模式和其他所有内容的内容,我发现以当前的心态很难实现我的目标,任何建议和具体答案将非常感激。

.net blazor asp.net-identity blazor-webassembly dotnet-httpclient
1个回答
0
投票

我有一组与您非常相似的要求,虽然这不完全是答案,而不仅仅是评论,但这就是我所学到的。

将所有 WASM 页面移至 WASM 客户端

Project Sdk="Microsoft.NET.Sdk.BlazorWebAssembly"
,并将所有可共享组件移至 Razor 组件库
Project Sdk="Microsoft.NET.Sdk.Razor"
。然后通过 Web 服务器的程序将它们导入到 Web 服务器
Project Sdk="Microsoft.NET.Sdk.Web"
...

builder.Services
    .AddRazorComponents()
    .AddInteractiveServerComponents()
    .AddInteractiveWebAssemblyComponents();
...
...
app.AddInteractiveServerRenderMode()
.AddInteractiveWebAssemblyRenderMode()
.AddAdditionalAssemblies(
    typeof(Client._Imports).Assembly //the client ProjectReference's the shared if needed. 
);

航线也需要进口...

<Router AppAssembly="@typeof(WebProgram).Assembly" AdditionalAssemblies="new[] { 
        typeof(Client._Imports).Assembly,
    }">
...

在客户的程序中,您需要...

builder.Services.AddHttpClient<HttpClient>("aNamedClient",
    getClientConfiguration(Configuration.GetSection("TheConfig")))
    .AddHttpMessageHandler<ApplicationIdentityCookieHandler>();

注意,

getClientConfiguration
仅从 appsettings.json 配置 http 客户端的路径和主机 -
ApplicationIdentityCookieHandler
是其中的重要部分。它是客户端应用程序将 Identity cookie 获取到 HttpClient 请求中的方式。我的看起来像...

private class ApplicationIdentityCookieHandler : DelegatingHandler
{
    protected override async Task<HttpResponseMessage> SendAsync(HttpRequestMessage request, CancellationToken cancellationToken)
    {

        request.SetBrowserRequestCredentials(BrowserRequestCredentials.Include); // get that cookie
        request.SetBrowserRequestMode(BrowserRequestMode.Cors); // allow it to go to the api. 
        return await base.SendAsync(request, cancellationToken);
    }
}

您还需要在 Web 服务器中执行相同的操作,但不要将

ApplicationIdentityCookieHandler
添加到 http 客户端。这是因为 Blazor Web App 的渲染方式 -
@rendermode RenderMode.InteractiveWebAssembly
不会立即在 WASM 中启动,服务器首先处理渲染它,然后再将控制权传递给 WASM 运行时。这有一个额外的警告,如果服务器尝试调用受身份保护的 Web API 端点,它将失败并显示 40[1/3] - 我正在尝试为此找到更好的解决方案。这在评论中已注明——您必须在两侧添加 http 客户端服务。

跨 FE 和 BE 的身份要求您:

  • 配置 API 和 Web 服务器以使用相同的 AuthNZ 和应用程序 Cookie 配置
builder.Services.AddAuthorization(...);
builder.Services.AddAuthentication(...);
builder.Services.ConfigureApplicationCookie(...); 
  • 在 API 和 Web 服务器中配置数据保护以使用相同的密钥
var dataProtect = builder.Services.AddDataProtection();
dataProtect
    .PersistKeysToFileSystem(new DirectoryInfo(keyPersistencePath))
    .SetApplicationName(applicationName);
  • 配置 CORS,以便 API 期望服务器调用它们
builder.Services.AddCors(setupAction=> ...);
© www.soinside.com 2019 - 2024. All rights reserved.