Add authentication support with login/logout UI
- Introduced AuthService, IAuthApiClient, and AuthApiClient for managing authentication state and API calls (login, logout, session restore). - Added Login.razor and LoginLayout.razor for the login page, including styling and logic. - MainLayout.razor now checks authentication on load, restores sessions from sessionStorage, and redirects to /login if unauthenticated. Displays username and logout button when logged in. - Implemented JS interop (authStorage) for persisting authentication info in sessionStorage. - Registered AuthService, CookieContainer, and API clients in Program.cs to share cookies and support authentication. - Updated AppSettings and appsettings files to support separate ApiBaseUrl and DataApiBaseUrl. - Minor CSS improvements for username display in the top bar.
This commit is contained in:
@@ -2,6 +2,7 @@ using DbFirst.BlazorWebApp;
|
||||
using DbFirst.BlazorWebApp.Components;
|
||||
using DbFirst.BlazorWebApp.Services;
|
||||
using DevExpress.Blazor;
|
||||
using System.Net;
|
||||
|
||||
var builder = WebApplication.CreateBuilder(args);
|
||||
|
||||
@@ -12,19 +13,45 @@ builder.Services.AddRazorComponents()
|
||||
builder.Services.AddDevExpressBlazor(options => options.BootstrapVersion = BootstrapVersion.v5);
|
||||
builder.Services.AddScoped<ThemeState>();
|
||||
builder.Services.AddScoped<BandLayoutService>();
|
||||
builder.Services.AddScoped<AuthService>();
|
||||
builder.Services.AddScoped<CookieContainer>();
|
||||
|
||||
builder.Services.Configure<AppSettings>(builder.Configuration);
|
||||
var appSettings = builder.Configuration.Get<AppSettings>() ?? new AppSettings();
|
||||
void ConfigureClient(HttpClient client)
|
||||
|
||||
// Alle API-Clients teilen sich denselben scoped CookieContainer (pro Blazor-Circuit),
|
||||
// damit das Auth-Cookie nach dem Login automatisch an alle Folgeanfragen angehängt wird.
|
||||
static HttpClient CreateHttpClientWithCookies(CookieContainer cookieContainer, string? baseUrl)
|
||||
{
|
||||
if (!string.IsNullOrWhiteSpace(appSettings.ApiBaseUrl))
|
||||
client.BaseAddress = new Uri(appSettings.ApiBaseUrl);
|
||||
var handler = new HttpClientHandler { CookieContainer = cookieContainer, UseCookies = true };
|
||||
var client = new HttpClient(handler);
|
||||
if (!string.IsNullOrWhiteSpace(baseUrl))
|
||||
client.BaseAddress = new Uri(baseUrl);
|
||||
return client;
|
||||
}
|
||||
|
||||
builder.Services.AddHttpClient<ICatalogApiClient, CatalogApiClient>(ConfigureClient);
|
||||
builder.Services.AddHttpClient<IDashboardApiClient, DashboardApiClient>(ConfigureClient);
|
||||
builder.Services.AddHttpClient<IMassDataApiClient, MassDataApiClient>(ConfigureClient);
|
||||
builder.Services.AddHttpClient<ILayoutApiClient, LayoutApiClient>(ConfigureClient);
|
||||
builder.Services.AddScoped<IAuthApiClient>(sp =>
|
||||
{
|
||||
var cc = sp.GetRequiredService<CookieContainer>();
|
||||
var client = CreateHttpClientWithCookies(cc, appSettings.ApiBaseUrl);
|
||||
return new AuthApiClient(client, sp.GetRequiredService<AuthService>(), cc);
|
||||
});
|
||||
|
||||
var dataApiBaseUrl = !string.IsNullOrWhiteSpace(appSettings.DataApiBaseUrl)
|
||||
? appSettings.DataApiBaseUrl
|
||||
: appSettings.ApiBaseUrl;
|
||||
|
||||
builder.Services.AddScoped<ICatalogApiClient>(sp =>
|
||||
new CatalogApiClient(CreateHttpClientWithCookies(sp.GetRequiredService<CookieContainer>(), dataApiBaseUrl)));
|
||||
|
||||
builder.Services.AddScoped<IDashboardApiClient>(sp =>
|
||||
new DashboardApiClient(CreateHttpClientWithCookies(sp.GetRequiredService<CookieContainer>(), dataApiBaseUrl)));
|
||||
|
||||
builder.Services.AddScoped<IMassDataApiClient>(sp =>
|
||||
new MassDataApiClient(CreateHttpClientWithCookies(sp.GetRequiredService<CookieContainer>(), dataApiBaseUrl)));
|
||||
|
||||
builder.Services.AddScoped<ILayoutApiClient>(sp =>
|
||||
new LayoutApiClient(CreateHttpClientWithCookies(sp.GetRequiredService<CookieContainer>(), dataApiBaseUrl)));
|
||||
|
||||
var app = builder.Build();
|
||||
|
||||
|
||||
Reference in New Issue
Block a user