diff --git a/Applications/SseServer/src/SseServer/Controllers/SseController.cs b/Applications/SseServer/src/SseServer/Controllers/SseController.cs index 569a06bbb6..deb1806f1f 100644 --- a/Applications/SseServer/src/SseServer/Controllers/SseController.cs +++ b/Applications/SseServer/src/SseServer/Controllers/SseController.cs @@ -1,5 +1,4 @@ -using Backbone.BuildingBlocks.API; -using Backbone.BuildingBlocks.Application.Abstractions.Infrastructure.UserContext; +using Backbone.BuildingBlocks.Application.Abstractions.Infrastructure.UserContext; using Backbone.Modules.Devices.Application.PushNotifications.Commands.DeleteDeviceRegistration; using Backbone.Modules.Devices.Application.PushNotifications.Commands.UpdateDeviceRegistration; using MediatR; @@ -25,7 +24,7 @@ public SseController(IEventQueue eventQueue, IUserContext userContext, IMediator [HttpGet("/api/v1/sse")] [Authorize] - public async Task Subscribe() + public async Task Subscribe(CancellationToken cancellationToken) { var address = _userContext.GetAddress().Value; @@ -34,7 +33,7 @@ await _mediator.Send(new UpdateDeviceRegistrationCommand Handle = "sse-handle", // this is just some dummy value; the SSE connector doesn't use it AppId = "sse-client", // this is just some dummy value; the SSE connector doesn't use it Platform = "sse" - }); + }, cancellationToken); Response.StatusCode = 200; Response.Headers.CacheControl = "no-cache"; @@ -56,8 +55,11 @@ await _mediator.Send(new UpdateDeviceRegistrationCommand } catch (ClientAlreadyRegisteredException) { - return BadRequest(HttpError.ForProduction("error.platform.sseClientAlreadyRegistered", - "An SSE client for your identity is already registered. You can only register once per identity.", "")); + // if it is already registered, everything is fine + } + catch (OperationCanceledException) + { + // this is expected when the client disconnects } catch (Exception ex) { @@ -66,10 +68,9 @@ await _mediator.Send(new UpdateDeviceRegistrationCommand finally { _eventQueue.Deregister(address); - await _mediator.Send(new DeleteDeviceRegistrationCommand()); + // we must NOT pass the cancellation token here, because otherwise the device registration would not be deleted in case the request was cancelled + await _mediator.Send(new DeleteDeviceRegistrationCommand(), CancellationToken.None); } - - return Ok(); } } diff --git a/Applications/SseServer/src/SseServer/Extensions/IServiceCollectionExtensions.cs b/Applications/SseServer/src/SseServer/Extensions/IServiceCollectionExtensions.cs index 8058bc0495..0a93c34720 100644 --- a/Applications/SseServer/src/SseServer/Extensions/IServiceCollectionExtensions.cs +++ b/Applications/SseServer/src/SseServer/Extensions/IServiceCollectionExtensions.cs @@ -65,7 +65,7 @@ public static void AddCustomAspNetCore(this IServiceCollection services, options.JsonSerializerOptions.DictionaryKeyPolicy = JsonNamingPolicy.CamelCase; }); - services.AddAuthentication().AddJwtBearer(options => + services.AddAuthentication().AddJwtBearer("default", options => { var privateKeyBytes = Convert.FromBase64String(configuration.Authentication.JwtSigningCertificate); #pragma warning disable SYSLIB0057 // The constructor is obsolete. But I didn't manage to get the suggested alternative to work. @@ -75,7 +75,13 @@ public static void AddCustomAspNetCore(this IServiceCollection services, options.TokenValidationParameters.ValidateIssuer = false; options.TokenValidationParameters.ValidateAudience = false; }); - services.AddAuthorization(); + + services.AddAuthorizationBuilder() + .AddDefaultPolicy("default", policy => + { + policy.AddAuthenticationSchemes("default"); + policy.RequireAuthenticatedUser(); + }); services.AddHttpContextAccessor(); diff --git a/Applications/SseServer/src/SseServer/Program.cs b/Applications/SseServer/src/SseServer/Program.cs index 8f88f495eb..6138e63518 100644 --- a/Applications/SseServer/src/SseServer/Program.cs +++ b/Applications/SseServer/src/SseServer/Program.cs @@ -13,7 +13,6 @@ using Backbone.Tooling.Extensions; using Microsoft.AspNetCore.HttpOverrides; using Microsoft.Extensions.Options; -using Microsoft.IdentityModel.Logging; using Serilog; using Serilog.Exceptions; using Serilog.Exceptions.Core; @@ -75,7 +74,7 @@ static WebApplication CreateApp(string[] args) ) .UseServiceProviderFactory(new AutofacServiceProviderFactory()); - ConfigureServices(builder.Services, builder.Configuration); + ConfigureServices(builder.Services, builder.Configuration, builder.Environment); var app = builder.Build(); Configure(app); @@ -88,7 +87,7 @@ static WebApplication CreateApp(string[] args) return app; } -static void ConfigureServices(IServiceCollection services, IConfiguration configuration) +static void ConfigureServices(IServiceCollection services, IConfiguration configuration, IWebHostEnvironment environment) { services.ConfigureAndValidate(configuration.Bind); @@ -117,6 +116,8 @@ static void ConfigureServices(IServiceCollection services, IConfiguration config options.KnownProxies.Clear(); }); + services.AddCustomIdentity(environment); + services.AddPushNotifications(parsedConfiguration.Modules.Devices.Infrastructure.PushNotifications); } @@ -141,16 +142,11 @@ static void Configure(WebApplication app) .AddCustomHeader("X-Frame-Options", "Deny") ); - if (app.Environment.IsDevelopment()) - IdentityModelEventSource.ShowPII = true; - app.UseAuthentication().UseAuthorization(); app.MapControllers(); app.MapHealthChecks("/health"); - - app.UseResponseCaching(); } static void LoadConfiguration(WebApplicationBuilder webApplicationBuilder, string[] strings) diff --git a/Modules/Devices/src/Devices.Infrastructure/PushNotifications/Connectors/Sse/SseMessageBuilder.cs b/Modules/Devices/src/Devices.Infrastructure/PushNotifications/Connectors/Sse/SseMessageBuilder.cs index 9e541cbab6..2f3a6d8197 100644 --- a/Modules/Devices/src/Devices.Infrastructure/PushNotifications/Connectors/Sse/SseMessageBuilder.cs +++ b/Modules/Devices/src/Devices.Infrastructure/PushNotifications/Connectors/Sse/SseMessageBuilder.cs @@ -1,5 +1,6 @@ using System.Net.Http.Json; using System.Text.Json.Serialization; +using System.Web; namespace Backbone.Modules.Devices.Infrastructure.PushNotifications.Connectors.Sse; @@ -16,7 +17,7 @@ public SseMessageBuilder(string recipient, string eventName) public HttpRequestMessage Build() { - var request = new HttpRequestMessage(HttpMethod.Post, $"{_recipient}/events") + var request = new HttpRequestMessage(HttpMethod.Post, $"{HttpUtility.UrlEncode(_recipient)}/events") { Content = JsonContent.Create(new EventPayload(_eventName)) };