From 7222d95025615e0f33faf6c50ff193e7b63cc1dd Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?K=C3=A9vin=20Chalet?= Date: Tue, 19 Apr 2022 16:40:15 +0200 Subject: [PATCH] React to the removal of the !! operator in C# 11 --- global.json | 7 +- .../Helpers/AsyncEnumerableExtensions.cs | 7 +- .../Helpers/OpenIddictHelpers.cs | 12 +- .../OpenIddictBuilder.cs | 4 +- .../OpenIddictExtensions.cs | 23 +- .../Primitives/OpenIddictConverter.cs | 38 +- .../Primitives/OpenIddictExtensions.cs | 400 ++++++++++++--- .../Primitives/OpenIddictMessage.cs | 42 +- .../Primitives/OpenIddictParameter.cs | 7 +- .../OpenIddictClientAspNetCoreBuilder.cs | 11 +- ...OpenIddictClientAspNetCoreConfiguration.cs | 21 +- .../OpenIddictClientAspNetCoreExtensions.cs | 19 +- .../OpenIddictClientAspNetCoreHandler.cs | 16 +- ...penIddictClientAspNetCoreHandlerFilters.cs | 56 +- ...ClientAspNetCoreHandlers.Authentication.cs | 7 +- .../OpenIddictClientAspNetCoreHandlers.cs | 92 +++- .../OpenIddictClientAspNetCoreHelpers.cs | 56 +- .../OpenIddictClientOwinBuilder.cs | 11 +- .../OpenIddictClientOwinConfiguration.cs | 14 +- .../OpenIddictClientOwinExtensions.cs | 19 +- .../OpenIddictClientOwinHandler.cs | 8 +- .../OpenIddictClientOwinHandlerFilters.cs | 41 +- ...IddictClientOwinHandlers.Authentication.cs | 7 +- .../OpenIddictClientOwinHandlers.cs | 85 +++- .../OpenIddictClientOwinHelpers.cs | 67 ++- .../OpenIddictClientOwinMiddleware.cs | 10 +- .../OpenIddictClientOwinMiddlewareFactory.cs | 7 +- .../OpenIddictClientSystemNetHttpBuilder.cs | 11 +- ...nIddictClientSystemNetHttpConfiguration.cs | 18 +- ...OpenIddictClientSystemNetHttpExtensions.cs | 19 +- ...IddictClientSystemNetHttpHandlerFilters.cs | 14 +- ...ictClientSystemNetHttpHandlers.Exchange.cs | 7 +- ...ictClientSystemNetHttpHandlers.Userinfo.cs | 14 +- .../OpenIddictClientSystemNetHttpHandlers.cs | 58 ++- .../OpenIddictClientBuilder.cs | 153 +++++- .../OpenIddictClientConfiguration.cs | 9 +- .../OpenIddictClientDispatcher.cs | 19 +- .../OpenIddictClientEvents.cs | 4 +- .../OpenIddictClientExtensions.cs | 19 +- .../OpenIddictClientFactory.cs | 8 +- .../OpenIddictClientHandler.cs | 7 +- .../OpenIddictClientHandlerDescriptor.cs | 65 ++- .../OpenIddictClientHandlerFilters.cs | 209 ++++++-- ...OpenIddictClientHandlers.Authentication.cs | 91 +++- .../OpenIddictClientHandlers.Discovery.cs | 105 +++- .../OpenIddictClientHandlers.Exchange.cs | 7 +- .../OpenIddictClientHandlers.Protection.cs | 49 +- .../OpenIddictClientHandlers.Userinfo.cs | 14 +- .../OpenIddictClientHandlers.cs | 481 +++++++++++++++--- .../OpenIddictClientHelpers.cs | 14 +- .../OpenIddictClientRetriever.cs | 7 +- .../OpenIddictClientService.cs | 53 +- .../Caches/OpenIddictApplicationCache.cs | 43 +- .../Caches/OpenIddictAuthorizationCache.cs | 43 +- .../Caches/OpenIddictScopeCache.cs | 45 +- .../Caches/OpenIddictTokenCache.cs | 43 +- .../Managers/OpenIddictApplicationManager.cs | 332 +++++++++--- .../OpenIddictAuthorizationManager.cs | 275 ++++++++-- .../Managers/OpenIddictScopeManager.cs | 276 ++++++++-- .../Managers/OpenIddictTokenManager.cs | 323 +++++++++--- src/OpenIddict.Core/OpenIddictCoreBuilder.cs | 123 ++++- .../OpenIddictCoreExtensions.cs | 19 +- .../OpenIddictApplicationStoreResolver.cs | 4 +- .../OpenIddictAuthorizationStoreResolver.cs | 4 +- .../Resolvers/OpenIddictScopeStoreResolver.cs | 4 +- .../Resolvers/OpenIddictTokenStoreResolver.cs | 4 +- .../OpenIddictEntityFrameworkBuilder.cs | 18 +- .../OpenIddictEntityFrameworkExtensions.cs | 19 +- .../OpenIddictEntityFrameworkHelpers.cs | 14 +- ...EntityFrameworkApplicationStoreResolver.cs | 12 +- ...tityFrameworkAuthorizationStoreResolver.cs | 12 +- ...IddictEntityFrameworkScopeStoreResolver.cs | 12 +- ...IddictEntityFrameworkTokenStoreResolver.cs | 12 +- ...enIddictEntityFrameworkApplicationStore.cs | 249 +++++++-- ...IddictEntityFrameworkAuthorizationStore.cs | 198 +++++-- .../OpenIddictEntityFrameworkScopeStore.cs | 187 +++++-- .../OpenIddictEntityFrameworkTokenStore.cs | 280 ++++++++-- ...tyFrameworkCoreApplicationConfiguration.cs | 7 +- ...FrameworkCoreAuthorizationConfiguration.cs | 7 +- ...ctEntityFrameworkCoreScopeConfiguration.cs | 7 +- ...ctEntityFrameworkCoreTokenConfiguration.cs | 7 +- .../OpenIddictEntityFrameworkCoreBuilder.cs | 18 +- ...OpenIddictEntityFrameworkCoreCustomizer.cs | 12 +- ...OpenIddictEntityFrameworkCoreExtensions.cs | 19 +- .../OpenIddictEntityFrameworkCoreHelpers.cs | 29 +- ...tyFrameworkCoreApplicationStoreResolver.cs | 12 +- ...FrameworkCoreAuthorizationStoreResolver.cs | 12 +- ...ctEntityFrameworkCoreScopeStoreResolver.cs | 12 +- ...ctEntityFrameworkCoreTokenStoreResolver.cs | 12 +- ...dictEntityFrameworkCoreApplicationStore.cs | 255 ++++++++-- ...ctEntityFrameworkCoreAuthorizationStore.cs | 196 +++++-- ...OpenIddictEntityFrameworkCoreScopeStore.cs | 193 +++++-- ...OpenIddictEntityFrameworkCoreTokenStore.cs | 282 ++++++++-- .../OpenIddictMongoDbBuilder.cs | 18 +- .../OpenIddictMongoDbContext.cs | 8 +- .../OpenIddictMongoDbExtensions.cs | 19 +- .../OpenIddictMongoDbHelpers.cs | 18 +- ...enIddictMongoDbApplicationStoreResolver.cs | 4 +- ...IddictMongoDbAuthorizationStoreResolver.cs | 4 +- .../OpenIddictMongoDbScopeStoreResolver.cs | 4 +- .../OpenIddictMongoDbTokenStoreResolver.cs | 4 +- .../OpenIddictMongoDbApplicationStore.cs | 289 +++++++++-- .../OpenIddictMongoDbAuthorizationStore.cs | 189 +++++-- .../Stores/OpenIddictMongoDbScopeStore.cs | 200 ++++++-- .../Stores/OpenIddictMongoDbTokenStore.cs | 262 ++++++++-- .../OpenIddictQuartzBuilder.cs | 11 +- .../OpenIddictQuartzConfiguration.cs | 7 +- .../OpenIddictQuartzExtensions.cs | 19 +- src/OpenIddict.Quartz/OpenIddictQuartzJob.cs | 13 +- .../OpenIddictServerAspNetCoreBuilder.cs | 33 +- ...OpenIddictServerAspNetCoreConfiguration.cs | 28 +- .../OpenIddictServerAspNetCoreExtensions.cs | 19 +- .../OpenIddictServerAspNetCoreHandler.cs | 23 +- ...penIddictServerAspNetCoreHandlerFilters.cs | 163 ++++-- ...ServerAspNetCoreHandlers.Authentication.cs | 61 ++- ...enIddictServerAspNetCoreHandlers.Device.cs | 7 +- ...nIddictServerAspNetCoreHandlers.Session.cs | 54 +- .../OpenIddictServerAspNetCoreHandlers.cs | 153 +++++- .../OpenIddictServerAspNetCoreHelpers.cs | 60 ++- .../OpenIddictServerDataProtectionBuilder.cs | 33 +- ...IddictServerDataProtectionConfiguration.cs | 16 +- ...penIddictServerDataProtectionExtensions.cs | 19 +- ...OpenIddictServerDataProtectionFormatter.cs | 31 +- ...ServerDataProtectionHandlers.Protection.cs | 15 +- .../OpenIddictServerOwinBuilder.cs | 33 +- .../OpenIddictServerOwinConfiguration.cs | 14 +- .../OpenIddictServerOwinExtensions.cs | 19 +- .../OpenIddictServerOwinHandler.cs | 8 +- .../OpenIddictServerOwinHandlerFilters.cs | 148 ++++-- ...IddictServerOwinHandlers.Authentication.cs | 71 ++- .../OpenIddictServerOwinHandlers.Device.cs | 7 +- .../OpenIddictServerOwinHandlers.Session.cs | 59 ++- .../OpenIddictServerOwinHandlers.cs | 132 ++++- .../OpenIddictServerOwinHelpers.cs | 71 ++- .../OpenIddictServerOwinMiddleware.cs | 10 +- .../OpenIddictServerOwinMiddlewareFactory.cs | 7 +- .../OpenIddictServerBuilder.cs | 333 ++++++++++-- .../OpenIddictServerConfiguration.cs | 7 +- .../OpenIddictServerDispatcher.cs | 19 +- .../OpenIddictServerEvents.cs | 4 +- .../OpenIddictServerExtensions.cs | 19 +- .../OpenIddictServerFactory.cs | 8 +- .../OpenIddictServerHandler.cs | 7 +- .../OpenIddictServerHandlerDescriptor.cs | 65 ++- .../OpenIddictServerHandlerFilters.cs | 429 +++++++++++++--- ...OpenIddictServerHandlers.Authentication.cs | 237 +++++++-- .../OpenIddictServerHandlers.Device.cs | 186 +++++-- .../OpenIddictServerHandlers.Discovery.cs | 172 +++++-- .../OpenIddictServerHandlers.Exchange.cs | 237 +++++++-- .../OpenIddictServerHandlers.Introspection.cs | 159 ++++-- .../OpenIddictServerHandlers.Protection.cs | 129 ++++- .../OpenIddictServerHandlers.Revocation.cs | 152 ++++-- .../OpenIddictServerHandlers.Session.cs | 76 ++- .../OpenIddictServerHandlers.Userinfo.cs | 83 ++- .../OpenIddictServerHandlers.cs | 385 ++++++++++---- .../OpenIddictServerHelpers.cs | 14 +- .../OpenIddictServerOptions.cs | 2 +- .../OpenIddictValidationAspNetCoreBuilder.cs | 11 +- ...IddictValidationAspNetCoreConfiguration.cs | 21 +- ...penIddictValidationAspNetCoreExtensions.cs | 19 +- .../OpenIddictValidationAspNetCoreHandler.cs | 16 +- ...ddictValidationAspNetCoreHandlerFilters.cs | 11 +- .../OpenIddictValidationAspNetCoreHandlers.cs | 74 ++- .../OpenIddictValidationAspNetCoreHelpers.cs | 60 ++- ...enIddictValidationDataProtectionBuilder.cs | 33 +- ...ctValidationDataProtectionConfiguration.cs | 20 +- ...ddictValidationDataProtectionExtensions.cs | 19 +- ...IddictValidationDataProtectionFormatter.cs | 7 +- ...dationDataProtectionHandlers.Protection.cs | 4 +- .../OpenIddictValidationOwinBuilder.cs | 11 +- .../OpenIddictValidationOwinConfiguration.cs | 7 +- .../OpenIddictValidationOwinExtensions.cs | 19 +- .../OpenIddictValidationOwinHandler.cs | 8 +- .../OpenIddictValidationOwinHandlerFilters.cs | 11 +- .../OpenIddictValidationOwinHandlers.cs | 74 ++- .../OpenIddictValidationOwinHelpers.cs | 71 ++- .../OpenIddictValidationOwinMiddleware.cs | 10 +- ...enIddictValidationOwinMiddlewareFactory.cs | 7 +- ...ddictValidationServerIntegrationBuilder.cs | 12 +- ...alidationServerIntegrationConfiguration.cs | 18 +- ...ctValidationServerIntegrationExtensions.cs | 19 +- ...penIddictValidationSystemNetHttpBuilder.cs | 11 +- ...ictValidationSystemNetHttpConfiguration.cs | 18 +- ...IddictValidationSystemNetHttpExtensions.cs | 19 +- ...ctValidationSystemNetHttpHandlerFilters.cs | 14 +- ...tionSystemNetHttpHandlers.Introspection.cs | 7 +- ...enIddictValidationSystemNetHttpHandlers.cs | 58 ++- .../OpenIddictValidationBuilder.cs | 102 +++- .../OpenIddictValidationConfiguration.cs | 11 +- .../OpenIddictValidationDispatcher.cs | 19 +- .../OpenIddictValidationEvents.cs | 4 +- .../OpenIddictValidationExtensions.cs | 21 +- .../OpenIddictValidationFactory.cs | 8 +- .../OpenIddictValidationHandler.cs | 7 +- .../OpenIddictValidationHandlerDescriptor.cs | 65 ++- .../OpenIddictValidationHandlerFilters.cs | 66 ++- .../OpenIddictValidationHandlers.Discovery.cs | 49 +- ...nIddictValidationHandlers.Introspection.cs | 49 +- ...OpenIddictValidationHandlers.Protection.cs | 102 +++- .../OpenIddictValidationHandlers.cs | 46 +- .../OpenIddictValidationHelpers.cs | 14 +- .../OpenIddictValidationOptions.cs | 2 +- .../OpenIddictValidationRetriever.cs | 7 +- .../OpenIddictValidationService.cs | 25 +- .../OpenIddictServerIntegrationTestClient.cs | 56 +- 205 files changed, 10158 insertions(+), 2443 deletions(-) diff --git a/global.json b/global.json index 6a633705..65a12775 100644 --- a/global.json +++ b/global.json @@ -1,17 +1,16 @@ { "sdk": { - "version": "7.0.100-preview.2.22153.17" + "version": "6.0.202" }, "tools": { - "dotnet": "7.0.100-preview.2.22153.17", + "dotnet": "6.0.202", "runtimes": { "aspnetcore": [ "2.1.28", "3.1.16", - "5.0.7", - "6.0.0" + "5.0.7" ] } }, diff --git a/sandbox/OpenIddict.Sandbox.AspNetCore.Server/Helpers/AsyncEnumerableExtensions.cs b/sandbox/OpenIddict.Sandbox.AspNetCore.Server/Helpers/AsyncEnumerableExtensions.cs index ac379075..946d35e7 100644 --- a/sandbox/OpenIddict.Sandbox.AspNetCore.Server/Helpers/AsyncEnumerableExtensions.cs +++ b/sandbox/OpenIddict.Sandbox.AspNetCore.Server/Helpers/AsyncEnumerableExtensions.cs @@ -2,8 +2,13 @@ public static class AsyncEnumerableExtensions { - public static Task> ToListAsync(this IAsyncEnumerable source!!) + public static Task> ToListAsync(this IAsyncEnumerable source) { + if (source is null) + { + throw new ArgumentNullException(nameof(source)); + } + return ExecuteAsync(); async Task> ExecuteAsync() diff --git a/shared/OpenIddict.Extensions/Helpers/OpenIddictHelpers.cs b/shared/OpenIddict.Extensions/Helpers/OpenIddictHelpers.cs index 0d3444e8..677a4d75 100644 --- a/shared/OpenIddict.Extensions/Helpers/OpenIddictHelpers.cs +++ b/shared/OpenIddict.Extensions/Helpers/OpenIddictHelpers.cs @@ -20,8 +20,18 @@ internal static class OpenIddictHelpers /// The type to introspect. /// The generic type definition. /// A instance if the base type was found, otherwise. - public static IEnumerable FindGenericBaseTypes(Type type!!, Type definition!!) + public static IEnumerable FindGenericBaseTypes(Type type, Type definition) { + if (type is null) + { + throw new ArgumentNullException(nameof(type)); + } + + if (definition is null) + { + throw new ArgumentNullException(nameof(definition)); + } + if (!definition.IsGenericTypeDefinition) { throw new ArgumentException(SR.GetResourceString(SR.ID0263), nameof(definition)); diff --git a/src/OpenIddict.Abstractions/OpenIddictBuilder.cs b/src/OpenIddict.Abstractions/OpenIddictBuilder.cs index e726618c..2cb4ec12 100644 --- a/src/OpenIddict.Abstractions/OpenIddictBuilder.cs +++ b/src/OpenIddict.Abstractions/OpenIddictBuilder.cs @@ -17,8 +17,8 @@ public class OpenIddictBuilder /// Initializes a new instance of . /// /// The services collection. - public OpenIddictBuilder(IServiceCollection services!!) - => Services = services; + public OpenIddictBuilder(IServiceCollection services) + => Services = services ?? throw new ArgumentNullException(nameof(services)); /// /// Gets the services collection. diff --git a/src/OpenIddict.Abstractions/OpenIddictExtensions.cs b/src/OpenIddict.Abstractions/OpenIddictExtensions.cs index 25025c78..1d30e8c3 100644 --- a/src/OpenIddict.Abstractions/OpenIddictExtensions.cs +++ b/src/OpenIddict.Abstractions/OpenIddictExtensions.cs @@ -17,8 +17,15 @@ public static class OpenIddictExtensions /// The services collection. /// This extension can be safely called multiple times. /// The . - public static OpenIddictBuilder AddOpenIddict(this IServiceCollection services!!) - => new OpenIddictBuilder(services); + public static OpenIddictBuilder AddOpenIddict(this IServiceCollection services) + { + if (services is null) + { + throw new ArgumentNullException(nameof(services)); + } + + return new OpenIddictBuilder(services); + } /// /// Provides a common entry point for registering the OpenIddict services. @@ -27,8 +34,18 @@ public static class OpenIddictExtensions /// The configuration delegate used to register new services. /// This extension can be safely called multiple times. /// The . - public static IServiceCollection AddOpenIddict(this IServiceCollection services!!, Action configuration!!) + public static IServiceCollection AddOpenIddict(this IServiceCollection services, Action configuration) { + if (services is null) + { + throw new ArgumentNullException(nameof(services)); + } + + if (configuration is null) + { + throw new ArgumentNullException(nameof(configuration)); + } + configuration(services.AddOpenIddict()); return services; diff --git a/src/OpenIddict.Abstractions/Primitives/OpenIddictConverter.cs b/src/OpenIddict.Abstractions/Primitives/OpenIddictConverter.cs index efa2c556..8c262337 100644 --- a/src/OpenIddict.Abstractions/Primitives/OpenIddictConverter.cs +++ b/src/OpenIddict.Abstractions/Primitives/OpenIddictConverter.cs @@ -19,10 +19,17 @@ public class OpenIddictConverter : JsonConverter /// /// The type to convert. /// if the type is supported, otherwise. - public override bool CanConvert(Type typeToConvert!!) - => typeToConvert == typeof(OpenIddictMessage) || - typeToConvert == typeof(OpenIddictRequest) || - typeToConvert == typeof(OpenIddictResponse); + public override bool CanConvert(Type typeToConvert) + { + if (typeToConvert is null) + { + throw new ArgumentNullException(nameof(typeToConvert)); + } + + return typeToConvert == typeof(OpenIddictMessage) || + typeToConvert == typeof(OpenIddictRequest) || + typeToConvert == typeof(OpenIddictResponse); + } /// /// Deserializes an instance. @@ -31,8 +38,13 @@ public class OpenIddictConverter : JsonConverter /// The type of the deserialized instance. /// The JSON serializer options. /// The deserialized instance. - public override OpenIddictMessage Read(ref Utf8JsonReader reader, Type typeToConvert!!, JsonSerializerOptions options) + public override OpenIddictMessage Read(ref Utf8JsonReader reader, Type typeToConvert, JsonSerializerOptions options) { + if (typeToConvert is null) + { + throw new ArgumentNullException(nameof(typeToConvert)); + } + using var document = JsonDocument.ParseValue(ref reader); return typeToConvert == typeof(OpenIddictMessage) ? new OpenIddictMessage(document.RootElement.Clone()) : @@ -47,6 +59,18 @@ public class OpenIddictConverter : JsonConverter /// The JSON writer. /// The instance. /// The JSON serializer options. - public override void Write(Utf8JsonWriter writer!!, OpenIddictMessage value!!, JsonSerializerOptions options) - => value.WriteTo(writer); + public override void Write(Utf8JsonWriter writer, OpenIddictMessage value, JsonSerializerOptions options) + { + if (writer is null) + { + throw new ArgumentNullException(nameof(writer)); + } + + if (value is null) + { + throw new ArgumentNullException(nameof(value)); + } + + value.WriteTo(writer); + } } diff --git a/src/OpenIddict.Abstractions/Primitives/OpenIddictExtensions.cs b/src/OpenIddict.Abstractions/Primitives/OpenIddictExtensions.cs index 28984294..d5cdd0e0 100644 --- a/src/OpenIddict.Abstractions/Primitives/OpenIddictExtensions.cs +++ b/src/OpenIddict.Abstractions/Primitives/OpenIddictExtensions.cs @@ -25,37 +25,70 @@ public static class OpenIddictExtensions /// Extracts the authentication context class values from an . /// /// The instance. - public static ImmutableArray GetAcrValues(this OpenIddictRequest request!!) - => GetValues(request.AcrValues, Separators.Space); + public static ImmutableArray GetAcrValues(this OpenIddictRequest request) + { + if (request is null) + { + throw new ArgumentNullException(nameof(request)); + } + + return GetValues(request.AcrValues, Separators.Space); + } /// /// Extracts the prompt values from an . /// /// The instance. - public static ImmutableArray GetPrompts(this OpenIddictRequest request!!) - => GetValues(request.Prompt, Separators.Space); + public static ImmutableArray GetPrompts(this OpenIddictRequest request) + { + if (request is null) + { + throw new ArgumentNullException(nameof(request)); + } + + return GetValues(request.Prompt, Separators.Space); + } /// /// Extracts the response types from an . /// /// The instance. - public static ImmutableArray GetResponseTypes(this OpenIddictRequest request!!) - => GetValues(request.ResponseType, Separators.Space); + public static ImmutableArray GetResponseTypes(this OpenIddictRequest request) + { + if (request is null) + { + throw new ArgumentNullException(nameof(request)); + } + + return GetValues(request.ResponseType, Separators.Space); + } /// /// Extracts the scopes from an . /// /// The instance. - public static ImmutableArray GetScopes(this OpenIddictRequest request!!) - => GetValues(request.Scope, Separators.Space); + public static ImmutableArray GetScopes(this OpenIddictRequest request) + { + if (request is null) + { + throw new ArgumentNullException(nameof(request)); + } + + return GetValues(request.Scope, Separators.Space); + } /// /// Determines whether the requested authentication context class values contain the specified item. /// /// The instance. /// The component to look for in the parameter. - public static bool HasAcrValue(this OpenIddictRequest request!!, string value) + public static bool HasAcrValue(this OpenIddictRequest request, string value) { + if (request is null) + { + throw new ArgumentNullException(nameof(request)); + } + if (string.IsNullOrEmpty(value)) { throw new ArgumentException(SR.GetResourceString(SR.ID0177), nameof(value)); @@ -69,8 +102,13 @@ public static class OpenIddictExtensions /// /// The instance. /// The component to look for in the parameter. - public static bool HasPrompt(this OpenIddictRequest request!!, string prompt) + public static bool HasPrompt(this OpenIddictRequest request, string prompt) { + if (request is null) + { + throw new ArgumentNullException(nameof(request)); + } + if (string.IsNullOrEmpty(prompt)) { throw new ArgumentException(SR.GetResourceString(SR.ID0178), nameof(prompt)); @@ -84,8 +122,13 @@ public static class OpenIddictExtensions /// /// The instance. /// The component to look for in the parameter. - public static bool HasResponseType(this OpenIddictRequest request!!, string type) + public static bool HasResponseType(this OpenIddictRequest request, string type) { + if (request is null) + { + throw new ArgumentNullException(nameof(request)); + } + if (string.IsNullOrEmpty(type)) { throw new ArgumentException(SR.GetResourceString(SR.ID0179), nameof(type)); @@ -99,8 +142,13 @@ public static class OpenIddictExtensions /// /// The instance. /// The component to look for in the parameter. - public static bool HasScope(this OpenIddictRequest request!!, string scope) + public static bool HasScope(this OpenIddictRequest request, string scope) { + if (request is null) + { + throw new ArgumentNullException(nameof(request)); + } + if (string.IsNullOrEmpty(scope)) { throw new ArgumentException(SR.GetResourceString(SR.ID0180), nameof(scope)); @@ -115,8 +163,13 @@ public static class OpenIddictExtensions /// /// The instance. /// if the request is a response_type=none request, otherwise. - public static bool IsNoneFlow(this OpenIddictRequest request!!) + public static bool IsNoneFlow(this OpenIddictRequest request) { + if (request is null) + { + throw new ArgumentNullException(nameof(request)); + } + if (string.IsNullOrEmpty(request.ResponseType)) { return false; @@ -137,8 +190,13 @@ public static class OpenIddictExtensions /// /// The instance. /// if the request is a code flow request, otherwise. - public static bool IsAuthorizationCodeFlow(this OpenIddictRequest request!!) + public static bool IsAuthorizationCodeFlow(this OpenIddictRequest request) { + if (request is null) + { + throw new ArgumentNullException(nameof(request)); + } + if (string.IsNullOrEmpty(request.ResponseType)) { return false; @@ -160,8 +218,13 @@ public static class OpenIddictExtensions /// /// The instance. /// if the request is an implicit flow request, otherwise. - public static bool IsImplicitFlow(this OpenIddictRequest request!!) + public static bool IsImplicitFlow(this OpenIddictRequest request) { + if (request is null) + { + throw new ArgumentNullException(nameof(request)); + } + if (string.IsNullOrEmpty(request.ResponseType)) { return false; @@ -209,8 +272,13 @@ public static class OpenIddictExtensions /// /// The instance. /// if the request is an hybrid flow request, otherwise. - public static bool IsHybridFlow(this OpenIddictRequest request!!) + public static bool IsHybridFlow(this OpenIddictRequest request) { + if (request is null) + { + throw new ArgumentNullException(nameof(request)); + } + if (string.IsNullOrEmpty(request.ResponseType)) { return false; @@ -271,8 +339,13 @@ public static class OpenIddictExtensions /// if the request specified the fragment response mode or if /// it's the default value for the requested flow, otherwise. /// - public static bool IsFragmentResponseMode(this OpenIddictRequest request!!) + public static bool IsFragmentResponseMode(this OpenIddictRequest request) { + if (request is null) + { + throw new ArgumentNullException(nameof(request)); + } + if (string.Equals(request.ResponseMode, ResponseModes.Fragment, StringComparison.Ordinal)) { return true; @@ -299,8 +372,13 @@ public static class OpenIddictExtensions /// if the request specified the query response mode or if /// it's the default value for the requested flow, otherwise. /// - public static bool IsQueryResponseMode(this OpenIddictRequest request!!) + public static bool IsQueryResponseMode(this OpenIddictRequest request) { + if (request is null) + { + throw new ArgumentNullException(nameof(request)); + } + if (string.Equals(request.ResponseMode, ResponseModes.Query, StringComparison.Ordinal)) { return true; @@ -326,8 +404,15 @@ public static class OpenIddictExtensions /// if the request specified the form post response mode or if /// it's the default value for the requested flow, otherwise. /// - public static bool IsFormPostResponseMode(this OpenIddictRequest request!!) - => string.Equals(request.ResponseMode, ResponseModes.FormPost, StringComparison.Ordinal); + public static bool IsFormPostResponseMode(this OpenIddictRequest request) + { + if (request is null) + { + throw new ArgumentNullException(nameof(request)); + } + + return string.Equals(request.ResponseMode, ResponseModes.FormPost, StringComparison.Ordinal); + } /// /// Determines whether the "grant_type" parameter corresponds to the authorization code grant. @@ -335,8 +420,15 @@ public static class OpenIddictExtensions /// /// The instance. /// if the request is a code grant request, otherwise. - public static bool IsAuthorizationCodeGrantType(this OpenIddictRequest request!!) - => string.Equals(request.GrantType, GrantTypes.AuthorizationCode, StringComparison.Ordinal); + public static bool IsAuthorizationCodeGrantType(this OpenIddictRequest request) + { + if (request is null) + { + throw new ArgumentNullException(nameof(request)); + } + + return string.Equals(request.GrantType, GrantTypes.AuthorizationCode, StringComparison.Ordinal); + } /// /// Determines whether the "grant_type" parameter corresponds to the client credentials grant. @@ -344,8 +436,15 @@ public static class OpenIddictExtensions /// /// The instance. /// if the request is a client credentials grant request, otherwise. - public static bool IsClientCredentialsGrantType(this OpenIddictRequest request!!) - => string.Equals(request.GrantType, GrantTypes.ClientCredentials, StringComparison.Ordinal); + public static bool IsClientCredentialsGrantType(this OpenIddictRequest request) + { + if (request is null) + { + throw new ArgumentNullException(nameof(request)); + } + + return string.Equals(request.GrantType, GrantTypes.ClientCredentials, StringComparison.Ordinal); + } /// /// Determines whether the "grant_type" parameter corresponds to the device code grant. @@ -353,8 +452,15 @@ public static class OpenIddictExtensions /// /// The instance. /// if the request is a device code grant request, otherwise. - public static bool IsDeviceCodeGrantType(this OpenIddictRequest request!!) - => string.Equals(request.GrantType, GrantTypes.DeviceCode, StringComparison.Ordinal); + public static bool IsDeviceCodeGrantType(this OpenIddictRequest request) + { + if (request is null) + { + throw new ArgumentNullException(nameof(request)); + } + + return string.Equals(request.GrantType, GrantTypes.DeviceCode, StringComparison.Ordinal); + } /// /// Determines whether the "grant_type" parameter corresponds to the password grant. @@ -362,8 +468,15 @@ public static class OpenIddictExtensions /// /// The instance. /// if the request is a password grant request, otherwise. - public static bool IsPasswordGrantType(this OpenIddictRequest request!!) - => string.Equals(request.GrantType, GrantTypes.Password, StringComparison.Ordinal); + public static bool IsPasswordGrantType(this OpenIddictRequest request) + { + if (request is null) + { + throw new ArgumentNullException(nameof(request)); + } + + return string.Equals(request.GrantType, GrantTypes.Password, StringComparison.Ordinal); + } /// /// Determines whether the "grant_type" parameter corresponds to the refresh token grant. @@ -371,16 +484,28 @@ public static class OpenIddictExtensions /// /// The instance. /// if the request is a refresh token grant request, otherwise. - public static bool IsRefreshTokenGrantType(this OpenIddictRequest request!!) - => string.Equals(request.GrantType, GrantTypes.RefreshToken, StringComparison.Ordinal); + public static bool IsRefreshTokenGrantType(this OpenIddictRequest request) + { + if (request is null) + { + throw new ArgumentNullException(nameof(request)); + } + + return string.Equals(request.GrantType, GrantTypes.RefreshToken, StringComparison.Ordinal); + } /// /// Gets the destinations associated with a claim. /// /// The instance. /// The destinations associated with the claim. - public static ImmutableArray GetDestinations(this Claim claim!!) + public static ImmutableArray GetDestinations(this Claim claim) { + if (claim is null) + { + throw new ArgumentNullException(nameof(claim)); + } + claim.Properties.TryGetValue(Properties.Destinations, out string? destinations); if (string.IsNullOrEmpty(destinations)) @@ -410,8 +535,13 @@ public static class OpenIddictExtensions /// /// The instance. /// The required destination. - public static bool HasDestination(this Claim claim!!, string destination) + public static bool HasDestination(this Claim claim, string destination) { + if (claim is null) + { + throw new ArgumentNullException(nameof(claim)); + } + if (string.IsNullOrEmpty(destination)) { throw new ArgumentException(SR.GetResourceString(SR.ID0181), nameof(destination)); @@ -443,8 +573,13 @@ public static class OpenIddictExtensions /// /// The instance. /// The destinations. - public static Claim SetDestinations(this Claim claim!!, ImmutableArray destinations) + public static Claim SetDestinations(this Claim claim, ImmutableArray destinations) { + if (claim is null) + { + throw new ArgumentNullException(nameof(claim)); + } + if (destinations.IsDefaultOrEmpty) { claim.Properties.Remove(Properties.Destinations); @@ -452,7 +587,7 @@ public static class OpenIddictExtensions return claim; } - if (destinations.Any(string.IsNullOrEmpty)) + if (destinations.Any(destination => string.IsNullOrEmpty(destination))) { throw new ArgumentException(SR.GetResourceString(SR.ID0182), nameof(destinations)); } @@ -500,8 +635,13 @@ public static class OpenIddictExtensions /// /// The principal. /// The destinations, returned as a flattened dictionary. - public static ImmutableDictionary GetDestinations(this ClaimsPrincipal principal!!) + public static ImmutableDictionary GetDestinations(this ClaimsPrincipal principal) { + if (principal is null) + { + throw new ArgumentNullException(nameof(principal)); + } + var builder = ImmutableDictionary.CreateBuilder(StringComparer.Ordinal); foreach (var group in principal.Claims.GroupBy(claim => claim.Type)) @@ -533,8 +673,18 @@ public static class OpenIddictExtensions /// The principal. /// The destinations, as a flattened dictionary. /// The principal. - public static ClaimsPrincipal SetDestinations(this ClaimsPrincipal principal!!, ImmutableDictionary destinations!!) + public static ClaimsPrincipal SetDestinations(this ClaimsPrincipal principal, ImmutableDictionary destinations) { + if (principal is null) + { + throw new ArgumentNullException(nameof(principal)); + } + + if (destinations is null) + { + throw new ArgumentNullException(nameof(destinations)); + } + foreach (var destination in destinations) { foreach (var claim in principal.Claims.Where(claim => claim.Type == destination.Key)) @@ -554,8 +704,18 @@ public static class OpenIddictExtensions /// The delegate filtering the claims: return /// to accept the claim, to remove it. /// - public static ClaimsIdentity Clone(this ClaimsIdentity identity!!, Func filter!!) + public static ClaimsIdentity Clone(this ClaimsIdentity identity, Func filter) { + if (identity is null) + { + throw new ArgumentNullException(nameof(identity)); + } + + if (filter is null) + { + throw new ArgumentNullException(nameof(filter)); + } + var clone = identity.Clone(); // Note: make sure to call ToList() to avoid modifying @@ -584,8 +744,18 @@ public static class OpenIddictExtensions /// The delegate filtering the claims: return /// to accept the claim, to remove it. /// - public static ClaimsPrincipal Clone(this ClaimsPrincipal principal!!, Func filter!!) + public static ClaimsPrincipal Clone(this ClaimsPrincipal principal, Func filter) { + if (principal is null) + { + throw new ArgumentNullException(nameof(principal)); + } + + if (filter is null) + { + throw new ArgumentNullException(nameof(filter)); + } + var clone = new ClaimsPrincipal(); foreach (var identity in principal.Identities) @@ -602,8 +772,13 @@ public static class OpenIddictExtensions /// The identity. /// The type associated with the claim. /// The value associated with the claim. - public static ClaimsIdentity AddClaim(this ClaimsIdentity identity!!, string type, string value) + public static ClaimsIdentity AddClaim(this ClaimsIdentity identity, string type, string value) { + if (identity is null) + { + throw new ArgumentNullException(nameof(identity)); + } + if (string.IsNullOrEmpty(type)) { throw new ArgumentException(SR.GetResourceString(SR.ID0184), nameof(type)); @@ -625,8 +800,13 @@ public static class OpenIddictExtensions /// The type associated with the claim. /// The value associated with the claim. /// The destinations associated with the claim. - public static ClaimsIdentity AddClaim(this ClaimsIdentity identity!!, string type, string value, ImmutableArray destinations) + public static ClaimsIdentity AddClaim(this ClaimsIdentity identity, string type, string value, ImmutableArray destinations) { + if (identity is null) + { + throw new ArgumentNullException(nameof(identity)); + } + if (string.IsNullOrEmpty(type)) { throw new ArgumentException(SR.GetResourceString(SR.ID0184), nameof(type)); @@ -657,8 +837,13 @@ public static class OpenIddictExtensions /// The identity. /// The type associated with the claim. /// The claim value. - public static string? GetClaim(this ClaimsIdentity identity!!, string type) + public static string? GetClaim(this ClaimsIdentity identity, string type) { + if (identity is null) + { + throw new ArgumentNullException(nameof(identity)); + } + if (string.IsNullOrEmpty(type)) { throw new ArgumentException(SR.GetResourceString(SR.ID0184), nameof(type)); @@ -673,8 +858,13 @@ public static class OpenIddictExtensions /// The principal. /// The type associated with the claim. /// The claim value. - public static string? GetClaim(this ClaimsPrincipal principal!!, string type) + public static string? GetClaim(this ClaimsPrincipal principal, string type) { + if (principal is null) + { + throw new ArgumentNullException(nameof(principal)); + } + if (string.IsNullOrEmpty(type)) { throw new ArgumentException(SR.GetResourceString(SR.ID0184), nameof(type)); @@ -689,8 +879,13 @@ public static class OpenIddictExtensions /// The identity. /// The type associated with the claims. /// The claim values. - public static ImmutableArray GetClaims(this ClaimsIdentity identity!!, string type) + public static ImmutableArray GetClaims(this ClaimsIdentity identity, string type) { + if (identity is null) + { + throw new ArgumentNullException(nameof(identity)); + } + if (string.IsNullOrEmpty(type)) { throw new ArgumentException(SR.GetResourceString(SR.ID0184), nameof(type)); @@ -705,8 +900,13 @@ public static class OpenIddictExtensions /// The claims identity. /// The claim type. /// if the identity contains at least one claim of the specified type. - public static bool HasClaim(this ClaimsIdentity identity!!, string type) + public static bool HasClaim(this ClaimsIdentity identity, string type) { + if (identity is null) + { + throw new ArgumentNullException(nameof(identity)); + } + if (string.IsNullOrEmpty(type)) { throw new ArgumentException(SR.GetResourceString(SR.ID0184), nameof(type)); @@ -721,8 +921,13 @@ public static class OpenIddictExtensions /// The principal. /// The type associated with the claims. /// The claim values. - public static ImmutableArray GetClaims(this ClaimsPrincipal principal!!, string type) + public static ImmutableArray GetClaims(this ClaimsPrincipal principal, string type) { + if (principal is null) + { + throw new ArgumentNullException(nameof(principal)); + } + if (string.IsNullOrEmpty(type)) { throw new ArgumentException(SR.GetResourceString(SR.ID0184), nameof(type)); @@ -737,8 +942,13 @@ public static class OpenIddictExtensions /// The claims principal. /// The claim type. /// if the principal contains at least one claim of the specified type. - public static bool HasClaim(this ClaimsPrincipal principal!!, string type) + public static bool HasClaim(this ClaimsPrincipal principal, string type) { + if (principal is null) + { + throw new ArgumentNullException(nameof(principal)); + } + if (string.IsNullOrEmpty(type)) { throw new ArgumentException(SR.GetResourceString(SR.ID0184), nameof(type)); @@ -753,8 +963,13 @@ public static class OpenIddictExtensions /// The identity. /// The type associated with the claims. /// The claims identity. - public static ClaimsIdentity RemoveClaims(this ClaimsIdentity identity!!, string type) + public static ClaimsIdentity RemoveClaims(this ClaimsIdentity identity, string type) { + if (identity is null) + { + throw new ArgumentNullException(nameof(identity)); + } + if (string.IsNullOrEmpty(type)) { throw new ArgumentException(SR.GetResourceString(SR.ID0184), nameof(type)); @@ -774,8 +989,13 @@ public static class OpenIddictExtensions /// The principal. /// The type associated with the claims. /// The claims identity. - public static ClaimsPrincipal RemoveClaims(this ClaimsPrincipal principal!!, string type) + public static ClaimsPrincipal RemoveClaims(this ClaimsPrincipal principal, string type) { + if (principal is null) + { + throw new ArgumentNullException(nameof(principal)); + } + if (string.IsNullOrEmpty(type)) { throw new ArgumentException(SR.GetResourceString(SR.ID0184), nameof(type)); @@ -799,8 +1019,13 @@ public static class OpenIddictExtensions /// The type associated with the claims. /// The claim value. /// The claims identity. - public static ClaimsIdentity SetClaims(this ClaimsIdentity identity!!, string type, string? value) + public static ClaimsIdentity SetClaims(this ClaimsIdentity identity, string type, string? value) { + if (identity is null) + { + throw new ArgumentNullException(nameof(identity)); + } + if (string.IsNullOrEmpty(type)) { throw new ArgumentException(SR.GetResourceString(SR.ID0184), nameof(type)); @@ -823,8 +1048,13 @@ public static class OpenIddictExtensions /// The type associated with the claims. /// The claim value. /// The claims identity. - public static ClaimsPrincipal SetClaim(this ClaimsPrincipal principal!!, string type, string? value) + public static ClaimsPrincipal SetClaim(this ClaimsPrincipal principal, string type, string? value) { + if (principal is null) + { + throw new ArgumentNullException(nameof(principal)); + } + if (principal.Identity is not ClaimsIdentity identity) { throw new ArgumentException(SR.GetResourceString(SR.ID0286), nameof(principal)); @@ -852,8 +1082,13 @@ public static class OpenIddictExtensions /// The type associated with the claims. /// The claim values. /// The claims identity. - public static ClaimsIdentity SetClaims(this ClaimsIdentity identity!!, string type, ImmutableArray values) + public static ClaimsIdentity SetClaims(this ClaimsIdentity identity, string type, ImmutableArray values) { + if (identity is null) + { + throw new ArgumentNullException(nameof(identity)); + } + if (string.IsNullOrEmpty(type)) { throw new ArgumentException(SR.GetResourceString(SR.ID0184), nameof(type)); @@ -876,8 +1111,13 @@ public static class OpenIddictExtensions /// The type associated with the claims. /// The claim values. /// The claims identity. - public static ClaimsPrincipal SetClaims(this ClaimsPrincipal principal!!, string type, ImmutableArray values) + public static ClaimsPrincipal SetClaims(this ClaimsPrincipal principal, string type, ImmutableArray values) { + if (principal is null) + { + throw new ArgumentNullException(nameof(principal)); + } + if (principal.Identity is not ClaimsIdentity identity) { throw new ArgumentException(SR.GetResourceString(SR.ID0286), nameof(principal)); @@ -903,8 +1143,13 @@ public static class OpenIddictExtensions /// /// The claims principal. /// The creation date or if the claim cannot be found. - public static DateTimeOffset? GetCreationDate(this ClaimsPrincipal principal!!) + public static DateTimeOffset? GetCreationDate(this ClaimsPrincipal principal) { + if (principal is null) + { + throw new ArgumentNullException(nameof(principal)); + } + var claim = principal.FindFirst(Claims.Private.CreationDate); if (claim is null) { @@ -924,8 +1169,13 @@ public static class OpenIddictExtensions /// /// The claims principal. /// The expiration date or if the claim cannot be found. - public static DateTimeOffset? GetExpirationDate(this ClaimsPrincipal principal!!) + public static DateTimeOffset? GetExpirationDate(this ClaimsPrincipal principal) { + if (principal is null) + { + throw new ArgumentNullException(nameof(principal)); + } + var claim = principal.FindFirst(Claims.Private.ExpirationDate); if (claim is null) { @@ -1058,8 +1308,13 @@ public static class OpenIddictExtensions /// The claims principal. /// The audience. /// if the principal contains the given audience. - public static bool HasAudience(this ClaimsPrincipal principal!!, string audience) + public static bool HasAudience(this ClaimsPrincipal principal, string audience) { + if (principal is null) + { + throw new ArgumentNullException(nameof(principal)); + } + if (string.IsNullOrEmpty(audience)) { throw new ArgumentException(SR.GetResourceString(SR.ID0186), nameof(audience)); @@ -1074,8 +1329,13 @@ public static class OpenIddictExtensions /// The claims principal. /// The presenter. /// if the principal contains the given presenter. - public static bool HasPresenter(this ClaimsPrincipal principal!!, string presenter) + public static bool HasPresenter(this ClaimsPrincipal principal, string presenter) { + if (principal is null) + { + throw new ArgumentNullException(nameof(principal)); + } + if (string.IsNullOrEmpty(presenter)) { throw new ArgumentException(SR.GetResourceString(SR.ID0187), nameof(presenter)); @@ -1090,8 +1350,13 @@ public static class OpenIddictExtensions /// The claims principal. /// The resource. /// if the principal contains the given resource. - public static bool HasResource(this ClaimsPrincipal principal!!, string resource) + public static bool HasResource(this ClaimsPrincipal principal, string resource) { + if (principal is null) + { + throw new ArgumentNullException(nameof(principal)); + } + if (string.IsNullOrEmpty(resource)) { throw new ArgumentException(SR.GetResourceString(SR.ID0062), nameof(resource)); @@ -1106,8 +1371,13 @@ public static class OpenIddictExtensions /// The claims principal. /// The scope. /// if the principal contains the given scope. - public static bool HasScope(this ClaimsPrincipal principal!!, string scope) + public static bool HasScope(this ClaimsPrincipal principal, string scope) { + if (principal is null) + { + throw new ArgumentNullException(nameof(principal)); + } + if (string.IsNullOrEmpty(scope)) { throw new ArgumentException(SR.GetResourceString(SR.ID0180), nameof(scope)); @@ -1122,8 +1392,13 @@ public static class OpenIddictExtensions /// The claims principal. /// The token type. /// if the token type matches the specified type. - public static bool HasTokenType(this ClaimsPrincipal principal!!, string type) + public static bool HasTokenType(this ClaimsPrincipal principal, string type) { + if (principal is null) + { + throw new ArgumentNullException(nameof(principal)); + } + if (string.IsNullOrEmpty(type)) { throw new ArgumentException(SR.GetResourceString(SR.ID0188), nameof(type)); @@ -1477,8 +1752,13 @@ public static class OpenIddictExtensions return false; } - private static TimeSpan? GetLifetime(ClaimsPrincipal principal!!, string type) + private static TimeSpan? GetLifetime(ClaimsPrincipal principal, string type) { + if (principal is null) + { + throw new ArgumentNullException(nameof(principal)); + } + var value = principal.GetClaim(type); if (string.IsNullOrEmpty(value)) { diff --git a/src/OpenIddict.Abstractions/Primitives/OpenIddictMessage.cs b/src/OpenIddict.Abstractions/Primitives/OpenIddictMessage.cs index 5649420b..dd6e897c 100644 --- a/src/OpenIddict.Abstractions/Primitives/OpenIddictMessage.cs +++ b/src/OpenIddict.Abstractions/Primitives/OpenIddictMessage.cs @@ -74,8 +74,13 @@ public class OpenIddictMessage /// /// The message parameters. /// Parameters with a null or empty key are always ignored. - public OpenIddictMessage(JsonObject parameters!!) + public OpenIddictMessage(JsonObject parameters) { + if (parameters is null) + { + throw new ArgumentNullException(nameof(parameters)); + } + foreach (var parameter in parameters) { // Ignore parameters whose name is null or empty. @@ -101,8 +106,13 @@ public class OpenIddictMessage /// /// The message parameters. /// Parameters with a null or empty key are always ignored. - public OpenIddictMessage(IEnumerable> parameters!!) + public OpenIddictMessage(IEnumerable> parameters) { + if (parameters is null) + { + throw new ArgumentNullException(nameof(parameters)); + } + foreach (var parameter in parameters) { // Ignore parameters whose name is null or empty. @@ -120,8 +130,13 @@ public class OpenIddictMessage /// /// The message parameters. /// Parameters with a null or empty key are always ignored. - public OpenIddictMessage(IEnumerable> parameters!!) + public OpenIddictMessage(IEnumerable> parameters) { + if (parameters is null) + { + throw new ArgumentNullException(nameof(parameters)); + } + foreach (var parameter in parameters.GroupBy(parameter => parameter.Key)) { // Ignore parameters whose name is null or empty. @@ -150,8 +165,13 @@ public class OpenIddictMessage /// /// The message parameters. /// Parameters with a null or empty key are always ignored. - public OpenIddictMessage(IEnumerable> parameters!!) + public OpenIddictMessage(IEnumerable> parameters) { + if (parameters is null) + { + throw new ArgumentNullException(nameof(parameters)); + } + foreach (var parameter in parameters) { // Ignore parameters whose name is null or empty. @@ -178,8 +198,13 @@ public class OpenIddictMessage /// /// The message parameters. /// Parameters with a null or empty key are always ignored. - public OpenIddictMessage(IEnumerable> parameters!!) + public OpenIddictMessage(IEnumerable> parameters) { + if (parameters is null) + { + throw new ArgumentNullException(nameof(parameters)); + } + foreach (var parameter in parameters) { // Ignore parameters whose name is null or empty. @@ -387,8 +412,13 @@ public class OpenIddictMessage /// Writes the message to the specified JSON writer. /// /// The UTF-8 JSON writer. - public void WriteTo(Utf8JsonWriter writer!!) + public void WriteTo(Utf8JsonWriter writer) { + if (writer is null) + { + throw new ArgumentNullException(nameof(writer)); + } + writer.WriteStartObject(); foreach (var parameter in Parameters) diff --git a/src/OpenIddict.Abstractions/Primitives/OpenIddictParameter.cs b/src/OpenIddict.Abstractions/Primitives/OpenIddictParameter.cs index 2f741d24..4f061d9c 100644 --- a/src/OpenIddict.Abstractions/Primitives/OpenIddictParameter.cs +++ b/src/OpenIddict.Abstractions/Primitives/OpenIddictParameter.cs @@ -695,8 +695,13 @@ public readonly struct OpenIddictParameter : IEquatable /// Writes the parameter value to the specified JSON writer. /// /// The UTF-8 JSON writer. - public void WriteTo(Utf8JsonWriter writer!!) + public void WriteTo(Utf8JsonWriter writer) { + if (writer is null) + { + throw new ArgumentNullException(nameof(writer)); + } + switch (Value) { // Note: undefined JsonElement values are assimilated to null values. diff --git a/src/OpenIddict.Client.AspNetCore/OpenIddictClientAspNetCoreBuilder.cs b/src/OpenIddict.Client.AspNetCore/OpenIddictClientAspNetCoreBuilder.cs index 4c6efa0f..f2453edd 100644 --- a/src/OpenIddict.Client.AspNetCore/OpenIddictClientAspNetCoreBuilder.cs +++ b/src/OpenIddict.Client.AspNetCore/OpenIddictClientAspNetCoreBuilder.cs @@ -20,8 +20,8 @@ public class OpenIddictClientAspNetCoreBuilder /// Initializes a new instance of . /// /// The services collection. - public OpenIddictClientAspNetCoreBuilder(IServiceCollection services!!) - => Services = services; + public OpenIddictClientAspNetCoreBuilder(IServiceCollection services) + => Services = services ?? throw new ArgumentNullException(nameof(services)); /// /// Gets the services collection. @@ -35,8 +35,13 @@ public class OpenIddictClientAspNetCoreBuilder /// The delegate used to configure the OpenIddict options. /// This extension can be safely called multiple times. /// The . - public OpenIddictClientAspNetCoreBuilder Configure(Action configuration!!) + public OpenIddictClientAspNetCoreBuilder Configure(Action configuration) { + if (configuration is null) + { + throw new ArgumentNullException(nameof(configuration)); + } + Services.Configure(configuration); return this; diff --git a/src/OpenIddict.Client.AspNetCore/OpenIddictClientAspNetCoreConfiguration.cs b/src/OpenIddict.Client.AspNetCore/OpenIddictClientAspNetCoreConfiguration.cs index 6eeea964..349ae54f 100644 --- a/src/OpenIddict.Client.AspNetCore/OpenIddictClientAspNetCoreConfiguration.cs +++ b/src/OpenIddict.Client.AspNetCore/OpenIddictClientAspNetCoreConfiguration.cs @@ -19,8 +19,13 @@ public class OpenIddictClientAspNetCoreConfiguration : IConfigureOptions /// The options instance to initialize. - public void Configure(AuthenticationOptions options!!) + public void Configure(AuthenticationOptions options) { + if (options is null) + { + throw new ArgumentNullException(nameof(options)); + } + // If a handler was already registered and the type doesn't correspond to the OpenIddict handler, throw an exception. if (options.SchemeMap.TryGetValue(OpenIddictClientAspNetCoreDefaults.AuthenticationScheme, out var builder) && builder.HandlerType != typeof(OpenIddictClientAspNetCoreHandler)) @@ -32,8 +37,13 @@ public class OpenIddictClientAspNetCoreConfiguration : IConfigureOptions /// The authentication scheme associated with the handler instance. /// The options instance to initialize. - public void PostConfigure(string name, AuthenticationOptions options!!) + public void PostConfigure(string name, AuthenticationOptions options) { + if (options is null) + { + throw new ArgumentNullException(nameof(options)); + } + if (!TryValidate(options.SchemeMap, options.DefaultAuthenticateScheme) || !TryValidate(options.SchemeMap, options.DefaultScheme) || !TryValidate(options.SchemeMap, options.DefaultSignInScheme) || diff --git a/src/OpenIddict.Client.AspNetCore/OpenIddictClientAspNetCoreExtensions.cs b/src/OpenIddict.Client.AspNetCore/OpenIddictClientAspNetCoreExtensions.cs index b3df243b..d9f7e705 100644 --- a/src/OpenIddict.Client.AspNetCore/OpenIddictClientAspNetCoreExtensions.cs +++ b/src/OpenIddict.Client.AspNetCore/OpenIddictClientAspNetCoreExtensions.cs @@ -22,8 +22,13 @@ public static class OpenIddictClientAspNetCoreExtensions /// The services builder used by OpenIddict to register new services. /// This extension can be safely called multiple times. /// The . - public static OpenIddictClientAspNetCoreBuilder UseAspNetCore(this OpenIddictClientBuilder builder!!) + public static OpenIddictClientAspNetCoreBuilder UseAspNetCore(this OpenIddictClientBuilder builder) { + if (builder is null) + { + throw new ArgumentNullException(nameof(builder)); + } + builder.Services.AddAuthentication(); builder.Services.TryAddScoped(); @@ -59,8 +64,18 @@ public static class OpenIddictClientAspNetCoreExtensions /// This extension can be safely called multiple times. /// The . public static OpenIddictClientBuilder UseAspNetCore( - this OpenIddictClientBuilder builder!!, Action configuration!!) + this OpenIddictClientBuilder builder, Action configuration) { + if (builder is null) + { + throw new ArgumentNullException(nameof(builder)); + } + + if (configuration is null) + { + throw new ArgumentNullException(nameof(configuration)); + } + configuration(builder.UseAspNetCore()); return builder; diff --git a/src/OpenIddict.Client.AspNetCore/OpenIddictClientAspNetCoreHandler.cs b/src/OpenIddict.Client.AspNetCore/OpenIddictClientAspNetCoreHandler.cs index 3f40c751..3a1ab85f 100644 --- a/src/OpenIddict.Client.AspNetCore/OpenIddictClientAspNetCoreHandler.cs +++ b/src/OpenIddict.Client.AspNetCore/OpenIddictClientAspNetCoreHandler.cs @@ -27,16 +27,16 @@ public class OpenIddictClientAspNetCoreHandler : AuthenticationHandler class. /// public OpenIddictClientAspNetCoreHandler( - IOpenIddictClientDispatcher dispatcher!!, - IOpenIddictClientFactory factory!!, - IOptionsMonitor options!!, - ILoggerFactory logger!!, - UrlEncoder encoder!!, - ISystemClock clock!!) + IOpenIddictClientDispatcher dispatcher, + IOpenIddictClientFactory factory, + IOptionsMonitor options, + ILoggerFactory logger, + UrlEncoder encoder, + ISystemClock clock) : base(options, logger, encoder, clock) { - _dispatcher = dispatcher; - _factory = factory; + _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); + _factory = factory ?? throw new ArgumentNullException(nameof(factory)); } /// diff --git a/src/OpenIddict.Client.AspNetCore/OpenIddictClientAspNetCoreHandlerFilters.cs b/src/OpenIddict.Client.AspNetCore/OpenIddictClientAspNetCoreHandlerFilters.cs index 3d621dbd..6e7e87c6 100644 --- a/src/OpenIddict.Client.AspNetCore/OpenIddictClientAspNetCoreHandlerFilters.cs +++ b/src/OpenIddict.Client.AspNetCore/OpenIddictClientAspNetCoreHandlerFilters.cs @@ -24,11 +24,18 @@ public static class OpenIddictClientAspNetCoreHandlerFilters { private readonly IOptionsMonitor _options; - public RequireRedirectionEndpointPassthroughEnabled(IOptionsMonitor options!!) - => _options = options; + public RequireRedirectionEndpointPassthroughEnabled(IOptionsMonitor options) + => _options = options ?? throw new ArgumentNullException(nameof(options)); - public ValueTask IsActiveAsync(BaseContext context!!) - => new(_options.CurrentValue.EnableRedirectionEndpointPassthrough); + public ValueTask IsActiveAsync(BaseContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(_options.CurrentValue.EnableRedirectionEndpointPassthrough); + } } /// @@ -38,11 +45,18 @@ public static class OpenIddictClientAspNetCoreHandlerFilters { private readonly IOptionsMonitor _options; - public RequireErrorPassthroughEnabled(IOptionsMonitor options!!) - => _options = options; + public RequireErrorPassthroughEnabled(IOptionsMonitor options) + => _options = options ?? throw new ArgumentNullException(nameof(options)); + + public ValueTask IsActiveAsync(BaseContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } - public ValueTask IsActiveAsync(BaseContext context!!) - => new(_options.CurrentValue.EnableErrorPassthrough); + return new(_options.CurrentValue.EnableErrorPassthrough); + } } /// @@ -50,8 +64,15 @@ public static class OpenIddictClientAspNetCoreHandlerFilters /// public class RequireHttpRequest : IOpenIddictClientHandlerFilter { - public ValueTask IsActiveAsync(BaseContext context!!) - => new(context.Transaction.GetHttpRequest() is not null); + public ValueTask IsActiveAsync(BaseContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(context.Transaction.GetHttpRequest() is not null); + } } /// @@ -61,10 +82,17 @@ public static class OpenIddictClientAspNetCoreHandlerFilters { private readonly IOptionsMonitor _options; - public RequireStatusCodePagesIntegrationEnabled(IOptionsMonitor options!!) - => _options = options; + public RequireStatusCodePagesIntegrationEnabled(IOptionsMonitor options) + => _options = options ?? throw new ArgumentNullException(nameof(options)); + + public ValueTask IsActiveAsync(BaseContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } - public ValueTask IsActiveAsync(BaseContext context!!) - => new(_options.CurrentValue.EnableStatusCodePagesIntegration); + return new(_options.CurrentValue.EnableStatusCodePagesIntegration); + } } } diff --git a/src/OpenIddict.Client.AspNetCore/OpenIddictClientAspNetCoreHandlers.Authentication.cs b/src/OpenIddict.Client.AspNetCore/OpenIddictClientAspNetCoreHandlers.Authentication.cs index bddd8faa..19486616 100644 --- a/src/OpenIddict.Client.AspNetCore/OpenIddictClientAspNetCoreHandlers.Authentication.cs +++ b/src/OpenIddict.Client.AspNetCore/OpenIddictClientAspNetCoreHandlers.Authentication.cs @@ -57,8 +57,13 @@ public static partial class OpenIddictClientAspNetCoreHandlers .Build(); /// - public ValueTask HandleAsync(ApplyAuthorizationRequestContext context!!) + public ValueTask HandleAsync(ApplyAuthorizationRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // This handler only applies to ASP.NET Core requests. If the HTTP context cannot be resolved, // this may indicate that the request was incorrectly processed by another server stack. var response = context.Transaction.GetHttpRequest()?.HttpContext.Response ?? diff --git a/src/OpenIddict.Client.AspNetCore/OpenIddictClientAspNetCoreHandlers.cs b/src/OpenIddict.Client.AspNetCore/OpenIddictClientAspNetCoreHandlers.cs index 6ff42472..63016206 100644 --- a/src/OpenIddict.Client.AspNetCore/OpenIddictClientAspNetCoreHandlers.cs +++ b/src/OpenIddict.Client.AspNetCore/OpenIddictClientAspNetCoreHandlers.cs @@ -61,8 +61,13 @@ public static partial class OpenIddictClientAspNetCoreHandlers .Build(); /// - public ValueTask HandleAsync(ProcessRequestContext context!!) + public ValueTask HandleAsync(ProcessRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // This handler only applies to ASP.NET Core requests. If the HTTP context cannot be resolved, // this may indicate that the request was incorrectly processed by another server stack. var request = context.Transaction.GetHttpRequest() ?? @@ -145,8 +150,13 @@ public static partial class OpenIddictClientAspNetCoreHandlers .Build(); /// - public async ValueTask HandleAsync(TContext context!!) + public async ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // This handler only applies to ASP.NET Core requests. If the HTTP context cannot be resolved, // this may indicate that the request was incorrectly processed by another server stack. var request = context.Transaction.GetHttpRequest() ?? @@ -210,8 +220,8 @@ public static partial class OpenIddictClientAspNetCoreHandlers { private readonly IOptionsMonitor _options; - public ValidateCorrelationCookie(IOptionsMonitor options!!) - => _options = options; + public ValidateCorrelationCookie(IOptionsMonitor options) + => _options = options ?? throw new ArgumentNullException(nameof(options)); /// /// Gets the default descriptor definition assigned to this handler. @@ -226,8 +236,13 @@ public static partial class OpenIddictClientAspNetCoreHandlers .Build(); /// - public ValueTask HandleAsync(ProcessAuthenticationContext context!!) + public ValueTask HandleAsync(ProcessAuthenticationContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.StateTokenPrincipal is { Identity: ClaimsIdentity }, SR.GetResourceString(SR.ID4006)); // This handler only applies to ASP.NET Core requests. If the HTTP context cannot be resolved, @@ -299,8 +314,13 @@ public static partial class OpenIddictClientAspNetCoreHandlers .Build(); /// - public ValueTask HandleAsync(ProcessChallengeContext context!!) + public ValueTask HandleAsync(ProcessChallengeContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var properties = context.Transaction.GetProperty(typeof(AuthenticationProperties).FullName!); if (properties is null) { @@ -356,8 +376,8 @@ public static partial class OpenIddictClientAspNetCoreHandlers { private readonly IOptionsMonitor _options; - public GenerateCorrelationCookie(IOptionsMonitor options!!) - => _options = options; + public GenerateCorrelationCookie(IOptionsMonitor options) + => _options = options ?? throw new ArgumentNullException(nameof(options)); /// /// Gets the default descriptor definition assigned to this handler. @@ -372,8 +392,13 @@ public static partial class OpenIddictClientAspNetCoreHandlers .Build(); /// - public ValueTask HandleAsync(ProcessChallengeContext context!!) + public ValueTask HandleAsync(ProcessChallengeContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // Note: using a correlation cookie serves as an antiforgery protection as the request will // always be rejected if a cookie corresponding to the request forgery protection claim // persisted in the state token cannot be found. This protection is considered essential @@ -437,8 +462,13 @@ public static partial class OpenIddictClientAspNetCoreHandlers .Build(); /// - public ValueTask HandleAsync(TContext context!!) + public ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + context.SkipRequest(); return default; @@ -463,8 +493,13 @@ public static partial class OpenIddictClientAspNetCoreHandlers .Build(); /// - public ValueTask HandleAsync(TContext context!!) + public ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // This handler only applies to ASP.NET Core requests. If the HTTP context cannot be resolved, // this may indicate that the request was incorrectly processed by another server stack. var response = context.Transaction.GetHttpRequest()?.HttpContext.Response ?? @@ -501,8 +536,13 @@ public static partial class OpenIddictClientAspNetCoreHandlers .Build(); /// - public ValueTask HandleAsync(TContext context!!) + public ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // This handler only applies to ASP.NET Core requests. If the HTTP context cannot be resolved, // this may indicate that the request was incorrectly processed by another server stack. var response = context.Transaction.GetHttpRequest()?.HttpContext.Response ?? @@ -540,8 +580,13 @@ public static partial class OpenIddictClientAspNetCoreHandlers .Build(); /// - public ValueTask HandleAsync(TContext context!!) + public ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.Transaction.Response is not null, SR.GetResourceString(SR.ID4007)); if (string.IsNullOrEmpty(context.Transaction.Response.Error)) @@ -575,8 +620,13 @@ public static partial class OpenIddictClientAspNetCoreHandlers .Build(); /// - public ValueTask HandleAsync(TContext context!!) + public ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // This handler only applies to ASP.NET Core requests. If the HTTP context cannot be resolved, // this may indicate that the request was incorrectly processed by another server stack. var response = context.Transaction.GetHttpRequest()?.HttpContext.Response ?? @@ -626,8 +676,13 @@ public static partial class OpenIddictClientAspNetCoreHandlers .Build(); /// - public async ValueTask HandleAsync(TContext context!!) + public async ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // This handler only applies to ASP.NET Core requests. If the HTTP context cannot be resolved, // this may indicate that the request was incorrectly processed by another server stack. var response = context.Transaction.GetHttpRequest()?.HttpContext.Response ?? @@ -695,8 +750,13 @@ public static partial class OpenIddictClientAspNetCoreHandlers .Build(); /// - public ValueTask HandleAsync(TContext context!!) + public ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + context.Logger.LogInformation(SR.GetResourceString(SR.ID6145)); context.HandleRequest(); diff --git a/src/OpenIddict.Client.AspNetCore/OpenIddictClientAspNetCoreHelpers.cs b/src/OpenIddict.Client.AspNetCore/OpenIddictClientAspNetCoreHelpers.cs index e10af7a4..ee856cf0 100644 --- a/src/OpenIddict.Client.AspNetCore/OpenIddictClientAspNetCoreHelpers.cs +++ b/src/OpenIddict.Client.AspNetCore/OpenIddictClientAspNetCoreHelpers.cs @@ -19,32 +19,68 @@ public static class OpenIddictClientAspNetCoreHelpers /// /// The transaction instance. /// The instance or if it couldn't be found. - public static HttpRequest? GetHttpRequest(this OpenIddictClientTransaction transaction!!) - => transaction.Properties.TryGetValue(typeof(HttpRequest).FullName!, out object? property) && - property is WeakReference reference && - reference.TryGetTarget(out HttpRequest? request) ? request : null; + public static HttpRequest? GetHttpRequest(this OpenIddictClientTransaction transaction) + { + if (transaction is null) + { + throw new ArgumentNullException(nameof(transaction)); + } + + if (!transaction.Properties.TryGetValue(typeof(HttpRequest).FullName!, out object? property)) + { + return null; + } + + if (property is WeakReference reference && reference.TryGetTarget(out HttpRequest? request)) + { + return request; + } + + return null; + } /// /// Retrieves the instance stored in . /// /// The context instance. /// The . - public static OpenIddictClientEndpointType GetOpenIddictClientEndpointType(this HttpContext context!!) - => context.Features.Get()?.Transaction?.EndpointType ?? default; + public static OpenIddictClientEndpointType GetOpenIddictClientEndpointType(this HttpContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return context.Features.Get()?.Transaction?.EndpointType ?? default; + } /// /// Retrieves the instance stored in . /// /// The context instance. /// The instance or if it couldn't be found. - public static OpenIddictRequest? GetOpenIddictClientRequest(this HttpContext context!!) - => context.Features.Get()?.Transaction?.Request; + public static OpenIddictRequest? GetOpenIddictClientRequest(this HttpContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return context.Features.Get()?.Transaction?.Request; + } /// /// Retrieves the instance stored in . /// /// The context instance. /// The instance or if it couldn't be found. - public static OpenIddictResponse? GetOpenIddictClientResponse(this HttpContext context!!) - => context.Features.Get()?.Transaction?.Response; + public static OpenIddictResponse? GetOpenIddictClientResponse(this HttpContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return context.Features.Get()?.Transaction?.Response; + } } diff --git a/src/OpenIddict.Client.Owin/OpenIddictClientOwinBuilder.cs b/src/OpenIddict.Client.Owin/OpenIddictClientOwinBuilder.cs index 5a6664f8..974cd502 100644 --- a/src/OpenIddict.Client.Owin/OpenIddictClientOwinBuilder.cs +++ b/src/OpenIddict.Client.Owin/OpenIddictClientOwinBuilder.cs @@ -20,8 +20,8 @@ public class OpenIddictClientOwinBuilder /// Initializes a new instance of . /// /// The services collection. - public OpenIddictClientOwinBuilder(IServiceCollection services!!) - => Services = services; + public OpenIddictClientOwinBuilder(IServiceCollection services) + => Services = services ?? throw new ArgumentNullException(nameof(services)); /// /// Gets the services collection. @@ -35,8 +35,13 @@ public class OpenIddictClientOwinBuilder /// The delegate used to configure the OpenIddict options. /// This extension can be safely called multiple times. /// The . - public OpenIddictClientOwinBuilder Configure(Action configuration!!) + public OpenIddictClientOwinBuilder Configure(Action configuration) { + if (configuration is null) + { + throw new ArgumentNullException(nameof(configuration)); + } + Services.Configure(configuration); return this; diff --git a/src/OpenIddict.Client.Owin/OpenIddictClientOwinConfiguration.cs b/src/OpenIddict.Client.Owin/OpenIddictClientOwinConfiguration.cs index 821e6be0..77fff3b6 100644 --- a/src/OpenIddict.Client.Owin/OpenIddictClientOwinConfiguration.cs +++ b/src/OpenIddict.Client.Owin/OpenIddictClientOwinConfiguration.cs @@ -14,14 +14,24 @@ namespace OpenIddict.Client.Owin; public class OpenIddictClientOwinConfiguration : IConfigureOptions, IPostConfigureOptions { - public void Configure(OpenIddictClientOptions options!!) + public void Configure(OpenIddictClientOptions options) { + if (options is null) + { + throw new ArgumentNullException(nameof(options)); + } + // Register the built-in event handlers used by the OpenIddict OWIN Client components. options.Handlers.AddRange(OpenIddictClientOwinHandlers.DefaultHandlers); } - public void PostConfigure(string name, OpenIddictClientOwinOptions options!!) + public void PostConfigure(string name, OpenIddictClientOwinOptions options) { + if (options is null) + { + throw new ArgumentNullException(nameof(options)); + } + if (options.AuthenticationMode is AuthenticationMode.Active) { throw new InvalidOperationException(SR.GetResourceString(SR.ID0314)); diff --git a/src/OpenIddict.Client.Owin/OpenIddictClientOwinExtensions.cs b/src/OpenIddict.Client.Owin/OpenIddictClientOwinExtensions.cs index 1c71868f..d0927dd4 100644 --- a/src/OpenIddict.Client.Owin/OpenIddictClientOwinExtensions.cs +++ b/src/OpenIddict.Client.Owin/OpenIddictClientOwinExtensions.cs @@ -22,8 +22,13 @@ public static class OpenIddictClientOwinExtensions /// The services builder used by OpenIddict to register new services. /// This extension can be safely called multiple times. /// The . - public static OpenIddictClientOwinBuilder UseOwin(this OpenIddictClientBuilder builder!!) + public static OpenIddictClientOwinBuilder UseOwin(this OpenIddictClientBuilder builder) { + if (builder is null) + { + throw new ArgumentNullException(nameof(builder)); + } + builder.Services.AddWebEncoders(); // Note: unlike regular OWIN middleware, the OpenIddict client middleware is registered @@ -59,8 +64,18 @@ public static class OpenIddictClientOwinExtensions /// This extension can be safely called multiple times. /// The . public static OpenIddictClientBuilder UseOwin( - this OpenIddictClientBuilder builder!!, Action configuration!!) + this OpenIddictClientBuilder builder, Action configuration) { + if (builder is null) + { + throw new ArgumentNullException(nameof(builder)); + } + + if (configuration is null) + { + throw new ArgumentNullException(nameof(configuration)); + } + configuration(builder.UseOwin()); return builder; diff --git a/src/OpenIddict.Client.Owin/OpenIddictClientOwinHandler.cs b/src/OpenIddict.Client.Owin/OpenIddictClientOwinHandler.cs index 26862619..f6732d51 100644 --- a/src/OpenIddict.Client.Owin/OpenIddictClientOwinHandler.cs +++ b/src/OpenIddict.Client.Owin/OpenIddictClientOwinHandler.cs @@ -26,11 +26,11 @@ public class OpenIddictClientOwinHandler : AuthenticationHandlerThe OpenIddict client dispatcher used by this instance. /// The OpenIddict client factory used by this instance. public OpenIddictClientOwinHandler( - IOpenIddictClientDispatcher dispatcher!!, - IOpenIddictClientFactory factory!!) + IOpenIddictClientDispatcher dispatcher, + IOpenIddictClientFactory factory) { - _dispatcher = dispatcher; - _factory = factory; + _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); + _factory = factory ?? throw new ArgumentNullException(nameof(factory)); } /// diff --git a/src/OpenIddict.Client.Owin/OpenIddictClientOwinHandlerFilters.cs b/src/OpenIddict.Client.Owin/OpenIddictClientOwinHandlerFilters.cs index 202f50da..d6c42974 100644 --- a/src/OpenIddict.Client.Owin/OpenIddictClientOwinHandlerFilters.cs +++ b/src/OpenIddict.Client.Owin/OpenIddictClientOwinHandlerFilters.cs @@ -24,11 +24,18 @@ public static class OpenIddictClientOwinHandlerFilters { private readonly IOptionsMonitor _options; - public RequireRedirectionEndpointPassthroughEnabled(IOptionsMonitor options!!) - => _options = options; + public RequireRedirectionEndpointPassthroughEnabled(IOptionsMonitor options) + => _options = options ?? throw new ArgumentNullException(nameof(options)); - public ValueTask IsActiveAsync(BaseContext context!!) - => new(_options.CurrentValue.EnableRedirectionEndpointPassthrough); + public ValueTask IsActiveAsync(BaseContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(_options.CurrentValue.EnableRedirectionEndpointPassthrough); + } } /// @@ -38,11 +45,18 @@ public static class OpenIddictClientOwinHandlerFilters { private readonly IOptionsMonitor _options; - public RequireErrorPassthroughEnabled(IOptionsMonitor options!!) - => _options = options; + public RequireErrorPassthroughEnabled(IOptionsMonitor options) + => _options = options ?? throw new ArgumentNullException(nameof(options)); + + public ValueTask IsActiveAsync(BaseContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } - public ValueTask IsActiveAsync(BaseContext context!!) - => new(_options.CurrentValue.EnableErrorPassthrough); + return new(_options.CurrentValue.EnableErrorPassthrough); + } } /// @@ -50,7 +64,14 @@ public static class OpenIddictClientOwinHandlerFilters /// public class RequireOwinRequest : IOpenIddictClientHandlerFilter { - public ValueTask IsActiveAsync(BaseContext context!!) - => new(context.Transaction.GetOwinRequest() is not null); + public ValueTask IsActiveAsync(BaseContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(context.Transaction.GetOwinRequest() is not null); + } } } diff --git a/src/OpenIddict.Client.Owin/OpenIddictClientOwinHandlers.Authentication.cs b/src/OpenIddict.Client.Owin/OpenIddictClientOwinHandlers.Authentication.cs index bdcd13b0..6e0f32ef 100644 --- a/src/OpenIddict.Client.Owin/OpenIddictClientOwinHandlers.Authentication.cs +++ b/src/OpenIddict.Client.Owin/OpenIddictClientOwinHandlers.Authentication.cs @@ -55,8 +55,13 @@ public static partial class OpenIddictClientOwinHandlers .Build(); /// - public ValueTask HandleAsync(ApplyAuthorizationRequestContext context!!) + public ValueTask HandleAsync(ApplyAuthorizationRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // This handler only applies to OWIN requests. If the HTTP context cannot be resolved, // this may indicate that the request was incorrectly processed by another server stack. var response = context.Transaction.GetOwinRequest()?.Context.Response ?? diff --git a/src/OpenIddict.Client.Owin/OpenIddictClientOwinHandlers.cs b/src/OpenIddict.Client.Owin/OpenIddictClientOwinHandlers.cs index 72ec6d3a..162951e1 100644 --- a/src/OpenIddict.Client.Owin/OpenIddictClientOwinHandlers.cs +++ b/src/OpenIddict.Client.Owin/OpenIddictClientOwinHandlers.cs @@ -58,8 +58,13 @@ public static partial class OpenIddictClientOwinHandlers .Build(); /// - public ValueTask HandleAsync(ProcessRequestContext context!!) + public ValueTask HandleAsync(ProcessRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // This handler only applies to OWIN requests. If The OWIN request cannot be resolved, // this may indicate that the request was incorrectly processed by another server stack. var request = context.Transaction.GetOwinRequest() ?? @@ -142,8 +147,13 @@ public static partial class OpenIddictClientOwinHandlers .Build(); /// - public async ValueTask HandleAsync(TContext context!!) + public async ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // This handler only applies to OWIN requests. If The OWIN request cannot be resolved, // this may indicate that the request was incorrectly processed by another server stack. var request = context.Transaction.GetOwinRequest() ?? @@ -207,8 +217,8 @@ public static partial class OpenIddictClientOwinHandlers { private readonly IOptionsMonitor _options; - public ValidateCorrelationCookie(IOptionsMonitor options!!) - => _options = options; + public ValidateCorrelationCookie(IOptionsMonitor options) + => _options = options ?? throw new ArgumentNullException(nameof(options)); /// /// Gets the default descriptor definition assigned to this handler. @@ -223,8 +233,13 @@ public static partial class OpenIddictClientOwinHandlers .Build(); /// - public ValueTask HandleAsync(ProcessAuthenticationContext context!!) + public ValueTask HandleAsync(ProcessAuthenticationContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.StateTokenPrincipal is { Identity: ClaimsIdentity }, SR.GetResourceString(SR.ID4006)); // This handler only applies to OWIN requests. If the HTTP context cannot be resolved, @@ -305,8 +320,13 @@ public static partial class OpenIddictClientOwinHandlers .Build(); /// - public ValueTask HandleAsync(ProcessChallengeContext context!!) + public ValueTask HandleAsync(ProcessChallengeContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var properties = context.Transaction.GetProperty(typeof(AuthenticationProperties).FullName!); if (properties is null) { @@ -343,8 +363,8 @@ public static partial class OpenIddictClientOwinHandlers { private readonly IOptionsMonitor _options; - public GenerateCorrelationCookie(IOptionsMonitor options!!) - => _options = options; + public GenerateCorrelationCookie(IOptionsMonitor options) + => _options = options ?? throw new ArgumentNullException(nameof(options)); /// /// Gets the default descriptor definition assigned to this handler. @@ -359,8 +379,13 @@ public static partial class OpenIddictClientOwinHandlers .Build(); /// - public ValueTask HandleAsync(ProcessChallengeContext context!!) + public ValueTask HandleAsync(ProcessChallengeContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // Note: using a correlation cookie serves as an antiforgery protection as the request will // always be rejected if a cookie corresponding to the request forgery protection claim // persisted in the state token cannot be found. This protection is considered essential @@ -433,8 +458,13 @@ public static partial class OpenIddictClientOwinHandlers .Build(); /// - public ValueTask HandleAsync(TContext context!!) + public ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + context.SkipRequest(); return default; @@ -459,8 +489,13 @@ public static partial class OpenIddictClientOwinHandlers .Build(); /// - public ValueTask HandleAsync(TContext context!!) + public ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // This handler only applies to OWIN requests. If the HTTP context cannot be resolved, // this may indicate that the request was incorrectly processed by another server stack. var response = context.Transaction.GetOwinRequest()?.Context.Response ?? @@ -497,8 +532,13 @@ public static partial class OpenIddictClientOwinHandlers .Build(); /// - public ValueTask HandleAsync(TContext context!!) + public ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // This handler only applies to OWIN requests. If the HTTP context cannot be resolved, // this may indicate that the request was incorrectly processed by another server stack. var response = context.Transaction.GetOwinRequest()?.Context.Response ?? @@ -536,8 +576,13 @@ public static partial class OpenIddictClientOwinHandlers .Build(); /// - public ValueTask HandleAsync(TContext context!!) + public ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.Transaction.Response is not null, SR.GetResourceString(SR.ID4007)); if (string.IsNullOrEmpty(context.Transaction.Response.Error)) @@ -570,8 +615,13 @@ public static partial class OpenIddictClientOwinHandlers .Build(); /// - public async ValueTask HandleAsync(TContext context!!) + public async ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // This handler only applies to OWIN requests. If the HTTP context cannot be resolved, // this may indicate that the request was incorrectly processed by another server stack. var response = context.Transaction.GetOwinRequest()?.Context.Response ?? @@ -639,8 +689,13 @@ public static partial class OpenIddictClientOwinHandlers .Build(); /// - public ValueTask HandleAsync(TContext context!!) + public ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + context.Logger.LogInformation(SR.GetResourceString(SR.ID6145)); context.HandleRequest(); diff --git a/src/OpenIddict.Client.Owin/OpenIddictClientOwinHelpers.cs b/src/OpenIddict.Client.Owin/OpenIddictClientOwinHelpers.cs index 3ad6d683..bd231324 100644 --- a/src/OpenIddict.Client.Owin/OpenIddictClientOwinHelpers.cs +++ b/src/OpenIddict.Client.Owin/OpenIddictClientOwinHelpers.cs @@ -21,40 +21,83 @@ public static class OpenIddictClientOwinHelpers /// /// The application builder used to register middleware instances. /// The . - public static IAppBuilder UseOpenIddictClient(this IAppBuilder app!!) - => app.Use(); + public static IAppBuilder UseOpenIddictClient(this IAppBuilder app) + { + if (app is null) + { + throw new ArgumentNullException(nameof(app)); + } + + return app.Use(); + } /// /// Retrieves the instance stored in the properties. /// /// The transaction instance. /// The instance or if it couldn't be found. - public static IOwinRequest? GetOwinRequest(this OpenIddictClientTransaction transaction!!) - => transaction.Properties.TryGetValue(typeof(IOwinRequest).FullName!, out object? property) && - property is WeakReference reference && - reference.TryGetTarget(out IOwinRequest? request) ? request : null; + public static IOwinRequest? GetOwinRequest(this OpenIddictClientTransaction transaction) + { + if (transaction is null) + { + throw new ArgumentNullException(nameof(transaction)); + } + + if (!transaction.Properties.TryGetValue(typeof(IOwinRequest).FullName!, out object? property)) + { + return null; + } + + if (property is WeakReference reference && reference.TryGetTarget(out IOwinRequest? request)) + { + return request; + } + + return null; + } /// /// Retrieves the instance stored in . /// /// The context instance. /// The . - public static OpenIddictClientEndpointType GetOpenIddictClientEndpointType(this IOwinContext context!!) - => context.Get(typeof(OpenIddictClientTransaction).FullName)?.EndpointType ?? default; + public static OpenIddictClientEndpointType GetOpenIddictClientEndpointType(this IOwinContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return context.Get(typeof(OpenIddictClientTransaction).FullName)?.EndpointType ?? default; + } /// /// Retrieves the instance stored in . /// /// The context instance. /// The instance or if it couldn't be found. - public static OpenIddictRequest? GetOpenIddictClientRequest(this IOwinContext context!!) - => context.Get(typeof(OpenIddictClientTransaction).FullName)?.Request; + public static OpenIddictRequest? GetOpenIddictClientRequest(this IOwinContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return context.Get(typeof(OpenIddictClientTransaction).FullName)?.Request; + } /// /// Retrieves the instance stored in . /// /// The context instance. /// The instance or if it couldn't be found. - public static OpenIddictResponse? GetOpenIddictClientResponse(this IOwinContext context!!) - => context.Get(typeof(OpenIddictClientTransaction).FullName)?.Response; + public static OpenIddictResponse? GetOpenIddictClientResponse(this IOwinContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return context.Get(typeof(OpenIddictClientTransaction).FullName)?.Response; + } } diff --git a/src/OpenIddict.Client.Owin/OpenIddictClientOwinMiddleware.cs b/src/OpenIddict.Client.Owin/OpenIddictClientOwinMiddleware.cs index 4726ceb0..b7fa3690 100644 --- a/src/OpenIddict.Client.Owin/OpenIddictClientOwinMiddleware.cs +++ b/src/OpenIddict.Client.Owin/OpenIddictClientOwinMiddleware.cs @@ -29,13 +29,13 @@ public class OpenIddictClientOwinMiddleware : AuthenticationMiddlewareThe OpenIddict client factory. public OpenIddictClientOwinMiddleware( OwinMiddleware? next, - IOptionsMonitor options!!, - IOpenIddictClientDispatcher dispatcher!!, - IOpenIddictClientFactory factory!!) + IOptionsMonitor options, + IOpenIddictClientDispatcher dispatcher, + IOpenIddictClientFactory factory) : base(next, options.CurrentValue) { - _dispatcher = dispatcher; - _factory = factory; + _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); + _factory = factory ?? throw new ArgumentNullException(nameof(factory)); } /// diff --git a/src/OpenIddict.Client.Owin/OpenIddictClientOwinMiddlewareFactory.cs b/src/OpenIddict.Client.Owin/OpenIddictClientOwinMiddlewareFactory.cs index 629b74f7..27a10e25 100644 --- a/src/OpenIddict.Client.Owin/OpenIddictClientOwinMiddlewareFactory.cs +++ b/src/OpenIddict.Client.Owin/OpenIddictClientOwinMiddlewareFactory.cs @@ -33,8 +33,13 @@ public class OpenIddictClientOwinMiddlewareFactory : OwinMiddleware /// /// A that can be used to monitor the asynchronous operation. /// - public override Task Invoke(IOwinContext context!!) + public override Task Invoke(IOwinContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var provider = context.Get(typeof(IServiceProvider).FullName) ?? throw new InvalidOperationException(SR.GetResourceString(SR.ID0316)); diff --git a/src/OpenIddict.Client.SystemNetHttp/OpenIddictClientSystemNetHttpBuilder.cs b/src/OpenIddict.Client.SystemNetHttp/OpenIddictClientSystemNetHttpBuilder.cs index cdf2c6ec..aa859f8d 100644 --- a/src/OpenIddict.Client.SystemNetHttp/OpenIddictClientSystemNetHttpBuilder.cs +++ b/src/OpenIddict.Client.SystemNetHttp/OpenIddictClientSystemNetHttpBuilder.cs @@ -19,8 +19,8 @@ public class OpenIddictClientSystemNetHttpBuilder /// Initializes a new instance of . /// /// The services collection. - public OpenIddictClientSystemNetHttpBuilder(IServiceCollection services!!) - => Services = services; + public OpenIddictClientSystemNetHttpBuilder(IServiceCollection services) + => Services = services ?? throw new ArgumentNullException(nameof(services)); /// /// Gets the services collection. @@ -34,8 +34,13 @@ public class OpenIddictClientSystemNetHttpBuilder /// The delegate used to configure the OpenIddict options. /// This extension can be safely called multiple times. /// The . - public OpenIddictClientSystemNetHttpBuilder Configure(Action configuration!!) + public OpenIddictClientSystemNetHttpBuilder Configure(Action configuration) { + if (configuration is null) + { + throw new ArgumentNullException(nameof(configuration)); + } + Services.Configure(configuration); return this; diff --git a/src/OpenIddict.Client.SystemNetHttp/OpenIddictClientSystemNetHttpConfiguration.cs b/src/OpenIddict.Client.SystemNetHttp/OpenIddictClientSystemNetHttpConfiguration.cs index 6ea31f51..6c1eda9b 100644 --- a/src/OpenIddict.Client.SystemNetHttp/OpenIddictClientSystemNetHttpConfiguration.cs +++ b/src/OpenIddict.Client.SystemNetHttp/OpenIddictClientSystemNetHttpConfiguration.cs @@ -21,12 +21,17 @@ public class OpenIddictClientSystemNetHttpConfiguration : IConfigureOptions _serviceProvider = serviceProvider; + public OpenIddictClientSystemNetHttpConfiguration(IServiceProvider serviceProvider) + => _serviceProvider = serviceProvider ?? throw new ArgumentNullException(nameof(serviceProvider)); #endif - public void Configure(OpenIddictClientOptions options!!) + public void Configure(OpenIddictClientOptions options) { + if (options is null) + { + throw new ArgumentNullException(nameof(options)); + } + // Register the built-in event handlers used by the OpenIddict System.Net.Http client components. options.Handlers.AddRange(OpenIddictClientSystemNetHttpHandlers.DefaultHandlers); } @@ -34,8 +39,13 @@ public class OpenIddictClientSystemNetHttpConfiguration : IConfigureOptions Debug.Fail("This infrastructure method shouldn't be called."); - public void Configure(string name, HttpClientFactoryOptions options!!) + public void Configure(string name, HttpClientFactoryOptions options) { + if (options is null) + { + throw new ArgumentNullException(nameof(options)); + } + var assembly = typeof(OpenIddictClientSystemNetHttpOptions).Assembly.GetName(); if (!string.Equals(name, assembly.Name, StringComparison.Ordinal)) diff --git a/src/OpenIddict.Client.SystemNetHttp/OpenIddictClientSystemNetHttpExtensions.cs b/src/OpenIddict.Client.SystemNetHttp/OpenIddictClientSystemNetHttpExtensions.cs index 4171cfd0..cded095c 100644 --- a/src/OpenIddict.Client.SystemNetHttp/OpenIddictClientSystemNetHttpExtensions.cs +++ b/src/OpenIddict.Client.SystemNetHttp/OpenIddictClientSystemNetHttpExtensions.cs @@ -23,8 +23,13 @@ public static class OpenIddictClientSystemNetHttpExtensions /// The services builder used by OpenIddict to register new services. /// This extension can be safely called multiple times. /// The . - public static OpenIddictClientSystemNetHttpBuilder UseSystemNetHttp(this OpenIddictClientBuilder builder!!) + public static OpenIddictClientSystemNetHttpBuilder UseSystemNetHttp(this OpenIddictClientBuilder builder) { + if (builder is null) + { + throw new ArgumentNullException(nameof(builder)); + } + builder.Services.AddHttpClient(); // Register the built-in validation event handlers used by the OpenIddict System.Net.Http components. @@ -52,8 +57,18 @@ public static class OpenIddictClientSystemNetHttpExtensions /// This extension can be safely called multiple times. /// The . public static OpenIddictClientBuilder UseSystemNetHttp( - this OpenIddictClientBuilder builder!!, Action configuration!!) + this OpenIddictClientBuilder builder, Action configuration) { + if (builder is null) + { + throw new ArgumentNullException(nameof(builder)); + } + + if (configuration is null) + { + throw new ArgumentNullException(nameof(configuration)); + } + configuration(builder.UseSystemNetHttp()); return builder; diff --git a/src/OpenIddict.Client.SystemNetHttp/OpenIddictClientSystemNetHttpHandlerFilters.cs b/src/OpenIddict.Client.SystemNetHttp/OpenIddictClientSystemNetHttpHandlerFilters.cs index 8a4ba4ab..3e4e9a23 100644 --- a/src/OpenIddict.Client.SystemNetHttp/OpenIddictClientSystemNetHttpHandlerFilters.cs +++ b/src/OpenIddict.Client.SystemNetHttp/OpenIddictClientSystemNetHttpHandlerFilters.cs @@ -16,8 +16,16 @@ public static class OpenIddictClientSystemNetHttpHandlerFilters /// public class RequireHttpMetadataAddress : IOpenIddictClientHandlerFilter { - public ValueTask IsActiveAsync(BaseExternalContext context!!) - => new(string.Equals(context.Address?.Scheme, Uri.UriSchemeHttp, StringComparison.OrdinalIgnoreCase) || - string.Equals(context.Address?.Scheme, Uri.UriSchemeHttps, StringComparison.OrdinalIgnoreCase)); + public ValueTask IsActiveAsync(BaseExternalContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new( + string.Equals(context.Address?.Scheme, Uri.UriSchemeHttp, StringComparison.OrdinalIgnoreCase) || + string.Equals(context.Address?.Scheme, Uri.UriSchemeHttps, StringComparison.OrdinalIgnoreCase)); + } } } diff --git a/src/OpenIddict.Client.SystemNetHttp/OpenIddictClientSystemNetHttpHandlers.Exchange.cs b/src/OpenIddict.Client.SystemNetHttp/OpenIddictClientSystemNetHttpHandlers.Exchange.cs index 1810b234..e88f26ca 100644 --- a/src/OpenIddict.Client.SystemNetHttp/OpenIddictClientSystemNetHttpHandlers.Exchange.cs +++ b/src/OpenIddict.Client.SystemNetHttp/OpenIddictClientSystemNetHttpHandlers.Exchange.cs @@ -48,8 +48,13 @@ public static partial class OpenIddictClientSystemNetHttpHandlers .Build(); /// - public async ValueTask HandleAsync(PrepareTokenRequestContext context!!) + public async ValueTask HandleAsync(PrepareTokenRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.Request is not null, SR.GetResourceString(SR.ID4008)); // This handler only applies to System.Net.Http requests. If the HTTP request cannot be resolved, diff --git a/src/OpenIddict.Client.SystemNetHttp/OpenIddictClientSystemNetHttpHandlers.Userinfo.cs b/src/OpenIddict.Client.SystemNetHttp/OpenIddictClientSystemNetHttpHandlers.Userinfo.cs index 1123c2d3..aef74189 100644 --- a/src/OpenIddict.Client.SystemNetHttp/OpenIddictClientSystemNetHttpHandlers.Userinfo.cs +++ b/src/OpenIddict.Client.SystemNetHttp/OpenIddictClientSystemNetHttpHandlers.Userinfo.cs @@ -47,8 +47,13 @@ public static partial class OpenIddictClientSystemNetHttpHandlers .Build(); /// - public ValueTask HandleAsync(PrepareUserinfoRequestContext context!!) + public ValueTask HandleAsync(PrepareUserinfoRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.Request is not null, SR.GetResourceString(SR.ID4008)); // This handler only applies to System.Net.Http requests. If the HTTP request cannot be resolved, @@ -83,8 +88,13 @@ public static partial class OpenIddictClientSystemNetHttpHandlers .Build(); /// - public async ValueTask HandleAsync(ExtractUserinfoResponseContext context!!) + public async ValueTask HandleAsync(ExtractUserinfoResponseContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // This handler only applies to System.Net.Http requests. If the HTTP response cannot be resolved, // this may indicate that the request was incorrectly processed by another client stack. var response = context.Transaction.GetHttpResponseMessage() ?? diff --git a/src/OpenIddict.Client.SystemNetHttp/OpenIddictClientSystemNetHttpHandlers.cs b/src/OpenIddict.Client.SystemNetHttp/OpenIddictClientSystemNetHttpHandlers.cs index 358935f3..a1fe9d4a 100644 --- a/src/OpenIddict.Client.SystemNetHttp/OpenIddictClientSystemNetHttpHandlers.cs +++ b/src/OpenIddict.Client.SystemNetHttp/OpenIddictClientSystemNetHttpHandlers.cs @@ -41,8 +41,13 @@ public static partial class OpenIddictClientSystemNetHttpHandlers /// [SuppressMessage("Reliability", "CA2000:Dispose objects before losing scope", Justification = "The HTTP request message is disposed later by a dedicated handler.")] - public ValueTask HandleAsync(TContext context!!) + public ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var request = new HttpRequestMessage(HttpMethod.Get, context.Address) { Headers = @@ -78,8 +83,13 @@ public static partial class OpenIddictClientSystemNetHttpHandlers /// [SuppressMessage("Reliability", "CA2000:Dispose objects before losing scope", Justification = "The HTTP request message is disposed later by a dedicated handler.")] - public ValueTask HandleAsync(TContext context!!) + public ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var request = new HttpRequestMessage(HttpMethod.Post, context.Address) { Headers = @@ -113,8 +123,13 @@ public static partial class OpenIddictClientSystemNetHttpHandlers .Build(); /// - public ValueTask HandleAsync(TContext context!!) + public ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.Transaction.Request is not null, SR.GetResourceString(SR.ID4008)); // This handler only applies to System.Net.Http requests. If the HTTP request cannot be resolved, @@ -171,8 +186,13 @@ public static partial class OpenIddictClientSystemNetHttpHandlers .Build(); /// - public ValueTask HandleAsync(TContext context!!) + public ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.Transaction.Request is not null, SR.GetResourceString(SR.ID4008)); // This handler only applies to System.Net.Http requests. If the HTTP request cannot be resolved, @@ -200,7 +220,7 @@ public static partial class OpenIddictClientSystemNetHttpHandlers private readonly IHttpClientFactory _factory; public SendHttpRequest(IHttpClientFactory factory) - => _factory = factory; + => _factory = factory ?? throw new ArgumentNullException(nameof(factory)); /// /// Gets the default descriptor definition assigned to this handler. @@ -214,8 +234,13 @@ public static partial class OpenIddictClientSystemNetHttpHandlers .Build(); /// - public async ValueTask HandleAsync(TContext context!!) + public async ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // This handler only applies to System.Net.Http requests. If the HTTP request cannot be resolved, // this may indicate that the request was incorrectly processed by another client stack. var request = context.Transaction.GetHttpRequestMessage() ?? @@ -254,8 +279,13 @@ public static partial class OpenIddictClientSystemNetHttpHandlers .Build(); /// - public ValueTask HandleAsync(TContext context!!) + public ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // This handler only applies to System.Net.Http requests. If the HTTP request cannot be resolved, // this may indicate that the request was incorrectly processed by another client stack. var request = context.Transaction.GetHttpRequestMessage() ?? @@ -287,8 +317,13 @@ public static partial class OpenIddictClientSystemNetHttpHandlers .Build(); /// - public async ValueTask HandleAsync(TContext context!!) + public async ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // This handler only applies to System.Net.Http requests. If the HTTP response cannot be resolved, // this may indicate that the request was incorrectly processed by another client stack. var response = context.Transaction.GetHttpResponseMessage() ?? @@ -320,8 +355,13 @@ public static partial class OpenIddictClientSystemNetHttpHandlers .Build(); /// - public ValueTask HandleAsync(TContext context!!) + public ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // This handler only applies to System.Net.Http requests. If the HTTP response cannot be resolved, // this may indicate that the request was incorrectly processed by another client stack. var response = context.Transaction.GetHttpResponseMessage() ?? diff --git a/src/OpenIddict.Client/OpenIddictClientBuilder.cs b/src/OpenIddict.Client/OpenIddictClientBuilder.cs index 90b2e7ec..dd5eac16 100644 --- a/src/OpenIddict.Client/OpenIddictClientBuilder.cs +++ b/src/OpenIddict.Client/OpenIddictClientBuilder.cs @@ -25,8 +25,8 @@ public class OpenIddictClientBuilder /// Initializes a new instance of . /// /// The services collection. - public OpenIddictClientBuilder(IServiceCollection services!!) - => Services = services; + public OpenIddictClientBuilder(IServiceCollection services) + => Services = services ?? throw new ArgumentNullException(nameof(services)); /// /// Gets the services collection. @@ -42,9 +42,14 @@ public class OpenIddictClientBuilder /// The . [EditorBrowsable(EditorBrowsableState.Advanced)] public OpenIddictClientBuilder AddEventHandler( - Action> configuration!!) + Action> configuration) where TContext : OpenIddictClientEvents.BaseContext { + if (configuration is null) + { + throw new ArgumentNullException(nameof(configuration)); + } + // Note: handlers registered using this API are assumed to be custom handlers by default. var builder = OpenIddictClientHandlerDescriptor.CreateBuilder() .SetType(OpenIddictClientHandlerType.Custom); @@ -60,8 +65,13 @@ public class OpenIddictClientBuilder /// The handler descriptor. /// The . [EditorBrowsable(EditorBrowsableState.Advanced)] - public OpenIddictClientBuilder AddEventHandler(OpenIddictClientHandlerDescriptor descriptor!!) + public OpenIddictClientBuilder AddEventHandler(OpenIddictClientHandlerDescriptor descriptor) { + if (descriptor is null) + { + throw new ArgumentNullException(nameof(descriptor)); + } + // Register the handler in the services collection. Services.Add(descriptor.ServiceDescriptor); @@ -74,8 +84,13 @@ public class OpenIddictClientBuilder /// The descriptor corresponding to the handler to remove. /// The . [EditorBrowsable(EditorBrowsableState.Advanced)] - public OpenIddictClientBuilder RemoveEventHandler(OpenIddictClientHandlerDescriptor descriptor!!) + public OpenIddictClientBuilder RemoveEventHandler(OpenIddictClientHandlerDescriptor descriptor) { + if (descriptor is null) + { + throw new ArgumentNullException(nameof(descriptor)); + } + Services.RemoveAll(descriptor.ServiceDescriptor.ServiceType); Services.PostConfigure(options => @@ -98,8 +113,13 @@ public class OpenIddictClientBuilder /// The delegate used to configure the OpenIddict options. /// This extension can be safely called multiple times. /// The . - public OpenIddictClientBuilder Configure(Action configuration!!) + public OpenIddictClientBuilder Configure(Action configuration) { + if (configuration is null) + { + throw new ArgumentNullException(nameof(configuration)); + } + Services.Configure(configuration); return this; @@ -110,16 +130,28 @@ public class OpenIddictClientBuilder /// /// The encrypting credentials. /// The . - public OpenIddictClientBuilder AddEncryptionCredentials(EncryptingCredentials credentials!!) - => Configure(options => options.EncryptionCredentials.Add(credentials)); + public OpenIddictClientBuilder AddEncryptionCredentials(EncryptingCredentials credentials) + { + if (credentials is null) + { + throw new ArgumentNullException(nameof(credentials)); + } + + return Configure(options => options.EncryptionCredentials.Add(credentials)); + } /// /// Registers an encryption key. /// /// The security key. /// The . - public OpenIddictClientBuilder AddEncryptionKey(SecurityKey key!!) + public OpenIddictClientBuilder AddEncryptionKey(SecurityKey key) { + if (key is null) + { + throw new ArgumentNullException(nameof(key)); + } + // If the encryption key is an asymmetric security key, ensure it has a private key. if (key is AsymmetricSecurityKey asymmetricSecurityKey && asymmetricSecurityKey.PrivateKeyStatus is PrivateKeyStatus.DoesNotExist) @@ -161,8 +193,13 @@ public class OpenIddictClientBuilder /// The . [SuppressMessage("Reliability", "CA2000:Dispose objects before losing scope", Justification = "The X.509 certificate is attached to the client options.")] - public OpenIddictClientBuilder AddDevelopmentEncryptionCertificate(X500DistinguishedName subject!!) + public OpenIddictClientBuilder AddDevelopmentEncryptionCertificate(X500DistinguishedName subject) { + if (subject is null) + { + throw new ArgumentNullException(nameof(subject)); + } + using var store = new X509Store(StoreName.My, StoreLocation.CurrentUser); store.Open(OpenFlags.ReadWrite); @@ -317,8 +354,13 @@ public class OpenIddictClientBuilder /// /// The encryption certificate. /// The . - public OpenIddictClientBuilder AddEncryptionCertificate(X509Certificate2 certificate!!) + public OpenIddictClientBuilder AddEncryptionCertificate(X509Certificate2 certificate) { + if (certificate is null) + { + throw new ArgumentNullException(nameof(certificate)); + } + // If the certificate is a X.509v3 certificate that specifies at least one // key usage, ensure that the certificate key can be used for key encryption. if (certificate.Version >= 3) @@ -364,9 +406,14 @@ public class OpenIddictClientBuilder /// An enumeration of flags indicating how and where to store the private key of the certificate. /// The . public OpenIddictClientBuilder AddEncryptionCertificate( - Assembly assembly!!, string resource, + Assembly assembly, string resource, string? password, X509KeyStorageFlags flags) { + if (assembly is null) + { + throw new ArgumentNullException(nameof(assembly)); + } + if (string.IsNullOrEmpty(resource)) { throw new ArgumentException(SR.GetResourceString(SR.ID0062), nameof(resource)); @@ -406,8 +453,13 @@ public class OpenIddictClientBuilder /// The . [SuppressMessage("Reliability", "CA2000:Dispose objects before losing scope", Justification = "The X.509 certificate is attached to the client options.")] - public OpenIddictClientBuilder AddEncryptionCertificate(Stream stream!!, string? password, X509KeyStorageFlags flags) + public OpenIddictClientBuilder AddEncryptionCertificate(Stream stream, string? password, X509KeyStorageFlags flags) { + if (stream is null) + { + throw new ArgumentNullException(nameof(stream)); + } + using var buffer = new MemoryStream(); stream.CopyTo(buffer); @@ -470,16 +522,28 @@ public class OpenIddictClientBuilder /// /// The signing credentials. /// The . - public OpenIddictClientBuilder AddSigningCredentials(SigningCredentials credentials!!) - => Configure(options => options.SigningCredentials.Add(credentials)); + public OpenIddictClientBuilder AddSigningCredentials(SigningCredentials credentials) + { + if (credentials is null) + { + throw new ArgumentNullException(nameof(credentials)); + } + + return Configure(options => options.SigningCredentials.Add(credentials)); + } /// /// Registers a signing key. /// /// The security key. /// The . - public OpenIddictClientBuilder AddSigningKey(SecurityKey key!!) + public OpenIddictClientBuilder AddSigningKey(SecurityKey key) { + if (key is null) + { + throw new ArgumentNullException(nameof(key)); + } + // If the signing key is an asymmetric security key, ensure it has a private key. if (key is AsymmetricSecurityKey asymmetricSecurityKey && asymmetricSecurityKey.PrivateKeyStatus is PrivateKeyStatus.DoesNotExist) @@ -539,8 +603,13 @@ public class OpenIddictClientBuilder /// The . [SuppressMessage("Reliability", "CA2000:Dispose objects before losing scope", Justification = "The X.509 certificate is attached to the client options.")] - public OpenIddictClientBuilder AddDevelopmentSigningCertificate(X500DistinguishedName subject!!) + public OpenIddictClientBuilder AddDevelopmentSigningCertificate(X500DistinguishedName subject) { + if (subject is null) + { + throw new ArgumentNullException(nameof(subject)); + } + using var store = new X509Store(StoreName.My, StoreLocation.CurrentUser); store.Open(OpenFlags.ReadWrite); @@ -713,8 +782,13 @@ public class OpenIddictClientBuilder /// /// The signing certificate. /// The . - public OpenIddictClientBuilder AddSigningCertificate(X509Certificate2 certificate!!) + public OpenIddictClientBuilder AddSigningCertificate(X509Certificate2 certificate) { + if (certificate is null) + { + throw new ArgumentNullException(nameof(certificate)); + } + // If the certificate is a X.509v3 certificate that specifies at least // one key usage, ensure that the certificate key can be used for signing. if (certificate.Version >= 3) @@ -760,9 +834,14 @@ public class OpenIddictClientBuilder /// An enumeration of flags indicating how and where to store the private key of the certificate. /// The . public OpenIddictClientBuilder AddSigningCertificate( - Assembly assembly!!, string resource, + Assembly assembly, string resource, string? password, X509KeyStorageFlags flags) { + if (assembly is null) + { + throw new ArgumentNullException(nameof(assembly)); + } + if (string.IsNullOrEmpty(resource)) { throw new ArgumentException(SR.GetResourceString(SR.ID0062), nameof(resource)); @@ -802,8 +881,13 @@ public class OpenIddictClientBuilder /// The . [SuppressMessage("Reliability", "CA2000:Dispose objects before losing scope", Justification = "The X.509 certificate is attached to the client options.")] - public OpenIddictClientBuilder AddSigningCertificate(Stream stream!!, string? password, X509KeyStorageFlags flags) + public OpenIddictClientBuilder AddSigningCertificate(Stream stream, string? password, X509KeyStorageFlags flags) { + if (stream is null) + { + throw new ArgumentNullException(nameof(stream)); + } + using var buffer = new MemoryStream(); stream.CopyTo(buffer); @@ -866,8 +950,15 @@ public class OpenIddictClientBuilder /// /// The client registration. /// The . - public OpenIddictClientBuilder AddRegistration(OpenIddictClientRegistration registration!!) - => Configure(options => options.Registrations.Add(registration)); + public OpenIddictClientBuilder AddRegistration(OpenIddictClientRegistration registration) + { + if (registration is null) + { + throw new ArgumentNullException(nameof(registration)); + } + + return Configure(options => options.Registrations.Add(registration)); + } /// /// Sets the relative or absolute URLs associated to the redirection endpoint. @@ -876,8 +967,15 @@ public class OpenIddictClientBuilder /// /// The addresses associated to the endpoint. /// The . - public OpenIddictClientBuilder SetRedirectionEndpointUris(params string[] addresses!!) - => SetRedirectionEndpointUris(addresses.Select(address => new Uri(address, UriKind.RelativeOrAbsolute)).ToArray()); + public OpenIddictClientBuilder SetRedirectionEndpointUris(params string[] addresses) + { + if (addresses is null) + { + throw new ArgumentNullException(nameof(addresses)); + } + + return SetRedirectionEndpointUris(addresses.Select(address => new Uri(address, UriKind.RelativeOrAbsolute)).ToArray()); + } /// /// Sets the relative or absolute URLs associated to the redirection endpoint. @@ -886,8 +984,13 @@ public class OpenIddictClientBuilder /// /// The addresses associated to the endpoint. /// The . - public OpenIddictClientBuilder SetRedirectionEndpointUris(params Uri[] addresses!!) + public OpenIddictClientBuilder SetRedirectionEndpointUris(params Uri[] addresses) { + if (addresses is null) + { + throw new ArgumentNullException(nameof(addresses)); + } + if (addresses.Any(address => !address.IsWellFormedOriginalString())) { throw new ArgumentException(SR.GetResourceString(SR.ID0072), nameof(addresses)); diff --git a/src/OpenIddict.Client/OpenIddictClientConfiguration.cs b/src/OpenIddict.Client/OpenIddictClientConfiguration.cs index ce0934fd..ef108c4e 100644 --- a/src/OpenIddict.Client/OpenIddictClientConfiguration.cs +++ b/src/OpenIddict.Client/OpenIddictClientConfiguration.cs @@ -19,7 +19,7 @@ public class OpenIddictClientConfiguration : IPostConfigureOptions _service = service; + => _service = service ?? throw new ArgumentNullException(nameof(service)); /// /// Populates the default OpenIddict client options and ensures @@ -27,8 +27,13 @@ public class OpenIddictClientConfiguration : IPostConfigureOptions /// The authentication scheme associated with the handler instance. /// The options instance to initialize. - public void PostConfigure(string name, OpenIddictClientOptions options!!) + public void PostConfigure(string name, OpenIddictClientOptions options) { + if (options is null) + { + throw new ArgumentNullException(nameof(options)); + } + if (options.JsonWebTokenHandler is null) { throw new InvalidOperationException(SR.GetResourceString(SR.ID0075)); diff --git a/src/OpenIddict.Client/OpenIddictClientDispatcher.cs b/src/OpenIddict.Client/OpenIddictClientDispatcher.cs index 2dcf2831..6c9fa60d 100644 --- a/src/OpenIddict.Client/OpenIddictClientDispatcher.cs +++ b/src/OpenIddict.Client/OpenIddictClientDispatcher.cs @@ -19,17 +19,22 @@ public class OpenIddictClientDispatcher : IOpenIddictClientDispatcher /// Creates a new instance of the class. /// public OpenIddictClientDispatcher( - ILogger logger!!, - IOptionsMonitor options!!, - IServiceProvider provider!!) + ILogger logger, + IOptionsMonitor options, + IServiceProvider provider) { - _logger = logger; - _options = options; - _provider = provider; + _logger = logger ?? throw new ArgumentNullException(nameof(logger)); + _options = options ?? throw new ArgumentNullException(nameof(options)); + _provider = provider ?? throw new ArgumentNullException(nameof(provider)); } - public async ValueTask DispatchAsync(TContext context!!) where TContext : BaseContext + public async ValueTask DispatchAsync(TContext context) where TContext : BaseContext { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + await foreach (var handler in GetHandlersAsync()) { try diff --git a/src/OpenIddict.Client/OpenIddictClientEvents.cs b/src/OpenIddict.Client/OpenIddictClientEvents.cs index 329d49da..0034a5a0 100644 --- a/src/OpenIddict.Client/OpenIddictClientEvents.cs +++ b/src/OpenIddict.Client/OpenIddictClientEvents.cs @@ -21,8 +21,8 @@ public static partial class OpenIddictClientEvents /// /// Creates a new instance of the class. /// - protected BaseContext(OpenIddictClientTransaction transaction!!) - => Transaction = transaction; + protected BaseContext(OpenIddictClientTransaction transaction) + => Transaction = transaction ?? throw new ArgumentNullException(nameof(transaction)); /// /// Gets the environment associated with the current request being processed. diff --git a/src/OpenIddict.Client/OpenIddictClientExtensions.cs b/src/OpenIddict.Client/OpenIddictClientExtensions.cs index f9d8f0fd..c0a76d10 100644 --- a/src/OpenIddict.Client/OpenIddictClientExtensions.cs +++ b/src/OpenIddict.Client/OpenIddictClientExtensions.cs @@ -21,8 +21,13 @@ public static class OpenIddictClientExtensions /// The services builder used by OpenIddict to register new services. /// This extension can be safely called multiple times. /// The . - public static OpenIddictClientBuilder AddClient(this OpenIddictBuilder builder!!) + public static OpenIddictClientBuilder AddClient(this OpenIddictBuilder builder) { + if (builder is null) + { + throw new ArgumentNullException(nameof(builder)); + } + builder.Services.AddLogging(); builder.Services.AddOptions(); @@ -69,8 +74,18 @@ public static class OpenIddictClientExtensions /// The configuration delegate used to configure the client services. /// This extension can be safely called multiple times. /// The . - public static OpenIddictBuilder AddClient(this OpenIddictBuilder builder!!, Action configuration!!) + public static OpenIddictBuilder AddClient(this OpenIddictBuilder builder, Action configuration) { + if (builder is null) + { + throw new ArgumentNullException(nameof(builder)); + } + + if (configuration is null) + { + throw new ArgumentNullException(nameof(configuration)); + } + configuration(builder.AddClient()); return builder; diff --git a/src/OpenIddict.Client/OpenIddictClientFactory.cs b/src/OpenIddict.Client/OpenIddictClientFactory.cs index 3d90c3f0..67e0ae99 100644 --- a/src/OpenIddict.Client/OpenIddictClientFactory.cs +++ b/src/OpenIddict.Client/OpenIddictClientFactory.cs @@ -18,11 +18,11 @@ public class OpenIddictClientFactory : IOpenIddictClientFactory /// Creates a new instance of the class. /// public OpenIddictClientFactory( - ILogger logger!!, - IOptionsMonitor options!!) + ILogger logger, + IOptionsMonitor options) { - _logger = logger; - _options = options; + _logger = logger ?? throw new ArgumentNullException(nameof(logger)); + _options = options ?? throw new ArgumentNullException(nameof(options)); } public ValueTask CreateTransactionAsync() diff --git a/src/OpenIddict.Client/OpenIddictClientHandler.cs b/src/OpenIddict.Client/OpenIddictClientHandler.cs index 3c2eea85..9abeaaf9 100644 --- a/src/OpenIddict.Client/OpenIddictClientHandler.cs +++ b/src/OpenIddict.Client/OpenIddictClientHandler.cs @@ -18,8 +18,8 @@ public class OpenIddictClientHandler : IOpenIddictClientHandler /// The event handler delegate. - public OpenIddictClientHandler(Func handler!!) - => _handler = handler; + public OpenIddictClientHandler(Func handler) + => _handler = handler ?? throw new ArgumentNullException(nameof(handler)); /// /// Processes the event. @@ -28,5 +28,6 @@ public class OpenIddictClientHandler : IOpenIddictClientHandler /// A that can be used to monitor the asynchronous operation. /// - public ValueTask HandleAsync(TContext context!!) => _handler(context); + public ValueTask HandleAsync(TContext context) + => _handler(context ?? throw new ArgumentNullException(nameof(context))); } diff --git a/src/OpenIddict.Client/OpenIddictClientHandlerDescriptor.cs b/src/OpenIddict.Client/OpenIddictClientHandlerDescriptor.cs index 5a718680..3bb67965 100644 --- a/src/OpenIddict.Client/OpenIddictClientHandlerDescriptor.cs +++ b/src/OpenIddict.Client/OpenIddictClientHandlerDescriptor.cs @@ -72,8 +72,13 @@ public class OpenIddictClientHandlerDescriptor /// /// The event handler filter type. /// The builder instance, so that calls can be easily chained. - public Builder AddFilter(Type type!!) + public Builder AddFilter(Type type) { + if (type is null) + { + throw new ArgumentNullException(nameof(type)); + } + if (!typeof(IOpenIddictClientHandlerFilter<>).MakeGenericType(typeof(TContext)).IsAssignableFrom(type)) { throw new InvalidOperationException(SR.GetResourceString(SR.ID0104)); @@ -99,8 +104,13 @@ public class OpenIddictClientHandlerDescriptor /// The existing descriptor properties are copied from. /// All the properties previously set on this instance are automatically replaced. /// The builder instance, so that calls can be easily chained. - public Builder Import(OpenIddictClientHandlerDescriptor descriptor!!) + public Builder Import(OpenIddictClientHandlerDescriptor descriptor) { + if (descriptor is null) + { + throw new ArgumentNullException(nameof(descriptor)); + } + if (descriptor.ContextType != typeof(TContext)) { throw new InvalidOperationException(SR.GetResourceString(SR.ID0284)); @@ -120,8 +130,13 @@ public class OpenIddictClientHandlerDescriptor /// /// The service descriptor. /// The builder instance, so that calls can be easily chained. - public Builder SetServiceDescriptor(ServiceDescriptor descriptor!!) + public Builder SetServiceDescriptor(ServiceDescriptor descriptor) { + if (descriptor is null) + { + throw new ArgumentNullException(nameof(descriptor)); + } + var type = descriptor.ServiceType; if (!typeof(IOpenIddictClientHandler<>).MakeGenericType(typeof(TContext)).IsAssignableFrom(type)) { @@ -167,8 +182,15 @@ public class OpenIddictClientHandlerDescriptor /// /// The handler instance. /// The builder instance, so that calls can be easily chained. - public Builder UseInlineHandler(Func handler!!) - => UseSingletonHandler(new OpenIddictClientHandler(handler)); + public Builder UseInlineHandler(Func handler) + { + if (handler is null) + { + throw new ArgumentNullException(nameof(handler)); + } + + return UseSingletonHandler(new OpenIddictClientHandler(handler)); + } /// /// Configures the descriptor to use the specified scoped handler. @@ -186,10 +208,17 @@ public class OpenIddictClientHandlerDescriptor /// The handler type. /// The factory used to create the handler. /// The builder instance, so that calls can be easily chained. - public Builder UseScopedHandler(Func factory!!) + public Builder UseScopedHandler(Func factory) where THandler : IOpenIddictClientHandler - => SetServiceDescriptor(new ServiceDescriptor( + { + if (factory is null) + { + throw new ArgumentNullException(nameof(factory)); + } + + return SetServiceDescriptor(new ServiceDescriptor( typeof(THandler), factory, ServiceLifetime.Scoped)); + } /// /// Configures the descriptor to use the specified singleton handler. @@ -207,10 +236,17 @@ public class OpenIddictClientHandlerDescriptor /// The handler type. /// The factory used to create the handler. /// The builder instance, so that calls can be easily chained. - public Builder UseSingletonHandler(Func factory!!) + public Builder UseSingletonHandler(Func factory) where THandler : IOpenIddictClientHandler - => SetServiceDescriptor(new ServiceDescriptor( + { + if (factory is null) + { + throw new ArgumentNullException(nameof(factory)); + } + + return SetServiceDescriptor(new ServiceDescriptor( typeof(THandler), factory, ServiceLifetime.Singleton)); + } /// /// Configures the descriptor to use the specified singleton handler. @@ -218,9 +254,16 @@ public class OpenIddictClientHandlerDescriptor /// The handler type. /// The handler instance. /// The builder instance, so that calls can be easily chained. - public Builder UseSingletonHandler(THandler handler!!) + public Builder UseSingletonHandler(THandler handler) where THandler : IOpenIddictClientHandler - => SetServiceDescriptor(new ServiceDescriptor(typeof(THandler), handler)); + { + if (handler is null) + { + throw new ArgumentNullException(nameof(handler)); + } + + return SetServiceDescriptor(new ServiceDescriptor(typeof(THandler), handler)); + } /// /// Build a new descriptor instance, based on the parameters that were previously set. diff --git a/src/OpenIddict.Client/OpenIddictClientHandlerFilters.cs b/src/OpenIddict.Client/OpenIddictClientHandlerFilters.cs index 4a03e9f6..6e7498d3 100644 --- a/src/OpenIddict.Client/OpenIddictClientHandlerFilters.cs +++ b/src/OpenIddict.Client/OpenIddictClientHandlerFilters.cs @@ -17,8 +17,15 @@ public static class OpenIddictClientHandlerFilters /// public class RequireAuthorizationCodeOrImplicitGrantType : IOpenIddictClientHandlerFilter { - public ValueTask IsActiveAsync(ProcessChallengeContext context!!) - => new(context.GrantType is GrantTypes.AuthorizationCode or GrantTypes.Implicit); + public ValueTask IsActiveAsync(ProcessChallengeContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(context.GrantType is GrantTypes.AuthorizationCode or GrantTypes.Implicit); + } } /// @@ -26,8 +33,15 @@ public static class OpenIddictClientHandlerFilters /// public class RequireAuthorizationCodeValidated : IOpenIddictClientHandlerFilter { - public ValueTask IsActiveAsync(ProcessAuthenticationContext context!!) - => new(context.ValidateAuthorizationCode); + public ValueTask IsActiveAsync(ProcessAuthenticationContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(context.ValidateAuthorizationCode); + } } /// @@ -35,8 +49,15 @@ public static class OpenIddictClientHandlerFilters /// public class RequireBackchannelAccessTokenValidated : IOpenIddictClientHandlerFilter { - public ValueTask IsActiveAsync(ProcessAuthenticationContext context!!) - => new(context.ValidateBackchannelAccessToken); + public ValueTask IsActiveAsync(ProcessAuthenticationContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(context.ValidateBackchannelAccessToken); + } } /// @@ -44,8 +65,15 @@ public static class OpenIddictClientHandlerFilters /// public class RequireBackchannelIdentityTokenPrincipal : IOpenIddictClientHandlerFilter { - public ValueTask IsActiveAsync(ProcessAuthenticationContext context!!) - => new(context.BackchannelIdentityTokenPrincipal is not null); + public ValueTask IsActiveAsync(ProcessAuthenticationContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(context.BackchannelIdentityTokenPrincipal is not null); + } } /// @@ -53,8 +81,15 @@ public static class OpenIddictClientHandlerFilters /// public class RequireBackchannelIdentityTokenValidated : IOpenIddictClientHandlerFilter { - public ValueTask IsActiveAsync(ProcessAuthenticationContext context!!) - => new(context.ValidateBackchannelIdentityToken); + public ValueTask IsActiveAsync(ProcessAuthenticationContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(context.ValidateBackchannelIdentityToken); + } } /// @@ -62,8 +97,15 @@ public static class OpenIddictClientHandlerFilters /// public class RequireFrontchannelAccessTokenValidated : IOpenIddictClientHandlerFilter { - public ValueTask IsActiveAsync(ProcessAuthenticationContext context!!) - => new(context.ValidateFrontchannelAccessToken); + public ValueTask IsActiveAsync(ProcessAuthenticationContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(context.ValidateFrontchannelAccessToken); + } } /// @@ -71,8 +113,15 @@ public static class OpenIddictClientHandlerFilters /// public class RequireFrontchannelIdentityTokenPrincipal : IOpenIddictClientHandlerFilter { - public ValueTask IsActiveAsync(ProcessAuthenticationContext context!!) - => new(context.FrontchannelIdentityTokenPrincipal is not null); + public ValueTask IsActiveAsync(ProcessAuthenticationContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(context.FrontchannelIdentityTokenPrincipal is not null); + } } /// @@ -80,8 +129,15 @@ public static class OpenIddictClientHandlerFilters /// public class RequireFrontchannelIdentityTokenValidated : IOpenIddictClientHandlerFilter { - public ValueTask IsActiveAsync(ProcessAuthenticationContext context!!) - => new(context.ValidateFrontchannelIdentityToken); + public ValueTask IsActiveAsync(ProcessAuthenticationContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(context.ValidateFrontchannelIdentityToken); + } } /// @@ -89,8 +145,15 @@ public static class OpenIddictClientHandlerFilters /// public class RequireRedirectionRequest : IOpenIddictClientHandlerFilter { - public ValueTask IsActiveAsync(BaseContext context!!) - => new(context.EndpointType is OpenIddictClientEndpointType.Redirection); + public ValueTask IsActiveAsync(BaseContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(context.EndpointType is OpenIddictClientEndpointType.Redirection); + } } /// @@ -98,8 +161,15 @@ public static class OpenIddictClientHandlerFilters /// public class RequireRefreshTokenValidated : IOpenIddictClientHandlerFilter { - public ValueTask IsActiveAsync(ProcessAuthenticationContext context!!) - => new(context.ValidateRefreshToken); + public ValueTask IsActiveAsync(ProcessAuthenticationContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(context.ValidateRefreshToken); + } } /// @@ -107,8 +177,15 @@ public static class OpenIddictClientHandlerFilters /// public class RequireStateTokenGenerated : IOpenIddictClientHandlerFilter { - public ValueTask IsActiveAsync(ProcessChallengeContext context!!) - => new(context.GenerateStateToken); + public ValueTask IsActiveAsync(ProcessChallengeContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(context.GenerateStateToken); + } } /// @@ -116,8 +193,15 @@ public static class OpenIddictClientHandlerFilters /// public class RequireStateTokenPrincipal : IOpenIddictClientHandlerFilter { - public ValueTask IsActiveAsync(ProcessAuthenticationContext context!!) - => new(context.StateTokenPrincipal is not null); + public ValueTask IsActiveAsync(ProcessAuthenticationContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(context.StateTokenPrincipal is not null); + } } /// @@ -125,8 +209,15 @@ public static class OpenIddictClientHandlerFilters /// public class RequireStateTokenValidated : IOpenIddictClientHandlerFilter { - public ValueTask IsActiveAsync(ProcessAuthenticationContext context!!) - => new(context.ValidateStateToken); + public ValueTask IsActiveAsync(ProcessAuthenticationContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(context.ValidateStateToken); + } } /// @@ -134,8 +225,15 @@ public static class OpenIddictClientHandlerFilters /// public class RequireTokenRequest : IOpenIddictClientHandlerFilter { - public ValueTask IsActiveAsync(ProcessAuthenticationContext context!!) - => new(context.TokenRequest is not null); + public ValueTask IsActiveAsync(ProcessAuthenticationContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(context.TokenRequest is not null); + } } /// @@ -143,8 +241,15 @@ public static class OpenIddictClientHandlerFilters /// public class RequireTokenResponse : IOpenIddictClientHandlerFilter { - public ValueTask IsActiveAsync(ProcessAuthenticationContext context!!) - => new(context.TokenResponse is not null); + public ValueTask IsActiveAsync(ProcessAuthenticationContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(context.TokenResponse is not null); + } } /// @@ -152,8 +257,15 @@ public static class OpenIddictClientHandlerFilters /// public class RequireUserinfoRequest : IOpenIddictClientHandlerFilter { - public ValueTask IsActiveAsync(ProcessAuthenticationContext context!!) - => new(context.UserinfoRequest is not null); + public ValueTask IsActiveAsync(ProcessAuthenticationContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(context.UserinfoRequest is not null); + } } /// @@ -161,8 +273,15 @@ public static class OpenIddictClientHandlerFilters /// public class RequireUserinfoResponse : IOpenIddictClientHandlerFilter { - public ValueTask IsActiveAsync(ProcessAuthenticationContext context!!) - => new(context.UserinfoResponse is not null); + public ValueTask IsActiveAsync(ProcessAuthenticationContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(context.UserinfoResponse is not null); + } } /// @@ -170,8 +289,15 @@ public static class OpenIddictClientHandlerFilters /// public class RequireUserinfoTokenExtracted : IOpenIddictClientHandlerFilter { - public ValueTask IsActiveAsync(ProcessAuthenticationContext context!!) - => new(context.ExtractUserinfoToken); + public ValueTask IsActiveAsync(ProcessAuthenticationContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(context.ExtractUserinfoToken); + } } /// @@ -179,7 +305,14 @@ public static class OpenIddictClientHandlerFilters /// public class RequireUserinfoTokenPrincipal : IOpenIddictClientHandlerFilter { - public ValueTask IsActiveAsync(ProcessAuthenticationContext context!!) - => new(context.UserinfoTokenPrincipal is not null); + public ValueTask IsActiveAsync(ProcessAuthenticationContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(context.UserinfoTokenPrincipal is not null); + } } } diff --git a/src/OpenIddict.Client/OpenIddictClientHandlers.Authentication.cs b/src/OpenIddict.Client/OpenIddictClientHandlers.Authentication.cs index d3b33390..65b7d114 100644 --- a/src/OpenIddict.Client/OpenIddictClientHandlers.Authentication.cs +++ b/src/OpenIddict.Client/OpenIddictClientHandlers.Authentication.cs @@ -51,8 +51,8 @@ public static partial class OpenIddictClientHandlers { private readonly IOpenIddictClientDispatcher _dispatcher; - public PrepareAuthorizationRequest(IOpenIddictClientDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public PrepareAuthorizationRequest(IOpenIddictClientDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -65,8 +65,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessChallengeContext context!!) + public async ValueTask HandleAsync(ProcessChallengeContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var notification = new PrepareAuthorizationRequestContext(context.Transaction); await _dispatcher.DispatchAsync(notification); @@ -91,8 +96,8 @@ public static partial class OpenIddictClientHandlers { private readonly IOpenIddictClientDispatcher _dispatcher; - public ApplyAuthorizationRequest(IOpenIddictClientDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public ApplyAuthorizationRequest(IOpenIddictClientDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -105,8 +110,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessChallengeContext context!!) + public async ValueTask HandleAsync(ProcessChallengeContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var notification = new ApplyAuthorizationRequestContext(context.Transaction); await _dispatcher.DispatchAsync(notification); @@ -139,8 +149,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public async ValueTask HandleAsync(ApplyAuthorizationRequestContext context!!) + public async ValueTask HandleAsync(ApplyAuthorizationRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var configuration = await context.Registration.ConfigurationManager.GetConfigurationAsync(default) ?? throw new InvalidOperationException(SR.GetResourceString(SR.ID0140)); @@ -168,8 +183,8 @@ public static partial class OpenIddictClientHandlers { private readonly IOpenIddictClientDispatcher _dispatcher; - public ExtractRedirectionRequest(IOpenIddictClientDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public ExtractRedirectionRequest(IOpenIddictClientDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -182,8 +197,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessRequestContext context!!) + public async ValueTask HandleAsync(ProcessRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var notification = new ExtractRedirectionRequestContext(context.Transaction); await _dispatcher.DispatchAsync(notification); @@ -224,8 +244,8 @@ public static partial class OpenIddictClientHandlers { private readonly IOpenIddictClientDispatcher _dispatcher; - public ValidateRedirectionRequest(IOpenIddictClientDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public ValidateRedirectionRequest(IOpenIddictClientDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -239,8 +259,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessRequestContext context!!) + public async ValueTask HandleAsync(ProcessRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var notification = new ValidateRedirectionRequestContext(context.Transaction); await _dispatcher.DispatchAsync(notification); @@ -276,8 +301,8 @@ public static partial class OpenIddictClientHandlers { private readonly IOpenIddictClientDispatcher _dispatcher; - public HandleRedirectionRequest(IOpenIddictClientDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public HandleRedirectionRequest(IOpenIddictClientDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -290,8 +315,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessRequestContext context!!) + public async ValueTask HandleAsync(ProcessRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var notification = new HandleRedirectionRequestContext(context.Transaction); await _dispatcher.DispatchAsync(notification); @@ -327,8 +357,8 @@ public static partial class OpenIddictClientHandlers { private readonly IOpenIddictClientDispatcher _dispatcher; - public ApplyRedirectionResponse(IOpenIddictClientDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public ApplyRedirectionResponse(IOpenIddictClientDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -342,8 +372,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public async ValueTask HandleAsync(TContext context!!) + public async ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var notification = new ApplyRedirectionResponseContext(context.Transaction); await _dispatcher.DispatchAsync(notification); @@ -379,8 +414,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public ValueTask HandleAsync(PrepareAuthorizationRequestContext context!!) + public ValueTask HandleAsync(PrepareAuthorizationRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // When the response mode corresponds to the default mode assigned to the selected // response type, the specification explicitly recommends omitting the response mode. // As such, this handler is expected to remove the mode parameter in the following cases: @@ -411,8 +451,8 @@ public static partial class OpenIddictClientHandlers { private readonly IOpenIddictClientDispatcher _dispatcher; - public ValidateTokens(IOpenIddictClientDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public ValidateTokens(IOpenIddictClientDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -425,8 +465,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public async ValueTask HandleAsync(ValidateRedirectionRequestContext context!!) + public async ValueTask HandleAsync(ValidateRedirectionRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var notification = new ProcessAuthenticationContext(context.Transaction); await _dispatcher.DispatchAsync(notification); diff --git a/src/OpenIddict.Client/OpenIddictClientHandlers.Discovery.cs b/src/OpenIddict.Client/OpenIddictClientHandlers.Discovery.cs index 59693226..b8da3cce 100644 --- a/src/OpenIddict.Client/OpenIddictClientHandlers.Discovery.cs +++ b/src/OpenIddict.Client/OpenIddictClientHandlers.Discovery.cs @@ -56,8 +56,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public ValueTask HandleAsync(HandleConfigurationResponseContext context!!) + public ValueTask HandleAsync(HandleConfigurationResponseContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + foreach (var parameter in context.Response.GetParameters()) { if (!ValidateParameterType(parameter.Key, parameter.Value)) @@ -139,8 +144,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public ValueTask HandleAsync(HandleConfigurationResponseContext context!!) + public ValueTask HandleAsync(HandleConfigurationResponseContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // The issuer returned in the discovery document must exactly match the URL used to access it. // See https://openid.net/specs/openid-connect-discovery-1_0.html#ProviderConfigurationClient. var issuer = (string?) context.Response[Metadata.Issuer]; @@ -186,8 +196,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public ValueTask HandleAsync(HandleConfigurationResponseContext context!!) + public ValueTask HandleAsync(HandleConfigurationResponseContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // Note: the authorization_endpoint node is required by the OpenID Connect discovery specification // but is optional in the OAuth 2.0 authorization server metadata specification. To make OpenIddict // compatible with the newer OAuth 2.0 specification, null/empty and missing values are allowed here. @@ -233,8 +248,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public ValueTask HandleAsync(HandleConfigurationResponseContext context!!) + public ValueTask HandleAsync(HandleConfigurationResponseContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // Note: the jwks_uri node is required by the OpenID Connect discovery specification. // See https://openid.net/specs/openid-connect-discovery-1_0.html#ProviderConfigurationClient. var address = (string?) context.Response[Metadata.JwksUri]; @@ -280,8 +300,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public ValueTask HandleAsync(HandleConfigurationResponseContext context!!) + public ValueTask HandleAsync(HandleConfigurationResponseContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var address = (string?) context.Response[Metadata.TokenEndpoint]; if (!string.IsNullOrEmpty(address)) { @@ -318,8 +343,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public ValueTask HandleAsync(HandleConfigurationResponseContext context!!) + public ValueTask HandleAsync(HandleConfigurationResponseContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var address = (string?) context.Response[Metadata.UserinfoEndpoint]; if (!string.IsNullOrEmpty(address)) { @@ -356,8 +386,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public ValueTask HandleAsync(HandleConfigurationResponseContext context!!) + public ValueTask HandleAsync(HandleConfigurationResponseContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // Resolve the grant types supported by the authorization endpoint, if available. var types = context.Response[Metadata.GrantTypesSupported]?.GetUnnamedParameters(); if (types is { Count: > 0 }) @@ -393,8 +428,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public ValueTask HandleAsync(HandleConfigurationResponseContext context!!) + public ValueTask HandleAsync(HandleConfigurationResponseContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // Resolve the response modes supported by the authorization endpoint, if available. var modes = context.Response[Metadata.ResponseModesSupported]?.GetUnnamedParameters(); if (modes is { Count: > 0 }) @@ -430,8 +470,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public ValueTask HandleAsync(HandleConfigurationResponseContext context!!) + public ValueTask HandleAsync(HandleConfigurationResponseContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // Resolve the response types supported by the authorization endpoint, if available. var types = context.Response[Metadata.ResponseTypesSupported]?.GetUnnamedParameters(); if (types is { Count: > 0 }) @@ -467,8 +512,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public ValueTask HandleAsync(HandleConfigurationResponseContext context!!) + public ValueTask HandleAsync(HandleConfigurationResponseContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // Resolve the code challenge methods supported by the authorization endpoint, if available. var methods = context.Response[Metadata.CodeChallengeMethodsSupported]?.GetUnnamedParameters(); if (methods is { Count: > 0 }) @@ -504,8 +554,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public ValueTask HandleAsync(HandleConfigurationResponseContext context!!) + public ValueTask HandleAsync(HandleConfigurationResponseContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // Resolve the scopes supported by the remote server, if available. var scopes = context.Response[Metadata.ScopesSupported]?.GetUnnamedParameters(); if (scopes is { Count: > 0 }) @@ -542,8 +597,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public ValueTask HandleAsync(HandleConfigurationResponseContext context!!) + public ValueTask HandleAsync(HandleConfigurationResponseContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + context.Configuration.AuthorizationResponseIssParameterSupported = (bool?) context.Response[Metadata.AuthorizationResponseIssParameterSupported]; @@ -568,8 +628,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public ValueTask HandleAsync(HandleConfigurationResponseContext context!!) + public ValueTask HandleAsync(HandleConfigurationResponseContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // Resolve the client authentication methods supported by the token endpoint, if available. var methods = context.Response[Metadata.TokenEndpointAuthMethodsSupported]?.GetUnnamedParameters(); if (methods is { Count: > 0 }) @@ -605,8 +670,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public ValueTask HandleAsync(HandleCryptographyResponseContext context!!) + public ValueTask HandleAsync(HandleCryptographyResponseContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + foreach (var parameter in context.Response.GetParameters()) { if (!ValidateParameterType(parameter.Key, parameter.Value)) @@ -670,8 +740,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public ValueTask HandleAsync(HandleCryptographyResponseContext context!!) + public ValueTask HandleAsync(HandleCryptographyResponseContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var keys = context.Response[JsonWebKeySetParameterNames.Keys]?.GetUnnamedParameters(); if (keys is not { Count: > 0 }) { diff --git a/src/OpenIddict.Client/OpenIddictClientHandlers.Exchange.cs b/src/OpenIddict.Client/OpenIddictClientHandlers.Exchange.cs index 4393df4c..ac9869e8 100644 --- a/src/OpenIddict.Client/OpenIddictClientHandlers.Exchange.cs +++ b/src/OpenIddict.Client/OpenIddictClientHandlers.Exchange.cs @@ -36,8 +36,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public ValueTask HandleAsync(HandleTokenResponseContext context!!) + public ValueTask HandleAsync(HandleTokenResponseContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + foreach (var parameter in context.Response.GetParameters()) { if (!ValidateParameterType(parameter.Key, parameter.Value)) diff --git a/src/OpenIddict.Client/OpenIddictClientHandlers.Protection.cs b/src/OpenIddict.Client/OpenIddictClientHandlers.Protection.cs index 9916a17d..d0170bdd 100644 --- a/src/OpenIddict.Client/OpenIddictClientHandlers.Protection.cs +++ b/src/OpenIddict.Client/OpenIddictClientHandlers.Protection.cs @@ -50,8 +50,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public async ValueTask HandleAsync(ValidateTokenContext context!!) + public async ValueTask HandleAsync(ValidateTokenContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // The OpenIddict client is expected to validate tokens it creates (e.g state tokens) and // tokens that are created by one or multiple authorization servers (e.g identity tokens). // @@ -157,8 +162,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public async ValueTask HandleAsync(ValidateTokenContext context!!) + public async ValueTask HandleAsync(ValidateTokenContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // If a principal was already attached, don't overwrite it. if (context.Principal is not null) { @@ -268,8 +278,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public ValueTask HandleAsync(ValidateTokenContext context!!) + public ValueTask HandleAsync(ValidateTokenContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // Note: only map the private claims from fully trusted tokens. if (context.Principal is null || !context.Principal.HasTokenType(TokenTypeHints.StateToken)) { @@ -320,8 +335,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public ValueTask HandleAsync(ValidateTokenContext context!!) + public ValueTask HandleAsync(ValidateTokenContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + if (context.Principal is null) { context.Reject( @@ -367,8 +387,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public ValueTask HandleAsync(ValidateTokenContext context!!) + public ValueTask HandleAsync(ValidateTokenContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.Principal is { Identity: ClaimsIdentity }, SR.GetResourceString(SR.ID4006)); var date = context.Principal.GetExpirationDate(); @@ -402,8 +427,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public ValueTask HandleAsync(GenerateTokenContext context!!) + public ValueTask HandleAsync(GenerateTokenContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + context.SecurityTokenHandler = context.Options.JsonWebTokenHandler; context.EncryptionCredentials = context.Options.EncryptionCredentials.First(); @@ -429,8 +459,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public ValueTask HandleAsync(GenerateTokenContext context!!) + public ValueTask HandleAsync(GenerateTokenContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // If a token was already attached by another handler, don't overwrite it. if (!string.IsNullOrEmpty(context.Token)) { diff --git a/src/OpenIddict.Client/OpenIddictClientHandlers.Userinfo.cs b/src/OpenIddict.Client/OpenIddictClientHandlers.Userinfo.cs index fb5005ce..102c124f 100644 --- a/src/OpenIddict.Client/OpenIddictClientHandlers.Userinfo.cs +++ b/src/OpenIddict.Client/OpenIddictClientHandlers.Userinfo.cs @@ -39,8 +39,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public ValueTask HandleAsync(HandleUserinfoResponseContext context!!) + public ValueTask HandleAsync(HandleUserinfoResponseContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // Ignore the response instance if a userinfo token was extracted. if (!string.IsNullOrEmpty(context.UserinfoToken)) { @@ -96,8 +101,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public async ValueTask HandleAsync(HandleUserinfoResponseContext context!!) + public async ValueTask HandleAsync(HandleUserinfoResponseContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // Ignore the response instance if a userinfo token was extracted. if (!string.IsNullOrEmpty(context.UserinfoToken)) { diff --git a/src/OpenIddict.Client/OpenIddictClientHandlers.cs b/src/OpenIddict.Client/OpenIddictClientHandlers.cs index 5376ca6d..004382dc 100644 --- a/src/OpenIddict.Client/OpenIddictClientHandlers.cs +++ b/src/OpenIddict.Client/OpenIddictClientHandlers.cs @@ -127,8 +127,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public ValueTask HandleAsync(ProcessAuthenticationContext context!!) + public ValueTask HandleAsync(ProcessAuthenticationContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // Authentication demands can be triggered from the redirection endpoint // to handle authorization callbacks but also from unknown endpoints // when using the refresh token grant, to perform a token refresh dance. @@ -179,8 +184,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public ValueTask HandleAsync(ProcessAuthenticationContext context!!) + public ValueTask HandleAsync(ProcessAuthenticationContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + (context.ExtractStateToken, context.RequireStateToken, context.ValidateStateToken) = context.EndpointType switch @@ -215,8 +225,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public ValueTask HandleAsync(ProcessAuthenticationContext context!!) + public ValueTask HandleAsync(ProcessAuthenticationContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + context.StateToken = context.EndpointType switch { OpenIddictClientEndpointType.Redirection when context.ExtractStateToken @@ -245,8 +260,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public ValueTask HandleAsync(ProcessAuthenticationContext context!!) + public ValueTask HandleAsync(ProcessAuthenticationContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + if (context.RequireStateToken && string.IsNullOrEmpty(context.StateToken)) { context.Reject( @@ -268,8 +288,8 @@ public static partial class OpenIddictClientHandlers { private readonly IOpenIddictClientDispatcher _dispatcher; - public ValidateStateToken(IOpenIddictClientDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public ValidateStateToken(IOpenIddictClientDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -283,8 +303,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessAuthenticationContext context!!) + public async ValueTask HandleAsync(ProcessAuthenticationContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + if (context.StateTokenPrincipal is not null || string.IsNullOrEmpty(context.StateToken)) { @@ -341,8 +366,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public ValueTask HandleAsync(ProcessAuthenticationContext context!!) + public ValueTask HandleAsync(ProcessAuthenticationContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.StateTokenPrincipal is { Identity: ClaimsIdentity }, SR.GetResourceString(SR.ID4006)); // Retrieve the client definition using the authorization server stored in the state token. @@ -391,8 +421,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessAuthenticationContext context!!) + public async ValueTask HandleAsync(ProcessAuthenticationContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.Issuer is { IsAbsoluteUri: true }, SR.GetResourceString(SR.ID4013)); var configuration = await context.Registration.ConfigurationManager.GetConfigurationAsync(default) ?? @@ -477,8 +512,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public ValueTask HandleAsync(ProcessAuthenticationContext context!!) + public ValueTask HandleAsync(ProcessAuthenticationContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var (error, description, uri) = ( (string?) context.Request[Parameters.Error], (string?) context.Request[Parameters.ErrorDescription], @@ -516,8 +556,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public ValueTask HandleAsync(ProcessAuthenticationContext context!!) + public ValueTask HandleAsync(ProcessAuthenticationContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.StateTokenPrincipal is { Identity: ClaimsIdentity }, SR.GetResourceString(SR.ID4006)); // Resolve the negotiated grant type from the state token. @@ -564,8 +609,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public ValueTask HandleAsync(ProcessAuthenticationContext context!!) + public ValueTask HandleAsync(ProcessAuthenticationContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.StateTokenPrincipal is { Identity: ClaimsIdentity }, SR.GetResourceString(SR.ID4006)); // Resolve the negotiated response type from the state token. @@ -591,8 +641,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public ValueTask HandleAsync(ProcessAuthenticationContext context!!) + public ValueTask HandleAsync(ProcessAuthenticationContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + (context.ExtractAuthorizationCode, context.RequireAuthorizationCode, context.ValidateAuthorizationCode) = context.GrantType switch @@ -668,8 +723,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public ValueTask HandleAsync(ProcessAuthenticationContext context!!) + public ValueTask HandleAsync(ProcessAuthenticationContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + context.AuthorizationCode = context.EndpointType switch { OpenIddictClientEndpointType.Redirection when context.ExtractAuthorizationCode @@ -714,8 +774,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public ValueTask HandleAsync(ProcessAuthenticationContext context!!) + public ValueTask HandleAsync(ProcessAuthenticationContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + if ((context.RequireAuthorizationCode && string.IsNullOrEmpty(context.AuthorizationCode)) || (context.RequireFrontchannelAccessToken && string.IsNullOrEmpty(context.FrontchannelAccessToken)) || (context.RequireFrontchannelIdentityToken && string.IsNullOrEmpty(context.FrontchannelIdentityToken))) @@ -739,8 +804,8 @@ public static partial class OpenIddictClientHandlers { private readonly IOpenIddictClientDispatcher _dispatcher; - public ValidateFrontchannelIdentityToken(IOpenIddictClientDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public ValidateFrontchannelIdentityToken(IOpenIddictClientDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -754,8 +819,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessAuthenticationContext context!!) + public async ValueTask HandleAsync(ProcessAuthenticationContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + if (context.FrontchannelIdentityTokenPrincipal is not null || string.IsNullOrEmpty(context.FrontchannelIdentityToken)) { @@ -812,8 +882,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public ValueTask HandleAsync(ProcessAuthenticationContext context!!) + public ValueTask HandleAsync(ProcessAuthenticationContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.FrontchannelIdentityTokenPrincipal is { Identity: ClaimsIdentity }, SR.GetResourceString(SR.ID4006)); foreach (var group in context.FrontchannelIdentityTokenPrincipal.Claims @@ -943,8 +1018,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public ValueTask HandleAsync(ProcessAuthenticationContext context!!) + public ValueTask HandleAsync(ProcessAuthenticationContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.FrontchannelIdentityTokenPrincipal is { Identity: ClaimsIdentity }, SR.GetResourceString(SR.ID4006)); // Note: while an identity token typically contains a single audience represented @@ -983,8 +1063,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public ValueTask HandleAsync(ProcessAuthenticationContext context!!) + public ValueTask HandleAsync(ProcessAuthenticationContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.FrontchannelIdentityTokenPrincipal is { Identity: ClaimsIdentity }, SR.GetResourceString(SR.ID4006)); // Note: the "azp" claim is optional, but if it's present, it MUST match the client identifier of the application. @@ -1022,8 +1107,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public ValueTask HandleAsync(ProcessAuthenticationContext context!!) + public ValueTask HandleAsync(ProcessAuthenticationContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.FrontchannelIdentityTokenPrincipal is { Identity: ClaimsIdentity }, SR.GetResourceString(SR.ID4006)); Debug.Assert(context.StateTokenPrincipal is { Identity: ClaimsIdentity }, SR.GetResourceString(SR.ID4006)); @@ -1080,8 +1170,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public ValueTask HandleAsync(ProcessAuthenticationContext context!!) + public ValueTask HandleAsync(ProcessAuthenticationContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.FrontchannelIdentityTokenPrincipal is { Identity: ClaimsIdentity }, SR.GetResourceString(SR.ID4006)); // Resolve the signing algorithm used to sign the identity token. If the private @@ -1200,8 +1295,8 @@ public static partial class OpenIddictClientHandlers { private readonly IOpenIddictClientDispatcher _dispatcher; - public ValidateFrontchannelAccessToken(IOpenIddictClientDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public ValidateFrontchannelAccessToken(IOpenIddictClientDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -1215,8 +1310,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessAuthenticationContext context!!) + public async ValueTask HandleAsync(ProcessAuthenticationContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + if (context.FrontchannelAccessTokenPrincipal is not null || string.IsNullOrEmpty(context.FrontchannelAccessToken)) { @@ -1265,8 +1365,8 @@ public static partial class OpenIddictClientHandlers { private readonly IOpenIddictClientDispatcher _dispatcher; - public ValidateAuthorizationCode(IOpenIddictClientDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public ValidateAuthorizationCode(IOpenIddictClientDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -1280,8 +1380,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessAuthenticationContext context!!) + public async ValueTask HandleAsync(ProcessAuthenticationContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + if (context.AuthorizationCodePrincipal is not null || string.IsNullOrEmpty(context.AuthorizationCode)) { @@ -1337,8 +1442,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public ValueTask HandleAsync(ProcessAuthenticationContext context!!) + public ValueTask HandleAsync(ProcessAuthenticationContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + (context.ExtractBackchannelAccessToken, context.RequireBackchannelAccessToken, context.ValidateBackchannelAccessToken) = context.GrantType switch @@ -1424,8 +1534,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessAuthenticationContext context!!) + public async ValueTask HandleAsync(ProcessAuthenticationContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + if (!context.ExtractBackchannelAccessToken && !context.ExtractBackchannelIdentityToken && !context.ExtractRefreshToken) @@ -1465,8 +1580,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public ValueTask HandleAsync(ProcessAuthenticationContext context!!) + public ValueTask HandleAsync(ProcessAuthenticationContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + if (!context.ExtractBackchannelAccessToken && !context.ExtractBackchannelIdentityToken && !context.ExtractRefreshToken) @@ -1530,7 +1650,7 @@ public static partial class OpenIddictClientHandlers private readonly OpenIddictClientService _service; public SendTokenRequest(OpenIddictClientService service) - => _service = service; + => _service = service ?? throw new ArgumentNullException(nameof(service)); /// /// Gets the default descriptor definition assigned to this handler. @@ -1543,8 +1663,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessAuthenticationContext context!!) + public async ValueTask HandleAsync(ProcessAuthenticationContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.TokenRequest is not null, SR.GetResourceString(SR.ID4008)); // Ensure the token endpoint is present and is a valid absolute URL. @@ -1575,8 +1700,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public ValueTask HandleAsync(ProcessAuthenticationContext context!!) + public ValueTask HandleAsync(ProcessAuthenticationContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.TokenResponse is not null, SR.GetResourceString(SR.ID4007)); if (!string.IsNullOrEmpty(context.TokenResponse.Error)) @@ -1609,8 +1739,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public ValueTask HandleAsync(ProcessAuthenticationContext context!!) + public ValueTask HandleAsync(ProcessAuthenticationContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.TokenResponse is not null, SR.GetResourceString(SR.ID4007)); context.BackchannelAccessToken = context.ExtractBackchannelAccessToken switch @@ -1651,8 +1786,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public ValueTask HandleAsync(ProcessAuthenticationContext context!!) + public ValueTask HandleAsync(ProcessAuthenticationContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + if ((context.RequireBackchannelAccessToken && string.IsNullOrEmpty(context.BackchannelAccessToken)) || (context.RequireBackchannelIdentityToken && string.IsNullOrEmpty(context.BackchannelIdentityToken)) || (context.RequireRefreshToken && string.IsNullOrEmpty(context.RefreshToken))) @@ -1676,8 +1816,8 @@ public static partial class OpenIddictClientHandlers { private readonly IOpenIddictClientDispatcher _dispatcher; - public ValidateBackchannelIdentityToken(IOpenIddictClientDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public ValidateBackchannelIdentityToken(IOpenIddictClientDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -1691,8 +1831,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessAuthenticationContext context!!) + public async ValueTask HandleAsync(ProcessAuthenticationContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + if (context.BackchannelIdentityTokenPrincipal is not null || string.IsNullOrEmpty(context.BackchannelIdentityToken)) { @@ -1749,8 +1894,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public ValueTask HandleAsync(ProcessAuthenticationContext context!!) + public ValueTask HandleAsync(ProcessAuthenticationContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.BackchannelIdentityTokenPrincipal is { Identity: ClaimsIdentity }, SR.GetResourceString(SR.ID4006)); foreach (var group in context.BackchannelIdentityTokenPrincipal.Claims @@ -1880,8 +2030,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public ValueTask HandleAsync(ProcessAuthenticationContext context!!) + public ValueTask HandleAsync(ProcessAuthenticationContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.BackchannelIdentityTokenPrincipal is { Identity: ClaimsIdentity }, SR.GetResourceString(SR.ID4006)); // Note: while an identity token typically contains a single audience represented @@ -1920,8 +2075,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public ValueTask HandleAsync(ProcessAuthenticationContext context!!) + public ValueTask HandleAsync(ProcessAuthenticationContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.BackchannelIdentityTokenPrincipal is { Identity: ClaimsIdentity }, SR.GetResourceString(SR.ID4006)); // Note: the "azp" claim is optional, but if it's present, it MUST match the client identifier of the application. @@ -1959,8 +2119,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public ValueTask HandleAsync(ProcessAuthenticationContext context!!) + public ValueTask HandleAsync(ProcessAuthenticationContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.BackchannelIdentityTokenPrincipal is { Identity: ClaimsIdentity }, SR.GetResourceString(SR.ID4006)); Debug.Assert(context.StateTokenPrincipal is { Identity: ClaimsIdentity }, SR.GetResourceString(SR.ID4006)); @@ -2017,8 +2182,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public ValueTask HandleAsync(ProcessAuthenticationContext context!!) + public ValueTask HandleAsync(ProcessAuthenticationContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.BackchannelIdentityTokenPrincipal is { Identity: ClaimsIdentity }, SR.GetResourceString(SR.ID4006)); Debug.Assert(!string.IsNullOrEmpty(context.BackchannelAccessToken), SR.GetResourceString(SR.ID4010)); @@ -2110,8 +2280,8 @@ public static partial class OpenIddictClientHandlers { private readonly IOpenIddictClientDispatcher _dispatcher; - public ValidateBackchannelAccessToken(IOpenIddictClientDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public ValidateBackchannelAccessToken(IOpenIddictClientDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -2125,8 +2295,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessAuthenticationContext context!!) + public async ValueTask HandleAsync(ProcessAuthenticationContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + if (context.BackchannelAccessTokenPrincipal is not null || string.IsNullOrEmpty(context.BackchannelAccessToken)) { @@ -2175,8 +2350,8 @@ public static partial class OpenIddictClientHandlers { private readonly IOpenIddictClientDispatcher _dispatcher; - public ValidateRefreshToken(IOpenIddictClientDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public ValidateRefreshToken(IOpenIddictClientDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -2190,8 +2365,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessAuthenticationContext context!!) + public async ValueTask HandleAsync(ProcessAuthenticationContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + if (context.RefreshTokenPrincipal is not null || string.IsNullOrEmpty(context.RefreshToken)) { @@ -2247,8 +2427,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessAuthenticationContext context!!) + public async ValueTask HandleAsync(ProcessAuthenticationContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var configuration = await context.Registration.ConfigurationManager.GetConfigurationAsync(default) ?? throw new InvalidOperationException(SR.GetResourceString(SR.ID0140)); @@ -2282,8 +2467,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessAuthenticationContext context!!) + public async ValueTask HandleAsync(ProcessAuthenticationContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var configuration = await context.Registration.ConfigurationManager.GetConfigurationAsync(default) ?? throw new InvalidOperationException(SR.GetResourceString(SR.ID0140)); @@ -2335,8 +2525,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public ValueTask HandleAsync(ProcessAuthenticationContext context!!) + public ValueTask HandleAsync(ProcessAuthenticationContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // Attach a new request instance if necessary. context.UserinfoRequest ??= new OpenIddictRequest(); @@ -2365,7 +2560,7 @@ public static partial class OpenIddictClientHandlers private readonly OpenIddictClientService _service; public SendUserinfoRequest(OpenIddictClientService service) - => _service = service; + => _service = service ?? throw new ArgumentNullException(nameof(service)); /// /// Gets the default descriptor definition assigned to this handler. @@ -2378,8 +2573,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessAuthenticationContext context!!) + public async ValueTask HandleAsync(ProcessAuthenticationContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.UserinfoRequest is not null, SR.GetResourceString(SR.ID4008)); // Ensure the userinfo endpoint is present and is a valid absolute URL. @@ -2414,8 +2614,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public ValueTask HandleAsync(ProcessAuthenticationContext context!!) + public ValueTask HandleAsync(ProcessAuthenticationContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.UserinfoResponse is not null, SR.GetResourceString(SR.ID4007)); if (!string.IsNullOrEmpty(context.UserinfoResponse.Error)) @@ -2448,8 +2653,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public ValueTask HandleAsync(ProcessAuthenticationContext context!!) + public ValueTask HandleAsync(ProcessAuthenticationContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + if (context.RequireUserinfoToken && string.IsNullOrEmpty(context.UserinfoToken)) { context.Reject( @@ -2471,8 +2681,8 @@ public static partial class OpenIddictClientHandlers { private readonly IOpenIddictClientDispatcher _dispatcher; - public ValidateUserinfoToken(IOpenIddictClientDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public ValidateUserinfoToken(IOpenIddictClientDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -2486,8 +2696,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessAuthenticationContext context!!) + public async ValueTask HandleAsync(ProcessAuthenticationContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + if (context.UserinfoTokenPrincipal is not null || string.IsNullOrEmpty(context.UserinfoToken)) { @@ -2544,8 +2759,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessAuthenticationContext context!!) + public async ValueTask HandleAsync(ProcessAuthenticationContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.UserinfoTokenPrincipal is { Identity: ClaimsIdentity }, SR.GetResourceString(SR.ID4006)); var configuration = await context.Registration.ConfigurationManager.GetConfigurationAsync(default) ?? @@ -2612,8 +2832,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessAuthenticationContext context!!) + public async ValueTask HandleAsync(ProcessAuthenticationContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.UserinfoTokenPrincipal is { Identity: ClaimsIdentity }, SR.GetResourceString(SR.ID4006)); var configuration = await context.Registration.ConfigurationManager.GetConfigurationAsync(default) ?? @@ -2692,8 +2917,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public ValueTask HandleAsync(ProcessChallengeContext context!!) + public ValueTask HandleAsync(ProcessChallengeContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // If an explicit grant type was specified, ensure it is supported by OpenIddict. if (!string.IsNullOrEmpty(context.GrantType) && context.GrantType is not (GrantTypes.AuthorizationCode or GrantTypes.Implicit)) @@ -2731,8 +2961,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public ValueTask HandleAsync(ProcessChallengeContext context!!) + public ValueTask HandleAsync(ProcessChallengeContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // Note: if the static registration cannot be found in the options, this may indicate // the client was removed after the authorization dance started and thus, can no longer // be used to authenticate users. In this case, throw an exception to abort the flow. @@ -2761,8 +2996,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessChallengeContext context!!) + public async ValueTask HandleAsync(ProcessChallengeContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // If an explicit grant type was specified, don't overwrite it. if (!string.IsNullOrEmpty(context.GrantType)) { @@ -2846,8 +3086,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public ValueTask HandleAsync(ProcessChallengeContext context!!) + public ValueTask HandleAsync(ProcessChallengeContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // In OpenIddict, per-authorization demand values are stored in an encrypted and signed token // called "state token", that allows flowing per-authorization demand data like the issuer // targeted by the authorization demand or secret values like the code verifier used to @@ -2885,8 +3130,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessChallengeContext context!!) + public async ValueTask HandleAsync(ProcessChallengeContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // If an explicit response type was specified, don't overwrite it. if (!string.IsNullOrEmpty(context.ResponseType)) { @@ -3078,8 +3328,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessChallengeContext context!!) + public async ValueTask HandleAsync(ProcessChallengeContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // If an explicit response type was specified, don't overwrite it. if (!string.IsNullOrEmpty(context.ResponseMode)) { @@ -3185,8 +3440,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public ValueTask HandleAsync(ProcessChallengeContext context!!) + public ValueTask HandleAsync(ProcessChallengeContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + context.ClientId ??= context.Registration.ClientId; return default; @@ -3209,8 +3469,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public ValueTask HandleAsync(ProcessChallengeContext context!!) + public ValueTask HandleAsync(ProcessChallengeContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // Unlike OpenID Connect, OAuth 2.0 and 2.1 don't require specifying a redirect_uri. // To keep OpenIddict compatible with OAuth 2.0/2.1 deployments, the redirect_uri // is not required for OAuth 2.0 requests but an exception will be thrown later @@ -3237,8 +3502,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessChallengeContext context!!) + public async ValueTask HandleAsync(ProcessChallengeContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // If an explicit set of scopes was specified, don't overwrite it. if (context.Scopes.Count > 0) { @@ -3284,8 +3554,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public ValueTask HandleAsync(ProcessChallengeContext context!!) + public ValueTask HandleAsync(ProcessChallengeContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // Generate a new crypto-secure random identifier that will // be used as the non-guessable part of the state token. var data = new byte[256 / 8]; @@ -3317,8 +3592,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessChallengeContext context!!) + public async ValueTask HandleAsync(ProcessChallengeContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var configuration = await context.Registration.ConfigurationManager.GetConfigurationAsync(default) ?? throw new InvalidOperationException(SR.GetResourceString(SR.ID0140)); @@ -3362,8 +3642,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessChallengeContext context!!) + public async ValueTask HandleAsync(ProcessChallengeContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // Don't attach a code challenge method if no authorization code is requested as some implementations // (like OpenIddict server) are known to eagerly block authorization requests that specify an invalid // code_challenge/code_challenge_method/response_type combination (e.g response_type=id_token). @@ -3464,8 +3749,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public ValueTask HandleAsync(ProcessChallengeContext context!!) + public ValueTask HandleAsync(ProcessChallengeContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.Issuer is { IsAbsoluteUri: true }, SR.GetResourceString(SR.ID4013)); Debug.Assert(context.Principal is { Identity: ClaimsIdentity }, SR.GetResourceString(SR.ID4006)); @@ -3556,8 +3846,8 @@ public static partial class OpenIddictClientHandlers { private readonly IOpenIddictClientDispatcher _dispatcher; - public GenerateStateToken(IOpenIddictClientDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public GenerateStateToken(IOpenIddictClientDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -3571,8 +3861,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessChallengeContext context!!) + public async ValueTask HandleAsync(ProcessChallengeContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var notification = new GenerateTokenContext(context.Transaction) { Principal = context.StateTokenPrincipal!, @@ -3623,8 +3918,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public ValueTask HandleAsync(ProcessChallengeContext context!!) + public ValueTask HandleAsync(ProcessChallengeContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // While OAuth 2.0/2.1 allows sending an authorization request without a redirect_uri, // doing so is illegal in OpenID Connect and such requests will always be rejected. // To make that requirement explicit, an exception is proactively thrown here. @@ -3653,8 +3953,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public ValueTask HandleAsync(ProcessChallengeContext context!!) + public ValueTask HandleAsync(ProcessChallengeContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // Note: while the exact order of the parameters has typically no effect on how requests // are handled by an authorization server, client_id and redirect_uri are deliberately // set first so that they appear early in the URL (when GET requests are used), making @@ -3709,8 +4014,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public ValueTask HandleAsync(TContext context!!) + public ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + if (!string.IsNullOrEmpty(context.Transaction.Response?.Error)) { context.Reject( @@ -3741,8 +4051,13 @@ public static partial class OpenIddictClientHandlers .Build(); /// - public ValueTask HandleAsync(ProcessErrorContext context!!) + public ValueTask HandleAsync(ProcessErrorContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + context.Response.Error = context.Error; context.Response.ErrorDescription = context.ErrorDescription; context.Response.ErrorUri = context.ErrorUri; diff --git a/src/OpenIddict.Client/OpenIddictClientHelpers.cs b/src/OpenIddict.Client/OpenIddictClientHelpers.cs index 5e016aba..3bbce2e9 100644 --- a/src/OpenIddict.Client/OpenIddictClientHelpers.cs +++ b/src/OpenIddict.Client/OpenIddictClientHelpers.cs @@ -19,8 +19,13 @@ public static class OpenIddictClientHelpers /// The property name. /// The property value or if it couldn't be found. public static TProperty? GetProperty( - this OpenIddictClientTransaction transaction!!, string name) where TProperty : class + this OpenIddictClientTransaction transaction, string name) where TProperty : class { + if (transaction is null) + { + throw new ArgumentNullException(nameof(transaction)); + } + if (string.IsNullOrEmpty(name)) { throw new ArgumentException(SR.GetResourceString(SR.ID0106), nameof(name)); @@ -43,9 +48,14 @@ public static class OpenIddictClientHelpers /// The property value. /// The client transaction, so that calls can be easily chained. public static OpenIddictClientTransaction SetProperty( - this OpenIddictClientTransaction transaction!!, + this OpenIddictClientTransaction transaction, string name, TProperty? value) where TProperty : class { + if (transaction is null) + { + throw new ArgumentNullException(nameof(transaction)); + } + if (string.IsNullOrEmpty(name)) { throw new ArgumentException(SR.GetResourceString(SR.ID0106), nameof(name)); diff --git a/src/OpenIddict.Client/OpenIddictClientRetriever.cs b/src/OpenIddict.Client/OpenIddictClientRetriever.cs index afdd8855..9ae70b90 100644 --- a/src/OpenIddict.Client/OpenIddictClientRetriever.cs +++ b/src/OpenIddict.Client/OpenIddictClientRetriever.cs @@ -16,8 +16,8 @@ public class OpenIddictClientRetriever : IConfigurationRetriever class. /// /// The validation service. - public OpenIddictClientRetriever(OpenIddictClientService service!!) - => _service = service; + public OpenIddictClientRetriever(OpenIddictClientService service) + => _service = service ?? throw new ArgumentNullException(nameof(service)); /// /// Retrieves the OpenID Connect server configuration from the specified address. @@ -26,8 +26,7 @@ public class OpenIddictClientRetriever : IConfigurationRetrieverThe retriever used by IdentityModel. /// The that can be used to abort the operation. /// The OpenID Connect server configuration retrieved from the remote server. - async Task IConfigurationRetriever.GetConfigurationAsync( - string address, IDocumentRetriever retriever, CancellationToken cancel) + async Task IConfigurationRetriever.GetConfigurationAsync(string address, IDocumentRetriever retriever, CancellationToken cancel) { if (string.IsNullOrEmpty(address)) { diff --git a/src/OpenIddict.Client/OpenIddictClientService.cs b/src/OpenIddict.Client/OpenIddictClientService.cs index 94faf009..2b857819 100644 --- a/src/OpenIddict.Client/OpenIddictClientService.cs +++ b/src/OpenIddict.Client/OpenIddictClientService.cs @@ -19,8 +19,8 @@ public class OpenIddictClientService /// Creates a new instance of the class. /// /// The service provider. - public OpenIddictClientService(IServiceProvider provider!!) - => _provider = provider; + public OpenIddictClientService(IServiceProvider provider) + => _provider = provider ?? throw new ArgumentNullException(nameof(provider)); /// /// Retrieves the OpenID Connect server configuration from the specified address. @@ -28,9 +28,14 @@ public class OpenIddictClientService /// The address of the remote metadata endpoint. /// The that can be used to abort the operation. /// The OpenID Connect server configuration retrieved from the remote server. - public async ValueTask GetConfigurationAsync(Uri address!!, CancellationToken cancellationToken = default) + public async ValueTask GetConfigurationAsync(Uri address, CancellationToken cancellationToken = default) { - if (!address.IsAbsoluteUri) + if (address is null) + { + throw new ArgumentNullException(nameof(address)); + } + + if (!address.IsAbsoluteUri || !address.IsWellFormedOriginalString()) { throw new ArgumentException(SR.GetResourceString(SR.ID0144), nameof(address)); } @@ -162,9 +167,14 @@ public class OpenIddictClientService /// The address of the remote metadata endpoint. /// The that can be used to abort the operation. /// The security keys retrieved from the remote server. - public async ValueTask GetSecurityKeysAsync(Uri address!!, CancellationToken cancellationToken = default) + public async ValueTask GetSecurityKeysAsync(Uri address, CancellationToken cancellationToken = default) { - if (!address.IsAbsoluteUri) + if (address is null) + { + throw new ArgumentNullException(nameof(address)); + } + + if (!address.IsAbsoluteUri || !address.IsWellFormedOriginalString()) { throw new ArgumentException(SR.GetResourceString(SR.ID0144), nameof(address)); } @@ -299,8 +309,13 @@ public class OpenIddictClientService /// The that can be used to abort the operation. /// The response and a merged principal containing the claims extracted from the tokens and userinfo response. public async ValueTask<(OpenIddictResponse Response, ClaimsPrincipal Principal)> RefreshTokensAsync( - OpenIddictClientRegistration registration!!, string token, CancellationToken cancellationToken = default) + OpenIddictClientRegistration registration, string token, CancellationToken cancellationToken = default) { + if (registration is null) + { + throw new ArgumentNullException(nameof(registration)); + } + if (string.IsNullOrEmpty(token)) { throw new ArgumentException(SR.GetResourceString(SR.ID0156), nameof(token)); @@ -418,8 +433,18 @@ public class OpenIddictClientService /// The that can be used to abort the operation. /// The token response. public async ValueTask SendTokenRequestAsync( - OpenIddictClientRegistration registration!!, Uri address!!, OpenIddictRequest request, CancellationToken cancellationToken = default) + OpenIddictClientRegistration registration, Uri address, OpenIddictRequest request, CancellationToken cancellationToken = default) { + if (registration is null) + { + throw new ArgumentNullException(nameof(registration)); + } + + if (address is null) + { + throw new ArgumentNullException(nameof(address)); + } + if (!address.IsAbsoluteUri || !address.IsWellFormedOriginalString()) { throw new ArgumentException(SR.GetResourceString(SR.ID0144), nameof(address)); @@ -562,8 +587,18 @@ public class OpenIddictClientService /// The that can be used to abort the operation. /// The response and the principal extracted from the userinfo response or the userinfo token. public async ValueTask<(OpenIddictResponse Response, (ClaimsPrincipal? Principal, string? Token))> SendUserinfoRequestAsync( - OpenIddictClientRegistration registration!!, Uri address!!, OpenIddictRequest request, CancellationToken cancellationToken = default) + OpenIddictClientRegistration registration, Uri address, OpenIddictRequest request, CancellationToken cancellationToken = default) { + if (registration is null) + { + throw new ArgumentNullException(nameof(registration)); + } + + if (address is null) + { + throw new ArgumentNullException(nameof(address)); + } + if (!address.IsAbsoluteUri || !address.IsWellFormedOriginalString()) { throw new ArgumentException(SR.GetResourceString(SR.ID0144), nameof(address)); diff --git a/src/OpenIddict.Core/Caches/OpenIddictApplicationCache.cs b/src/OpenIddict.Core/Caches/OpenIddictApplicationCache.cs index f097c0d7..9ba5be58 100644 --- a/src/OpenIddict.Core/Caches/OpenIddictApplicationCache.cs +++ b/src/OpenIddict.Core/Caches/OpenIddictApplicationCache.cs @@ -24,21 +24,26 @@ public class OpenIddictApplicationCache : IOpenIddictApplicationCa private readonly IOpenIddictApplicationStore _store; public OpenIddictApplicationCache( - IOptionsMonitor options!!, - IOpenIddictApplicationStoreResolver resolver!!) + IOptionsMonitor options, + IOpenIddictApplicationStoreResolver resolver) { _cache = new MemoryCache(new MemoryCacheOptions { - SizeLimit = options.CurrentValue.EntityCacheLimit + SizeLimit = (options ?? throw new ArgumentNullException(nameof(options))).CurrentValue.EntityCacheLimit }); _signals = new ConcurrentDictionary(StringComparer.Ordinal); - _store = resolver.Get(); + _store = (resolver ?? throw new ArgumentNullException(nameof(resolver))).Get(); } /// - public async ValueTask AddAsync(TApplication application!!, CancellationToken cancellationToken) + public async ValueTask AddAsync(TApplication application, CancellationToken cancellationToken) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + _cache.Remove(new { Method = nameof(FindByClientIdAsync), @@ -244,8 +249,13 @@ public class OpenIddictApplicationCache : IOpenIddictApplicationCa } /// - public async ValueTask RemoveAsync(TApplication application!!, CancellationToken cancellationToken) + public async ValueTask RemoveAsync(TApplication application, CancellationToken cancellationToken) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + var identifier = await _store.GetIdAsync(application, cancellationToken); if (string.IsNullOrEmpty(identifier)) { @@ -266,8 +276,13 @@ public class OpenIddictApplicationCache : IOpenIddictApplicationCa /// The application to store in the cache entry, if applicable. /// The that can be used to abort the operation. /// A that can be used to monitor the asynchronous operation. - protected virtual async ValueTask CreateEntryAsync(object key!!, TApplication? application, CancellationToken cancellationToken) + protected virtual async ValueTask CreateEntryAsync(object key, TApplication? application, CancellationToken cancellationToken) { + if (key is null) + { + throw new ArgumentNullException(nameof(key)); + } + using var entry = _cache.CreateEntry(key); if (application is not null) @@ -288,8 +303,13 @@ public class OpenIddictApplicationCache : IOpenIddictApplicationCa /// The that can be used to abort the operation. /// A that can be used to monitor the asynchronous operation. protected virtual async ValueTask CreateEntryAsync( - object key!!, ImmutableArray applications, CancellationToken cancellationToken) + object key, ImmutableArray applications, CancellationToken cancellationToken) { + if (key is null) + { + throw new ArgumentNullException(nameof(key)); + } + using var entry = _cache.CreateEntry(key); foreach (var application in applications) @@ -313,8 +333,13 @@ public class OpenIddictApplicationCache : IOpenIddictApplicationCa /// whose result returns an expiration signal for the specified application. /// protected virtual async ValueTask CreateExpirationSignalAsync( - TApplication application!!, CancellationToken cancellationToken) + TApplication application, CancellationToken cancellationToken) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + var identifier = await _store.GetIdAsync(application, cancellationToken); if (string.IsNullOrEmpty(identifier)) { diff --git a/src/OpenIddict.Core/Caches/OpenIddictAuthorizationCache.cs b/src/OpenIddict.Core/Caches/OpenIddictAuthorizationCache.cs index f9da27b7..cffc13f8 100644 --- a/src/OpenIddict.Core/Caches/OpenIddictAuthorizationCache.cs +++ b/src/OpenIddict.Core/Caches/OpenIddictAuthorizationCache.cs @@ -24,21 +24,26 @@ public class OpenIddictAuthorizationCache : IOpenIddictAuthoriza private readonly IOpenIddictAuthorizationStore _store; public OpenIddictAuthorizationCache( - IOptionsMonitor options!!, - IOpenIddictAuthorizationStoreResolver resolver!!) + IOptionsMonitor options, + IOpenIddictAuthorizationStoreResolver resolver) { _cache = new MemoryCache(new MemoryCacheOptions { - SizeLimit = options.CurrentValue.EntityCacheLimit + SizeLimit = (options ?? throw new ArgumentNullException(nameof(options))).CurrentValue.EntityCacheLimit }); _signals = new ConcurrentDictionary(StringComparer.Ordinal); - _store = resolver.Get(); + _store = (resolver ?? throw new ArgumentNullException(nameof(resolver))).Get(); } /// - public async ValueTask AddAsync(TAuthorization authorization!!, CancellationToken cancellationToken) + public async ValueTask AddAsync(TAuthorization authorization, CancellationToken cancellationToken) { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + _cache.Remove(new { Method = nameof(FindAsync), @@ -420,8 +425,13 @@ public class OpenIddictAuthorizationCache : IOpenIddictAuthoriza } /// - public async ValueTask RemoveAsync(TAuthorization authorization!!, CancellationToken cancellationToken) + public async ValueTask RemoveAsync(TAuthorization authorization, CancellationToken cancellationToken) { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + var identifier = await _store.GetIdAsync(authorization, cancellationToken); if (string.IsNullOrEmpty(identifier)) { @@ -442,8 +452,13 @@ public class OpenIddictAuthorizationCache : IOpenIddictAuthoriza /// The authorization to store in the cache entry, if applicable. /// The that can be used to abort the operation. /// A that can be used to monitor the asynchronous operation. - protected virtual async ValueTask CreateEntryAsync(object key!!, TAuthorization? authorization, CancellationToken cancellationToken) + protected virtual async ValueTask CreateEntryAsync(object key, TAuthorization? authorization, CancellationToken cancellationToken) { + if (key is null) + { + throw new ArgumentNullException(nameof(key)); + } + using var entry = _cache.CreateEntry(key); if (authorization is not null) @@ -464,8 +479,13 @@ public class OpenIddictAuthorizationCache : IOpenIddictAuthoriza /// The that can be used to abort the operation. /// A that can be used to monitor the asynchronous operation. protected virtual async ValueTask CreateEntryAsync( - object key!!, ImmutableArray authorizations, CancellationToken cancellationToken) + object key, ImmutableArray authorizations, CancellationToken cancellationToken) { + if (key is null) + { + throw new ArgumentNullException(nameof(key)); + } + using var entry = _cache.CreateEntry(key); foreach (var authorization in authorizations) @@ -489,8 +509,13 @@ public class OpenIddictAuthorizationCache : IOpenIddictAuthoriza /// whose result returns an expiration signal for the specified authorization. /// protected virtual async ValueTask CreateExpirationSignalAsync( - TAuthorization authorization!!, CancellationToken cancellationToken) + TAuthorization authorization, CancellationToken cancellationToken) { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + var identifier = await _store.GetIdAsync(authorization, cancellationToken); if (string.IsNullOrEmpty(identifier)) { diff --git a/src/OpenIddict.Core/Caches/OpenIddictScopeCache.cs b/src/OpenIddict.Core/Caches/OpenIddictScopeCache.cs index e795f873..4ea3614c 100644 --- a/src/OpenIddict.Core/Caches/OpenIddictScopeCache.cs +++ b/src/OpenIddict.Core/Caches/OpenIddictScopeCache.cs @@ -24,21 +24,26 @@ public class OpenIddictScopeCache : IOpenIddictScopeCache, IDisp private readonly IOpenIddictScopeStore _store; public OpenIddictScopeCache( - IOptionsMonitor options!!, - IOpenIddictScopeStoreResolver resolver!!) + IOptionsMonitor options, + IOpenIddictScopeStoreResolver resolver) { _cache = new MemoryCache(new MemoryCacheOptions { - SizeLimit = options.CurrentValue.EntityCacheLimit + SizeLimit = (options ?? throw new ArgumentNullException(nameof(options))).CurrentValue.EntityCacheLimit }); _signals = new ConcurrentDictionary(StringComparer.Ordinal); - _store = resolver.Get(); + _store = (resolver ?? throw new ArgumentNullException(nameof(resolver))).Get(); } /// - public async ValueTask AddAsync(TScope scope!!, CancellationToken cancellationToken) + public async ValueTask AddAsync(TScope scope, CancellationToken cancellationToken) { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + _cache.Remove(new { Method = nameof(FindByIdAsync), @@ -155,7 +160,7 @@ public class OpenIddictScopeCache : IOpenIddictScopeCache, IDisp /// public IAsyncEnumerable FindByNamesAsync(ImmutableArray names, CancellationToken cancellationToken) { - if (names.Any(string.IsNullOrEmpty)) + if (names.Any(name => string.IsNullOrEmpty(name))) { throw new ArgumentException(SR.GetResourceString(SR.ID0203), nameof(names)); } @@ -217,8 +222,13 @@ public class OpenIddictScopeCache : IOpenIddictScopeCache, IDisp } /// - public async ValueTask RemoveAsync(TScope scope!!, CancellationToken cancellationToken) + public async ValueTask RemoveAsync(TScope scope, CancellationToken cancellationToken) { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + var identifier = await _store.GetIdAsync(scope, cancellationToken); if (string.IsNullOrEmpty(identifier)) { @@ -239,8 +249,13 @@ public class OpenIddictScopeCache : IOpenIddictScopeCache, IDisp /// The scope to store in the cache entry, if applicable. /// The that can be used to abort the operation. /// A that can be used to monitor the asynchronous operation. - protected virtual async ValueTask CreateEntryAsync(object key!!, TScope? scope, CancellationToken cancellationToken) + protected virtual async ValueTask CreateEntryAsync(object key, TScope? scope, CancellationToken cancellationToken) { + if (key is null) + { + throw new ArgumentNullException(nameof(key)); + } + using var entry = _cache.CreateEntry(key); if (scope is not null) @@ -261,8 +276,13 @@ public class OpenIddictScopeCache : IOpenIddictScopeCache, IDisp /// The that can be used to abort the operation. /// A that can be used to monitor the asynchronous operation. protected virtual async ValueTask CreateEntryAsync( - object key!!, ImmutableArray scopes, CancellationToken cancellationToken) + object key, ImmutableArray scopes, CancellationToken cancellationToken) { + if (key is null) + { + throw new ArgumentNullException(nameof(key)); + } + using var entry = _cache.CreateEntry(key); foreach (var scope in scopes) @@ -285,8 +305,13 @@ public class OpenIddictScopeCache : IOpenIddictScopeCache, IDisp /// A that can be used to monitor the asynchronous operation, /// whose result returns an expiration signal for the specified scope. /// - protected virtual async ValueTask CreateExpirationSignalAsync(TScope scope!!, CancellationToken cancellationToken) + protected virtual async ValueTask CreateExpirationSignalAsync(TScope scope, CancellationToken cancellationToken) { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + var identifier = await _store.GetIdAsync(scope, cancellationToken); if (string.IsNullOrEmpty(identifier)) { diff --git a/src/OpenIddict.Core/Caches/OpenIddictTokenCache.cs b/src/OpenIddict.Core/Caches/OpenIddictTokenCache.cs index 13fa9477..70411384 100644 --- a/src/OpenIddict.Core/Caches/OpenIddictTokenCache.cs +++ b/src/OpenIddict.Core/Caches/OpenIddictTokenCache.cs @@ -24,21 +24,26 @@ public class OpenIddictTokenCache : IOpenIddictTokenCache, IDisp private readonly IOpenIddictTokenStore _store; public OpenIddictTokenCache( - IOptionsMonitor options!!, - IOpenIddictTokenStoreResolver resolver!!) + IOptionsMonitor options, + IOpenIddictTokenStoreResolver resolver) { _cache = new MemoryCache(new MemoryCacheOptions { - SizeLimit = options.CurrentValue.EntityCacheLimit + SizeLimit = (options ?? throw new ArgumentNullException(nameof(options))).CurrentValue.EntityCacheLimit }); _signals = new ConcurrentDictionary(StringComparer.Ordinal); - _store = resolver.Get(); + _store = (resolver ?? throw new ArgumentNullException(nameof(resolver))).Get(); } /// - public async ValueTask AddAsync(TToken token!!, CancellationToken cancellationToken) + public async ValueTask AddAsync(TToken token, CancellationToken cancellationToken) { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + _cache.Remove(new { Method = nameof(FindAsync), @@ -472,8 +477,13 @@ public class OpenIddictTokenCache : IOpenIddictTokenCache, IDisp } /// - public async ValueTask RemoveAsync(TToken token!!, CancellationToken cancellationToken) + public async ValueTask RemoveAsync(TToken token, CancellationToken cancellationToken) { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + var identifier = await _store.GetIdAsync(token, cancellationToken); if (string.IsNullOrEmpty(identifier)) { @@ -494,8 +504,13 @@ public class OpenIddictTokenCache : IOpenIddictTokenCache, IDisp /// The token to store in the cache entry, if applicable. /// The that can be used to abort the operation. /// A that can be used to monitor the asynchronous operation. - protected virtual async ValueTask CreateEntryAsync(object key!!, TToken? token, CancellationToken cancellationToken) + protected virtual async ValueTask CreateEntryAsync(object key, TToken? token, CancellationToken cancellationToken) { + if (key is null) + { + throw new ArgumentNullException(nameof(key)); + } + using var entry = _cache.CreateEntry(key); if (token is not null) @@ -516,8 +531,13 @@ public class OpenIddictTokenCache : IOpenIddictTokenCache, IDisp /// The that can be used to abort the operation. /// A that can be used to monitor the asynchronous operation. protected virtual async ValueTask CreateEntryAsync( - object key!!, ImmutableArray tokens, CancellationToken cancellationToken) + object key, ImmutableArray tokens, CancellationToken cancellationToken) { + if (key is null) + { + throw new ArgumentNullException(nameof(key)); + } + using var entry = _cache.CreateEntry(key); foreach (var token in tokens) @@ -540,8 +560,13 @@ public class OpenIddictTokenCache : IOpenIddictTokenCache, IDisp /// A that can be used to monitor the asynchronous operation, /// whose result returns an expiration signal for the specified token. /// - protected virtual async ValueTask CreateExpirationSignalAsync(TToken token!!, CancellationToken cancellationToken) + protected virtual async ValueTask CreateExpirationSignalAsync(TToken token, CancellationToken cancellationToken) { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + var identifier = await _store.GetIdAsync(token, cancellationToken); if (string.IsNullOrEmpty(identifier)) { diff --git a/src/OpenIddict.Core/Managers/OpenIddictApplicationManager.cs b/src/OpenIddict.Core/Managers/OpenIddictApplicationManager.cs index 32809641..811aed59 100644 --- a/src/OpenIddict.Core/Managers/OpenIddictApplicationManager.cs +++ b/src/OpenIddict.Core/Managers/OpenIddictApplicationManager.cs @@ -41,15 +41,15 @@ namespace OpenIddict.Core; public class OpenIddictApplicationManager : IOpenIddictApplicationManager where TApplication : class { public OpenIddictApplicationManager( - IOpenIddictApplicationCache cache!!, - ILogger> logger!!, - IOptionsMonitor options!!, - IOpenIddictApplicationStoreResolver resolver!!) + IOpenIddictApplicationCache cache, + ILogger> logger, + IOptionsMonitor options, + IOpenIddictApplicationStoreResolver resolver) { - Cache = cache; - Logger = logger; - Options = options; - Store = resolver.Get(); + Cache = cache ?? throw new ArgumentNullException(nameof(cache)); + Logger = logger ?? throw new ArgumentNullException(nameof(logger)); + Options = options ?? throw new ArgumentNullException(nameof(options)); + Store = (resolver ?? throw new ArgumentNullException(nameof(resolver))).Get(); } /// @@ -94,8 +94,15 @@ public class OpenIddictApplicationManager : IOpenIddictApplication /// whose result returns the number of applications that match the specified query. /// public virtual ValueTask CountAsync( - Func, IQueryable> query!!, CancellationToken cancellationToken = default) - => Store.CountAsync(query, cancellationToken); + Func, IQueryable> query, CancellationToken cancellationToken = default) + { + if (query is null) + { + throw new ArgumentNullException(nameof(query)); + } + + return Store.CountAsync(query, cancellationToken); + } /// /// Creates a new application. @@ -119,8 +126,13 @@ public class OpenIddictApplicationManager : IOpenIddictApplication /// /// A that can be used to monitor the asynchronous operation. /// - public virtual async ValueTask CreateAsync(TApplication application!!, string? secret, CancellationToken cancellationToken = default) + public virtual async ValueTask CreateAsync(TApplication application, string? secret, CancellationToken cancellationToken = default) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + if (!string.IsNullOrEmpty(await Store.GetClientSecretAsync(application, cancellationToken))) { throw new ArgumentException(SR.GetResourceString(SR.ID0206), nameof(application)); @@ -189,8 +201,13 @@ public class OpenIddictApplicationManager : IOpenIddictApplication /// whose result returns the unique identifier associated with the application. /// public virtual async ValueTask CreateAsync( - OpenIddictApplicationDescriptor descriptor!!, CancellationToken cancellationToken = default) + OpenIddictApplicationDescriptor descriptor, CancellationToken cancellationToken = default) { + if (descriptor is null) + { + throw new ArgumentNullException(nameof(descriptor)); + } + var application = await Store.InstantiateAsync(cancellationToken) ?? throw new InvalidOperationException(SR.GetResourceString(SR.ID0208)); @@ -218,8 +235,13 @@ public class OpenIddictApplicationManager : IOpenIddictApplication /// /// A that can be used to monitor the asynchronous operation. /// - public virtual async ValueTask DeleteAsync(TApplication application!!, CancellationToken cancellationToken = default) + public virtual async ValueTask DeleteAsync(TApplication application, CancellationToken cancellationToken = default) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + if (!Options.CurrentValue.DisableEntityCaching) { await Cache.RemoveAsync(application, cancellationToken); @@ -398,8 +420,15 @@ public class OpenIddictApplicationManager : IOpenIddictApplication /// whose result returns the first element returned when executing the query. /// public virtual ValueTask GetAsync( - Func, IQueryable> query!!, CancellationToken cancellationToken = default) - => GetAsync(static (applications, query) => query(applications), query, cancellationToken); + Func, IQueryable> query, CancellationToken cancellationToken = default) + { + if (query is null) + { + throw new ArgumentNullException(nameof(query)); + } + + return GetAsync(static (applications, query) => query(applications), query, cancellationToken); + } /// /// Executes the specified query and returns the first element. @@ -414,9 +443,16 @@ public class OpenIddictApplicationManager : IOpenIddictApplication /// whose result returns the first element returned when executing the query. /// public virtual ValueTask GetAsync( - Func, TState, IQueryable> query!!, + Func, TState, IQueryable> query, TState state, CancellationToken cancellationToken = default) - => Store.GetAsync(query, state, cancellationToken); + { + if (query is null) + { + throw new ArgumentNullException(nameof(query)); + } + + return Store.GetAsync(query, state, cancellationToken); + } /// /// Retrieves the client identifier associated with an application. @@ -428,8 +464,15 @@ public class OpenIddictApplicationManager : IOpenIddictApplication /// whose result returns the client identifier associated with the application. /// public virtual ValueTask GetClientIdAsync( - TApplication application!!, CancellationToken cancellationToken = default) - => Store.GetClientIdAsync(application, cancellationToken); + TApplication application, CancellationToken cancellationToken = default) + { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + + return Store.GetClientIdAsync(application, cancellationToken); + } /// /// Retrieves the client type associated with an application. @@ -441,8 +484,15 @@ public class OpenIddictApplicationManager : IOpenIddictApplication /// whose result returns the client type of the application (by default, "public"). /// public virtual ValueTask GetClientTypeAsync( - TApplication application!!, CancellationToken cancellationToken = default) - => Store.GetClientTypeAsync(application, cancellationToken); + TApplication application, CancellationToken cancellationToken = default) + { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + + return Store.GetClientTypeAsync(application, cancellationToken); + } /// /// Retrieves the consent type associated with an application. @@ -454,8 +504,13 @@ public class OpenIddictApplicationManager : IOpenIddictApplication /// whose result returns the consent type of the application (by default, "explicit"). /// public virtual async ValueTask GetConsentTypeAsync( - TApplication application!!, CancellationToken cancellationToken = default) + TApplication application, CancellationToken cancellationToken = default) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + var type = await Store.GetConsentTypeAsync(application, cancellationToken); if (string.IsNullOrEmpty(type)) { @@ -475,8 +530,15 @@ public class OpenIddictApplicationManager : IOpenIddictApplication /// whose result returns the display name associated with the application. /// public virtual ValueTask GetDisplayNameAsync( - TApplication application!!, CancellationToken cancellationToken = default) - => Store.GetDisplayNameAsync(application, cancellationToken); + TApplication application, CancellationToken cancellationToken = default) + { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + + return Store.GetDisplayNameAsync(application, cancellationToken); + } /// /// Retrieves the localized display names associated with an application. @@ -488,9 +550,21 @@ public class OpenIddictApplicationManager : IOpenIddictApplication /// whose result returns all the localized display names associated with the application. /// public virtual async ValueTask> GetDisplayNamesAsync( - TApplication application!!, CancellationToken cancellationToken = default) - => await Store.GetDisplayNamesAsync(application, cancellationToken) is { Count: > 0 } names ? - names : ImmutableDictionary.Create(); + TApplication application, CancellationToken cancellationToken = default) + { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + + var names = await Store.GetDisplayNamesAsync(application, cancellationToken); + if (names is null || names.Count == 0) + { + return ImmutableDictionary.Create(); + } + + return names; + } /// /// Retrieves the unique identifier associated with an application. @@ -501,8 +575,15 @@ public class OpenIddictApplicationManager : IOpenIddictApplication /// A that can be used to monitor the asynchronous operation, /// whose result returns the unique identifier associated with the application. /// - public virtual ValueTask GetIdAsync(TApplication application!!, CancellationToken cancellationToken = default) - => Store.GetIdAsync(application, cancellationToken); + public virtual ValueTask GetIdAsync(TApplication application, CancellationToken cancellationToken = default) + { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + + return Store.GetIdAsync(application, cancellationToken); + } /// /// Retrieves the localized display name associated with an application @@ -532,8 +613,18 @@ public class OpenIddictApplicationManager : IOpenIddictApplication /// whose result returns the matching localized display name associated with the application. /// public virtual async ValueTask GetLocalizedDisplayNameAsync( - TApplication application!!, CultureInfo culture!!, CancellationToken cancellationToken = default) + TApplication application, CultureInfo culture, CancellationToken cancellationToken = default) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + + if (culture is null) + { + throw new ArgumentNullException(nameof(culture)); + } + var names = await Store.GetDisplayNamesAsync(application, cancellationToken); if (names is not { Count: > 0 }) { @@ -565,8 +656,15 @@ public class OpenIddictApplicationManager : IOpenIddictApplication /// whose result returns all the permissions associated with the application. /// public virtual ValueTask> GetPermissionsAsync( - TApplication application!!, CancellationToken cancellationToken = default) - => Store.GetPermissionsAsync(application, cancellationToken); + TApplication application, CancellationToken cancellationToken = default) + { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + + return Store.GetPermissionsAsync(application, cancellationToken); + } /// /// Retrieves the logout callback addresses associated with an application. @@ -578,8 +676,15 @@ public class OpenIddictApplicationManager : IOpenIddictApplication /// whose result returns all the post_logout_redirect_uri associated with the application. /// public virtual ValueTask> GetPostLogoutRedirectUrisAsync( - TApplication application!!, CancellationToken cancellationToken = default) - => Store.GetPostLogoutRedirectUrisAsync(application, cancellationToken); + TApplication application, CancellationToken cancellationToken = default) + { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + + return Store.GetPostLogoutRedirectUrisAsync(application, cancellationToken); + } /// /// Retrieves the additional properties associated with an application. @@ -591,8 +696,15 @@ public class OpenIddictApplicationManager : IOpenIddictApplication /// whose result returns all the additional properties associated with the application. /// public virtual ValueTask> GetPropertiesAsync( - TApplication application!!, CancellationToken cancellationToken = default) - => Store.GetPropertiesAsync(application, cancellationToken); + TApplication application, CancellationToken cancellationToken = default) + { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + + return Store.GetPropertiesAsync(application, cancellationToken); + } /// /// Retrieves the callback addresses associated with an application. @@ -604,8 +716,15 @@ public class OpenIddictApplicationManager : IOpenIddictApplication /// whose result returns all the redirect_uri associated with the application. /// public virtual ValueTask> GetRedirectUrisAsync( - TApplication application!!, CancellationToken cancellationToken = default) - => Store.GetRedirectUrisAsync(application, cancellationToken); + TApplication application, CancellationToken cancellationToken = default) + { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + + return Store.GetRedirectUrisAsync(application, cancellationToken); + } /// /// Retrieves the requirements associated with an application. @@ -617,8 +736,15 @@ public class OpenIddictApplicationManager : IOpenIddictApplication /// whose result returns all the requirements associated with the application. /// public virtual ValueTask> GetRequirementsAsync( - TApplication application!!, CancellationToken cancellationToken = default) - => Store.GetRequirementsAsync(application, cancellationToken); + TApplication application, CancellationToken cancellationToken = default) + { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + + return Store.GetRequirementsAsync(application, cancellationToken); + } /// /// Determines whether a given application has the specified client type. @@ -628,8 +754,13 @@ public class OpenIddictApplicationManager : IOpenIddictApplication /// The that can be used to abort the operation. /// if the application has the specified client type, otherwise. public virtual async ValueTask HasClientTypeAsync( - TApplication application!!, string type, CancellationToken cancellationToken = default) + TApplication application, string type, CancellationToken cancellationToken = default) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + if (string.IsNullOrEmpty(type)) { throw new ArgumentException(SR.GetResourceString(SR.ID0209), nameof(type)); @@ -646,8 +777,13 @@ public class OpenIddictApplicationManager : IOpenIddictApplication /// The that can be used to abort the operation. /// if the application has the specified consent type, otherwise. public virtual async ValueTask HasConsentTypeAsync( - TApplication application!!, string type, CancellationToken cancellationToken = default) + TApplication application, string type, CancellationToken cancellationToken = default) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + if (string.IsNullOrEmpty(type)) { throw new ArgumentException(SR.GetResourceString(SR.ID0210), nameof(type)); @@ -664,8 +800,13 @@ public class OpenIddictApplicationManager : IOpenIddictApplication /// The that can be used to abort the operation. /// if the application has been granted the specified permission, otherwise. public virtual async ValueTask HasPermissionAsync( - TApplication application!!, string permission, CancellationToken cancellationToken = default) + TApplication application, string permission, CancellationToken cancellationToken = default) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + if (string.IsNullOrEmpty(permission)) { throw new ArgumentException(SR.GetResourceString(SR.ID0211), nameof(permission)); @@ -682,8 +823,13 @@ public class OpenIddictApplicationManager : IOpenIddictApplication /// The that can be used to abort the operation. /// if the requirement has been enforced for the specified application, otherwise. public virtual async ValueTask HasRequirementAsync( - TApplication application!!, string requirement, CancellationToken cancellationToken = default) + TApplication application, string requirement, CancellationToken cancellationToken = default) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + if (string.IsNullOrEmpty(requirement)) { throw new ArgumentException(SR.GetResourceString(SR.ID0212), nameof(requirement)); @@ -711,8 +857,15 @@ public class OpenIddictApplicationManager : IOpenIddictApplication /// The that can be used to abort the operation. /// All the elements returned when executing the specified query. public virtual IAsyncEnumerable ListAsync( - Func, IQueryable> query!!, CancellationToken cancellationToken = default) - => ListAsync(static (applications, query) => query(applications), query, cancellationToken); + Func, IQueryable> query, CancellationToken cancellationToken = default) + { + if (query is null) + { + throw new ArgumentNullException(nameof(query)); + } + + return ListAsync(static (applications, query) => query(applications), query, cancellationToken); + } /// /// Executes the specified query and returns all the corresponding elements. @@ -724,9 +877,16 @@ public class OpenIddictApplicationManager : IOpenIddictApplication /// The that can be used to abort the operation. /// All the elements returned when executing the specified query. public virtual IAsyncEnumerable ListAsync( - Func, TState, IQueryable> query!!, + Func, TState, IQueryable> query, TState state, CancellationToken cancellationToken = default) - => Store.ListAsync(query, state, cancellationToken); + { + if (query is null) + { + throw new ArgumentNullException(nameof(query)); + } + + return Store.ListAsync(query, state, cancellationToken); + } /// /// Populates the application using the specified descriptor. @@ -737,9 +897,19 @@ public class OpenIddictApplicationManager : IOpenIddictApplication /// /// A that can be used to monitor the asynchronous operation. /// - public virtual async ValueTask PopulateAsync(TApplication application!!, - OpenIddictApplicationDescriptor descriptor!!, CancellationToken cancellationToken = default) + public virtual async ValueTask PopulateAsync(TApplication application, + OpenIddictApplicationDescriptor descriptor, CancellationToken cancellationToken = default) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + + if (descriptor is null) + { + throw new ArgumentNullException(nameof(descriptor)); + } + await Store.SetClientIdAsync(application, descriptor.ClientId, cancellationToken); await Store.SetClientSecretAsync(application, descriptor.ClientSecret, cancellationToken); await Store.SetClientTypeAsync(application, descriptor.Type, cancellationToken); @@ -765,9 +935,19 @@ public class OpenIddictApplicationManager : IOpenIddictApplication /// A that can be used to monitor the asynchronous operation. /// public virtual async ValueTask PopulateAsync( - OpenIddictApplicationDescriptor descriptor!!, - TApplication application!!, CancellationToken cancellationToken = default) + OpenIddictApplicationDescriptor descriptor, + TApplication application, CancellationToken cancellationToken = default) { + if (descriptor is null) + { + throw new ArgumentNullException(nameof(descriptor)); + } + + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + descriptor.ClientId = await Store.GetClientIdAsync(application, cancellationToken); descriptor.ClientSecret = await Store.GetClientSecretAsync(application, cancellationToken); descriptor.ConsentType = await Store.GetConsentTypeAsync(application, cancellationToken); @@ -835,8 +1015,13 @@ public class OpenIddictApplicationManager : IOpenIddictApplication /// /// A that can be used to monitor the asynchronous operation. /// - public virtual async ValueTask UpdateAsync(TApplication application!!, CancellationToken cancellationToken = default) + public virtual async ValueTask UpdateAsync(TApplication application, CancellationToken cancellationToken = default) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + var results = await GetValidationResultsAsync(application, cancellationToken); if (results.Any(result => result != ValidationResult.Success)) { @@ -885,8 +1070,13 @@ public class OpenIddictApplicationManager : IOpenIddictApplication /// /// A that can be used to monitor the asynchronous operation. /// - public virtual async ValueTask UpdateAsync(TApplication application!!, string? secret, CancellationToken cancellationToken = default) + public virtual async ValueTask UpdateAsync(TApplication application, string? secret, CancellationToken cancellationToken = default) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + if (string.IsNullOrEmpty(secret)) { await Store.SetClientSecretAsync(application, null, cancellationToken); @@ -910,9 +1100,19 @@ public class OpenIddictApplicationManager : IOpenIddictApplication /// /// A that can be used to monitor the asynchronous operation. /// - public virtual async ValueTask UpdateAsync(TApplication application!!, - OpenIddictApplicationDescriptor descriptor!!, CancellationToken cancellationToken = default) + public virtual async ValueTask UpdateAsync(TApplication application, + OpenIddictApplicationDescriptor descriptor, CancellationToken cancellationToken = default) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + + if (descriptor is null) + { + throw new ArgumentNullException(nameof(descriptor)); + } + // Store the original client secret for later comparison. var comparand = await Store.GetClientSecretAsync(application, cancellationToken); await PopulateAsync(application, descriptor, cancellationToken); @@ -936,8 +1136,13 @@ public class OpenIddictApplicationManager : IOpenIddictApplication /// The that can be used to abort the operation. /// The validation error encountered when validating the application. public virtual async IAsyncEnumerable ValidateAsync( - TApplication application!!, [EnumeratorCancellation] CancellationToken cancellationToken = default) + TApplication application, [EnumeratorCancellation] CancellationToken cancellationToken = default) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + // Ensure the client_id is not null or empty and is not already used for a different application. var identifier = await Store.GetClientIdAsync(application, cancellationToken); if (string.IsNullOrEmpty(identifier)) @@ -1046,8 +1251,12 @@ public class OpenIddictApplicationManager : IOpenIddictApplication /// whose result returns a boolean indicating whether the client secret was valid. /// public virtual async ValueTask ValidateClientSecretAsync( - TApplication application!!, string secret, CancellationToken cancellationToken = default) + TApplication application, string secret, CancellationToken cancellationToken = default) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } if (string.IsNullOrEmpty(secret)) { throw new ArgumentException(SR.GetResourceString(SR.ID0216), nameof(secret)); @@ -1089,8 +1298,13 @@ public class OpenIddictApplicationManager : IOpenIddictApplication /// whose result returns a boolean indicating whether the redirect_uri was valid. /// public virtual async ValueTask ValidateRedirectUriAsync( - TApplication application!!, string address, CancellationToken cancellationToken = default) + TApplication application, string address, CancellationToken cancellationToken = default) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + if (string.IsNullOrEmpty(address)) { throw new ArgumentException(SR.GetResourceString(SR.ID0143), nameof(address)); diff --git a/src/OpenIddict.Core/Managers/OpenIddictAuthorizationManager.cs b/src/OpenIddict.Core/Managers/OpenIddictAuthorizationManager.cs index e5f0d8ab..5762d370 100644 --- a/src/OpenIddict.Core/Managers/OpenIddictAuthorizationManager.cs +++ b/src/OpenIddict.Core/Managers/OpenIddictAuthorizationManager.cs @@ -28,15 +28,15 @@ namespace OpenIddict.Core; public class OpenIddictAuthorizationManager : IOpenIddictAuthorizationManager where TAuthorization : class { public OpenIddictAuthorizationManager( - IOpenIddictAuthorizationCache cache!!, - ILogger> logger!!, - IOptionsMonitor options!!, - IOpenIddictAuthorizationStoreResolver resolver!!) + IOpenIddictAuthorizationCache cache, + ILogger> logger, + IOptionsMonitor options, + IOpenIddictAuthorizationStoreResolver resolver) { - Cache = cache; - Logger = logger; - Options = options; - Store = resolver.Get(); + Cache = cache ?? throw new ArgumentNullException(nameof(cache)); + Logger = logger ?? throw new ArgumentNullException(nameof(logger)); + Options = options ?? throw new ArgumentNullException(nameof(options)); + Store = (resolver ?? throw new ArgumentNullException(nameof(resolver))).Get(); } /// @@ -81,8 +81,15 @@ public class OpenIddictAuthorizationManager : IOpenIddictAuthori /// whose result returns the number of authorizations that match the specified query. /// public virtual ValueTask CountAsync( - Func, IQueryable> query!!, CancellationToken cancellationToken = default) - => Store.CountAsync(query, cancellationToken); + Func, IQueryable> query, CancellationToken cancellationToken = default) + { + if (query is null) + { + throw new ArgumentNullException(nameof(query)); + } + + return Store.CountAsync(query, cancellationToken); + } /// /// Creates a new authorization. @@ -92,8 +99,13 @@ public class OpenIddictAuthorizationManager : IOpenIddictAuthori /// /// A that can be used to monitor the asynchronous operation. /// - public virtual async ValueTask CreateAsync(TAuthorization authorization!!, CancellationToken cancellationToken = default) + public virtual async ValueTask CreateAsync(TAuthorization authorization, CancellationToken cancellationToken = default) { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + // If no status was explicitly specified, assume that the authorization is valid. if (string.IsNullOrEmpty(await Store.GetStatusAsync(authorization, cancellationToken))) { @@ -145,8 +157,13 @@ public class OpenIddictAuthorizationManager : IOpenIddictAuthori /// A that can be used to monitor the asynchronous operation, whose result returns the authorization. /// public virtual async ValueTask CreateAsync( - OpenIddictAuthorizationDescriptor descriptor!!, CancellationToken cancellationToken = default) + OpenIddictAuthorizationDescriptor descriptor, CancellationToken cancellationToken = default) { + if (descriptor is null) + { + throw new ArgumentNullException(nameof(descriptor)); + } + var authorization = await Store.InstantiateAsync(cancellationToken) ?? throw new InvalidOperationException(SR.GetResourceString(SR.ID0220)); @@ -169,9 +186,14 @@ public class OpenIddictAuthorizationManager : IOpenIddictAuthori /// A that can be used to monitor the asynchronous operation, whose result returns the authorization. /// public virtual ValueTask CreateAsync( - ClaimsPrincipal principal!!, string subject, string client, + ClaimsPrincipal principal, string subject, string client, string type, ImmutableArray scopes, CancellationToken cancellationToken = default) { + if (principal is null) + { + throw new ArgumentNullException(nameof(principal)); + } + if (string.IsNullOrEmpty(subject)) { throw new ArgumentException(SR.GetResourceString(SR.ID0198), nameof(subject)); @@ -210,8 +232,13 @@ public class OpenIddictAuthorizationManager : IOpenIddictAuthori /// /// A that can be used to monitor the asynchronous operation. /// - public virtual async ValueTask DeleteAsync(TAuthorization authorization!!, CancellationToken cancellationToken = default) + public virtual async ValueTask DeleteAsync(TAuthorization authorization, CancellationToken cancellationToken = default) { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + if (!Options.CurrentValue.DisableEntityCaching) { await Cache.RemoveAsync(authorization, cancellationToken); @@ -584,8 +611,15 @@ public class OpenIddictAuthorizationManager : IOpenIddictAuthori /// whose result returns the application identifier associated with the authorization. /// public virtual ValueTask GetApplicationIdAsync( - TAuthorization authorization!!, CancellationToken cancellationToken = default) - => Store.GetApplicationIdAsync(authorization, cancellationToken); + TAuthorization authorization, CancellationToken cancellationToken = default) + { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + + return Store.GetApplicationIdAsync(authorization, cancellationToken); + } /// /// Executes the specified query and returns the first element. @@ -598,8 +632,15 @@ public class OpenIddictAuthorizationManager : IOpenIddictAuthori /// whose result returns the first element returned when executing the query. /// public virtual ValueTask GetAsync( - Func, IQueryable> query!!, CancellationToken cancellationToken = default) - => GetAsync(static (authorizations, query) => query(authorizations), query, cancellationToken); + Func, IQueryable> query, CancellationToken cancellationToken = default) + { + if (query is null) + { + throw new ArgumentNullException(nameof(query)); + } + + return GetAsync(static (authorizations, query) => query(authorizations), query, cancellationToken); + } /// /// Executes the specified query and returns the first element. @@ -614,9 +655,16 @@ public class OpenIddictAuthorizationManager : IOpenIddictAuthori /// whose result returns the first element returned when executing the query. /// public virtual ValueTask GetAsync( - Func, TState, IQueryable> query!!, + Func, TState, IQueryable> query, TState state, CancellationToken cancellationToken = default) - => Store.GetAsync(query, state, cancellationToken); + { + if (query is null) + { + throw new ArgumentNullException(nameof(query)); + } + + return Store.GetAsync(query, state, cancellationToken); + } /// /// Retrieves the creation date associated with an authorization. @@ -628,8 +676,15 @@ public class OpenIddictAuthorizationManager : IOpenIddictAuthori /// whose result returns the creation date associated with the specified authorization. /// public virtual ValueTask GetCreationDateAsync( - TAuthorization authorization!!, CancellationToken cancellationToken = default) - => Store.GetCreationDateAsync(authorization, cancellationToken); + TAuthorization authorization, CancellationToken cancellationToken = default) + { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + + return Store.GetCreationDateAsync(authorization, cancellationToken); + } /// /// Retrieves the unique identifier associated with an authorization. @@ -640,8 +695,15 @@ public class OpenIddictAuthorizationManager : IOpenIddictAuthori /// A that can be used to monitor the asynchronous operation, /// whose result returns the unique identifier associated with the authorization. /// - public virtual ValueTask GetIdAsync(TAuthorization authorization!!, CancellationToken cancellationToken = default) - => Store.GetIdAsync(authorization, cancellationToken); + public virtual ValueTask GetIdAsync(TAuthorization authorization, CancellationToken cancellationToken = default) + { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + + return Store.GetIdAsync(authorization, cancellationToken); + } /// /// Retrieves the additional properties associated with an authorization. @@ -653,8 +715,15 @@ public class OpenIddictAuthorizationManager : IOpenIddictAuthori /// whose result returns all the additional properties associated with the authorization. /// public virtual ValueTask> GetPropertiesAsync( - TAuthorization authorization!!, CancellationToken cancellationToken = default) - => Store.GetPropertiesAsync(authorization, cancellationToken); + TAuthorization authorization, CancellationToken cancellationToken = default) + { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + + return Store.GetPropertiesAsync(authorization, cancellationToken); + } /// /// Retrieves the scopes associated with an authorization. @@ -666,8 +735,15 @@ public class OpenIddictAuthorizationManager : IOpenIddictAuthori /// whose result returns the scopes associated with the specified authorization. /// public virtual ValueTask> GetScopesAsync( - TAuthorization authorization!!, CancellationToken cancellationToken = default) - => Store.GetScopesAsync(authorization, cancellationToken); + TAuthorization authorization, CancellationToken cancellationToken = default) + { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + + return Store.GetScopesAsync(authorization, cancellationToken); + } /// /// Retrieves the status associated with an authorization. @@ -679,8 +755,15 @@ public class OpenIddictAuthorizationManager : IOpenIddictAuthori /// whose result returns the status associated with the specified authorization. /// public virtual ValueTask GetStatusAsync( - TAuthorization authorization!!, CancellationToken cancellationToken = default) - => Store.GetStatusAsync(authorization, cancellationToken); + TAuthorization authorization, CancellationToken cancellationToken = default) + { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + + return Store.GetStatusAsync(authorization, cancellationToken); + } /// /// Retrieves the subject associated with an authorization. @@ -692,8 +775,15 @@ public class OpenIddictAuthorizationManager : IOpenIddictAuthori /// whose result returns the subject associated with the specified authorization. /// public virtual ValueTask GetSubjectAsync( - TAuthorization authorization!!, CancellationToken cancellationToken = default) - => Store.GetSubjectAsync(authorization, cancellationToken); + TAuthorization authorization, CancellationToken cancellationToken = default) + { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + + return Store.GetSubjectAsync(authorization, cancellationToken); + } /// /// Retrieves the type associated with an authorization. @@ -705,8 +795,15 @@ public class OpenIddictAuthorizationManager : IOpenIddictAuthori /// whose result returns the type associated with the specified authorization. /// public virtual ValueTask GetTypeAsync( - TAuthorization authorization!!, CancellationToken cancellationToken = default) - => Store.GetTypeAsync(authorization, cancellationToken); + TAuthorization authorization, CancellationToken cancellationToken = default) + { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + + return Store.GetTypeAsync(authorization, cancellationToken); + } /// /// Determines whether the specified scopes are included in the authorization. @@ -715,10 +812,17 @@ public class OpenIddictAuthorizationManager : IOpenIddictAuthori /// The scopes. /// The that can be used to abort the operation. /// if the scopes are included in the authorization, otherwise. - public virtual async ValueTask HasScopesAsync(TAuthorization authorization!!, + public virtual async ValueTask HasScopesAsync(TAuthorization authorization, ImmutableArray scopes, CancellationToken cancellationToken = default) - => new HashSet(await Store.GetScopesAsync( + { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + + return new HashSet(await Store.GetScopesAsync( authorization, cancellationToken), StringComparer.Ordinal).IsSupersetOf(scopes); + } /// /// Determines whether a given authorization has the specified status. @@ -727,9 +831,14 @@ public class OpenIddictAuthorizationManager : IOpenIddictAuthori /// The expected status. /// The that can be used to abort the operation. /// if the authorization has the specified status, otherwise. - public virtual async ValueTask HasStatusAsync(TAuthorization authorization!!, + public virtual async ValueTask HasStatusAsync(TAuthorization authorization, string status, CancellationToken cancellationToken = default) { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + if (string.IsNullOrEmpty(status)) { throw new ArgumentException(SR.GetResourceString(SR.ID0199), nameof(status)); @@ -746,8 +855,13 @@ public class OpenIddictAuthorizationManager : IOpenIddictAuthori /// The that can be used to abort the operation. /// if the authorization has the specified type, otherwise. public virtual async ValueTask HasTypeAsync( - TAuthorization authorization!!, string type, CancellationToken cancellationToken = default) + TAuthorization authorization, string type, CancellationToken cancellationToken = default) { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + if (string.IsNullOrEmpty(type)) { throw new ArgumentException(SR.GetResourceString(SR.ID0200), nameof(type)); @@ -775,8 +889,15 @@ public class OpenIddictAuthorizationManager : IOpenIddictAuthori /// The that can be used to abort the operation. /// All the elements returned when executing the specified query. public virtual IAsyncEnumerable ListAsync( - Func, IQueryable> query!!, CancellationToken cancellationToken = default) - => ListAsync(static (authorizations, query) => query(authorizations), query, cancellationToken); + Func, IQueryable> query, CancellationToken cancellationToken = default) + { + if (query is null) + { + throw new ArgumentNullException(nameof(query)); + } + + return ListAsync(static (authorizations, query) => query(authorizations), query, cancellationToken); + } /// /// Executes the specified query and returns all the corresponding elements. @@ -788,9 +909,16 @@ public class OpenIddictAuthorizationManager : IOpenIddictAuthori /// The that can be used to abort the operation. /// All the elements returned when executing the specified query. public virtual IAsyncEnumerable ListAsync( - Func, TState, IQueryable> query!!, + Func, TState, IQueryable> query, TState state, CancellationToken cancellationToken = default) - => Store.ListAsync(query, state, cancellationToken); + { + if (query is null) + { + throw new ArgumentNullException(nameof(query)); + } + + return Store.ListAsync(query, state, cancellationToken); + } /// /// Populates the authorization using the specified descriptor. @@ -801,9 +929,19 @@ public class OpenIddictAuthorizationManager : IOpenIddictAuthori /// /// A that can be used to monitor the asynchronous operation. /// - public virtual async ValueTask PopulateAsync(TAuthorization authorization!!, - OpenIddictAuthorizationDescriptor descriptor!!, CancellationToken cancellationToken = default) + public virtual async ValueTask PopulateAsync(TAuthorization authorization, + OpenIddictAuthorizationDescriptor descriptor, CancellationToken cancellationToken = default) { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + + if (descriptor is null) + { + throw new ArgumentNullException(nameof(descriptor)); + } + await Store.SetApplicationIdAsync(authorization, descriptor.ApplicationId, cancellationToken); await Store.SetCreationDateAsync(authorization, descriptor.CreationDate, cancellationToken); await Store.SetPropertiesAsync(authorization, descriptor.Properties.ToImmutableDictionary(), cancellationToken); @@ -823,9 +961,19 @@ public class OpenIddictAuthorizationManager : IOpenIddictAuthori /// A that can be used to monitor the asynchronous operation. /// public virtual async ValueTask PopulateAsync( - OpenIddictAuthorizationDescriptor descriptor!!, - TAuthorization authorization!!, CancellationToken cancellationToken = default) + OpenIddictAuthorizationDescriptor descriptor, + TAuthorization authorization, CancellationToken cancellationToken = default) { + if (descriptor is null) + { + throw new ArgumentNullException(nameof(descriptor)); + } + + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + descriptor.ApplicationId = await Store.GetApplicationIdAsync(authorization, cancellationToken); descriptor.CreationDate = await Store.GetCreationDateAsync(authorization, cancellationToken); descriptor.Scopes.Clear(); @@ -863,8 +1011,13 @@ public class OpenIddictAuthorizationManager : IOpenIddictAuthori /// The authorization to revoke. /// The that can be used to abort the operation. /// if the authorization was successfully revoked, otherwise. - public virtual async ValueTask TryRevokeAsync(TAuthorization authorization!!, CancellationToken cancellationToken = default) + public virtual async ValueTask TryRevokeAsync(TAuthorization authorization, CancellationToken cancellationToken = default) { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + var status = await Store.GetStatusAsync(authorization, cancellationToken); if (string.Equals(status, Statuses.Revoked, StringComparison.OrdinalIgnoreCase)) { @@ -905,8 +1058,13 @@ public class OpenIddictAuthorizationManager : IOpenIddictAuthori /// /// A that can be used to monitor the asynchronous operation. /// - public virtual async ValueTask UpdateAsync(TAuthorization authorization!!, CancellationToken cancellationToken = default) + public virtual async ValueTask UpdateAsync(TAuthorization authorization, CancellationToken cancellationToken = default) { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + var results = await GetValidationResultsAsync(authorization, cancellationToken); if (results.Any(result => result != ValidationResult.Success)) { @@ -953,9 +1111,19 @@ public class OpenIddictAuthorizationManager : IOpenIddictAuthori /// /// A that can be used to monitor the asynchronous operation. /// - public virtual async ValueTask UpdateAsync(TAuthorization authorization!!, - OpenIddictAuthorizationDescriptor descriptor!!, CancellationToken cancellationToken = default) + public virtual async ValueTask UpdateAsync(TAuthorization authorization, + OpenIddictAuthorizationDescriptor descriptor, CancellationToken cancellationToken = default) { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + + if (descriptor is null) + { + throw new ArgumentNullException(nameof(descriptor)); + } + await PopulateAsync(authorization, descriptor, cancellationToken); await UpdateAsync(authorization, cancellationToken); } @@ -967,8 +1135,13 @@ public class OpenIddictAuthorizationManager : IOpenIddictAuthori /// The that can be used to abort the operation. /// The validation error encountered when validating the authorization. public virtual async IAsyncEnumerable ValidateAsync( - TAuthorization authorization!!, [EnumeratorCancellation] CancellationToken cancellationToken = default) + TAuthorization authorization, [EnumeratorCancellation] CancellationToken cancellationToken = default) { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + var type = await Store.GetTypeAsync(authorization, cancellationToken); if (string.IsNullOrEmpty(type)) { diff --git a/src/OpenIddict.Core/Managers/OpenIddictScopeManager.cs b/src/OpenIddict.Core/Managers/OpenIddictScopeManager.cs index a419c38c..a11cc491 100644 --- a/src/OpenIddict.Core/Managers/OpenIddictScopeManager.cs +++ b/src/OpenIddict.Core/Managers/OpenIddictScopeManager.cs @@ -27,15 +27,15 @@ namespace OpenIddict.Core; public class OpenIddictScopeManager : IOpenIddictScopeManager where TScope : class { public OpenIddictScopeManager( - IOpenIddictScopeCache cache!!, - ILogger> logger!!, - IOptionsMonitor options!!, - IOpenIddictScopeStoreResolver resolver!!) + IOpenIddictScopeCache cache, + ILogger> logger, + IOptionsMonitor options, + IOpenIddictScopeStoreResolver resolver) { - Cache = cache; - Logger = logger; - Options = options; - Store = resolver.Get(); + Cache = cache ?? throw new ArgumentNullException(nameof(cache)); + Logger = logger ?? throw new ArgumentNullException(nameof(logger)); + Options = options ?? throw new ArgumentNullException(nameof(options)); + Store = (resolver ?? throw new ArgumentNullException(nameof(resolver))).Get(); } /// @@ -80,8 +80,15 @@ public class OpenIddictScopeManager : IOpenIddictScopeManager where TSco /// whose result returns the number of scopes that match the specified query. /// public virtual ValueTask CountAsync( - Func, IQueryable> query!!, CancellationToken cancellationToken = default) - => Store.CountAsync(query, cancellationToken); + Func, IQueryable> query, CancellationToken cancellationToken = default) + { + if (query is null) + { + throw new ArgumentNullException(nameof(query)); + } + + return Store.CountAsync(query, cancellationToken); + } /// /// Creates a new scope. @@ -91,8 +98,13 @@ public class OpenIddictScopeManager : IOpenIddictScopeManager where TSco /// /// A that can be used to monitor the asynchronous operation. /// - public virtual async ValueTask CreateAsync(TScope scope!!, CancellationToken cancellationToken = default) + public virtual async ValueTask CreateAsync(TScope scope, CancellationToken cancellationToken = default) { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + var results = await GetValidationResultsAsync(scope, cancellationToken); if (results.Any(result => result != ValidationResult.Success)) { @@ -138,8 +150,13 @@ public class OpenIddictScopeManager : IOpenIddictScopeManager where TSco /// A that can be used to monitor the asynchronous operation, whose result returns the scope. /// public virtual async ValueTask CreateAsync( - OpenIddictScopeDescriptor descriptor!!, CancellationToken cancellationToken = default) + OpenIddictScopeDescriptor descriptor, CancellationToken cancellationToken = default) { + if (descriptor is null) + { + throw new ArgumentNullException(nameof(descriptor)); + } + var scope = await Store.InstantiateAsync(cancellationToken) ?? throw new InvalidOperationException(SR.GetResourceString(SR.ID0223)); @@ -157,8 +174,13 @@ public class OpenIddictScopeManager : IOpenIddictScopeManager where TSco /// /// A that can be used to monitor the asynchronous operation. /// - public virtual async ValueTask DeleteAsync(TScope scope!!, CancellationToken cancellationToken = default) + public virtual async ValueTask DeleteAsync(TScope scope, CancellationToken cancellationToken = default) { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + if (!Options.CurrentValue.DisableEntityCaching) { await Cache.RemoveAsync(scope, cancellationToken); @@ -251,7 +273,7 @@ public class OpenIddictScopeManager : IOpenIddictScopeManager where TSco public virtual IAsyncEnumerable FindByNamesAsync( ImmutableArray names, CancellationToken cancellationToken = default) { - if (names.Any(string.IsNullOrEmpty)) + if (names.Any(name => string.IsNullOrEmpty(name))) { throw new ArgumentException(SR.GetResourceString(SR.ID0203), nameof(names)); } @@ -336,8 +358,15 @@ public class OpenIddictScopeManager : IOpenIddictScopeManager where TSco /// whose result returns the first element returned when executing the query. /// public virtual ValueTask GetAsync( - Func, IQueryable> query!!, CancellationToken cancellationToken = default) - => GetAsync(static (scopes, query) => query(scopes), query, cancellationToken); + Func, IQueryable> query, CancellationToken cancellationToken = default) + { + if (query is null) + { + throw new ArgumentNullException(nameof(query)); + } + + return GetAsync(static (scopes, query) => query(scopes), query, cancellationToken); + } /// /// Executes the specified query and returns the first element. @@ -352,9 +381,16 @@ public class OpenIddictScopeManager : IOpenIddictScopeManager where TSco /// whose result returns the first element returned when executing the query. /// public virtual ValueTask GetAsync( - Func, TState, IQueryable> query!!, + Func, TState, IQueryable> query, TState state, CancellationToken cancellationToken = default) - => Store.GetAsync(query, state, cancellationToken); + { + if (query is null) + { + throw new ArgumentNullException(nameof(query)); + } + + return Store.GetAsync(query, state, cancellationToken); + } /// /// Retrieves the description associated with a scope. @@ -365,8 +401,15 @@ public class OpenIddictScopeManager : IOpenIddictScopeManager where TSco /// A that can be used to monitor the asynchronous operation, /// whose result returns the description associated with the specified scope. /// - public virtual ValueTask GetDescriptionAsync(TScope scope!!, CancellationToken cancellationToken = default) - => Store.GetDescriptionAsync(scope, cancellationToken); + public virtual ValueTask GetDescriptionAsync(TScope scope, CancellationToken cancellationToken = default) + { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + + return Store.GetDescriptionAsync(scope, cancellationToken); + } /// /// Retrieves the localized descriptions associated with an scope. @@ -378,9 +421,21 @@ public class OpenIddictScopeManager : IOpenIddictScopeManager where TSco /// whose result returns all the localized descriptions associated with the scope. /// public virtual async ValueTask> GetDescriptionsAsync( - TScope scope!!, CancellationToken cancellationToken = default) - => await Store.GetDescriptionsAsync(scope, cancellationToken) is { Count: > 0 } descriptions ? - descriptions : ImmutableDictionary.Create(); + TScope scope, CancellationToken cancellationToken = default) + { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + + var descriptions = await Store.GetDescriptionsAsync(scope, cancellationToken); + if (descriptions is null || descriptions.Count == 0) + { + return ImmutableDictionary.Create(); + } + + return descriptions; + } /// /// Retrieves the display name associated with a scope. @@ -391,8 +446,15 @@ public class OpenIddictScopeManager : IOpenIddictScopeManager where TSco /// A that can be used to monitor the asynchronous operation, /// whose result returns the display name associated with the scope. /// - public virtual ValueTask GetDisplayNameAsync(TScope scope!!, CancellationToken cancellationToken = default) - => Store.GetDisplayNameAsync(scope, cancellationToken); + public virtual ValueTask GetDisplayNameAsync(TScope scope, CancellationToken cancellationToken = default) + { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + + return Store.GetDisplayNameAsync(scope, cancellationToken); + } /// /// Retrieves the localized display names associated with an scope. @@ -404,9 +466,21 @@ public class OpenIddictScopeManager : IOpenIddictScopeManager where TSco /// whose result returns all the localized display names associated with the scope. /// public virtual async ValueTask> GetDisplayNamesAsync( - TScope scope!!, CancellationToken cancellationToken = default) - => await Store.GetDisplayNamesAsync(scope, cancellationToken) is { Count: > 0 } names ? - names : ImmutableDictionary.Create(); + TScope scope, CancellationToken cancellationToken = default) + { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + + var names = await Store.GetDisplayNamesAsync(scope, cancellationToken); + if (names is null || names.Count == 0) + { + return ImmutableDictionary.Create(); + } + + return names; + } /// /// Retrieves the unique identifier associated with a scope. @@ -417,8 +491,15 @@ public class OpenIddictScopeManager : IOpenIddictScopeManager where TSco /// A that can be used to monitor the asynchronous operation, /// whose result returns the unique identifier associated with the scope. /// - public virtual ValueTask GetIdAsync(TScope scope!!, CancellationToken cancellationToken = default) - => Store.GetIdAsync(scope, cancellationToken); + public virtual ValueTask GetIdAsync(TScope scope, CancellationToken cancellationToken = default) + { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + + return Store.GetIdAsync(scope, cancellationToken); + } /// /// Retrieves the localized display name associated with an scope @@ -447,8 +528,18 @@ public class OpenIddictScopeManager : IOpenIddictScopeManager where TSco /// whose result returns the matching display name associated with the scope. /// public virtual async ValueTask GetLocalizedDisplayNameAsync( - TScope scope!!, CultureInfo culture!!, CancellationToken cancellationToken = default) + TScope scope, CultureInfo culture, CancellationToken cancellationToken = default) { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + + if (culture is null) + { + throw new ArgumentNullException(nameof(culture)); + } + var names = await Store.GetDisplayNamesAsync(scope, cancellationToken); if (names is not { Count: > 0 }) { @@ -497,8 +588,18 @@ public class OpenIddictScopeManager : IOpenIddictScopeManager where TSco /// whose result returns the matching localized description associated with the scope. /// public virtual async ValueTask GetLocalizedDescriptionAsync( - TScope scope!!, CultureInfo culture!!, CancellationToken cancellationToken = default) + TScope scope, CultureInfo culture, CancellationToken cancellationToken = default) { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + + if (culture is null) + { + throw new ArgumentNullException(nameof(culture)); + } + var descriptions = await Store.GetDescriptionsAsync(scope, cancellationToken); if (descriptions is not { Count: > 0 }) { @@ -529,8 +630,15 @@ public class OpenIddictScopeManager : IOpenIddictScopeManager where TSco /// A that can be used to monitor the asynchronous operation, /// whose result returns the name associated with the specified scope. /// - public virtual ValueTask GetNameAsync(TScope scope!!, CancellationToken cancellationToken = default) - => Store.GetNameAsync(scope, cancellationToken); + public virtual ValueTask GetNameAsync(TScope scope, CancellationToken cancellationToken = default) + { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + + return Store.GetNameAsync(scope, cancellationToken); + } /// /// Retrieves the additional properties associated with a scope. @@ -542,8 +650,15 @@ public class OpenIddictScopeManager : IOpenIddictScopeManager where TSco /// whose result returns all the additional properties associated with the scope. /// public virtual ValueTask> GetPropertiesAsync( - TScope scope!!, CancellationToken cancellationToken = default) - => Store.GetPropertiesAsync(scope, cancellationToken); + TScope scope, CancellationToken cancellationToken = default) + { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + + return Store.GetPropertiesAsync(scope, cancellationToken); + } /// /// Retrieves the resources associated with a scope. @@ -555,8 +670,15 @@ public class OpenIddictScopeManager : IOpenIddictScopeManager where TSco /// whose result returns all the resources associated with the scope. /// public virtual ValueTask> GetResourcesAsync( - TScope scope!!, CancellationToken cancellationToken = default) - => Store.GetResourcesAsync(scope, cancellationToken); + TScope scope, CancellationToken cancellationToken = default) + { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + + return Store.GetResourcesAsync(scope, cancellationToken); + } /// /// Executes the specified query and returns all the corresponding elements. @@ -577,8 +699,15 @@ public class OpenIddictScopeManager : IOpenIddictScopeManager where TSco /// The that can be used to abort the operation. /// All the elements returned when executing the specified query. public virtual IAsyncEnumerable ListAsync( - Func, IQueryable> query!!, CancellationToken cancellationToken = default) - => ListAsync(static (scopes, query) => query(scopes), query, cancellationToken); + Func, IQueryable> query, CancellationToken cancellationToken = default) + { + if (query is null) + { + throw new ArgumentNullException(nameof(query)); + } + + return ListAsync(static (scopes, query) => query(scopes), query, cancellationToken); + } /// /// Executes the specified query and returns all the corresponding elements. @@ -590,9 +719,16 @@ public class OpenIddictScopeManager : IOpenIddictScopeManager where TSco /// The that can be used to abort the operation. /// All the elements returned when executing the specified query. public virtual IAsyncEnumerable ListAsync( - Func, TState, IQueryable> query!!, + Func, TState, IQueryable> query, TState state, CancellationToken cancellationToken = default) - => Store.ListAsync(query, state, cancellationToken); + { + if (query is null) + { + throw new ArgumentNullException(nameof(query)); + } + + return Store.ListAsync(query, state, cancellationToken); + } /// /// Lists all the resources associated with the specified scopes. @@ -625,9 +761,19 @@ public class OpenIddictScopeManager : IOpenIddictScopeManager where TSco /// /// A that can be used to monitor the asynchronous operation. /// - public virtual async ValueTask PopulateAsync(TScope scope!!, - OpenIddictScopeDescriptor descriptor!!, CancellationToken cancellationToken = default) + public virtual async ValueTask PopulateAsync(TScope scope, + OpenIddictScopeDescriptor descriptor, CancellationToken cancellationToken = default) { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + + if (descriptor is null) + { + throw new ArgumentNullException(nameof(descriptor)); + } + await Store.SetDescriptionAsync(scope, descriptor.Description, cancellationToken); await Store.SetDescriptionsAsync(scope, descriptor.Descriptions.ToImmutableDictionary(), cancellationToken); await Store.SetDisplayNameAsync(scope, descriptor.DisplayName, cancellationToken); @@ -647,9 +793,19 @@ public class OpenIddictScopeManager : IOpenIddictScopeManager where TSco /// A that can be used to monitor the asynchronous operation. /// public virtual async ValueTask PopulateAsync( - OpenIddictScopeDescriptor descriptor!!, - TScope scope!!, CancellationToken cancellationToken = default) + OpenIddictScopeDescriptor descriptor, + TScope scope, CancellationToken cancellationToken = default) { + if (descriptor is null) + { + throw new ArgumentNullException(nameof(descriptor)); + } + + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + descriptor.Description = await Store.GetDescriptionAsync(scope, cancellationToken); descriptor.DisplayName = await Store.GetDisplayNameAsync(scope, cancellationToken); descriptor.Name = await Store.GetNameAsync(scope, cancellationToken); @@ -683,8 +839,13 @@ public class OpenIddictScopeManager : IOpenIddictScopeManager where TSco /// /// A that can be used to monitor the asynchronous operation. /// - public virtual async ValueTask UpdateAsync(TScope scope!!, CancellationToken cancellationToken = default) + public virtual async ValueTask UpdateAsync(TScope scope, CancellationToken cancellationToken = default) { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + var results = await GetValidationResultsAsync(scope, cancellationToken); if (results.Any(result => result != ValidationResult.Success)) { @@ -731,9 +892,19 @@ public class OpenIddictScopeManager : IOpenIddictScopeManager where TSco /// /// A that can be used to monitor the asynchronous operation. /// - public virtual async ValueTask UpdateAsync(TScope scope!!, - OpenIddictScopeDescriptor descriptor!!, CancellationToken cancellationToken = default) + public virtual async ValueTask UpdateAsync(TScope scope, + OpenIddictScopeDescriptor descriptor, CancellationToken cancellationToken = default) { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + + if (descriptor is null) + { + throw new ArgumentNullException(nameof(descriptor)); + } + await PopulateAsync(scope, descriptor, cancellationToken); await UpdateAsync(scope, cancellationToken); } @@ -745,8 +916,13 @@ public class OpenIddictScopeManager : IOpenIddictScopeManager where TSco /// The that can be used to abort the operation. /// The validation error encountered when validating the scope. public virtual async IAsyncEnumerable ValidateAsync( - TScope scope!!, [EnumeratorCancellation] CancellationToken cancellationToken = default) + TScope scope, [EnumeratorCancellation] CancellationToken cancellationToken = default) { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + // Ensure the name is not null or empty, does not contain a // space and is not already used for a different scope entity. var name = await Store.GetNameAsync(scope, cancellationToken); diff --git a/src/OpenIddict.Core/Managers/OpenIddictTokenManager.cs b/src/OpenIddict.Core/Managers/OpenIddictTokenManager.cs index ec72369e..68080892 100644 --- a/src/OpenIddict.Core/Managers/OpenIddictTokenManager.cs +++ b/src/OpenIddict.Core/Managers/OpenIddictTokenManager.cs @@ -28,15 +28,15 @@ namespace OpenIddict.Core; public class OpenIddictTokenManager : IOpenIddictTokenManager where TToken : class { public OpenIddictTokenManager( - IOpenIddictTokenCache cache!!, - ILogger> logger!!, - IOptionsMonitor options!!, - IOpenIddictTokenStoreResolver resolver!!) + IOpenIddictTokenCache cache, + ILogger> logger, + IOptionsMonitor options, + IOpenIddictTokenStoreResolver resolver) { - Cache = cache; - Logger = logger; - Options = options; - Store = resolver.Get(); + Cache = cache ?? throw new ArgumentNullException(nameof(cache)); + Logger = logger ?? throw new ArgumentNullException(nameof(logger)); + Options = options ?? throw new ArgumentNullException(nameof(options)); + Store = (resolver ?? throw new ArgumentNullException(nameof(resolver))).Get(); } /// @@ -81,8 +81,15 @@ public class OpenIddictTokenManager : IOpenIddictTokenManager where TTok /// whose result returns the number of tokens that match the specified query. /// public virtual ValueTask CountAsync( - Func, IQueryable> query!!, CancellationToken cancellationToken = default) - => Store.CountAsync(query, cancellationToken); + Func, IQueryable> query, CancellationToken cancellationToken = default) + { + if (query is null) + { + throw new ArgumentNullException(nameof(query)); + } + + return Store.CountAsync(query, cancellationToken); + } /// /// Creates a new token. @@ -92,8 +99,13 @@ public class OpenIddictTokenManager : IOpenIddictTokenManager where TTok /// /// A that can be used to monitor the asynchronous operation. /// - public virtual async ValueTask CreateAsync(TToken token!!, CancellationToken cancellationToken = default) + public virtual async ValueTask CreateAsync(TToken token, CancellationToken cancellationToken = default) { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + // If no status was explicitly specified, assume that the token is valid. if (string.IsNullOrEmpty(await Store.GetStatusAsync(token, cancellationToken))) { @@ -153,8 +165,13 @@ public class OpenIddictTokenManager : IOpenIddictTokenManager where TTok /// A that can be used to monitor the asynchronous operation, whose result returns the token. /// public virtual async ValueTask CreateAsync( - OpenIddictTokenDescriptor descriptor!!, CancellationToken cancellationToken = default) + OpenIddictTokenDescriptor descriptor, CancellationToken cancellationToken = default) { + if (descriptor is null) + { + throw new ArgumentNullException(nameof(descriptor)); + } + var token = await Store.InstantiateAsync(cancellationToken) ?? throw new InvalidOperationException(SR.GetResourceString(SR.ID0226)); @@ -172,8 +189,13 @@ public class OpenIddictTokenManager : IOpenIddictTokenManager where TTok /// /// A that can be used to monitor the asynchronous operation. /// - public virtual async ValueTask DeleteAsync(TToken token!!, CancellationToken cancellationToken = default) + public virtual async ValueTask DeleteAsync(TToken token, CancellationToken cancellationToken = default) { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + if (!Options.CurrentValue.DisableEntityCaching) { await Cache.RemoveAsync(token, cancellationToken); @@ -554,8 +576,15 @@ public class OpenIddictTokenManager : IOpenIddictTokenManager where TTok /// A that can be used to monitor the asynchronous operation, /// whose result returns the application identifier associated with the token. /// - public virtual ValueTask GetApplicationIdAsync(TToken token!!, CancellationToken cancellationToken = default) - => Store.GetApplicationIdAsync(token, cancellationToken); + public virtual ValueTask GetApplicationIdAsync(TToken token, CancellationToken cancellationToken = default) + { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + + return Store.GetApplicationIdAsync(token, cancellationToken); + } /// /// Executes the specified query and returns the first element. @@ -568,8 +597,15 @@ public class OpenIddictTokenManager : IOpenIddictTokenManager where TTok /// whose result returns the first element returned when executing the query. /// public virtual ValueTask GetAsync( - Func, IQueryable> query!!, CancellationToken cancellationToken = default) - => GetAsync(static (tokens, query) => query(tokens), query, cancellationToken); + Func, IQueryable> query, CancellationToken cancellationToken = default) + { + if (query is null) + { + throw new ArgumentNullException(nameof(query)); + } + + return GetAsync(static (tokens, query) => query(tokens), query, cancellationToken); + } /// /// Executes the specified query and returns the first element. @@ -584,9 +620,16 @@ public class OpenIddictTokenManager : IOpenIddictTokenManager where TTok /// whose result returns the first element returned when executing the query. /// public virtual ValueTask GetAsync( - Func, TState, IQueryable> query!!, + Func, TState, IQueryable> query, TState state, CancellationToken cancellationToken = default) - => Store.GetAsync(query, state, cancellationToken); + { + if (query is null) + { + throw new ArgumentNullException(nameof(query)); + } + + return Store.GetAsync(query, state, cancellationToken); + } /// /// Retrieves the optional authorization identifier associated with a token. @@ -597,8 +640,15 @@ public class OpenIddictTokenManager : IOpenIddictTokenManager where TTok /// A that can be used to monitor the asynchronous operation, /// whose result returns the authorization identifier associated with the token. /// - public virtual ValueTask GetAuthorizationIdAsync(TToken token!!, CancellationToken cancellationToken = default) - => Store.GetAuthorizationIdAsync(token, cancellationToken); + public virtual ValueTask GetAuthorizationIdAsync(TToken token, CancellationToken cancellationToken = default) + { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + + return Store.GetAuthorizationIdAsync(token, cancellationToken); + } /// /// Retrieves the creation date associated with a token. @@ -609,8 +659,15 @@ public class OpenIddictTokenManager : IOpenIddictTokenManager where TTok /// A that can be used to monitor the asynchronous operation, /// whose result returns the creation date associated with the specified token. /// - public virtual ValueTask GetCreationDateAsync(TToken token!!, CancellationToken cancellationToken = default) - => Store.GetCreationDateAsync(token, cancellationToken); + public virtual ValueTask GetCreationDateAsync(TToken token, CancellationToken cancellationToken = default) + { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + + return Store.GetCreationDateAsync(token, cancellationToken); + } /// /// Retrieves the expiration date associated with a token. @@ -621,8 +678,15 @@ public class OpenIddictTokenManager : IOpenIddictTokenManager where TTok /// A that can be used to monitor the asynchronous operation, /// whose result returns the expiration date associated with the specified token. /// - public virtual ValueTask GetExpirationDateAsync(TToken token!!, CancellationToken cancellationToken = default) - => Store.GetExpirationDateAsync(token, cancellationToken); + public virtual ValueTask GetExpirationDateAsync(TToken token, CancellationToken cancellationToken = default) + { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + + return Store.GetExpirationDateAsync(token, cancellationToken); + } /// /// Retrieves the unique identifier associated with a token. @@ -633,8 +697,15 @@ public class OpenIddictTokenManager : IOpenIddictTokenManager where TTok /// A that can be used to monitor the asynchronous operation, /// whose result returns the unique identifier associated with the token. /// - public virtual ValueTask GetIdAsync(TToken token!!, CancellationToken cancellationToken = default) - => Store.GetIdAsync(token, cancellationToken); + public virtual ValueTask GetIdAsync(TToken token, CancellationToken cancellationToken = default) + { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + + return Store.GetIdAsync(token, cancellationToken); + } /// /// Retrieves the payload associated with a token. @@ -645,8 +716,15 @@ public class OpenIddictTokenManager : IOpenIddictTokenManager where TTok /// A that can be used to monitor the asynchronous operation, /// whose result returns the payload associated with the specified token. /// - public virtual ValueTask GetPayloadAsync(TToken token!!, CancellationToken cancellationToken = default) - => Store.GetPayloadAsync(token, cancellationToken); + public virtual ValueTask GetPayloadAsync(TToken token, CancellationToken cancellationToken = default) + { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + + return Store.GetPayloadAsync(token, cancellationToken); + } /// /// Retrieves the additional properties associated with a token. @@ -658,8 +736,15 @@ public class OpenIddictTokenManager : IOpenIddictTokenManager where TTok /// whose result returns all the additional properties associated with the token. /// public virtual ValueTask> GetPropertiesAsync( - TToken token!!, CancellationToken cancellationToken = default) - => Store.GetPropertiesAsync(token, cancellationToken); + TToken token, CancellationToken cancellationToken = default) + { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + + return Store.GetPropertiesAsync(token, cancellationToken); + } /// /// Retrieves the redemption date associated with a token. @@ -670,8 +755,15 @@ public class OpenIddictTokenManager : IOpenIddictTokenManager where TTok /// A that can be used to monitor the asynchronous operation, /// whose result returns the redemption date associated with the specified token. /// - public virtual ValueTask GetRedemptionDateAsync(TToken token!!, CancellationToken cancellationToken = default) - => Store.GetRedemptionDateAsync(token, cancellationToken); + public virtual ValueTask GetRedemptionDateAsync(TToken token, CancellationToken cancellationToken = default) + { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + + return Store.GetRedemptionDateAsync(token, cancellationToken); + } /// /// Retrieves the reference identifier associated with a token. @@ -684,8 +776,15 @@ public class OpenIddictTokenManager : IOpenIddictTokenManager where TTok /// A that can be used to monitor the asynchronous operation, /// whose result returns the reference identifier associated with the specified token. /// - public virtual ValueTask GetReferenceIdAsync(TToken token!!, CancellationToken cancellationToken = default) - => Store.GetReferenceIdAsync(token, cancellationToken); + public virtual ValueTask GetReferenceIdAsync(TToken token, CancellationToken cancellationToken = default) + { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + + return Store.GetReferenceIdAsync(token, cancellationToken); + } /// /// Retrieves the status associated with a token. @@ -696,8 +795,15 @@ public class OpenIddictTokenManager : IOpenIddictTokenManager where TTok /// A that can be used to monitor the asynchronous operation, /// whose result returns the status associated with the specified token. /// - public virtual ValueTask GetStatusAsync(TToken token!!, CancellationToken cancellationToken = default) - => Store.GetStatusAsync(token, cancellationToken); + public virtual ValueTask GetStatusAsync(TToken token, CancellationToken cancellationToken = default) + { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + + return Store.GetStatusAsync(token, cancellationToken); + } /// /// Retrieves the subject associated with a token. @@ -708,8 +814,15 @@ public class OpenIddictTokenManager : IOpenIddictTokenManager where TTok /// A that can be used to monitor the asynchronous operation, /// whose result returns the subject associated with the specified token. /// - public virtual ValueTask GetSubjectAsync(TToken token!!, CancellationToken cancellationToken = default) - => Store.GetSubjectAsync(token, cancellationToken); + public virtual ValueTask GetSubjectAsync(TToken token, CancellationToken cancellationToken = default) + { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + + return Store.GetSubjectAsync(token, cancellationToken); + } /// /// Retrieves the token type associated with a token. @@ -720,8 +833,15 @@ public class OpenIddictTokenManager : IOpenIddictTokenManager where TTok /// A that can be used to monitor the asynchronous operation, /// whose result returns the token type associated with the specified token. /// - public virtual ValueTask GetTypeAsync(TToken token!!, CancellationToken cancellationToken = default) - => Store.GetTypeAsync(token, cancellationToken); + public virtual ValueTask GetTypeAsync(TToken token, CancellationToken cancellationToken = default) + { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + + return Store.GetTypeAsync(token, cancellationToken); + } /// /// Determines whether a given token has the specified status. @@ -730,8 +850,13 @@ public class OpenIddictTokenManager : IOpenIddictTokenManager where TTok /// The expected status. /// The that can be used to abort the operation. /// if the token has the specified status, otherwise. - public virtual async ValueTask HasStatusAsync(TToken token!!, string status, CancellationToken cancellationToken = default) + public virtual async ValueTask HasStatusAsync(TToken token, string status, CancellationToken cancellationToken = default) { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + if (string.IsNullOrEmpty(status)) { throw new ArgumentException(SR.GetResourceString(SR.ID0199), nameof(status)); @@ -747,8 +872,13 @@ public class OpenIddictTokenManager : IOpenIddictTokenManager where TTok /// The expected type. /// The that can be used to abort the operation. /// if the token has the specified type, otherwise. - public virtual async ValueTask HasTypeAsync(TToken token!!, string type, CancellationToken cancellationToken = default) + public virtual async ValueTask HasTypeAsync(TToken token, string type, CancellationToken cancellationToken = default) { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + if (string.IsNullOrEmpty(type)) { throw new ArgumentException(SR.GetResourceString(SR.ID0200), nameof(type)); @@ -764,8 +894,13 @@ public class OpenIddictTokenManager : IOpenIddictTokenManager where TTok /// The expected types. /// The that can be used to abort the operation. /// if the token has any of the specified types, otherwise. - public virtual async ValueTask HasTypeAsync(TToken token!!, ImmutableArray types, CancellationToken cancellationToken = default) + public virtual async ValueTask HasTypeAsync(TToken token, ImmutableArray types, CancellationToken cancellationToken = default) { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + var type = await Store.GetTypeAsync(token, cancellationToken); if (string.IsNullOrEmpty(type)) { @@ -802,8 +937,15 @@ public class OpenIddictTokenManager : IOpenIddictTokenManager where TTok /// The that can be used to abort the operation. /// All the elements returned when executing the specified query. public virtual IAsyncEnumerable ListAsync( - Func, IQueryable> query!!, CancellationToken cancellationToken = default) - => ListAsync(static (tokens, query) => query(tokens), query, cancellationToken); + Func, IQueryable> query, CancellationToken cancellationToken = default) + { + if (query is null) + { + throw new ArgumentNullException(nameof(query)); + } + + return ListAsync(static (tokens, query) => query(tokens), query, cancellationToken); + } /// /// Executes the specified query and returns all the corresponding elements. @@ -815,9 +957,16 @@ public class OpenIddictTokenManager : IOpenIddictTokenManager where TTok /// The that can be used to abort the operation. /// All the elements returned when executing the specified query. public virtual IAsyncEnumerable ListAsync( - Func, TState, IQueryable> query!!, + Func, TState, IQueryable> query, TState state, CancellationToken cancellationToken = default) - => Store.ListAsync(query, state, cancellationToken); + { + if (query is null) + { + throw new ArgumentNullException(nameof(query)); + } + + return Store.ListAsync(query, state, cancellationToken); + } /// /// Populates the token using the specified descriptor. @@ -828,9 +977,19 @@ public class OpenIddictTokenManager : IOpenIddictTokenManager where TTok /// /// A that can be used to monitor the asynchronous operation. /// - public virtual async ValueTask PopulateAsync(TToken token!!, - OpenIddictTokenDescriptor descriptor!!, CancellationToken cancellationToken = default) + public virtual async ValueTask PopulateAsync(TToken token, + OpenIddictTokenDescriptor descriptor, CancellationToken cancellationToken = default) { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + + if (descriptor is null) + { + throw new ArgumentNullException(nameof(descriptor)); + } + await Store.SetApplicationIdAsync(token, descriptor.ApplicationId, cancellationToken); await Store.SetAuthorizationIdAsync(token, descriptor.AuthorizationId, cancellationToken); await Store.SetCreationDateAsync(token, descriptor.CreationDate, cancellationToken); @@ -854,9 +1013,19 @@ public class OpenIddictTokenManager : IOpenIddictTokenManager where TTok /// A that can be used to monitor the asynchronous operation. /// public virtual async ValueTask PopulateAsync( - OpenIddictTokenDescriptor descriptor!!, - TToken token!!, CancellationToken cancellationToken = default) + OpenIddictTokenDescriptor descriptor, + TToken token, CancellationToken cancellationToken = default) { + if (descriptor is null) + { + throw new ArgumentNullException(nameof(descriptor)); + } + + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + descriptor.ApplicationId = await Store.GetApplicationIdAsync(token, cancellationToken); descriptor.AuthorizationId = await Store.GetAuthorizationIdAsync(token, cancellationToken); descriptor.CreationDate = await Store.GetCreationDateAsync(token, cancellationToken); @@ -886,15 +1055,19 @@ public class OpenIddictTokenManager : IOpenIddictTokenManager where TTok /// public virtual ValueTask PruneAsync(DateTimeOffset threshold, CancellationToken cancellationToken = default) => Store.PruneAsync(threshold, cancellationToken); - /// /// Tries to redeem a token. /// /// The token to redeem. /// The that can be used to abort the operation. /// if the token was successfully redemeed, otherwise. - public virtual async ValueTask TryRedeemAsync(TToken token!!, CancellationToken cancellationToken = default) + public virtual async ValueTask TryRedeemAsync(TToken token, CancellationToken cancellationToken = default) { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + // If the token doesn't have a redemption date attached, this likely means it's // the first time the token is redeemed. In this case, attach the current date. if (await Store.GetRedemptionDateAsync(token, cancellationToken) is null) @@ -934,8 +1107,13 @@ public class OpenIddictTokenManager : IOpenIddictTokenManager where TTok /// The token to reject. /// The that can be used to abort the operation. /// if the token was successfully redemeed, otherwise. - public virtual async ValueTask TryRejectAsync(TToken token!!, CancellationToken cancellationToken = default) + public virtual async ValueTask TryRejectAsync(TToken token, CancellationToken cancellationToken = default) { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + await Store.SetStatusAsync(token, Statuses.Rejected, cancellationToken); try @@ -968,8 +1146,13 @@ public class OpenIddictTokenManager : IOpenIddictTokenManager where TTok /// The token to revoke. /// The that can be used to abort the operation. /// if the token was successfully revoked, otherwise. - public virtual async ValueTask TryRevokeAsync(TToken token!!, CancellationToken cancellationToken = default) + public virtual async ValueTask TryRevokeAsync(TToken token, CancellationToken cancellationToken = default) { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + await Store.SetStatusAsync(token, Statuses.Revoked, cancellationToken); try @@ -1004,8 +1187,13 @@ public class OpenIddictTokenManager : IOpenIddictTokenManager where TTok /// /// A that can be used to monitor the asynchronous operation. /// - public virtual async ValueTask UpdateAsync(TToken token!!, CancellationToken cancellationToken = default) + public virtual async ValueTask UpdateAsync(TToken token, CancellationToken cancellationToken = default) { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + var results = await GetValidationResultsAsync(token, cancellationToken); if (results.Any(result => result != ValidationResult.Success)) { @@ -1052,9 +1240,19 @@ public class OpenIddictTokenManager : IOpenIddictTokenManager where TTok /// /// A that can be used to monitor the asynchronous operation. /// - public virtual async ValueTask UpdateAsync(TToken token!!, - OpenIddictTokenDescriptor descriptor!!, CancellationToken cancellationToken = default) + public virtual async ValueTask UpdateAsync(TToken token, + OpenIddictTokenDescriptor descriptor, CancellationToken cancellationToken = default) { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + + if (descriptor is null) + { + throw new ArgumentNullException(nameof(descriptor)); + } + // Store the original reference identifier for later comparison. var comparand = await Store.GetReferenceIdAsync(token, cancellationToken); await PopulateAsync(token, descriptor, cancellationToken); @@ -1077,8 +1275,13 @@ public class OpenIddictTokenManager : IOpenIddictTokenManager where TTok /// The that can be used to abort the operation. /// The validation error encountered when validating the token. public virtual async IAsyncEnumerable ValidateAsync( - TToken token!!, [EnumeratorCancellation] CancellationToken cancellationToken = default) + TToken token, [EnumeratorCancellation] CancellationToken cancellationToken = default) { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + // If a reference identifier was associated with the token, // ensure it's not already used for a different token. var identifier = await Store.GetReferenceIdAsync(token, cancellationToken); diff --git a/src/OpenIddict.Core/OpenIddictCoreBuilder.cs b/src/OpenIddict.Core/OpenIddictCoreBuilder.cs index b370d34e..1afd03ca 100644 --- a/src/OpenIddict.Core/OpenIddictCoreBuilder.cs +++ b/src/OpenIddict.Core/OpenIddictCoreBuilder.cs @@ -20,8 +20,8 @@ public class OpenIddictCoreBuilder /// Initializes a new instance of . /// /// The services collection. - public OpenIddictCoreBuilder(IServiceCollection services!!) - => Services = services; + public OpenIddictCoreBuilder(IServiceCollection services) + => Services = services ?? throw new ArgumentNullException(nameof(services)); /// /// Gets the services collection. @@ -35,8 +35,13 @@ public class OpenIddictCoreBuilder /// The delegate used to configure the OpenIddict options. /// This extension can be safely called multiple times. /// The . - public OpenIddictCoreBuilder Configure(Action configuration!!) + public OpenIddictCoreBuilder Configure(Action configuration) { + if (configuration is null) + { + throw new ArgumentNullException(nameof(configuration)); + } + Services.Configure(configuration); return this; @@ -64,8 +69,13 @@ public class OpenIddictCoreBuilder /// The type of the custom store. /// The lifetime of the registered service. /// The . - public OpenIddictCoreBuilder AddApplicationStore(Type type!!, ServiceLifetime lifetime = ServiceLifetime.Scoped) + public OpenIddictCoreBuilder AddApplicationStore(Type type, ServiceLifetime lifetime = ServiceLifetime.Scoped) { + if (type is null) + { + throw new ArgumentNullException(nameof(type)); + } + var root = OpenIddictHelpers.FindGenericBaseType(type, typeof(IOpenIddictApplicationStore<>)) ?? throw new ArgumentException(SR.GetResourceString(SR.ID0232), nameof(type)); @@ -112,8 +122,13 @@ public class OpenIddictCoreBuilder /// The type of the custom store. /// The lifetime of the registered service. /// The . - public OpenIddictCoreBuilder AddAuthorizationStore(Type type!!, ServiceLifetime lifetime = ServiceLifetime.Scoped) + public OpenIddictCoreBuilder AddAuthorizationStore(Type type, ServiceLifetime lifetime = ServiceLifetime.Scoped) { + if (type is null) + { + throw new ArgumentNullException(nameof(type)); + } + var root = OpenIddictHelpers.FindGenericBaseType(type, typeof(IOpenIddictAuthorizationStore<>)) ?? throw new ArgumentException(SR.GetResourceString(SR.ID0232), nameof(type)); @@ -160,8 +175,13 @@ public class OpenIddictCoreBuilder /// The type of the custom store. /// The lifetime of the registered service. /// The . - public OpenIddictCoreBuilder AddScopeStore(Type type!!, ServiceLifetime lifetime = ServiceLifetime.Scoped) + public OpenIddictCoreBuilder AddScopeStore(Type type, ServiceLifetime lifetime = ServiceLifetime.Scoped) { + if (type is null) + { + throw new ArgumentNullException(nameof(type)); + } + var root = OpenIddictHelpers.FindGenericBaseType(type, typeof(IOpenIddictScopeStore<>)) ?? throw new ArgumentException(SR.GetResourceString(SR.ID0232), nameof(type)); @@ -208,8 +228,13 @@ public class OpenIddictCoreBuilder /// The type of the custom store. /// The lifetime of the registered service. /// The . - public OpenIddictCoreBuilder AddTokenStore(Type type!!, ServiceLifetime lifetime = ServiceLifetime.Scoped) + public OpenIddictCoreBuilder AddTokenStore(Type type, ServiceLifetime lifetime = ServiceLifetime.Scoped) { + if (type is null) + { + throw new ArgumentNullException(nameof(type)); + } + var root = OpenIddictHelpers.FindGenericBaseType(type, typeof(IOpenIddictTokenStore<>)) ?? throw new ArgumentException(SR.GetResourceString(SR.ID0232), nameof(type)); @@ -254,8 +279,13 @@ public class OpenIddictCoreBuilder /// /// The type of the custom manager. /// The . - public OpenIddictCoreBuilder ReplaceApplicationManager(Type type!!) + public OpenIddictCoreBuilder ReplaceApplicationManager(Type type) { + if (type is null) + { + throw new ArgumentNullException(nameof(type)); + } + var root = OpenIddictHelpers.FindGenericBaseType(type, typeof(OpenIddictApplicationManager<>)) ?? throw new ArgumentException(SR.GetResourceString(SR.ID0232), nameof(type)); @@ -303,8 +333,13 @@ public class OpenIddictCoreBuilder /// The lifetime of the registered service. /// The . public OpenIddictCoreBuilder ReplaceApplicationStoreResolver( - Type type!!, ServiceLifetime lifetime = ServiceLifetime.Scoped) + Type type, ServiceLifetime lifetime = ServiceLifetime.Scoped) { + if (type is null) + { + throw new ArgumentNullException(nameof(type)); + } + if (!typeof(IOpenIddictApplicationStoreResolver).IsAssignableFrom(type)) { throw new ArgumentException(SR.GetResourceString(SR.ID0232), nameof(type)); @@ -335,8 +370,13 @@ public class OpenIddictCoreBuilder /// /// The type of the custom manager. /// The . - public OpenIddictCoreBuilder ReplaceAuthorizationManager(Type type!!) + public OpenIddictCoreBuilder ReplaceAuthorizationManager(Type type) { + if (type is null) + { + throw new ArgumentNullException(nameof(type)); + } + var root = OpenIddictHelpers.FindGenericBaseType(type, typeof(OpenIddictAuthorizationManager<>)) ?? throw new ArgumentException(SR.GetResourceString(SR.ID0232), nameof(type)); @@ -384,8 +424,13 @@ public class OpenIddictCoreBuilder /// The lifetime of the registered service. /// The . public OpenIddictCoreBuilder ReplaceAuthorizationStoreResolver( - Type type!!, ServiceLifetime lifetime = ServiceLifetime.Scoped) + Type type, ServiceLifetime lifetime = ServiceLifetime.Scoped) { + if (type is null) + { + throw new ArgumentNullException(nameof(type)); + } + if (!typeof(IOpenIddictAuthorizationStoreResolver).IsAssignableFrom(type)) { throw new ArgumentException(SR.GetResourceString(SR.ID0232), nameof(type)); @@ -416,8 +461,13 @@ public class OpenIddictCoreBuilder /// /// The type of the custom manager. /// The . - public OpenIddictCoreBuilder ReplaceScopeManager(Type type!!) + public OpenIddictCoreBuilder ReplaceScopeManager(Type type) { + if (type is null) + { + throw new ArgumentNullException(nameof(type)); + } + var root = OpenIddictHelpers.FindGenericBaseType(type, typeof(OpenIddictScopeManager<>)) ?? throw new ArgumentException(SR.GetResourceString(SR.ID0232), nameof(type)); @@ -465,8 +515,13 @@ public class OpenIddictCoreBuilder /// The lifetime of the registered service. /// The . public OpenIddictCoreBuilder ReplaceScopeStoreResolver( - Type type!!, ServiceLifetime lifetime = ServiceLifetime.Scoped) + Type type, ServiceLifetime lifetime = ServiceLifetime.Scoped) { + if (type is null) + { + throw new ArgumentNullException(nameof(type)); + } + if (!typeof(IOpenIddictScopeStoreResolver).IsAssignableFrom(type)) { throw new ArgumentException(SR.GetResourceString(SR.ID0232), nameof(type)); @@ -497,8 +552,13 @@ public class OpenIddictCoreBuilder /// /// The type of the custom manager. /// The . - public OpenIddictCoreBuilder ReplaceTokenManager(Type type!!) + public OpenIddictCoreBuilder ReplaceTokenManager(Type type) { + if (type is null) + { + throw new ArgumentNullException(nameof(type)); + } + var root = OpenIddictHelpers.FindGenericBaseType(type, typeof(OpenIddictTokenManager<>)) ?? throw new ArgumentException(SR.GetResourceString(SR.ID0232), nameof(type)); @@ -546,8 +606,13 @@ public class OpenIddictCoreBuilder /// The lifetime of the registered service. /// The . public OpenIddictCoreBuilder ReplaceTokenStoreResolver( - Type type!!, ServiceLifetime lifetime = ServiceLifetime.Scoped) + Type type, ServiceLifetime lifetime = ServiceLifetime.Scoped) { + if (type is null) + { + throw new ArgumentNullException(nameof(type)); + } + if (!typeof(IOpenIddictTokenStoreResolver).IsAssignableFrom(type)) { throw new ArgumentException(SR.GetResourceString(SR.ID0232), nameof(type)); @@ -590,8 +655,13 @@ public class OpenIddictCoreBuilder /// /// The application entity type. /// The . - public OpenIddictCoreBuilder SetDefaultApplicationEntity(Type type!!) + public OpenIddictCoreBuilder SetDefaultApplicationEntity(Type type) { + if (type is null) + { + throw new ArgumentNullException(nameof(type)); + } + if (type.IsValueType) { throw new ArgumentException(SR.GetResourceString(SR.ID0232), nameof(type)); @@ -612,8 +682,13 @@ public class OpenIddictCoreBuilder /// /// The authorization entity type. /// The . - public OpenIddictCoreBuilder SetDefaultAuthorizationEntity(Type type!!) + public OpenIddictCoreBuilder SetDefaultAuthorizationEntity(Type type) { + if (type is null) + { + throw new ArgumentNullException(nameof(type)); + } + if (type.IsValueType) { throw new ArgumentException(SR.GetResourceString(SR.ID0232), nameof(type)); @@ -634,8 +709,13 @@ public class OpenIddictCoreBuilder /// /// The scope entity type. /// The . - public OpenIddictCoreBuilder SetDefaultScopeEntity(Type type!!) + public OpenIddictCoreBuilder SetDefaultScopeEntity(Type type) { + if (type is null) + { + throw new ArgumentNullException(nameof(type)); + } + if (type.IsValueType) { throw new ArgumentException(SR.GetResourceString(SR.ID0232), nameof(type)); @@ -656,8 +736,13 @@ public class OpenIddictCoreBuilder /// /// The token entity type. /// The . - public OpenIddictCoreBuilder SetDefaultTokenEntity(Type type!!) + public OpenIddictCoreBuilder SetDefaultTokenEntity(Type type) { + if (type is null) + { + throw new ArgumentNullException(nameof(type)); + } + if (type.IsValueType) { throw new ArgumentException(SR.GetResourceString(SR.ID0232), nameof(type)); diff --git a/src/OpenIddict.Core/OpenIddictCoreExtensions.cs b/src/OpenIddict.Core/OpenIddictCoreExtensions.cs index 24a32f98..9f68a839 100644 --- a/src/OpenIddict.Core/OpenIddictCoreExtensions.cs +++ b/src/OpenIddict.Core/OpenIddictCoreExtensions.cs @@ -22,8 +22,13 @@ public static class OpenIddictCoreExtensions /// The services builder used by OpenIddict to register new services. /// This extension can be safely called multiple times. /// The . - public static OpenIddictCoreBuilder AddCore(this OpenIddictBuilder builder!!) + public static OpenIddictCoreBuilder AddCore(this OpenIddictBuilder builder) { + if (builder is null) + { + throw new ArgumentNullException(nameof(builder)); + } + builder.Services.AddLogging(); builder.Services.AddMemoryCache(); builder.Services.AddOptions(); @@ -93,8 +98,18 @@ public static class OpenIddictCoreExtensions /// The configuration delegate used to configure the core services. /// This extension can be safely called multiple times. /// The . - public static OpenIddictBuilder AddCore(this OpenIddictBuilder builder!!, Action configuration!!) + public static OpenIddictBuilder AddCore(this OpenIddictBuilder builder, Action configuration) { + if (builder is null) + { + throw new ArgumentNullException(nameof(builder)); + } + + if (configuration is null) + { + throw new ArgumentNullException(nameof(configuration)); + } + configuration(builder.AddCore()); return builder; diff --git a/src/OpenIddict.Core/Resolvers/OpenIddictApplicationStoreResolver.cs b/src/OpenIddict.Core/Resolvers/OpenIddictApplicationStoreResolver.cs index 290d57cd..cbd36b4b 100644 --- a/src/OpenIddict.Core/Resolvers/OpenIddictApplicationStoreResolver.cs +++ b/src/OpenIddict.Core/Resolvers/OpenIddictApplicationStoreResolver.cs @@ -9,8 +9,8 @@ public class OpenIddictApplicationStoreResolver : IOpenIddictApplicationStoreRes { private readonly IServiceProvider _provider; - public OpenIddictApplicationStoreResolver(IServiceProvider provider!!) - => _provider = provider; + public OpenIddictApplicationStoreResolver(IServiceProvider provider) + => _provider = provider ?? throw new ArgumentNullException(nameof(provider)); /// /// Returns an application store compatible with the specified application type or throws an diff --git a/src/OpenIddict.Core/Resolvers/OpenIddictAuthorizationStoreResolver.cs b/src/OpenIddict.Core/Resolvers/OpenIddictAuthorizationStoreResolver.cs index e8c97b55..5c91a048 100644 --- a/src/OpenIddict.Core/Resolvers/OpenIddictAuthorizationStoreResolver.cs +++ b/src/OpenIddict.Core/Resolvers/OpenIddictAuthorizationStoreResolver.cs @@ -9,8 +9,8 @@ public class OpenIddictAuthorizationStoreResolver : IOpenIddictAuthorizationStor { private readonly IServiceProvider _provider; - public OpenIddictAuthorizationStoreResolver(IServiceProvider provider!!) - => _provider = provider; + public OpenIddictAuthorizationStoreResolver(IServiceProvider provider) + => _provider = provider ?? throw new ArgumentNullException(nameof(provider)); /// /// Returns an authorization store compatible with the specified authorization type or throws an diff --git a/src/OpenIddict.Core/Resolvers/OpenIddictScopeStoreResolver.cs b/src/OpenIddict.Core/Resolvers/OpenIddictScopeStoreResolver.cs index 9bd7bf23..297622ca 100644 --- a/src/OpenIddict.Core/Resolvers/OpenIddictScopeStoreResolver.cs +++ b/src/OpenIddict.Core/Resolvers/OpenIddictScopeStoreResolver.cs @@ -9,8 +9,8 @@ public class OpenIddictScopeStoreResolver : IOpenIddictScopeStoreResolver { private readonly IServiceProvider _provider; - public OpenIddictScopeStoreResolver(IServiceProvider provider!!) - => _provider = provider; + public OpenIddictScopeStoreResolver(IServiceProvider provider) + => _provider = provider ?? throw new ArgumentNullException(nameof(provider)); /// /// Returns a scope store compatible with the specified scope type or throws an diff --git a/src/OpenIddict.Core/Resolvers/OpenIddictTokenStoreResolver.cs b/src/OpenIddict.Core/Resolvers/OpenIddictTokenStoreResolver.cs index ab2e0e61..7292d6d5 100644 --- a/src/OpenIddict.Core/Resolvers/OpenIddictTokenStoreResolver.cs +++ b/src/OpenIddict.Core/Resolvers/OpenIddictTokenStoreResolver.cs @@ -9,8 +9,8 @@ public class OpenIddictTokenStoreResolver : IOpenIddictTokenStoreResolver { private readonly IServiceProvider _provider; - public OpenIddictTokenStoreResolver(IServiceProvider provider!!) - => _provider = provider; + public OpenIddictTokenStoreResolver(IServiceProvider provider) + => _provider = provider ?? throw new ArgumentNullException(nameof(provider)); /// /// Returns a token store compatible with the specified token type or throws an diff --git a/src/OpenIddict.EntityFramework/OpenIddictEntityFrameworkBuilder.cs b/src/OpenIddict.EntityFramework/OpenIddictEntityFrameworkBuilder.cs index 25920105..ea02d3a7 100644 --- a/src/OpenIddict.EntityFramework/OpenIddictEntityFrameworkBuilder.cs +++ b/src/OpenIddict.EntityFramework/OpenIddictEntityFrameworkBuilder.cs @@ -21,8 +21,8 @@ public class OpenIddictEntityFrameworkBuilder /// Initializes a new instance of . /// /// The services collection. - public OpenIddictEntityFrameworkBuilder(IServiceCollection services!!) - => Services = services; + public OpenIddictEntityFrameworkBuilder(IServiceCollection services) + => Services = services ?? throw new ArgumentNullException(nameof(services)); /// /// Gets the services collection. @@ -36,8 +36,13 @@ public class OpenIddictEntityFrameworkBuilder /// The delegate used to configure the OpenIddict options. /// This extension can be safely called multiple times. /// The . - public OpenIddictEntityFrameworkBuilder Configure(Action configuration!!) + public OpenIddictEntityFrameworkBuilder Configure(Action configuration) { + if (configuration is null) + { + throw new ArgumentNullException(nameof(configuration)); + } + Services.Configure(configuration); return this; @@ -89,8 +94,13 @@ public class OpenIddictEntityFrameworkBuilder /// /// The type of the used by OpenIddict. /// The . - public OpenIddictEntityFrameworkBuilder UseDbContext(Type type!!) + public OpenIddictEntityFrameworkBuilder UseDbContext(Type type) { + if (type is null) + { + throw new ArgumentNullException(nameof(type)); + } + if (!typeof(DbContext).IsAssignableFrom(type)) { throw new ArgumentException(SR.GetResourceString(SR.ID0232), nameof(type)); diff --git a/src/OpenIddict.EntityFramework/OpenIddictEntityFrameworkExtensions.cs b/src/OpenIddict.EntityFramework/OpenIddictEntityFrameworkExtensions.cs index c525f94f..b77ca34a 100644 --- a/src/OpenIddict.EntityFramework/OpenIddictEntityFrameworkExtensions.cs +++ b/src/OpenIddict.EntityFramework/OpenIddictEntityFrameworkExtensions.cs @@ -22,8 +22,13 @@ public static class OpenIddictEntityFrameworkExtensions /// The services builder used by OpenIddict to register new services. /// This extension can be safely called multiple times. /// The . - public static OpenIddictEntityFrameworkBuilder UseEntityFramework(this OpenIddictCoreBuilder builder!!) + public static OpenIddictEntityFrameworkBuilder UseEntityFramework(this OpenIddictCoreBuilder builder) { + if (builder is null) + { + throw new ArgumentNullException(nameof(builder)); + } + // Since Entity Framework 6.x may be used with databases performing case-insensitive // or culture-sensitive comparisons, ensure the additional filtering logic is enforced // in case case-sensitive stores were registered before this extension was called. @@ -61,8 +66,18 @@ public static class OpenIddictEntityFrameworkExtensions /// This extension can be safely called multiple times. /// The . public static OpenIddictCoreBuilder UseEntityFramework( - this OpenIddictCoreBuilder builder!!, Action configuration!!) + this OpenIddictCoreBuilder builder, Action configuration) { + if (builder is null) + { + throw new ArgumentNullException(nameof(builder)); + } + + if (configuration is null) + { + throw new ArgumentNullException(nameof(configuration)); + } + configuration(builder.UseEntityFramework()); return builder; diff --git a/src/OpenIddict.EntityFramework/OpenIddictEntityFrameworkHelpers.cs b/src/OpenIddict.EntityFramework/OpenIddictEntityFrameworkHelpers.cs index a0b669e5..92ea38ca 100644 --- a/src/OpenIddict.EntityFramework/OpenIddictEntityFrameworkHelpers.cs +++ b/src/OpenIddict.EntityFramework/OpenIddictEntityFrameworkHelpers.cs @@ -38,13 +38,18 @@ public static class OpenIddictEntityFrameworkHelpers /// /// The builder used to configure the Entity Framework context. /// The Entity Framework context builder. - public static DbModelBuilder UseOpenIddict(this DbModelBuilder builder!!) + public static DbModelBuilder UseOpenIddict(this DbModelBuilder builder) where TApplication : OpenIddictEntityFrameworkApplication where TAuthorization : OpenIddictEntityFrameworkAuthorization where TScope : OpenIddictEntityFrameworkScope where TToken : OpenIddictEntityFrameworkToken where TKey : notnull, IEquatable { + if (builder is null) + { + throw new ArgumentNullException(nameof(builder)); + } + builder.Configurations .Add(new OpenIddictEntityFrameworkApplicationConfiguration()) .Add(new OpenIddictEntityFrameworkAuthorizationConfiguration()) @@ -61,8 +66,13 @@ public static class OpenIddictEntityFrameworkHelpers /// The query source. /// The that can be used to abort the operation. /// The non-streamed async enumeration containing the results. - internal static IAsyncEnumerable AsAsyncEnumerable(this IQueryable source!!, CancellationToken cancellationToken) + internal static IAsyncEnumerable AsAsyncEnumerable(this IQueryable source, CancellationToken cancellationToken) { + if (source is null) + { + throw new ArgumentNullException(nameof(source)); + } + return ExecuteAsync(source, cancellationToken); static async IAsyncEnumerable ExecuteAsync(IQueryable source, [EnumeratorCancellation] CancellationToken cancellationToken) diff --git a/src/OpenIddict.EntityFramework/Resolvers/OpenIddictEntityFrameworkApplicationStoreResolver.cs b/src/OpenIddict.EntityFramework/Resolvers/OpenIddictEntityFrameworkApplicationStoreResolver.cs index 3f5c6eb3..380accac 100644 --- a/src/OpenIddict.EntityFramework/Resolvers/OpenIddictEntityFrameworkApplicationStoreResolver.cs +++ b/src/OpenIddict.EntityFramework/Resolvers/OpenIddictEntityFrameworkApplicationStoreResolver.cs @@ -22,13 +22,13 @@ public class OpenIddictEntityFrameworkApplicationStoreResolver : IOpenIddictAppl private readonly IServiceProvider _provider; public OpenIddictEntityFrameworkApplicationStoreResolver( - TypeResolutionCache cache!!, - IOptionsMonitor options!!, - IServiceProvider provider!!) + TypeResolutionCache cache, + IOptionsMonitor options, + IServiceProvider provider) { - _cache = cache; - _options = options; - _provider = provider; + _cache = cache ?? throw new ArgumentNullException(nameof(cache)); + _options = options ?? throw new ArgumentNullException(nameof(options)); + _provider = provider ?? throw new ArgumentNullException(nameof(provider)); } /// diff --git a/src/OpenIddict.EntityFramework/Resolvers/OpenIddictEntityFrameworkAuthorizationStoreResolver.cs b/src/OpenIddict.EntityFramework/Resolvers/OpenIddictEntityFrameworkAuthorizationStoreResolver.cs index 7ed3f682..e5fef634 100644 --- a/src/OpenIddict.EntityFramework/Resolvers/OpenIddictEntityFrameworkAuthorizationStoreResolver.cs +++ b/src/OpenIddict.EntityFramework/Resolvers/OpenIddictEntityFrameworkAuthorizationStoreResolver.cs @@ -22,13 +22,13 @@ public class OpenIddictEntityFrameworkAuthorizationStoreResolver : IOpenIddictAu private readonly IServiceProvider _provider; public OpenIddictEntityFrameworkAuthorizationStoreResolver( - TypeResolutionCache cache!!, - IOptionsMonitor options!!, - IServiceProvider provider!!) + TypeResolutionCache cache, + IOptionsMonitor options, + IServiceProvider provider) { - _cache = cache; - _options = options; - _provider = provider; + _cache = cache ?? throw new ArgumentNullException(nameof(cache)); + _options = options ?? throw new ArgumentNullException(nameof(options)); + _provider = provider ?? throw new ArgumentNullException(nameof(provider)); } /// diff --git a/src/OpenIddict.EntityFramework/Resolvers/OpenIddictEntityFrameworkScopeStoreResolver.cs b/src/OpenIddict.EntityFramework/Resolvers/OpenIddictEntityFrameworkScopeStoreResolver.cs index 1515084a..b71ab3bd 100644 --- a/src/OpenIddict.EntityFramework/Resolvers/OpenIddictEntityFrameworkScopeStoreResolver.cs +++ b/src/OpenIddict.EntityFramework/Resolvers/OpenIddictEntityFrameworkScopeStoreResolver.cs @@ -22,13 +22,13 @@ public class OpenIddictEntityFrameworkScopeStoreResolver : IOpenIddictScopeStore private readonly IServiceProvider _provider; public OpenIddictEntityFrameworkScopeStoreResolver( - TypeResolutionCache cache!!, - IOptionsMonitor options!!, - IServiceProvider provider!!) + TypeResolutionCache cache, + IOptionsMonitor options, + IServiceProvider provider) { - _cache = cache; - _options = options; - _provider = provider; + _cache = cache ?? throw new ArgumentNullException(nameof(cache)); + _options = options ?? throw new ArgumentNullException(nameof(options)); + _provider = provider ?? throw new ArgumentNullException(nameof(provider)); } /// diff --git a/src/OpenIddict.EntityFramework/Resolvers/OpenIddictEntityFrameworkTokenStoreResolver.cs b/src/OpenIddict.EntityFramework/Resolvers/OpenIddictEntityFrameworkTokenStoreResolver.cs index 04f9711f..1badfcd4 100644 --- a/src/OpenIddict.EntityFramework/Resolvers/OpenIddictEntityFrameworkTokenStoreResolver.cs +++ b/src/OpenIddict.EntityFramework/Resolvers/OpenIddictEntityFrameworkTokenStoreResolver.cs @@ -22,13 +22,13 @@ public class OpenIddictEntityFrameworkTokenStoreResolver : IOpenIddictTokenStore private readonly IServiceProvider _provider; public OpenIddictEntityFrameworkTokenStoreResolver( - TypeResolutionCache cache!!, - IOptionsMonitor options!!, - IServiceProvider provider!!) + TypeResolutionCache cache, + IOptionsMonitor options, + IServiceProvider provider) { - _cache = cache; - _options = options; - _provider = provider; + _cache = cache ?? throw new ArgumentNullException(nameof(cache)); + _options = options ?? throw new ArgumentNullException(nameof(options)); + _provider = provider ?? throw new ArgumentNullException(nameof(provider)); } /// diff --git a/src/OpenIddict.EntityFramework/Stores/OpenIddictEntityFrameworkApplicationStore.cs b/src/OpenIddict.EntityFramework/Stores/OpenIddictEntityFrameworkApplicationStore.cs index ad23b0f4..43225633 100644 --- a/src/OpenIddict.EntityFramework/Stores/OpenIddictEntityFrameworkApplicationStore.cs +++ b/src/OpenIddict.EntityFramework/Stores/OpenIddictEntityFrameworkApplicationStore.cs @@ -32,7 +32,7 @@ public class OpenIddictEntityFrameworkApplicationStore : public OpenIddictEntityFrameworkApplicationStore( IMemoryCache cache, TContext context, - IOptionsMonitor options!!) + IOptionsMonitor options) : base(cache, context, options) { } @@ -54,13 +54,13 @@ public class OpenIddictEntityFrameworkApplicationStore { public OpenIddictEntityFrameworkApplicationStore( - IMemoryCache cache!!, - TContext context!!, - IOptionsMonitor options!!) + IMemoryCache cache, + TContext context, + IOptionsMonitor options) { - Cache = cache; - Context = context; - Options = options; + Cache = cache ?? throw new ArgumentNullException(nameof(cache)); + Context = context ?? throw new ArgumentNullException(nameof(context)); + Options = options ?? throw new ArgumentNullException(nameof(options)); } /// @@ -98,20 +98,37 @@ public class OpenIddictEntityFrameworkApplicationStore await Applications.LongCountAsync(cancellationToken); /// - public virtual async ValueTask CountAsync(Func, IQueryable> query!!, CancellationToken cancellationToken) - => await query(Applications).LongCountAsync(cancellationToken); + public virtual async ValueTask CountAsync(Func, IQueryable> query, CancellationToken cancellationToken) + { + if (query is null) + { + throw new ArgumentNullException(nameof(query)); + } + + return await query(Applications).LongCountAsync(cancellationToken); + } /// - public virtual async ValueTask CreateAsync(TApplication application!!, CancellationToken cancellationToken) + public virtual async ValueTask CreateAsync(TApplication application, CancellationToken cancellationToken) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + Applications.Add(application); await Context.SaveChangesAsync(cancellationToken); } /// - public virtual async ValueTask DeleteAsync(TApplication application!!, CancellationToken cancellationToken) + public virtual async ValueTask DeleteAsync(TApplication application, CancellationToken cancellationToken) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + DbContextTransaction? CreateTransaction() { try @@ -286,33 +303,80 @@ public class OpenIddictEntityFrameworkApplicationStore public virtual async ValueTask GetAsync( - Func, TState, IQueryable> query!!, + Func, TState, IQueryable> query, TState state, CancellationToken cancellationToken) - => await query(Applications, state).FirstOrDefaultAsync(cancellationToken); + { + if (query is null) + { + throw new ArgumentNullException(nameof(query)); + } + + return await query(Applications, state).FirstOrDefaultAsync(cancellationToken); + } /// - public virtual ValueTask GetClientIdAsync(TApplication application!!, CancellationToken cancellationToken) - => new(application.ClientId); + public virtual ValueTask GetClientIdAsync(TApplication application, CancellationToken cancellationToken) + { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + + return new(application.ClientId); + } /// - public virtual ValueTask GetClientSecretAsync(TApplication application!!, CancellationToken cancellationToken) - => new(application.ClientSecret); + public virtual ValueTask GetClientSecretAsync(TApplication application, CancellationToken cancellationToken) + { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + + return new(application.ClientSecret); + } /// - public virtual ValueTask GetClientTypeAsync(TApplication application!!, CancellationToken cancellationToken) - => new(application.Type); + public virtual ValueTask GetClientTypeAsync(TApplication application, CancellationToken cancellationToken) + { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + + return new(application.Type); + } /// - public virtual ValueTask GetConsentTypeAsync(TApplication application!!, CancellationToken cancellationToken) - => new(application.ConsentType); + public virtual ValueTask GetConsentTypeAsync(TApplication application, CancellationToken cancellationToken) + { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + + return new(application.ConsentType); + } /// - public virtual ValueTask GetDisplayNameAsync(TApplication application!!, CancellationToken cancellationToken) - => new(application.DisplayName); + public virtual ValueTask GetDisplayNameAsync(TApplication application, CancellationToken cancellationToken) + { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + + return new(application.DisplayName); + } /// - public virtual ValueTask> GetDisplayNamesAsync(TApplication application!!, CancellationToken cancellationToken) + public virtual ValueTask> GetDisplayNamesAsync(TApplication application, CancellationToken cancellationToken) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + if (string.IsNullOrEmpty(application.DisplayNames)) { return new(ImmutableDictionary.Create()); @@ -347,12 +411,24 @@ public class OpenIddictEntityFrameworkApplicationStore - public virtual ValueTask GetIdAsync(TApplication application!!, CancellationToken cancellationToken) - => new(ConvertIdentifierToString(application.Id)); + public virtual ValueTask GetIdAsync(TApplication application, CancellationToken cancellationToken) + { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + + return new(ConvertIdentifierToString(application.Id)); + } /// - public virtual ValueTask> GetPermissionsAsync(TApplication application!!, CancellationToken cancellationToken) + public virtual ValueTask> GetPermissionsAsync(TApplication application, CancellationToken cancellationToken) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + if (string.IsNullOrEmpty(application.Permissions)) { return new(ImmutableArray.Create()); @@ -387,8 +463,13 @@ public class OpenIddictEntityFrameworkApplicationStore - public virtual ValueTask> GetPostLogoutRedirectUrisAsync(TApplication application!!, CancellationToken cancellationToken) + public virtual ValueTask> GetPostLogoutRedirectUrisAsync(TApplication application, CancellationToken cancellationToken) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + if (string.IsNullOrEmpty(application.PostLogoutRedirectUris)) { return new(ImmutableArray.Create()); @@ -423,8 +504,13 @@ public class OpenIddictEntityFrameworkApplicationStore - public virtual ValueTask> GetPropertiesAsync(TApplication application!!, CancellationToken cancellationToken) + public virtual ValueTask> GetPropertiesAsync(TApplication application, CancellationToken cancellationToken) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + if (string.IsNullOrEmpty(application.Properties)) { return new(ImmutableDictionary.Create()); @@ -453,8 +539,13 @@ public class OpenIddictEntityFrameworkApplicationStore - public virtual ValueTask> GetRedirectUrisAsync(TApplication application!!, CancellationToken cancellationToken) + public virtual ValueTask> GetRedirectUrisAsync(TApplication application, CancellationToken cancellationToken) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + if (string.IsNullOrEmpty(application.RedirectUris)) { return new(ImmutableArray.Create()); @@ -489,8 +580,13 @@ public class OpenIddictEntityFrameworkApplicationStore - public virtual ValueTask> GetRequirementsAsync(TApplication application!!, CancellationToken cancellationToken) + public virtual ValueTask> GetRequirementsAsync(TApplication application, CancellationToken cancellationToken) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + if (string.IsNullOrEmpty(application.Requirements)) { return new(ImmutableArray.Create()); @@ -560,56 +656,91 @@ public class OpenIddictEntityFrameworkApplicationStore public virtual IAsyncEnumerable ListAsync( - Func, TState, IQueryable> query!!, + Func, TState, IQueryable> query, TState state, CancellationToken cancellationToken) { + if (query is null) + { + throw new ArgumentNullException(nameof(query)); + } + return query(Applications, state).AsAsyncEnumerable(cancellationToken); } /// - public virtual ValueTask SetClientIdAsync(TApplication application!!, string? identifier, CancellationToken cancellationToken) + public virtual ValueTask SetClientIdAsync(TApplication application, string? identifier, CancellationToken cancellationToken) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + application.ClientId = identifier; return default; } /// - public virtual ValueTask SetClientSecretAsync(TApplication application!!, string? secret, CancellationToken cancellationToken) + public virtual ValueTask SetClientSecretAsync(TApplication application, string? secret, CancellationToken cancellationToken) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + application.ClientSecret = secret; return default; } /// - public virtual ValueTask SetClientTypeAsync(TApplication application!!, string? type, CancellationToken cancellationToken) + public virtual ValueTask SetClientTypeAsync(TApplication application, string? type, CancellationToken cancellationToken) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + application.Type = type; return default; } /// - public virtual ValueTask SetConsentTypeAsync(TApplication application!!, string? type, CancellationToken cancellationToken) + public virtual ValueTask SetConsentTypeAsync(TApplication application, string? type, CancellationToken cancellationToken) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + application.ConsentType = type; return default; } /// - public virtual ValueTask SetDisplayNameAsync(TApplication application!!, string? name, CancellationToken cancellationToken) + public virtual ValueTask SetDisplayNameAsync(TApplication application, string? name, CancellationToken cancellationToken) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + application.DisplayName = name; return default; } /// - public virtual ValueTask SetDisplayNamesAsync(TApplication application!!, + public virtual ValueTask SetDisplayNamesAsync(TApplication application, ImmutableDictionary names, CancellationToken cancellationToken) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + if (names is not { Count: > 0 }) { application.DisplayNames = null; @@ -641,8 +772,13 @@ public class OpenIddictEntityFrameworkApplicationStore - public virtual ValueTask SetPermissionsAsync(TApplication application!!, ImmutableArray permissions, CancellationToken cancellationToken) + public virtual ValueTask SetPermissionsAsync(TApplication application, ImmutableArray permissions, CancellationToken cancellationToken) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + if (permissions.IsDefaultOrEmpty) { application.Permissions = null; @@ -673,9 +809,14 @@ public class OpenIddictEntityFrameworkApplicationStore - public virtual ValueTask SetPostLogoutRedirectUrisAsync(TApplication application!!, + public virtual ValueTask SetPostLogoutRedirectUrisAsync(TApplication application, ImmutableArray addresses, CancellationToken cancellationToken) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + if (addresses.IsDefaultOrEmpty) { application.PostLogoutRedirectUris = null; @@ -706,9 +847,14 @@ public class OpenIddictEntityFrameworkApplicationStore - public virtual ValueTask SetPropertiesAsync(TApplication application!!, + public virtual ValueTask SetPropertiesAsync(TApplication application, ImmutableDictionary properties, CancellationToken cancellationToken) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + if (properties is not { Count: > 0 }) { application.Properties = null; @@ -740,9 +886,14 @@ public class OpenIddictEntityFrameworkApplicationStore - public virtual ValueTask SetRedirectUrisAsync(TApplication application!!, + public virtual ValueTask SetRedirectUrisAsync(TApplication application, ImmutableArray addresses, CancellationToken cancellationToken) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + if (addresses.IsDefaultOrEmpty) { application.RedirectUris = null; @@ -773,8 +924,13 @@ public class OpenIddictEntityFrameworkApplicationStore - public virtual ValueTask SetRequirementsAsync(TApplication application!!, ImmutableArray requirements, CancellationToken cancellationToken) + public virtual ValueTask SetRequirementsAsync(TApplication application, ImmutableArray requirements, CancellationToken cancellationToken) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + if (requirements.IsDefaultOrEmpty) { application.Requirements = null; @@ -805,8 +961,13 @@ public class OpenIddictEntityFrameworkApplicationStore - public virtual async ValueTask UpdateAsync(TApplication application!!, CancellationToken cancellationToken) + public virtual async ValueTask UpdateAsync(TApplication application, CancellationToken cancellationToken) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + Applications.Attach(application); // Generate a new concurrency token and attach it diff --git a/src/OpenIddict.EntityFramework/Stores/OpenIddictEntityFrameworkAuthorizationStore.cs b/src/OpenIddict.EntityFramework/Stores/OpenIddictEntityFrameworkAuthorizationStore.cs index 406e2a40..bfc6469f 100644 --- a/src/OpenIddict.EntityFramework/Stores/OpenIddictEntityFrameworkAuthorizationStore.cs +++ b/src/OpenIddict.EntityFramework/Stores/OpenIddictEntityFrameworkAuthorizationStore.cs @@ -31,7 +31,7 @@ public class OpenIddictEntityFrameworkAuthorizationStore : public OpenIddictEntityFrameworkAuthorizationStore( IMemoryCache cache, TContext context, - IOptionsMonitor options!!) + IOptionsMonitor options) : base(cache, context, options) { } @@ -53,13 +53,13 @@ public class OpenIddictEntityFrameworkAuthorizationStore { public OpenIddictEntityFrameworkAuthorizationStore( - IMemoryCache cache!!, - TContext context!!, - IOptionsMonitor options!!) + IMemoryCache cache, + TContext context, + IOptionsMonitor options) { - Cache = cache; - Context = context; - Options = options; + Cache = cache ?? throw new ArgumentNullException(nameof(cache)); + Context = context ?? throw new ArgumentNullException(nameof(context)); + Options = options ?? throw new ArgumentNullException(nameof(options)); } /// @@ -97,20 +97,37 @@ public class OpenIddictEntityFrameworkAuthorizationStore await Authorizations.LongCountAsync(cancellationToken); /// - public virtual async ValueTask CountAsync(Func, IQueryable> query!!, CancellationToken cancellationToken) - => await query(Authorizations).LongCountAsync(cancellationToken); + public virtual async ValueTask CountAsync(Func, IQueryable> query, CancellationToken cancellationToken) + { + if (query is null) + { + throw new ArgumentNullException(nameof(query)); + } + + return await query(Authorizations).LongCountAsync(cancellationToken); + } /// - public virtual async ValueTask CreateAsync(TAuthorization authorization!!, CancellationToken cancellationToken) + public virtual async ValueTask CreateAsync(TAuthorization authorization, CancellationToken cancellationToken) { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + Authorizations.Add(authorization); await Context.SaveChangesAsync(cancellationToken); } /// - public virtual async ValueTask DeleteAsync(TAuthorization authorization!!, CancellationToken cancellationToken) + public virtual async ValueTask DeleteAsync(TAuthorization authorization, CancellationToken cancellationToken) { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + DbContextTransaction? CreateTransaction() { try @@ -344,8 +361,13 @@ public class OpenIddictEntityFrameworkAuthorizationStore - public virtual async ValueTask GetApplicationIdAsync(TAuthorization authorization!!, CancellationToken cancellationToken) + public virtual async ValueTask GetApplicationIdAsync(TAuthorization authorization, CancellationToken cancellationToken) { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + // If the application is not attached to the authorization, try to load it manually. if (authorization.Application is null) { @@ -368,22 +390,53 @@ public class OpenIddictEntityFrameworkAuthorizationStore public virtual async ValueTask GetAsync( - Func, TState, IQueryable> query!!, + Func, TState, IQueryable> query, TState state, CancellationToken cancellationToken) - => await query( + { + if (query is null) + { + throw new ArgumentNullException(nameof(query)); + } + + return await query( Authorizations.Include(authorization => authorization.Application), state).FirstOrDefaultAsync(cancellationToken); + } /// - public virtual ValueTask GetCreationDateAsync(TAuthorization authorization!!, CancellationToken cancellationToken) - => new(authorization.CreationDate is DateTime date ? DateTime.SpecifyKind(date, DateTimeKind.Utc) : null); + public virtual ValueTask GetCreationDateAsync(TAuthorization authorization, CancellationToken cancellationToken) + { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + + if (authorization.CreationDate is null) + { + return new(result: null); + } + + return new(DateTime.SpecifyKind(authorization.CreationDate.Value, DateTimeKind.Utc)); + } /// - public virtual ValueTask GetIdAsync(TAuthorization authorization!!, CancellationToken cancellationToken) - => new(ConvertIdentifierToString(authorization.Id)); + public virtual ValueTask GetIdAsync(TAuthorization authorization, CancellationToken cancellationToken) + { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + + return new(ConvertIdentifierToString(authorization.Id)); + } /// - public virtual ValueTask> GetPropertiesAsync(TAuthorization authorization!!, CancellationToken cancellationToken) + public virtual ValueTask> GetPropertiesAsync(TAuthorization authorization, CancellationToken cancellationToken) { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + if (string.IsNullOrEmpty(authorization.Properties)) { return new(ImmutableDictionary.Create()); @@ -412,8 +465,13 @@ public class OpenIddictEntityFrameworkAuthorizationStore - public virtual ValueTask> GetScopesAsync(TAuthorization authorization!!, CancellationToken cancellationToken) + public virtual ValueTask> GetScopesAsync(TAuthorization authorization, CancellationToken cancellationToken) { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + if (string.IsNullOrEmpty(authorization.Scopes)) { return new(ImmutableArray.Create()); @@ -448,16 +506,37 @@ public class OpenIddictEntityFrameworkAuthorizationStore - public virtual ValueTask GetStatusAsync(TAuthorization authorization!!, CancellationToken cancellationToken) - => new(authorization.Status); + public virtual ValueTask GetStatusAsync(TAuthorization authorization, CancellationToken cancellationToken) + { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + + return new(authorization.Status); + } /// - public virtual ValueTask GetSubjectAsync(TAuthorization authorization!!, CancellationToken cancellationToken) - => new(authorization.Subject); + public virtual ValueTask GetSubjectAsync(TAuthorization authorization, CancellationToken cancellationToken) + { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + + return new(authorization.Subject); + } /// - public virtual ValueTask GetTypeAsync(TAuthorization authorization!!, CancellationToken cancellationToken) - => new(authorization.Type); + public virtual ValueTask GetTypeAsync(TAuthorization authorization, CancellationToken cancellationToken) + { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + + return new(authorization.Type); + } /// public virtual ValueTask InstantiateAsync(CancellationToken cancellationToken) @@ -496,9 +575,16 @@ public class OpenIddictEntityFrameworkAuthorizationStore public virtual IAsyncEnumerable ListAsync( - Func, TState, IQueryable> query!!, + Func, TState, IQueryable> query, TState state, CancellationToken cancellationToken) - => query(Authorizations.Include(authorization => authorization.Application), state).AsAsyncEnumerable(cancellationToken); + { + if (query is null) + { + throw new ArgumentNullException(nameof(query)); + } + + return query(Authorizations.Include(authorization => authorization.Application), state).AsAsyncEnumerable(cancellationToken); + } /// public virtual async ValueTask PruneAsync(DateTimeOffset threshold, CancellationToken cancellationToken) @@ -582,9 +668,14 @@ public class OpenIddictEntityFrameworkAuthorizationStore - public virtual async ValueTask SetApplicationIdAsync(TAuthorization authorization!!, + public virtual async ValueTask SetApplicationIdAsync(TAuthorization authorization, string? identifier, CancellationToken cancellationToken) { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + if (!string.IsNullOrEmpty(identifier)) { authorization.Application = await Applications.FindAsync( @@ -611,18 +702,28 @@ public class OpenIddictEntityFrameworkAuthorizationStore - public virtual ValueTask SetCreationDateAsync(TAuthorization authorization!!, + public virtual ValueTask SetCreationDateAsync(TAuthorization authorization, DateTimeOffset? date, CancellationToken cancellationToken) { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + authorization.CreationDate = date?.UtcDateTime; return default; } /// - public virtual ValueTask SetPropertiesAsync(TAuthorization authorization!!, + public virtual ValueTask SetPropertiesAsync(TAuthorization authorization, ImmutableDictionary properties, CancellationToken cancellationToken) { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + if (properties is not { Count: > 0 }) { authorization.Properties = null; @@ -654,9 +755,14 @@ public class OpenIddictEntityFrameworkAuthorizationStore - public virtual ValueTask SetScopesAsync(TAuthorization authorization!!, + public virtual ValueTask SetScopesAsync(TAuthorization authorization, ImmutableArray scopes, CancellationToken cancellationToken) { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + if (scopes.IsDefaultOrEmpty) { authorization.Scopes = null; @@ -687,32 +793,52 @@ public class OpenIddictEntityFrameworkAuthorizationStore - public virtual ValueTask SetStatusAsync(TAuthorization authorization!!, string? status, CancellationToken cancellationToken) + public virtual ValueTask SetStatusAsync(TAuthorization authorization, string? status, CancellationToken cancellationToken) { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + authorization.Status = status; return default; } /// - public virtual ValueTask SetSubjectAsync(TAuthorization authorization!!, string? subject, CancellationToken cancellationToken) + public virtual ValueTask SetSubjectAsync(TAuthorization authorization, string? subject, CancellationToken cancellationToken) { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + authorization.Subject = subject; return default; } /// - public virtual ValueTask SetTypeAsync(TAuthorization authorization!!, string? type, CancellationToken cancellationToken) + public virtual ValueTask SetTypeAsync(TAuthorization authorization, string? type, CancellationToken cancellationToken) { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + authorization.Type = type; return default; } /// - public virtual async ValueTask UpdateAsync(TAuthorization authorization!!, CancellationToken cancellationToken) + public virtual async ValueTask UpdateAsync(TAuthorization authorization, CancellationToken cancellationToken) { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + Authorizations.Attach(authorization); // Generate a new concurrency token and attach it diff --git a/src/OpenIddict.EntityFramework/Stores/OpenIddictEntityFrameworkScopeStore.cs b/src/OpenIddict.EntityFramework/Stores/OpenIddictEntityFrameworkScopeStore.cs index f81c5618..317add5a 100644 --- a/src/OpenIddict.EntityFramework/Stores/OpenIddictEntityFrameworkScopeStore.cs +++ b/src/OpenIddict.EntityFramework/Stores/OpenIddictEntityFrameworkScopeStore.cs @@ -29,7 +29,7 @@ public class OpenIddictEntityFrameworkScopeStore : public OpenIddictEntityFrameworkScopeStore( IMemoryCache cache, TContext context, - IOptionsMonitor options!!) + IOptionsMonitor options) : base(cache, context, options) { } @@ -47,13 +47,13 @@ public class OpenIddictEntityFrameworkScopeStore : IOpen where TKey : notnull, IEquatable { public OpenIddictEntityFrameworkScopeStore( - IMemoryCache cache!!, - TContext context!!, - IOptionsMonitor options!!) + IMemoryCache cache, + TContext context, + IOptionsMonitor options) { - Cache = cache; - Context = context; - Options = options; + Cache = cache ?? throw new ArgumentNullException(nameof(cache)); + Context = context ?? throw new ArgumentNullException(nameof(context)); + Options = options ?? throw new ArgumentNullException(nameof(options)); } /// @@ -81,20 +81,37 @@ public class OpenIddictEntityFrameworkScopeStore : IOpen => await Scopes.LongCountAsync(cancellationToken); /// - public virtual async ValueTask CountAsync(Func, IQueryable> query!!, CancellationToken cancellationToken) - => await query(Scopes).LongCountAsync(cancellationToken); + public virtual async ValueTask CountAsync(Func, IQueryable> query, CancellationToken cancellationToken) + { + if (query is null) + { + throw new ArgumentNullException(nameof(query)); + } + + return await query(Scopes).LongCountAsync(cancellationToken); + } /// - public virtual async ValueTask CreateAsync(TScope scope!!, CancellationToken cancellationToken) + public virtual async ValueTask CreateAsync(TScope scope, CancellationToken cancellationToken) { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + Scopes.Add(scope); await Context.SaveChangesAsync(cancellationToken); } /// - public virtual async ValueTask DeleteAsync(TScope scope!!, CancellationToken cancellationToken) + public virtual async ValueTask DeleteAsync(TScope scope, CancellationToken cancellationToken) { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + Scopes.Remove(scope); try @@ -143,7 +160,7 @@ public class OpenIddictEntityFrameworkScopeStore : IOpen public virtual IAsyncEnumerable FindByNamesAsync( ImmutableArray names, CancellationToken cancellationToken) { - if (names.Any(string.IsNullOrEmpty)) + if (names.Any(name => string.IsNullOrEmpty(name))) { throw new ArgumentException(SR.GetResourceString(SR.ID0203), nameof(names)); } @@ -191,17 +208,36 @@ public class OpenIddictEntityFrameworkScopeStore : IOpen /// public virtual async ValueTask GetAsync( - Func, TState, IQueryable> query!!, + Func, TState, IQueryable> query, TState state, CancellationToken cancellationToken) - => await query(Scopes, state).FirstOrDefaultAsync(cancellationToken); + { + if (query is null) + { + throw new ArgumentNullException(nameof(query)); + } + + return await query(Scopes, state).FirstOrDefaultAsync(cancellationToken); + } /// - public virtual ValueTask GetDescriptionAsync(TScope scope!!, CancellationToken cancellationToken) - => new(scope.Description); + public virtual ValueTask GetDescriptionAsync(TScope scope, CancellationToken cancellationToken) + { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + + return new(scope.Description); + } /// - public virtual ValueTask> GetDescriptionsAsync(TScope scope!!, CancellationToken cancellationToken) + public virtual ValueTask> GetDescriptionsAsync(TScope scope, CancellationToken cancellationToken) { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + if (string.IsNullOrEmpty(scope.Descriptions)) { return new(ImmutableDictionary.Create()); @@ -236,14 +272,24 @@ public class OpenIddictEntityFrameworkScopeStore : IOpen } /// - public virtual ValueTask GetDisplayNameAsync(TScope scope!!, CancellationToken cancellationToken) + public virtual ValueTask GetDisplayNameAsync(TScope scope, CancellationToken cancellationToken) { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + return new(scope.DisplayName); } /// - public virtual ValueTask> GetDisplayNamesAsync(TScope scope!!, CancellationToken cancellationToken) + public virtual ValueTask> GetDisplayNamesAsync(TScope scope, CancellationToken cancellationToken) { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + if (string.IsNullOrEmpty(scope.DisplayNames)) { return new(ImmutableDictionary.Create()); @@ -278,16 +324,35 @@ public class OpenIddictEntityFrameworkScopeStore : IOpen } /// - public virtual ValueTask GetIdAsync(TScope scope!!, CancellationToken cancellationToken) - => new(ConvertIdentifierToString(scope.Id)); + public virtual ValueTask GetIdAsync(TScope scope, CancellationToken cancellationToken) + { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + + return new(ConvertIdentifierToString(scope.Id)); + } /// - public virtual ValueTask GetNameAsync(TScope scope!!, CancellationToken cancellationToken) - => new(scope.Name); + public virtual ValueTask GetNameAsync(TScope scope, CancellationToken cancellationToken) + { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + + return new(scope.Name); + } /// - public virtual ValueTask> GetPropertiesAsync(TScope scope!!, CancellationToken cancellationToken) + public virtual ValueTask> GetPropertiesAsync(TScope scope, CancellationToken cancellationToken) { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + if (string.IsNullOrEmpty(scope.Properties)) { return new(ImmutableDictionary.Create()); @@ -316,8 +381,13 @@ public class OpenIddictEntityFrameworkScopeStore : IOpen } /// - public virtual ValueTask> GetResourcesAsync(TScope scope!!, CancellationToken cancellationToken) + public virtual ValueTask> GetResourcesAsync(TScope scope, CancellationToken cancellationToken) { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + if (string.IsNullOrEmpty(scope.Resources)) { return new(ImmutableArray.Create()); @@ -386,22 +456,39 @@ public class OpenIddictEntityFrameworkScopeStore : IOpen /// public virtual IAsyncEnumerable ListAsync( - Func, TState, IQueryable> query!!, + Func, TState, IQueryable> query, TState state, CancellationToken cancellationToken) - => query(Scopes, state).AsAsyncEnumerable(cancellationToken); + { + if (query is null) + { + throw new ArgumentNullException(nameof(query)); + } + + return query(Scopes, state).AsAsyncEnumerable(cancellationToken); + } /// - public virtual ValueTask SetDescriptionAsync(TScope scope!!, string? description, CancellationToken cancellationToken) + public virtual ValueTask SetDescriptionAsync(TScope scope, string? description, CancellationToken cancellationToken) { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + scope.Description = description; return default; } /// - public virtual ValueTask SetDescriptionsAsync(TScope scope!!, + public virtual ValueTask SetDescriptionsAsync(TScope scope, ImmutableDictionary descriptions, CancellationToken cancellationToken) { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + if (descriptions is not { Count: > 0 }) { scope.Descriptions = null; @@ -433,17 +520,27 @@ public class OpenIddictEntityFrameworkScopeStore : IOpen } /// - public virtual ValueTask SetDisplayNameAsync(TScope scope!!, string? name, CancellationToken cancellationToken) + public virtual ValueTask SetDisplayNameAsync(TScope scope, string? name, CancellationToken cancellationToken) { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + scope.DisplayName = name; return default; } /// - public virtual ValueTask SetDisplayNamesAsync(TScope scope!!, + public virtual ValueTask SetDisplayNamesAsync(TScope scope, ImmutableDictionary names, CancellationToken cancellationToken) { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + if (names is not { Count: > 0 }) { scope.DisplayNames = null; @@ -475,17 +572,27 @@ public class OpenIddictEntityFrameworkScopeStore : IOpen } /// - public virtual ValueTask SetNameAsync(TScope scope!!, string? name, CancellationToken cancellationToken) + public virtual ValueTask SetNameAsync(TScope scope, string? name, CancellationToken cancellationToken) { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + scope.Name = name; return default; } /// - public virtual ValueTask SetPropertiesAsync(TScope scope!!, + public virtual ValueTask SetPropertiesAsync(TScope scope, ImmutableDictionary properties, CancellationToken cancellationToken) { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + if (properties is not { Count: > 0 }) { scope.Properties = null; @@ -517,8 +624,13 @@ public class OpenIddictEntityFrameworkScopeStore : IOpen } /// - public virtual ValueTask SetResourcesAsync(TScope scope!!, ImmutableArray resources, CancellationToken cancellationToken) + public virtual ValueTask SetResourcesAsync(TScope scope, ImmutableArray resources, CancellationToken cancellationToken) { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + if (resources.IsDefaultOrEmpty) { scope.Resources = null; @@ -549,8 +661,13 @@ public class OpenIddictEntityFrameworkScopeStore : IOpen } /// - public virtual async ValueTask UpdateAsync(TScope scope!!, CancellationToken cancellationToken) + public virtual async ValueTask UpdateAsync(TScope scope, CancellationToken cancellationToken) { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + Scopes.Attach(scope); // Generate a new concurrency token and attach it diff --git a/src/OpenIddict.EntityFramework/Stores/OpenIddictEntityFrameworkTokenStore.cs b/src/OpenIddict.EntityFramework/Stores/OpenIddictEntityFrameworkTokenStore.cs index 9176e987..75485a50 100644 --- a/src/OpenIddict.EntityFramework/Stores/OpenIddictEntityFrameworkTokenStore.cs +++ b/src/OpenIddict.EntityFramework/Stores/OpenIddictEntityFrameworkTokenStore.cs @@ -30,7 +30,7 @@ public class OpenIddictEntityFrameworkTokenStore : public OpenIddictEntityFrameworkTokenStore( IMemoryCache cache, TContext context, - IOptionsMonitor options!!) + IOptionsMonitor options) : base(cache, context, options) { } @@ -52,13 +52,13 @@ public class OpenIddictEntityFrameworkTokenStore { public OpenIddictEntityFrameworkTokenStore( - IMemoryCache cache!!, - TContext context!!, - IOptionsMonitor options!!) + IMemoryCache cache, + TContext context, + IOptionsMonitor options) { - Cache = cache; - Context = context; - Options = options; + Cache = cache ?? throw new ArgumentNullException(nameof(cache)); + Context = context ?? throw new ArgumentNullException(nameof(context)); + Options = options ?? throw new ArgumentNullException(nameof(options)); } /// @@ -96,20 +96,37 @@ public class OpenIddictEntityFrameworkTokenStore await Tokens.LongCountAsync(cancellationToken); /// - public virtual async ValueTask CountAsync(Func, IQueryable> query!!, CancellationToken cancellationToken) - => await query(Tokens).LongCountAsync(cancellationToken); + public virtual async ValueTask CountAsync(Func, IQueryable> query, CancellationToken cancellationToken) + { + if (query is null) + { + throw new ArgumentNullException(nameof(query)); + } + + return await query(Tokens).LongCountAsync(cancellationToken); + } /// - public virtual async ValueTask CreateAsync(TToken token!!, CancellationToken cancellationToken) + public virtual async ValueTask CreateAsync(TToken token, CancellationToken cancellationToken) { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + Tokens.Add(token); await Context.SaveChangesAsync(cancellationToken); } /// - public virtual async ValueTask DeleteAsync(TToken token!!, CancellationToken cancellationToken) + public virtual async ValueTask DeleteAsync(TToken token, CancellationToken cancellationToken) { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + Tokens.Remove(token); try @@ -284,8 +301,13 @@ public class OpenIddictEntityFrameworkTokenStore - public virtual async ValueTask GetApplicationIdAsync(TToken token!!, CancellationToken cancellationToken) + public virtual async ValueTask GetApplicationIdAsync(TToken token, CancellationToken cancellationToken) { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + // If the application is not attached to the token, try to load it manually. if (token.Application is null) { @@ -308,15 +330,27 @@ public class OpenIddictEntityFrameworkTokenStore public virtual async ValueTask GetAsync( - Func, TState, IQueryable> query!!, + Func, TState, IQueryable> query, TState state, CancellationToken cancellationToken) - => await query( + { + if (query is null) + { + throw new ArgumentNullException(nameof(query)); + } + + return await query( Tokens.Include(token => token.Application) .Include(token => token.Authorization), state).FirstOrDefaultAsync(cancellationToken); + } /// - public virtual async ValueTask GetAuthorizationIdAsync(TToken token!!, CancellationToken cancellationToken) + public virtual async ValueTask GetAuthorizationIdAsync(TToken token, CancellationToken cancellationToken) { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + // If the authorization is not attached to the token, try to load it manually. if (token.Authorization is null) { @@ -338,24 +372,67 @@ public class OpenIddictEntityFrameworkTokenStore - public virtual ValueTask GetCreationDateAsync(TToken token!!, CancellationToken cancellationToken) - => new(token.CreationDate is DateTime date ? DateTime.SpecifyKind(date, DateTimeKind.Utc) : null); + public virtual ValueTask GetCreationDateAsync(TToken token, CancellationToken cancellationToken) + { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + + if (token.CreationDate is null) + { + return new(result: null); + } + + return new(DateTime.SpecifyKind(token.CreationDate.Value, DateTimeKind.Utc)); + } /// - public virtual ValueTask GetExpirationDateAsync(TToken token!!, CancellationToken cancellationToken) - => new(token.ExpirationDate is DateTime date ? DateTime.SpecifyKind(date, DateTimeKind.Utc) : null); + public virtual ValueTask GetExpirationDateAsync(TToken token, CancellationToken cancellationToken) + { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + + if (token.ExpirationDate is null) + { + return new(result: null); + } + + return new(DateTime.SpecifyKind(token.ExpirationDate.Value, DateTimeKind.Utc)); + } /// - public virtual ValueTask GetIdAsync(TToken token!!, CancellationToken cancellationToken) - => new(ConvertIdentifierToString(token.Id)); + public virtual ValueTask GetIdAsync(TToken token, CancellationToken cancellationToken) + { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + + return new(ConvertIdentifierToString(token.Id)); + } /// - public virtual ValueTask GetPayloadAsync(TToken token!!, CancellationToken cancellationToken) - => new(token.Payload); + public virtual ValueTask GetPayloadAsync(TToken token, CancellationToken cancellationToken) + { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + + return new(token.Payload); + } /// - public virtual ValueTask> GetPropertiesAsync(TToken token!!, CancellationToken cancellationToken) + public virtual ValueTask> GetPropertiesAsync(TToken token, CancellationToken cancellationToken) { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + if (string.IsNullOrEmpty(token.Properties)) { return new(ImmutableDictionary.Create()); @@ -384,24 +461,64 @@ public class OpenIddictEntityFrameworkTokenStore - public virtual ValueTask GetRedemptionDateAsync(TToken token!!, CancellationToken cancellationToken) - => new(token.RedemptionDate is DateTime date ? DateTime.SpecifyKind(date, DateTimeKind.Utc) : null); + public virtual ValueTask GetRedemptionDateAsync(TToken token, CancellationToken cancellationToken) + { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + + if (token.RedemptionDate is null) + { + return new(result: null); + } + + return new(DateTime.SpecifyKind(token.RedemptionDate.Value, DateTimeKind.Utc)); + } /// - public virtual ValueTask GetReferenceIdAsync(TToken token!!, CancellationToken cancellationToken) - => new(token.ReferenceId); + public virtual ValueTask GetReferenceIdAsync(TToken token, CancellationToken cancellationToken) + { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + + return new(token.ReferenceId); + } /// - public virtual ValueTask GetStatusAsync(TToken token!!, CancellationToken cancellationToken) - => new(token.Status); + public virtual ValueTask GetStatusAsync(TToken token, CancellationToken cancellationToken) + { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + + return new(token.Status); + } /// - public virtual ValueTask GetSubjectAsync(TToken token!!, CancellationToken cancellationToken) - => new(token.Subject); + public virtual ValueTask GetSubjectAsync(TToken token, CancellationToken cancellationToken) + { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + + return new(token.Subject); + } /// - public virtual ValueTask GetTypeAsync(TToken token!!, CancellationToken cancellationToken) - => new(token.Type); + public virtual ValueTask GetTypeAsync(TToken token, CancellationToken cancellationToken) + { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + + return new(token.Type); + } /// public virtual ValueTask InstantiateAsync(CancellationToken cancellationToken) @@ -441,11 +558,18 @@ public class OpenIddictEntityFrameworkTokenStore public virtual IAsyncEnumerable ListAsync( - Func, TState, IQueryable> query!!, + Func, TState, IQueryable> query, TState state, CancellationToken cancellationToken) - => query( + { + if (query is null) + { + throw new ArgumentNullException(nameof(query)); + } + + return query( Tokens.Include(token => token.Application) .Include(token => token.Authorization), state).AsAsyncEnumerable(cancellationToken); + } /// public virtual async ValueTask PruneAsync(DateTimeOffset threshold, CancellationToken cancellationToken) @@ -526,8 +650,13 @@ public class OpenIddictEntityFrameworkTokenStore - public virtual async ValueTask SetApplicationIdAsync(TToken token!!, string? identifier, CancellationToken cancellationToken) + public virtual async ValueTask SetApplicationIdAsync(TToken token, string? identifier, CancellationToken cancellationToken) { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + if (!string.IsNullOrEmpty(identifier)) { token.Application = await Applications.FindAsync( @@ -554,8 +683,13 @@ public class OpenIddictEntityFrameworkTokenStore - public virtual async ValueTask SetAuthorizationIdAsync(TToken token!!, string? identifier, CancellationToken cancellationToken) + public virtual async ValueTask SetAuthorizationIdAsync(TToken token, string? identifier, CancellationToken cancellationToken) { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + if (!string.IsNullOrEmpty(identifier)) { token.Authorization = await Authorizations.FindAsync( @@ -582,33 +716,53 @@ public class OpenIddictEntityFrameworkTokenStore - public virtual ValueTask SetCreationDateAsync(TToken token!!, DateTimeOffset? date, CancellationToken cancellationToken) + public virtual ValueTask SetCreationDateAsync(TToken token, DateTimeOffset? date, CancellationToken cancellationToken) { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + token.CreationDate = date?.UtcDateTime; return default; } /// - public virtual ValueTask SetExpirationDateAsync(TToken token!!, DateTimeOffset? date, CancellationToken cancellationToken) + public virtual ValueTask SetExpirationDateAsync(TToken token, DateTimeOffset? date, CancellationToken cancellationToken) { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + token.ExpirationDate = date?.UtcDateTime; return default; } /// - public virtual ValueTask SetPayloadAsync(TToken token!!, string? payload, CancellationToken cancellationToken) + public virtual ValueTask SetPayloadAsync(TToken token, string? payload, CancellationToken cancellationToken) { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + token.Payload = payload; return default; } /// - public virtual ValueTask SetPropertiesAsync(TToken token!!, + public virtual ValueTask SetPropertiesAsync(TToken token, ImmutableDictionary properties, CancellationToken cancellationToken) { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + if (properties is not { Count: > 0 }) { token.Properties = null; @@ -640,48 +794,78 @@ public class OpenIddictEntityFrameworkTokenStore - public virtual ValueTask SetRedemptionDateAsync(TToken token!!, DateTimeOffset? date, CancellationToken cancellationToken) + public virtual ValueTask SetRedemptionDateAsync(TToken token, DateTimeOffset? date, CancellationToken cancellationToken) { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + token.RedemptionDate = date?.UtcDateTime; return default; } /// - public virtual ValueTask SetReferenceIdAsync(TToken token!!, string? identifier, CancellationToken cancellationToken) + public virtual ValueTask SetReferenceIdAsync(TToken token, string? identifier, CancellationToken cancellationToken) { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + token.ReferenceId = identifier; return default; } /// - public virtual ValueTask SetStatusAsync(TToken token!!, string? status, CancellationToken cancellationToken) + public virtual ValueTask SetStatusAsync(TToken token, string? status, CancellationToken cancellationToken) { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + token.Status = status; return default; } /// - public virtual ValueTask SetSubjectAsync(TToken token!!, string? subject, CancellationToken cancellationToken) + public virtual ValueTask SetSubjectAsync(TToken token, string? subject, CancellationToken cancellationToken) { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + token.Subject = subject; return default; } /// - public virtual ValueTask SetTypeAsync(TToken token!!, string? type, CancellationToken cancellationToken) + public virtual ValueTask SetTypeAsync(TToken token, string? type, CancellationToken cancellationToken) { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + token.Type = type; return default; } /// - public virtual async ValueTask UpdateAsync(TToken token!!, CancellationToken cancellationToken) + public virtual async ValueTask UpdateAsync(TToken token, CancellationToken cancellationToken) { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + Tokens.Attach(token); // Generate a new concurrency token and attach it diff --git a/src/OpenIddict.EntityFrameworkCore/Configurations/OpenIddictEntityFrameworkCoreApplicationConfiguration.cs b/src/OpenIddict.EntityFrameworkCore/Configurations/OpenIddictEntityFrameworkCoreApplicationConfiguration.cs index a07f5d20..140bb402 100644 --- a/src/OpenIddict.EntityFrameworkCore/Configurations/OpenIddictEntityFrameworkCoreApplicationConfiguration.cs +++ b/src/OpenIddict.EntityFrameworkCore/Configurations/OpenIddictEntityFrameworkCoreApplicationConfiguration.cs @@ -24,8 +24,13 @@ public class OpenIddictEntityFrameworkCoreApplicationConfiguration where TKey : notnull, IEquatable { - public void Configure(EntityTypeBuilder builder!!) + public void Configure(EntityTypeBuilder builder) { + if (builder is null) + { + throw new ArgumentNullException(nameof(builder)); + } + // Warning: optional foreign keys MUST NOT be added as CLR properties because // Entity Framework would throw an exception due to the TKey generic parameter // being non-nullable when using value types like short, int, long or Guid. diff --git a/src/OpenIddict.EntityFrameworkCore/Configurations/OpenIddictEntityFrameworkCoreAuthorizationConfiguration.cs b/src/OpenIddict.EntityFrameworkCore/Configurations/OpenIddictEntityFrameworkCoreAuthorizationConfiguration.cs index 4590271f..2ce61897 100644 --- a/src/OpenIddict.EntityFrameworkCore/Configurations/OpenIddictEntityFrameworkCoreAuthorizationConfiguration.cs +++ b/src/OpenIddict.EntityFrameworkCore/Configurations/OpenIddictEntityFrameworkCoreAuthorizationConfiguration.cs @@ -24,8 +24,13 @@ public class OpenIddictEntityFrameworkCoreAuthorizationConfiguration where TKey : notnull, IEquatable { - public void Configure(EntityTypeBuilder builder!!) + public void Configure(EntityTypeBuilder builder) { + if (builder is null) + { + throw new ArgumentNullException(nameof(builder)); + } + // Warning: optional foreign keys MUST NOT be added as CLR properties because // Entity Framework would throw an exception due to the TKey generic parameter // being non-nullable when using value types like short, int, long or Guid. diff --git a/src/OpenIddict.EntityFrameworkCore/Configurations/OpenIddictEntityFrameworkCoreScopeConfiguration.cs b/src/OpenIddict.EntityFrameworkCore/Configurations/OpenIddictEntityFrameworkCoreScopeConfiguration.cs index aa7e2180..828623d3 100644 --- a/src/OpenIddict.EntityFrameworkCore/Configurations/OpenIddictEntityFrameworkCoreScopeConfiguration.cs +++ b/src/OpenIddict.EntityFrameworkCore/Configurations/OpenIddictEntityFrameworkCoreScopeConfiguration.cs @@ -20,8 +20,13 @@ public class OpenIddictEntityFrameworkCoreScopeConfiguration : IEn where TScope : OpenIddictEntityFrameworkCoreScope where TKey : notnull, IEquatable { - public void Configure(EntityTypeBuilder builder!!) + public void Configure(EntityTypeBuilder builder) { + if (builder is null) + { + throw new ArgumentNullException(nameof(builder)); + } + // Warning: optional foreign keys MUST NOT be added as CLR properties because // Entity Framework would throw an exception due to the TKey generic parameter // being non-nullable when using value types like short, int, long or Guid. diff --git a/src/OpenIddict.EntityFrameworkCore/Configurations/OpenIddictEntityFrameworkCoreTokenConfiguration.cs b/src/OpenIddict.EntityFrameworkCore/Configurations/OpenIddictEntityFrameworkCoreTokenConfiguration.cs index 4935c363..bafb2138 100644 --- a/src/OpenIddict.EntityFrameworkCore/Configurations/OpenIddictEntityFrameworkCoreTokenConfiguration.cs +++ b/src/OpenIddict.EntityFrameworkCore/Configurations/OpenIddictEntityFrameworkCoreTokenConfiguration.cs @@ -24,8 +24,13 @@ public class OpenIddictEntityFrameworkCoreTokenConfiguration where TKey : notnull, IEquatable { - public void Configure(EntityTypeBuilder builder!!) + public void Configure(EntityTypeBuilder builder) { + if (builder is null) + { + throw new ArgumentNullException(nameof(builder)); + } + // Warning: optional foreign keys MUST NOT be added as CLR properties because // Entity Framework would throw an exception due to the TKey generic parameter // being non-nullable when using value types like short, int, long or Guid. diff --git a/src/OpenIddict.EntityFrameworkCore/OpenIddictEntityFrameworkCoreBuilder.cs b/src/OpenIddict.EntityFrameworkCore/OpenIddictEntityFrameworkCoreBuilder.cs index e3c88e6c..e5f54c24 100644 --- a/src/OpenIddict.EntityFrameworkCore/OpenIddictEntityFrameworkCoreBuilder.cs +++ b/src/OpenIddict.EntityFrameworkCore/OpenIddictEntityFrameworkCoreBuilder.cs @@ -20,8 +20,8 @@ public class OpenIddictEntityFrameworkCoreBuilder /// Initializes a new instance of . /// /// The services collection. - public OpenIddictEntityFrameworkCoreBuilder(IServiceCollection services!!) - => Services = services; + public OpenIddictEntityFrameworkCoreBuilder(IServiceCollection services) + => Services = services ?? throw new ArgumentNullException(nameof(services)); /// /// Gets the services collection. @@ -35,8 +35,13 @@ public class OpenIddictEntityFrameworkCoreBuilder /// The delegate used to configure the OpenIddict options. /// This extension can be safely called multiple times. /// The . - public OpenIddictEntityFrameworkCoreBuilder Configure(Action configuration!!) + public OpenIddictEntityFrameworkCoreBuilder Configure(Action configuration) { + if (configuration is null) + { + throw new ArgumentNullException(nameof(configuration)); + } + Services.Configure(configuration); return this; @@ -91,8 +96,13 @@ public class OpenIddictEntityFrameworkCoreBuilder /// /// The type of the used by OpenIddict. /// The . - public OpenIddictEntityFrameworkCoreBuilder UseDbContext(Type type!!) + public OpenIddictEntityFrameworkCoreBuilder UseDbContext(Type type) { + if (type is null) + { + throw new ArgumentNullException(nameof(type)); + } + if (!typeof(DbContext).IsAssignableFrom(type)) { throw new ArgumentException(SR.GetResourceString(SR.ID0232), nameof(type)); diff --git a/src/OpenIddict.EntityFrameworkCore/OpenIddictEntityFrameworkCoreCustomizer.cs b/src/OpenIddict.EntityFrameworkCore/OpenIddictEntityFrameworkCoreCustomizer.cs index 586aba69..7413d67f 100644 --- a/src/OpenIddict.EntityFrameworkCore/OpenIddictEntityFrameworkCoreCustomizer.cs +++ b/src/OpenIddict.EntityFrameworkCore/OpenIddictEntityFrameworkCoreCustomizer.cs @@ -25,8 +25,18 @@ public class OpenIddictEntityFrameworkCoreCustomizer - public override void Customize(ModelBuilder modelBuilder!!, DbContext context!!) + public override void Customize(ModelBuilder modelBuilder, DbContext context) { + if (modelBuilder is null) + { + throw new ArgumentNullException(nameof(modelBuilder)); + } + + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // Register the OpenIddict entity sets. modelBuilder.UseOpenIddict(); diff --git a/src/OpenIddict.EntityFrameworkCore/OpenIddictEntityFrameworkCoreExtensions.cs b/src/OpenIddict.EntityFrameworkCore/OpenIddictEntityFrameworkCoreExtensions.cs index d8a0066a..d99b7113 100644 --- a/src/OpenIddict.EntityFrameworkCore/OpenIddictEntityFrameworkCoreExtensions.cs +++ b/src/OpenIddict.EntityFrameworkCore/OpenIddictEntityFrameworkCoreExtensions.cs @@ -22,8 +22,13 @@ public static class OpenIddictEntityFrameworkCoreExtensions /// The services builder used by OpenIddict to register new services. /// This extension can be safely called multiple times. /// The . - public static OpenIddictEntityFrameworkCoreBuilder UseEntityFrameworkCore(this OpenIddictCoreBuilder builder!!) + public static OpenIddictEntityFrameworkCoreBuilder UseEntityFrameworkCore(this OpenIddictCoreBuilder builder) { + if (builder is null) + { + throw new ArgumentNullException(nameof(builder)); + } + // Since Entity Framework Core may be used with databases performing case-insensitive // or culture-sensitive comparisons, ensure the additional filtering logic is enforced // in case case-sensitive stores were registered before this extension was called. @@ -61,8 +66,18 @@ public static class OpenIddictEntityFrameworkCoreExtensions /// This extension can be safely called multiple times. /// The . public static OpenIddictCoreBuilder UseEntityFrameworkCore( - this OpenIddictCoreBuilder builder!!, Action configuration!!) + this OpenIddictCoreBuilder builder, Action configuration) { + if (builder is null) + { + throw new ArgumentNullException(nameof(builder)); + } + + if (configuration is null) + { + throw new ArgumentNullException(nameof(configuration)); + } + configuration(builder.UseEntityFrameworkCore()); return builder; diff --git a/src/OpenIddict.EntityFrameworkCore/OpenIddictEntityFrameworkCoreHelpers.cs b/src/OpenIddict.EntityFrameworkCore/OpenIddictEntityFrameworkCoreHelpers.cs index 770e6f66..fddd7dc6 100644 --- a/src/OpenIddict.EntityFrameworkCore/OpenIddictEntityFrameworkCoreHelpers.cs +++ b/src/OpenIddict.EntityFrameworkCore/OpenIddictEntityFrameworkCoreHelpers.cs @@ -56,14 +56,21 @@ public static class OpenIddictEntityFrameworkCoreHelpers /// The builder used to configure the Entity Framework context. /// The Entity Framework context builder. public static DbContextOptionsBuilder UseOpenIddict( - this DbContextOptionsBuilder builder!!) + this DbContextOptionsBuilder builder) where TApplication : OpenIddictEntityFrameworkCoreApplication where TAuthorization : OpenIddictEntityFrameworkCoreAuthorization where TScope : OpenIddictEntityFrameworkCoreScope where TToken : OpenIddictEntityFrameworkCoreToken where TKey : notnull, IEquatable - => builder.ReplaceService>(); + } /// /// Registers the OpenIddict entity sets in the Entity Framework Core context @@ -103,17 +110,24 @@ public static class OpenIddictEntityFrameworkCoreHelpers /// /// The builder used to configure the Entity Framework context. /// The Entity Framework context builder. - public static ModelBuilder UseOpenIddict(this ModelBuilder builder!!) + public static ModelBuilder UseOpenIddict(this ModelBuilder builder) where TApplication : OpenIddictEntityFrameworkCoreApplication where TAuthorization : OpenIddictEntityFrameworkCoreAuthorization where TScope : OpenIddictEntityFrameworkCoreScope where TToken : OpenIddictEntityFrameworkCoreToken where TKey : notnull, IEquatable - => builder + { + if (builder is null) + { + throw new ArgumentNullException(nameof(builder)); + } + + return builder .ApplyConfiguration(new OpenIddictEntityFrameworkCoreApplicationConfiguration()) .ApplyConfiguration(new OpenIddictEntityFrameworkCoreAuthorizationConfiguration()) .ApplyConfiguration(new OpenIddictEntityFrameworkCoreScopeConfiguration()) .ApplyConfiguration(new OpenIddictEntityFrameworkCoreTokenConfiguration()); + } #if SUPPORTS_BCL_ASYNC_ENUMERABLE /// @@ -132,8 +146,13 @@ public static class OpenIddictEntityFrameworkCoreHelpers /// The that can be used to abort the operation. /// The non-streamed async enumeration containing the results. #endif - internal static IAsyncEnumerable AsAsyncEnumerable(this IQueryable source!!, CancellationToken cancellationToken) + internal static IAsyncEnumerable AsAsyncEnumerable(this IQueryable source, CancellationToken cancellationToken) { + if (source is null) + { + throw new ArgumentNullException(nameof(source)); + } + return ExecuteAsync(source, cancellationToken); static async IAsyncEnumerable ExecuteAsync(IQueryable source, [EnumeratorCancellation] CancellationToken cancellationToken) diff --git a/src/OpenIddict.EntityFrameworkCore/Resolvers/OpenIddictEntityFrameworkCoreApplicationStoreResolver.cs b/src/OpenIddict.EntityFrameworkCore/Resolvers/OpenIddictEntityFrameworkCoreApplicationStoreResolver.cs index 05acfb63..2431acda 100644 --- a/src/OpenIddict.EntityFrameworkCore/Resolvers/OpenIddictEntityFrameworkCoreApplicationStoreResolver.cs +++ b/src/OpenIddict.EntityFrameworkCore/Resolvers/OpenIddictEntityFrameworkCoreApplicationStoreResolver.cs @@ -22,13 +22,13 @@ public class OpenIddictEntityFrameworkCoreApplicationStoreResolver : IOpenIddict private readonly IServiceProvider _provider; public OpenIddictEntityFrameworkCoreApplicationStoreResolver( - TypeResolutionCache cache!!, - IOptionsMonitor options!!, - IServiceProvider provider!!) + TypeResolutionCache cache, + IOptionsMonitor options, + IServiceProvider provider) { - _cache = cache; - _options = options; - _provider = provider; + _cache = cache ?? throw new ArgumentNullException(nameof(cache)); + _options = options ?? throw new ArgumentNullException(nameof(options)); + _provider = provider ?? throw new ArgumentNullException(nameof(provider)); } /// diff --git a/src/OpenIddict.EntityFrameworkCore/Resolvers/OpenIddictEntityFrameworkCoreAuthorizationStoreResolver.cs b/src/OpenIddict.EntityFrameworkCore/Resolvers/OpenIddictEntityFrameworkCoreAuthorizationStoreResolver.cs index 2212f801..d6db96fd 100644 --- a/src/OpenIddict.EntityFrameworkCore/Resolvers/OpenIddictEntityFrameworkCoreAuthorizationStoreResolver.cs +++ b/src/OpenIddict.EntityFrameworkCore/Resolvers/OpenIddictEntityFrameworkCoreAuthorizationStoreResolver.cs @@ -22,13 +22,13 @@ public class OpenIddictEntityFrameworkCoreAuthorizationStoreResolver : IOpenIddi private readonly IServiceProvider _provider; public OpenIddictEntityFrameworkCoreAuthorizationStoreResolver( - TypeResolutionCache cache!!, - IOptionsMonitor options!!, - IServiceProvider provider!!) + TypeResolutionCache cache, + IOptionsMonitor options, + IServiceProvider provider) { - _cache = cache; - _options = options; - _provider = provider; + _cache = cache ?? throw new ArgumentNullException(nameof(cache)); + _options = options ?? throw new ArgumentNullException(nameof(options)); + _provider = provider ?? throw new ArgumentNullException(nameof(provider)); } /// diff --git a/src/OpenIddict.EntityFrameworkCore/Resolvers/OpenIddictEntityFrameworkCoreScopeStoreResolver.cs b/src/OpenIddict.EntityFrameworkCore/Resolvers/OpenIddictEntityFrameworkCoreScopeStoreResolver.cs index ccb2cf97..13e61f93 100644 --- a/src/OpenIddict.EntityFrameworkCore/Resolvers/OpenIddictEntityFrameworkCoreScopeStoreResolver.cs +++ b/src/OpenIddict.EntityFrameworkCore/Resolvers/OpenIddictEntityFrameworkCoreScopeStoreResolver.cs @@ -22,13 +22,13 @@ public class OpenIddictEntityFrameworkCoreScopeStoreResolver : IOpenIddictScopeS private readonly IServiceProvider _provider; public OpenIddictEntityFrameworkCoreScopeStoreResolver( - TypeResolutionCache cache!!, - IOptionsMonitor options!!, - IServiceProvider provider!!) + TypeResolutionCache cache, + IOptionsMonitor options, + IServiceProvider provider) { - _cache = cache; - _options = options; - _provider = provider; + _cache = cache ?? throw new ArgumentNullException(nameof(cache)); + _options = options ?? throw new ArgumentNullException(nameof(options)); + _provider = provider ?? throw new ArgumentNullException(nameof(provider)); } /// diff --git a/src/OpenIddict.EntityFrameworkCore/Resolvers/OpenIddictEntityFrameworkCoreTokenStoreResolver.cs b/src/OpenIddict.EntityFrameworkCore/Resolvers/OpenIddictEntityFrameworkCoreTokenStoreResolver.cs index 54e66729..6c924cfe 100644 --- a/src/OpenIddict.EntityFrameworkCore/Resolvers/OpenIddictEntityFrameworkCoreTokenStoreResolver.cs +++ b/src/OpenIddict.EntityFrameworkCore/Resolvers/OpenIddictEntityFrameworkCoreTokenStoreResolver.cs @@ -22,13 +22,13 @@ public class OpenIddictEntityFrameworkCoreTokenStoreResolver : IOpenIddictTokenS private readonly IServiceProvider _provider; public OpenIddictEntityFrameworkCoreTokenStoreResolver( - TypeResolutionCache cache!!, - IOptionsMonitor options!!, - IServiceProvider provider!!) + TypeResolutionCache cache, + IOptionsMonitor options, + IServiceProvider provider) { - _cache = cache; - _options = options; - _provider = provider; + _cache = cache ?? throw new ArgumentNullException(nameof(cache)); + _options = options ?? throw new ArgumentNullException(nameof(options)); + _provider = provider ?? throw new ArgumentNullException(nameof(provider)); } /// diff --git a/src/OpenIddict.EntityFrameworkCore/Stores/OpenIddictEntityFrameworkCoreApplicationStore.cs b/src/OpenIddict.EntityFrameworkCore/Stores/OpenIddictEntityFrameworkCoreApplicationStore.cs index e644c35e..0aaf9449 100644 --- a/src/OpenIddict.EntityFrameworkCore/Stores/OpenIddictEntityFrameworkCoreApplicationStore.cs +++ b/src/OpenIddict.EntityFrameworkCore/Stores/OpenIddictEntityFrameworkCoreApplicationStore.cs @@ -31,7 +31,7 @@ public class OpenIddictEntityFrameworkCoreApplicationStore : public OpenIddictEntityFrameworkCoreApplicationStore( IMemoryCache cache, TContext context, - IOptionsMonitor options!!) + IOptionsMonitor options) : base(cache, context, options) { } @@ -52,7 +52,7 @@ public class OpenIddictEntityFrameworkCoreApplicationStore : public OpenIddictEntityFrameworkCoreApplicationStore( IMemoryCache cache, TContext context, - IOptionsMonitor options!!) + IOptionsMonitor options) : base(cache, context, options) { } @@ -74,13 +74,13 @@ public class OpenIddictEntityFrameworkCoreApplicationStore { public OpenIddictEntityFrameworkCoreApplicationStore( - IMemoryCache cache!!, - TContext context!!, - IOptionsMonitor options!!) + IMemoryCache cache, + TContext context, + IOptionsMonitor options) { - Cache = cache; - Context = context; - Options = options; + Cache = cache ?? throw new ArgumentNullException(nameof(cache)); + Context = context ?? throw new ArgumentNullException(nameof(context)); + Options = options ?? throw new ArgumentNullException(nameof(options)); } /// @@ -118,20 +118,37 @@ public class OpenIddictEntityFrameworkCoreApplicationStore await Applications.AsQueryable().LongCountAsync(cancellationToken); /// - public virtual async ValueTask CountAsync(Func, IQueryable> query!!, CancellationToken cancellationToken) - => await query(Applications).LongCountAsync(cancellationToken); + public virtual async ValueTask CountAsync(Func, IQueryable> query, CancellationToken cancellationToken) + { + if (query is null) + { + throw new ArgumentNullException(nameof(query)); + } + + return await query(Applications).LongCountAsync(cancellationToken); + } /// - public virtual async ValueTask CreateAsync(TApplication application!!, CancellationToken cancellationToken) + public virtual async ValueTask CreateAsync(TApplication application, CancellationToken cancellationToken) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + Context.Add(application); await Context.SaveChangesAsync(cancellationToken); } /// - public virtual async ValueTask DeleteAsync(TApplication application!!, CancellationToken cancellationToken) + public virtual async ValueTask DeleteAsync(TApplication application, CancellationToken cancellationToken) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + async ValueTask CreateTransactionAsync() { // Note: transactions that specify an explicit isolation level are only supported by @@ -328,33 +345,80 @@ public class OpenIddictEntityFrameworkCoreApplicationStore public virtual async ValueTask GetAsync( - Func, TState, IQueryable> query!!, + Func, TState, IQueryable> query, TState state, CancellationToken cancellationToken) - => await query(Applications.AsTracking(), state).FirstOrDefaultAsync(cancellationToken); + { + if (query is null) + { + throw new ArgumentNullException(nameof(query)); + } + + return await query(Applications.AsTracking(), state).FirstOrDefaultAsync(cancellationToken); + } /// - public virtual ValueTask GetClientIdAsync(TApplication application!!, CancellationToken cancellationToken) - => new(application.ClientId); + public virtual ValueTask GetClientIdAsync(TApplication application, CancellationToken cancellationToken) + { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + + return new(application.ClientId); + } /// - public virtual ValueTask GetClientSecretAsync(TApplication application!!, CancellationToken cancellationToken) - => new(application.ClientSecret); + public virtual ValueTask GetClientSecretAsync(TApplication application, CancellationToken cancellationToken) + { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + + return new(application.ClientSecret); + } /// - public virtual ValueTask GetClientTypeAsync(TApplication application!!, CancellationToken cancellationToken) - => new(application.Type); + public virtual ValueTask GetClientTypeAsync(TApplication application, CancellationToken cancellationToken) + { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + + return new(application.Type); + } /// - public virtual ValueTask GetConsentTypeAsync(TApplication application!!, CancellationToken cancellationToken) - => new(application.ConsentType); + public virtual ValueTask GetConsentTypeAsync(TApplication application, CancellationToken cancellationToken) + { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + + return new(application.ConsentType); + } /// - public virtual ValueTask GetDisplayNameAsync(TApplication application!!, CancellationToken cancellationToken) - => new(application.DisplayName); + public virtual ValueTask GetDisplayNameAsync(TApplication application, CancellationToken cancellationToken) + { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + + return new(application.DisplayName); + } /// - public virtual ValueTask> GetDisplayNamesAsync(TApplication application!!, CancellationToken cancellationToken) + public virtual ValueTask> GetDisplayNamesAsync(TApplication application, CancellationToken cancellationToken) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + if (string.IsNullOrEmpty(application.DisplayNames)) { return new(ImmutableDictionary.Create()); @@ -389,12 +453,24 @@ public class OpenIddictEntityFrameworkCoreApplicationStore - public virtual ValueTask GetIdAsync(TApplication application!!, CancellationToken cancellationToken) - => new(ConvertIdentifierToString(application.Id)); + public virtual ValueTask GetIdAsync(TApplication application, CancellationToken cancellationToken) + { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + + return new(ConvertIdentifierToString(application.Id)); + } /// - public virtual ValueTask> GetPermissionsAsync(TApplication application!!, CancellationToken cancellationToken) + public virtual ValueTask> GetPermissionsAsync(TApplication application, CancellationToken cancellationToken) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + if (string.IsNullOrEmpty(application.Permissions)) { return new(ImmutableArray.Create()); @@ -429,8 +505,13 @@ public class OpenIddictEntityFrameworkCoreApplicationStore - public virtual ValueTask> GetPostLogoutRedirectUrisAsync(TApplication application!!, CancellationToken cancellationToken) + public virtual ValueTask> GetPostLogoutRedirectUrisAsync(TApplication application, CancellationToken cancellationToken) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + if (string.IsNullOrEmpty(application.PostLogoutRedirectUris)) { return new(ImmutableArray.Create()); @@ -465,8 +546,13 @@ public class OpenIddictEntityFrameworkCoreApplicationStore - public virtual ValueTask> GetPropertiesAsync(TApplication application!!, CancellationToken cancellationToken) + public virtual ValueTask> GetPropertiesAsync(TApplication application, CancellationToken cancellationToken) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + if (string.IsNullOrEmpty(application.Properties)) { return new(ImmutableDictionary.Create()); @@ -495,8 +581,13 @@ public class OpenIddictEntityFrameworkCoreApplicationStore - public virtual ValueTask> GetRedirectUrisAsync(TApplication application!!, CancellationToken cancellationToken) + public virtual ValueTask> GetRedirectUrisAsync(TApplication application, CancellationToken cancellationToken) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + if (string.IsNullOrEmpty(application.RedirectUris)) { return new(ImmutableArray.Create()); @@ -531,8 +622,13 @@ public class OpenIddictEntityFrameworkCoreApplicationStore - public virtual ValueTask> GetRequirementsAsync(TApplication application!!, CancellationToken cancellationToken) + public virtual ValueTask> GetRequirementsAsync(TApplication application, CancellationToken cancellationToken) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + if (string.IsNullOrEmpty(application.Requirements)) { return new(ImmutableArray.Create()); @@ -601,54 +697,91 @@ public class OpenIddictEntityFrameworkCoreApplicationStore public virtual IAsyncEnumerable ListAsync( - Func, TState, IQueryable> query!!, + Func, TState, IQueryable> query, TState state, CancellationToken cancellationToken) - => query(Applications.AsTracking(), state).AsAsyncEnumerable(cancellationToken); + { + if (query is null) + { + throw new ArgumentNullException(nameof(query)); + } + + return query(Applications.AsTracking(), state).AsAsyncEnumerable(cancellationToken); + } /// - public virtual ValueTask SetClientIdAsync(TApplication application!!, string? identifier, CancellationToken cancellationToken) + public virtual ValueTask SetClientIdAsync(TApplication application, string? identifier, CancellationToken cancellationToken) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + application.ClientId = identifier; return default; } /// - public virtual ValueTask SetClientSecretAsync(TApplication application!!, string? secret, CancellationToken cancellationToken) + public virtual ValueTask SetClientSecretAsync(TApplication application, string? secret, CancellationToken cancellationToken) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + application.ClientSecret = secret; return default; } /// - public virtual ValueTask SetClientTypeAsync(TApplication application!!, string? type, CancellationToken cancellationToken) + public virtual ValueTask SetClientTypeAsync(TApplication application, string? type, CancellationToken cancellationToken) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + application.Type = type; return default; } /// - public virtual ValueTask SetConsentTypeAsync(TApplication application!!, string? type, CancellationToken cancellationToken) + public virtual ValueTask SetConsentTypeAsync(TApplication application, string? type, CancellationToken cancellationToken) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + application.ConsentType = type; return default; } /// - public virtual ValueTask SetDisplayNameAsync(TApplication application!!, string? name, CancellationToken cancellationToken) + public virtual ValueTask SetDisplayNameAsync(TApplication application, string? name, CancellationToken cancellationToken) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + application.DisplayName = name; return default; } /// - public virtual ValueTask SetDisplayNamesAsync(TApplication application!!, + public virtual ValueTask SetDisplayNamesAsync(TApplication application, ImmutableDictionary names, CancellationToken cancellationToken) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + if (names is not { Count: > 0 }) { application.DisplayNames = null; @@ -680,8 +813,13 @@ public class OpenIddictEntityFrameworkCoreApplicationStore - public virtual ValueTask SetPermissionsAsync(TApplication application!!, ImmutableArray permissions, CancellationToken cancellationToken) + public virtual ValueTask SetPermissionsAsync(TApplication application, ImmutableArray permissions, CancellationToken cancellationToken) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + if (permissions.IsDefaultOrEmpty) { application.Permissions = null; @@ -712,9 +850,14 @@ public class OpenIddictEntityFrameworkCoreApplicationStore - public virtual ValueTask SetPostLogoutRedirectUrisAsync(TApplication application!!, + public virtual ValueTask SetPostLogoutRedirectUrisAsync(TApplication application, ImmutableArray addresses, CancellationToken cancellationToken) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + if (addresses.IsDefaultOrEmpty) { application.PostLogoutRedirectUris = null; @@ -745,9 +888,14 @@ public class OpenIddictEntityFrameworkCoreApplicationStore - public virtual ValueTask SetPropertiesAsync(TApplication application!!, + public virtual ValueTask SetPropertiesAsync(TApplication application, ImmutableDictionary properties, CancellationToken cancellationToken) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + if (properties is not { Count: > 0 }) { application.Properties = null; @@ -779,9 +927,14 @@ public class OpenIddictEntityFrameworkCoreApplicationStore - public virtual ValueTask SetRedirectUrisAsync(TApplication application!!, + public virtual ValueTask SetRedirectUrisAsync(TApplication application, ImmutableArray addresses, CancellationToken cancellationToken) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + if (addresses.IsDefaultOrEmpty) { application.RedirectUris = null; @@ -812,8 +965,13 @@ public class OpenIddictEntityFrameworkCoreApplicationStore - public virtual ValueTask SetRequirementsAsync(TApplication application!!, ImmutableArray requirements, CancellationToken cancellationToken) + public virtual ValueTask SetRequirementsAsync(TApplication application, ImmutableArray requirements, CancellationToken cancellationToken) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + if (requirements.IsDefaultOrEmpty) { application.Requirements = null; @@ -844,8 +1002,13 @@ public class OpenIddictEntityFrameworkCoreApplicationStore - public virtual async ValueTask UpdateAsync(TApplication application!!, CancellationToken cancellationToken) + public virtual async ValueTask UpdateAsync(TApplication application, CancellationToken cancellationToken) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + Context.Attach(application); // Generate a new concurrency token and attach it diff --git a/src/OpenIddict.EntityFrameworkCore/Stores/OpenIddictEntityFrameworkCoreAuthorizationStore.cs b/src/OpenIddict.EntityFrameworkCore/Stores/OpenIddictEntityFrameworkCoreAuthorizationStore.cs index 9830d112..53174d07 100644 --- a/src/OpenIddict.EntityFrameworkCore/Stores/OpenIddictEntityFrameworkCoreAuthorizationStore.cs +++ b/src/OpenIddict.EntityFrameworkCore/Stores/OpenIddictEntityFrameworkCoreAuthorizationStore.cs @@ -30,7 +30,7 @@ public class OpenIddictEntityFrameworkCoreAuthorizationStore : public OpenIddictEntityFrameworkCoreAuthorizationStore( IMemoryCache cache, TContext context, - IOptionsMonitor options!!) + IOptionsMonitor options) : base(cache, context, options) { } @@ -51,7 +51,7 @@ public class OpenIddictEntityFrameworkCoreAuthorizationStore : public OpenIddictEntityFrameworkCoreAuthorizationStore( IMemoryCache cache, TContext context, - IOptionsMonitor options!!) + IOptionsMonitor options) : base(cache, context, options) { } @@ -73,13 +73,13 @@ public class OpenIddictEntityFrameworkCoreAuthorizationStore { public OpenIddictEntityFrameworkCoreAuthorizationStore( - IMemoryCache cache!!, - TContext context!!, - IOptionsMonitor options!!) + IMemoryCache cache, + TContext context, + IOptionsMonitor options) { - Cache = cache; - Context = context; - Options = options; + Cache = cache ?? throw new ArgumentNullException(nameof(cache)); + Context = context ?? throw new ArgumentNullException(nameof(context)); + Options = options ?? throw new ArgumentNullException(nameof(options)); } /// @@ -117,20 +117,37 @@ public class OpenIddictEntityFrameworkCoreAuthorizationStore await Authorizations.AsQueryable().LongCountAsync(cancellationToken); /// - public virtual async ValueTask CountAsync(Func, IQueryable> query!!, CancellationToken cancellationToken) - => await query(Authorizations).LongCountAsync(cancellationToken); + public virtual async ValueTask CountAsync(Func, IQueryable> query, CancellationToken cancellationToken) + { + if (query is null) + { + throw new ArgumentNullException(nameof(query)); + } + + return await query(Authorizations).LongCountAsync(cancellationToken); + } /// - public virtual async ValueTask CreateAsync(TAuthorization authorization!!, CancellationToken cancellationToken) + public virtual async ValueTask CreateAsync(TAuthorization authorization, CancellationToken cancellationToken) { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + Context.Add(authorization); await Context.SaveChangesAsync(cancellationToken); } /// - public virtual async ValueTask DeleteAsync(TAuthorization authorization!!, CancellationToken cancellationToken) + public virtual async ValueTask DeleteAsync(TAuthorization authorization, CancellationToken cancellationToken) { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + async ValueTask CreateTransactionAsync() { // Note: transactions that specify an explicit isolation level are only supported by @@ -409,8 +426,13 @@ public class OpenIddictEntityFrameworkCoreAuthorizationStore - public virtual async ValueTask GetApplicationIdAsync(TAuthorization authorization!!, CancellationToken cancellationToken) + public virtual async ValueTask GetApplicationIdAsync(TAuthorization authorization, CancellationToken cancellationToken) { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + // If the application is not attached to the authorization, try to load it manually. if (authorization.Application is null) { @@ -433,23 +455,54 @@ public class OpenIddictEntityFrameworkCoreAuthorizationStore public virtual async ValueTask GetAsync( - Func, TState, IQueryable> query!!, + Func, TState, IQueryable> query, TState state, CancellationToken cancellationToken) - => await query( + { + if (query is null) + { + throw new ArgumentNullException(nameof(query)); + } + + return await query( Authorizations.Include(authorization => authorization.Application) .AsTracking(), state).FirstOrDefaultAsync(cancellationToken); + } /// - public virtual ValueTask GetCreationDateAsync(TAuthorization authorization!!, CancellationToken cancellationToken) - => new(authorization.CreationDate is DateTime date ? DateTime.SpecifyKind(date, DateTimeKind.Utc) : null); + public virtual ValueTask GetCreationDateAsync(TAuthorization authorization, CancellationToken cancellationToken) + { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + + if (authorization.CreationDate is null) + { + return new(result: null); + } + + return new(DateTime.SpecifyKind(authorization.CreationDate.Value, DateTimeKind.Utc)); + } /// - public virtual ValueTask GetIdAsync(TAuthorization authorization!!, CancellationToken cancellationToken) - => new(ConvertIdentifierToString(authorization.Id)); + public virtual ValueTask GetIdAsync(TAuthorization authorization, CancellationToken cancellationToken) + { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + + return new(ConvertIdentifierToString(authorization.Id)); + } /// - public virtual ValueTask> GetPropertiesAsync(TAuthorization authorization!!, CancellationToken cancellationToken) + public virtual ValueTask> GetPropertiesAsync(TAuthorization authorization, CancellationToken cancellationToken) { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + if (string.IsNullOrEmpty(authorization.Properties)) { return new(ImmutableDictionary.Create()); @@ -478,8 +531,13 @@ public class OpenIddictEntityFrameworkCoreAuthorizationStore - public virtual ValueTask> GetScopesAsync(TAuthorization authorization!!, CancellationToken cancellationToken) + public virtual ValueTask> GetScopesAsync(TAuthorization authorization, CancellationToken cancellationToken) { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + if (string.IsNullOrEmpty(authorization.Scopes)) { return new(ImmutableArray.Create()); @@ -514,16 +572,37 @@ public class OpenIddictEntityFrameworkCoreAuthorizationStore - public virtual ValueTask GetStatusAsync(TAuthorization authorization!!, CancellationToken cancellationToken) - => new(authorization.Status); + public virtual ValueTask GetStatusAsync(TAuthorization authorization, CancellationToken cancellationToken) + { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + + return new(authorization.Status); + } /// - public virtual ValueTask GetSubjectAsync(TAuthorization authorization!!, CancellationToken cancellationToken) - => new(authorization.Subject); + public virtual ValueTask GetSubjectAsync(TAuthorization authorization, CancellationToken cancellationToken) + { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + + return new(authorization.Subject); + } /// - public virtual ValueTask GetTypeAsync(TAuthorization authorization!!, CancellationToken cancellationToken) - => new(authorization.Type); + public virtual ValueTask GetTypeAsync(TAuthorization authorization, CancellationToken cancellationToken) + { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + + return new(authorization.Type); + } /// public virtual ValueTask InstantiateAsync(CancellationToken cancellationToken) @@ -562,9 +641,14 @@ public class OpenIddictEntityFrameworkCoreAuthorizationStore public virtual IAsyncEnumerable ListAsync( - Func, TState, IQueryable> query!!, + Func, TState, IQueryable> query, TState state, CancellationToken cancellationToken) { + if (query is null) + { + throw new ArgumentNullException(nameof(query)); + } + return query( Authorizations.Include(authorization => authorization.Application) .AsTracking(), state).AsAsyncEnumerable(cancellationToken); @@ -662,9 +746,14 @@ public class OpenIddictEntityFrameworkCoreAuthorizationStore - public virtual async ValueTask SetApplicationIdAsync(TAuthorization authorization!!, + public virtual async ValueTask SetApplicationIdAsync(TAuthorization authorization, string? identifier, CancellationToken cancellationToken) { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + if (!string.IsNullOrEmpty(identifier)) { var key = ConvertIdentifierFromString(identifier); @@ -696,18 +785,28 @@ public class OpenIddictEntityFrameworkCoreAuthorizationStore - public virtual ValueTask SetCreationDateAsync(TAuthorization authorization!!, + public virtual ValueTask SetCreationDateAsync(TAuthorization authorization, DateTimeOffset? date, CancellationToken cancellationToken) { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + authorization.CreationDate = date?.UtcDateTime; return default; } /// - public virtual ValueTask SetPropertiesAsync(TAuthorization authorization!!, + public virtual ValueTask SetPropertiesAsync(TAuthorization authorization, ImmutableDictionary properties, CancellationToken cancellationToken) { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + if (properties is not { Count: > 0 }) { authorization.Properties = null; @@ -739,9 +838,14 @@ public class OpenIddictEntityFrameworkCoreAuthorizationStore - public virtual ValueTask SetScopesAsync(TAuthorization authorization!!, + public virtual ValueTask SetScopesAsync(TAuthorization authorization, ImmutableArray scopes, CancellationToken cancellationToken) { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + if (scopes.IsDefaultOrEmpty) { authorization.Scopes = null; @@ -772,35 +876,55 @@ public class OpenIddictEntityFrameworkCoreAuthorizationStore - public virtual ValueTask SetStatusAsync(TAuthorization authorization!!, + public virtual ValueTask SetStatusAsync(TAuthorization authorization, string? status, CancellationToken cancellationToken) { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + authorization.Status = status; return default; } /// - public virtual ValueTask SetSubjectAsync(TAuthorization authorization!!, + public virtual ValueTask SetSubjectAsync(TAuthorization authorization, string? subject, CancellationToken cancellationToken) { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + authorization.Subject = subject; return default; } /// - public virtual ValueTask SetTypeAsync(TAuthorization authorization!!, + public virtual ValueTask SetTypeAsync(TAuthorization authorization, string? type, CancellationToken cancellationToken) { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + authorization.Type = type; return default; } /// - public virtual async ValueTask UpdateAsync(TAuthorization authorization!!, CancellationToken cancellationToken) + public virtual async ValueTask UpdateAsync(TAuthorization authorization, CancellationToken cancellationToken) { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + Context.Attach(authorization); // Generate a new concurrency token and attach it diff --git a/src/OpenIddict.EntityFrameworkCore/Stores/OpenIddictEntityFrameworkCoreScopeStore.cs b/src/OpenIddict.EntityFrameworkCore/Stores/OpenIddictEntityFrameworkCoreScopeStore.cs index 12590ba0..bf21aa50 100644 --- a/src/OpenIddict.EntityFrameworkCore/Stores/OpenIddictEntityFrameworkCoreScopeStore.cs +++ b/src/OpenIddict.EntityFrameworkCore/Stores/OpenIddictEntityFrameworkCoreScopeStore.cs @@ -27,7 +27,7 @@ public class OpenIddictEntityFrameworkCoreScopeStore : OpenIddictEntit public OpenIddictEntityFrameworkCoreScopeStore( IMemoryCache cache, TContext context, - IOptionsMonitor options!!) + IOptionsMonitor options) : base(cache, context, options) { } @@ -45,7 +45,7 @@ public class OpenIddictEntityFrameworkCoreScopeStore : OpenIddic public OpenIddictEntityFrameworkCoreScopeStore( IMemoryCache cache, TContext context, - IOptionsMonitor options!!) + IOptionsMonitor options) : base(cache, context, options) { } @@ -63,13 +63,13 @@ public class OpenIddictEntityFrameworkCoreScopeStore : I where TKey : notnull, IEquatable { public OpenIddictEntityFrameworkCoreScopeStore( - IMemoryCache cache!!, - TContext context!!, - IOptionsMonitor options!!) + IMemoryCache cache, + TContext context, + IOptionsMonitor options) { - Cache = cache; - Context = context; - Options = options; + Cache = cache ?? throw new ArgumentNullException(nameof(cache)); + Context = context ?? throw new ArgumentNullException(nameof(context)); + Options = options ?? throw new ArgumentNullException(nameof(options)); } /// @@ -97,20 +97,37 @@ public class OpenIddictEntityFrameworkCoreScopeStore : I => await Scopes.AsQueryable().LongCountAsync(cancellationToken); /// - public virtual async ValueTask CountAsync(Func, IQueryable> query!!, CancellationToken cancellationToken) - => await query(Scopes).LongCountAsync(cancellationToken); + public virtual async ValueTask CountAsync(Func, IQueryable> query, CancellationToken cancellationToken) + { + if (query is null) + { + throw new ArgumentNullException(nameof(query)); + } + + return await query(Scopes).LongCountAsync(cancellationToken); + } /// - public virtual async ValueTask CreateAsync(TScope scope!!, CancellationToken cancellationToken) + public virtual async ValueTask CreateAsync(TScope scope, CancellationToken cancellationToken) { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + Scopes.Add(scope); await Context.SaveChangesAsync(cancellationToken); } /// - public virtual async ValueTask DeleteAsync(TScope scope!!, CancellationToken cancellationToken) + public virtual async ValueTask DeleteAsync(TScope scope, CancellationToken cancellationToken) { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + Context.Remove(scope); try @@ -159,7 +176,7 @@ public class OpenIddictEntityFrameworkCoreScopeStore : I public virtual IAsyncEnumerable FindByNamesAsync( ImmutableArray names, CancellationToken cancellationToken) { - if (names.Any(string.IsNullOrEmpty)) + if (names.Any(name => string.IsNullOrEmpty(name))) { throw new ArgumentException(SR.GetResourceString(SR.ID0203), nameof(names)); } @@ -207,17 +224,36 @@ public class OpenIddictEntityFrameworkCoreScopeStore : I /// public virtual async ValueTask GetAsync( - Func, TState, IQueryable> query!!, + Func, TState, IQueryable> query, TState state, CancellationToken cancellationToken) - => await query(Scopes.AsTracking(), state).FirstOrDefaultAsync(cancellationToken); + { + if (query is null) + { + throw new ArgumentNullException(nameof(query)); + } + + return await query(Scopes.AsTracking(), state).FirstOrDefaultAsync(cancellationToken); + } /// - public virtual ValueTask GetDescriptionAsync(TScope scope!!, CancellationToken cancellationToken) - => new(scope.Description); + public virtual ValueTask GetDescriptionAsync(TScope scope, CancellationToken cancellationToken) + { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + + return new(scope.Description); + } /// - public virtual ValueTask> GetDescriptionsAsync(TScope scope!!, CancellationToken cancellationToken) + public virtual ValueTask> GetDescriptionsAsync(TScope scope, CancellationToken cancellationToken) { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + if (string.IsNullOrEmpty(scope.Descriptions)) { return new(ImmutableDictionary.Create()); @@ -252,12 +288,24 @@ public class OpenIddictEntityFrameworkCoreScopeStore : I } /// - public virtual ValueTask GetDisplayNameAsync(TScope scope!!, CancellationToken cancellationToken) - => new(scope.DisplayName); + public virtual ValueTask GetDisplayNameAsync(TScope scope, CancellationToken cancellationToken) + { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + + return new(scope.DisplayName); + } /// - public virtual ValueTask> GetDisplayNamesAsync(TScope scope!!, CancellationToken cancellationToken) + public virtual ValueTask> GetDisplayNamesAsync(TScope scope, CancellationToken cancellationToken) { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + if (string.IsNullOrEmpty(scope.DisplayNames)) { return new(ImmutableDictionary.Create()); @@ -292,16 +340,35 @@ public class OpenIddictEntityFrameworkCoreScopeStore : I } /// - public virtual ValueTask GetIdAsync(TScope scope!!, CancellationToken cancellationToken) - => new(ConvertIdentifierToString(scope.Id)); + public virtual ValueTask GetIdAsync(TScope scope, CancellationToken cancellationToken) + { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + + return new(ConvertIdentifierToString(scope.Id)); + } /// - public virtual ValueTask GetNameAsync(TScope scope!!, CancellationToken cancellationToken) - => new(scope.Name); + public virtual ValueTask GetNameAsync(TScope scope, CancellationToken cancellationToken) + { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + + return new(scope.Name); + } /// - public virtual ValueTask> GetPropertiesAsync(TScope scope!!, CancellationToken cancellationToken) + public virtual ValueTask> GetPropertiesAsync(TScope scope, CancellationToken cancellationToken) { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + if (string.IsNullOrEmpty(scope.Properties)) { return new(ImmutableDictionary.Create()); @@ -330,8 +397,13 @@ public class OpenIddictEntityFrameworkCoreScopeStore : I } /// - public virtual ValueTask> GetResourcesAsync(TScope scope!!, CancellationToken cancellationToken) + public virtual ValueTask> GetResourcesAsync(TScope scope, CancellationToken cancellationToken) { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + if (string.IsNullOrEmpty(scope.Resources)) { return new(ImmutableArray.Create()); @@ -400,22 +472,39 @@ public class OpenIddictEntityFrameworkCoreScopeStore : I /// public virtual IAsyncEnumerable ListAsync( - Func, TState, IQueryable> query!!, + Func, TState, IQueryable> query, TState state, CancellationToken cancellationToken) - => query(Scopes.AsTracking(), state).AsAsyncEnumerable(cancellationToken); + { + if (query is null) + { + throw new ArgumentNullException(nameof(query)); + } + + return query(Scopes.AsTracking(), state).AsAsyncEnumerable(cancellationToken); + } /// - public virtual ValueTask SetDescriptionAsync(TScope scope!!, string? description, CancellationToken cancellationToken) + public virtual ValueTask SetDescriptionAsync(TScope scope, string? description, CancellationToken cancellationToken) { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + scope.Description = description; return default; } /// - public virtual ValueTask SetDescriptionsAsync(TScope scope!!, + public virtual ValueTask SetDescriptionsAsync(TScope scope, ImmutableDictionary descriptions, CancellationToken cancellationToken) { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + if (descriptions is not { Count: > 0 }) { scope.Descriptions = null; @@ -447,17 +536,27 @@ public class OpenIddictEntityFrameworkCoreScopeStore : I } /// - public virtual ValueTask SetDisplayNameAsync(TScope scope!!, string? name, CancellationToken cancellationToken) + public virtual ValueTask SetDisplayNameAsync(TScope scope, string? name, CancellationToken cancellationToken) { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + scope.DisplayName = name; return default; } /// - public virtual ValueTask SetDisplayNamesAsync(TScope scope!!, + public virtual ValueTask SetDisplayNamesAsync(TScope scope, ImmutableDictionary names, CancellationToken cancellationToken) { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + if (names is not { Count: > 0 }) { scope.DisplayNames = null; @@ -489,17 +588,27 @@ public class OpenIddictEntityFrameworkCoreScopeStore : I } /// - public virtual ValueTask SetNameAsync(TScope scope!!, string? name, CancellationToken cancellationToken) + public virtual ValueTask SetNameAsync(TScope scope, string? name, CancellationToken cancellationToken) { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + scope.Name = name; return default; } /// - public virtual ValueTask SetPropertiesAsync(TScope scope!!, + public virtual ValueTask SetPropertiesAsync(TScope scope, ImmutableDictionary properties, CancellationToken cancellationToken) { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + if (properties is not { Count: > 0 }) { scope.Properties = null; @@ -531,8 +640,13 @@ public class OpenIddictEntityFrameworkCoreScopeStore : I } /// - public virtual ValueTask SetResourcesAsync(TScope scope!!, ImmutableArray resources, CancellationToken cancellationToken) + public virtual ValueTask SetResourcesAsync(TScope scope, ImmutableArray resources, CancellationToken cancellationToken) { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + if (resources.IsDefaultOrEmpty) { scope.Resources = null; @@ -563,8 +677,13 @@ public class OpenIddictEntityFrameworkCoreScopeStore : I } /// - public virtual async ValueTask UpdateAsync(TScope scope!!, CancellationToken cancellationToken) + public virtual async ValueTask UpdateAsync(TScope scope, CancellationToken cancellationToken) { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + Context.Attach(scope); // Generate a new concurrency token and attach it diff --git a/src/OpenIddict.EntityFrameworkCore/Stores/OpenIddictEntityFrameworkCoreTokenStore.cs b/src/OpenIddict.EntityFrameworkCore/Stores/OpenIddictEntityFrameworkCoreTokenStore.cs index 881d6d17..50ef2831 100644 --- a/src/OpenIddict.EntityFrameworkCore/Stores/OpenIddictEntityFrameworkCoreTokenStore.cs +++ b/src/OpenIddict.EntityFrameworkCore/Stores/OpenIddictEntityFrameworkCoreTokenStore.cs @@ -29,7 +29,7 @@ public class OpenIddictEntityFrameworkCoreTokenStore : public OpenIddictEntityFrameworkCoreTokenStore( IMemoryCache cache, TContext context, - IOptionsMonitor options!!) + IOptionsMonitor options) : base(cache, context, options) { } @@ -50,7 +50,7 @@ public class OpenIddictEntityFrameworkCoreTokenStore : public OpenIddictEntityFrameworkCoreTokenStore( IMemoryCache cache, TContext context, - IOptionsMonitor options!!) + IOptionsMonitor options) : base(cache, context, options) { } @@ -72,13 +72,13 @@ public class OpenIddictEntityFrameworkCoreTokenStore { public OpenIddictEntityFrameworkCoreTokenStore( - IMemoryCache cache!!, - TContext context!!, - IOptionsMonitor options!!) + IMemoryCache cache, + TContext context, + IOptionsMonitor options) { - Cache = cache; - Context = context; - Options = options; + Cache = cache ?? throw new ArgumentNullException(nameof(cache)); + Context = context ?? throw new ArgumentNullException(nameof(context)); + Options = options ?? throw new ArgumentNullException(nameof(options)); } /// @@ -116,20 +116,37 @@ public class OpenIddictEntityFrameworkCoreTokenStore await Tokens.AsQueryable().LongCountAsync(cancellationToken); /// - public virtual async ValueTask CountAsync(Func, IQueryable> query!!, CancellationToken cancellationToken) - => await query(Tokens).LongCountAsync(cancellationToken); + public virtual async ValueTask CountAsync(Func, IQueryable> query, CancellationToken cancellationToken) + { + if (query is null) + { + throw new ArgumentNullException(nameof(query)); + } + + return await query(Tokens).LongCountAsync(cancellationToken); + } /// - public virtual async ValueTask CreateAsync(TToken token!!, CancellationToken cancellationToken) + public virtual async ValueTask CreateAsync(TToken token, CancellationToken cancellationToken) { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + Context.Add(token); await Context.SaveChangesAsync(cancellationToken); } /// - public virtual async ValueTask DeleteAsync(TToken token!!, CancellationToken cancellationToken) + public virtual async ValueTask DeleteAsync(TToken token, CancellationToken cancellationToken) { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + Context.Remove(token); try @@ -333,8 +350,13 @@ public class OpenIddictEntityFrameworkCoreTokenStore - public virtual async ValueTask GetApplicationIdAsync(TToken token!!, CancellationToken cancellationToken) + public virtual async ValueTask GetApplicationIdAsync(TToken token, CancellationToken cancellationToken) { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + // If the application is not attached to the token, try to load it manually. if (token.Application is null) { @@ -357,15 +379,27 @@ public class OpenIddictEntityFrameworkCoreTokenStore public virtual async ValueTask GetAsync( - Func, TState, IQueryable> query!!, + Func, TState, IQueryable> query, TState state, CancellationToken cancellationToken) - => await query(Tokens.Include(token => token.Application) + { + if (query is null) + { + throw new ArgumentNullException(nameof(query)); + } + + return await query(Tokens.Include(token => token.Application) .Include(token => token.Authorization) .AsTracking(), state).FirstOrDefaultAsync(cancellationToken); + } /// - public virtual async ValueTask GetAuthorizationIdAsync(TToken token!!, CancellationToken cancellationToken) + public virtual async ValueTask GetAuthorizationIdAsync(TToken token, CancellationToken cancellationToken) { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + // If the authorization is not attached to the token, try to load it manually. if (token.Authorization is null) { @@ -387,24 +421,67 @@ public class OpenIddictEntityFrameworkCoreTokenStore - public virtual ValueTask GetCreationDateAsync(TToken token!!, CancellationToken cancellationToken) - => new(token.CreationDate is DateTime date ? DateTime.SpecifyKind(date, DateTimeKind.Utc) : null); + public virtual ValueTask GetCreationDateAsync(TToken token, CancellationToken cancellationToken) + { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + + if (token.CreationDate is null) + { + return new(result: null); + } + + return new(DateTime.SpecifyKind(token.CreationDate.Value, DateTimeKind.Utc)); + } /// - public virtual ValueTask GetExpirationDateAsync(TToken token!!, CancellationToken cancellationToken) - => new(token.ExpirationDate is DateTime date ? DateTime.SpecifyKind(date, DateTimeKind.Utc) : null); + public virtual ValueTask GetExpirationDateAsync(TToken token, CancellationToken cancellationToken) + { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + + if (token.ExpirationDate is null) + { + return new(result: null); + } + + return new(DateTime.SpecifyKind(token.ExpirationDate.Value, DateTimeKind.Utc)); + } /// - public virtual ValueTask GetIdAsync(TToken token!!, CancellationToken cancellationToken) - => new(ConvertIdentifierToString(token.Id)); + public virtual ValueTask GetIdAsync(TToken token, CancellationToken cancellationToken) + { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + + return new(ConvertIdentifierToString(token.Id)); + } /// - public virtual ValueTask GetPayloadAsync(TToken token!!, CancellationToken cancellationToken) - => new(token.Payload); + public virtual ValueTask GetPayloadAsync(TToken token, CancellationToken cancellationToken) + { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + + return new(token.Payload); + } /// - public virtual ValueTask> GetPropertiesAsync(TToken token!!, CancellationToken cancellationToken) + public virtual ValueTask> GetPropertiesAsync(TToken token, CancellationToken cancellationToken) { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + if (string.IsNullOrEmpty(token.Properties)) { return new(ImmutableDictionary.Create()); @@ -433,24 +510,64 @@ public class OpenIddictEntityFrameworkCoreTokenStore - public virtual ValueTask GetRedemptionDateAsync(TToken token!!, CancellationToken cancellationToken) - => new(token.RedemptionDate is DateTime date ? DateTime.SpecifyKind(date, DateTimeKind.Utc) : null); + public virtual ValueTask GetRedemptionDateAsync(TToken token, CancellationToken cancellationToken) + { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + + if (token.RedemptionDate is null) + { + return new(result: null); + } + + return new(DateTime.SpecifyKind(token.RedemptionDate.Value, DateTimeKind.Utc)); + } /// - public virtual ValueTask GetReferenceIdAsync(TToken token!!, CancellationToken cancellationToken) - => new(token.ReferenceId); + public virtual ValueTask GetReferenceIdAsync(TToken token, CancellationToken cancellationToken) + { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + + return new(token.ReferenceId); + } /// - public virtual ValueTask GetStatusAsync(TToken token!!, CancellationToken cancellationToken) - => new(token.Status); + public virtual ValueTask GetStatusAsync(TToken token, CancellationToken cancellationToken) + { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + + return new(token.Status); + } /// - public virtual ValueTask GetSubjectAsync(TToken token!!, CancellationToken cancellationToken) - => new(token.Subject); + public virtual ValueTask GetSubjectAsync(TToken token, CancellationToken cancellationToken) + { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + + return new(token.Subject); + } /// - public virtual ValueTask GetTypeAsync(TToken token!!, CancellationToken cancellationToken) - => new(token.Type); + public virtual ValueTask GetTypeAsync(TToken token, CancellationToken cancellationToken) + { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + + return new(token.Type); + } /// public virtual ValueTask InstantiateAsync(CancellationToken cancellationToken) @@ -490,12 +607,19 @@ public class OpenIddictEntityFrameworkCoreTokenStore public virtual IAsyncEnumerable ListAsync( - Func, TState, IQueryable> query!!, + Func, TState, IQueryable> query, TState state, CancellationToken cancellationToken) - => query( + { + if (query is null) + { + throw new ArgumentNullException(nameof(query)); + } + + return query( Tokens.Include(token => token.Application) .Include(token => token.Authorization) .AsTracking(), state).AsAsyncEnumerable(cancellationToken); + } /// public virtual async ValueTask PruneAsync(DateTimeOffset threshold, CancellationToken cancellationToken) @@ -586,8 +710,13 @@ public class OpenIddictEntityFrameworkCoreTokenStore - public virtual async ValueTask SetApplicationIdAsync(TToken token!!, string? identifier, CancellationToken cancellationToken) + public virtual async ValueTask SetApplicationIdAsync(TToken token, string? identifier, CancellationToken cancellationToken) { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + if (!string.IsNullOrEmpty(identifier)) { var key = ConvertIdentifierFromString(identifier); @@ -619,8 +748,13 @@ public class OpenIddictEntityFrameworkCoreTokenStore - public virtual async ValueTask SetAuthorizationIdAsync(TToken token!!, string? identifier, CancellationToken cancellationToken) + public virtual async ValueTask SetAuthorizationIdAsync(TToken token, string? identifier, CancellationToken cancellationToken) { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + if (!string.IsNullOrEmpty(identifier)) { var key = ConvertIdentifierFromString(identifier); @@ -652,33 +786,53 @@ public class OpenIddictEntityFrameworkCoreTokenStore - public virtual ValueTask SetCreationDateAsync(TToken token!!, DateTimeOffset? date, CancellationToken cancellationToken) + public virtual ValueTask SetCreationDateAsync(TToken token, DateTimeOffset? date, CancellationToken cancellationToken) { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + token.CreationDate = date?.UtcDateTime; return default; } /// - public virtual ValueTask SetExpirationDateAsync(TToken token!!, DateTimeOffset? date, CancellationToken cancellationToken) + public virtual ValueTask SetExpirationDateAsync(TToken token, DateTimeOffset? date, CancellationToken cancellationToken) { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + token.ExpirationDate = date?.UtcDateTime; return default; } /// - public virtual ValueTask SetPayloadAsync(TToken token!!, string? payload, CancellationToken cancellationToken) + public virtual ValueTask SetPayloadAsync(TToken token, string? payload, CancellationToken cancellationToken) { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + token.Payload = payload; return default; } /// - public virtual ValueTask SetPropertiesAsync(TToken token!!, + public virtual ValueTask SetPropertiesAsync(TToken token, ImmutableDictionary properties, CancellationToken cancellationToken) { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + if (properties is not { Count: > 0 }) { token.Properties = null; @@ -710,48 +864,78 @@ public class OpenIddictEntityFrameworkCoreTokenStore - public virtual ValueTask SetRedemptionDateAsync(TToken token!!, DateTimeOffset? date, CancellationToken cancellationToken) + public virtual ValueTask SetRedemptionDateAsync(TToken token, DateTimeOffset? date, CancellationToken cancellationToken) { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + token.RedemptionDate = date?.UtcDateTime; return default; } /// - public virtual ValueTask SetReferenceIdAsync(TToken token!!, string? identifier, CancellationToken cancellationToken) + public virtual ValueTask SetReferenceIdAsync(TToken token, string? identifier, CancellationToken cancellationToken) { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + token.ReferenceId = identifier; return default; } /// - public virtual ValueTask SetStatusAsync(TToken token!!, string? status, CancellationToken cancellationToken) + public virtual ValueTask SetStatusAsync(TToken token, string? status, CancellationToken cancellationToken) { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + token.Status = status; return default; } /// - public virtual ValueTask SetSubjectAsync(TToken token!!, string? subject, CancellationToken cancellationToken) + public virtual ValueTask SetSubjectAsync(TToken token, string? subject, CancellationToken cancellationToken) { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + token.Subject = subject; return default; } /// - public virtual ValueTask SetTypeAsync(TToken token!!, string? type, CancellationToken cancellationToken) + public virtual ValueTask SetTypeAsync(TToken token, string? type, CancellationToken cancellationToken) { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + token.Type = type; return default; } /// - public virtual async ValueTask UpdateAsync(TToken token!!, CancellationToken cancellationToken) + public virtual async ValueTask UpdateAsync(TToken token, CancellationToken cancellationToken) { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + Context.Attach(token); // Generate a new concurrency token and attach it diff --git a/src/OpenIddict.MongoDb/OpenIddictMongoDbBuilder.cs b/src/OpenIddict.MongoDb/OpenIddictMongoDbBuilder.cs index 185e7ad4..f6fac7bd 100644 --- a/src/OpenIddict.MongoDb/OpenIddictMongoDbBuilder.cs +++ b/src/OpenIddict.MongoDb/OpenIddictMongoDbBuilder.cs @@ -20,8 +20,8 @@ public class OpenIddictMongoDbBuilder /// Initializes a new instance of . /// /// The services collection. - public OpenIddictMongoDbBuilder(IServiceCollection services!!) - => Services = services; + public OpenIddictMongoDbBuilder(IServiceCollection services) + => Services = services ?? throw new ArgumentNullException(nameof(services)); /// /// Gets the services collection. @@ -35,8 +35,13 @@ public class OpenIddictMongoDbBuilder /// The delegate used to configure the OpenIddict options. /// This extension can be safely called multiple times. /// The . - public OpenIddictMongoDbBuilder Configure(Action configuration!!) + public OpenIddictMongoDbBuilder Configure(Action configuration) { + if (configuration is null) + { + throw new ArgumentNullException(nameof(configuration)); + } + Services.Configure(configuration); return this; @@ -156,8 +161,13 @@ public class OpenIddictMongoDbBuilder /// /// The . /// The . - public OpenIddictMongoDbBuilder UseDatabase(IMongoDatabase database!!) + public OpenIddictMongoDbBuilder UseDatabase(IMongoDatabase database) { + if (database is null) + { + throw new ArgumentNullException(nameof(database)); + } + return Configure(options => options.Database = database); } diff --git a/src/OpenIddict.MongoDb/OpenIddictMongoDbContext.cs b/src/OpenIddict.MongoDb/OpenIddictMongoDbContext.cs index d589f56b..35b10d9a 100644 --- a/src/OpenIddict.MongoDb/OpenIddictMongoDbContext.cs +++ b/src/OpenIddict.MongoDb/OpenIddictMongoDbContext.cs @@ -16,11 +16,11 @@ public class OpenIddictMongoDbContext : IOpenIddictMongoDbContext private readonly IServiceProvider _provider; public OpenIddictMongoDbContext( - IOptionsMonitor options!!, - IServiceProvider provider!!) + IOptionsMonitor options, + IServiceProvider provider) { - _options = options; - _provider = provider; + _options = options ?? throw new ArgumentNullException(nameof(options)); + _provider = provider ?? throw new ArgumentNullException(nameof(provider)); } /// diff --git a/src/OpenIddict.MongoDb/OpenIddictMongoDbExtensions.cs b/src/OpenIddict.MongoDb/OpenIddictMongoDbExtensions.cs index 154b9a9e..6e33434c 100644 --- a/src/OpenIddict.MongoDb/OpenIddictMongoDbExtensions.cs +++ b/src/OpenIddict.MongoDb/OpenIddictMongoDbExtensions.cs @@ -22,8 +22,13 @@ public static class OpenIddictMongoDbExtensions /// The services builder used by OpenIddict to register new services. /// This extension can be safely called multiple times. /// The . - public static OpenIddictMongoDbBuilder UseMongoDb(this OpenIddictCoreBuilder builder!!) + public static OpenIddictMongoDbBuilder UseMongoDb(this OpenIddictCoreBuilder builder) { + if (builder is null) + { + throw new ArgumentNullException(nameof(builder)); + } + // Note: Mongo uses simple binary comparison checks by default so the additional // query filtering applied by the default OpenIddict managers can be safely disabled. builder.DisableAdditionalFiltering(); @@ -59,8 +64,18 @@ public static class OpenIddictMongoDbExtensions /// This extension can be safely called multiple times. /// The . public static OpenIddictCoreBuilder UseMongoDb( - this OpenIddictCoreBuilder builder!!, Action configuration!!) + this OpenIddictCoreBuilder builder, Action configuration) { + if (builder is null) + { + throw new ArgumentNullException(nameof(builder)); + } + + if (configuration is null) + { + throw new ArgumentNullException(nameof(configuration)); + } + configuration(builder.UseMongoDb()); return builder; diff --git a/src/OpenIddict.MongoDb/OpenIddictMongoDbHelpers.cs b/src/OpenIddict.MongoDb/OpenIddictMongoDbHelpers.cs index e2f29d81..d0d38490 100644 --- a/src/OpenIddict.MongoDb/OpenIddictMongoDbHelpers.cs +++ b/src/OpenIddict.MongoDb/OpenIddictMongoDbHelpers.cs @@ -20,8 +20,13 @@ internal static class OpenIddictMongoDbHelpers /// The query source. /// The that can be used to abort the operation. /// The streamed async enumeration containing the results. - internal static IAsyncEnumerable ToAsyncEnumerable(this IAsyncCursorSource source!!, CancellationToken cancellationToken) + internal static IAsyncEnumerable ToAsyncEnumerable(this IAsyncCursorSource source, CancellationToken cancellationToken) { + if (source is null) + { + throw new ArgumentNullException(nameof(source)); + } + return ExecuteAsync(source, cancellationToken); static async IAsyncEnumerable ExecuteAsync(IAsyncCursorSource source, [EnumeratorCancellation] CancellationToken cancellationToken) @@ -45,6 +50,13 @@ internal static class OpenIddictMongoDbHelpers /// The query source. /// The that can be used to abort the operation. /// The streamed async enumeration containing the results. - internal static IAsyncEnumerable ToAsyncEnumerable(this IQueryable source!!, CancellationToken cancellationToken) - => ((IAsyncCursorSource) source).ToAsyncEnumerable(cancellationToken); + internal static IAsyncEnumerable ToAsyncEnumerable(this IQueryable source, CancellationToken cancellationToken) + { + if (source is null) + { + throw new ArgumentNullException(nameof(source)); + } + + return ((IAsyncCursorSource) source).ToAsyncEnumerable(cancellationToken); + } } diff --git a/src/OpenIddict.MongoDb/Resolvers/OpenIddictMongoDbApplicationStoreResolver.cs b/src/OpenIddict.MongoDb/Resolvers/OpenIddictMongoDbApplicationStoreResolver.cs index 9a1770a7..294f1c99 100644 --- a/src/OpenIddict.MongoDb/Resolvers/OpenIddictMongoDbApplicationStoreResolver.cs +++ b/src/OpenIddict.MongoDb/Resolvers/OpenIddictMongoDbApplicationStoreResolver.cs @@ -18,8 +18,8 @@ public class OpenIddictMongoDbApplicationStoreResolver : IOpenIddictApplicationS private readonly ConcurrentDictionary _cache = new ConcurrentDictionary(); private readonly IServiceProvider _provider; - public OpenIddictMongoDbApplicationStoreResolver(IServiceProvider provider!!) - => _provider = provider; + public OpenIddictMongoDbApplicationStoreResolver(IServiceProvider provider) + => _provider = provider ?? throw new ArgumentNullException(nameof(provider)); /// /// Returns an application store compatible with the specified application type or throws an diff --git a/src/OpenIddict.MongoDb/Resolvers/OpenIddictMongoDbAuthorizationStoreResolver.cs b/src/OpenIddict.MongoDb/Resolvers/OpenIddictMongoDbAuthorizationStoreResolver.cs index 73e0788f..2ed07560 100644 --- a/src/OpenIddict.MongoDb/Resolvers/OpenIddictMongoDbAuthorizationStoreResolver.cs +++ b/src/OpenIddict.MongoDb/Resolvers/OpenIddictMongoDbAuthorizationStoreResolver.cs @@ -18,8 +18,8 @@ public class OpenIddictMongoDbAuthorizationStoreResolver : IOpenIddictAuthorizat private readonly ConcurrentDictionary _cache = new ConcurrentDictionary(); private readonly IServiceProvider _provider; - public OpenIddictMongoDbAuthorizationStoreResolver(IServiceProvider provider!!) - => _provider = provider; + public OpenIddictMongoDbAuthorizationStoreResolver(IServiceProvider provider) + => _provider = provider ?? throw new ArgumentNullException(nameof(provider)); /// /// Returns an authorization store compatible with the specified authorization type or throws an diff --git a/src/OpenIddict.MongoDb/Resolvers/OpenIddictMongoDbScopeStoreResolver.cs b/src/OpenIddict.MongoDb/Resolvers/OpenIddictMongoDbScopeStoreResolver.cs index c2b8edd1..b7490090 100644 --- a/src/OpenIddict.MongoDb/Resolvers/OpenIddictMongoDbScopeStoreResolver.cs +++ b/src/OpenIddict.MongoDb/Resolvers/OpenIddictMongoDbScopeStoreResolver.cs @@ -18,8 +18,8 @@ public class OpenIddictMongoDbScopeStoreResolver : IOpenIddictScopeStoreResolver private readonly ConcurrentDictionary _cache = new ConcurrentDictionary(); private readonly IServiceProvider _provider; - public OpenIddictMongoDbScopeStoreResolver(IServiceProvider provider!!) - => _provider = provider; + public OpenIddictMongoDbScopeStoreResolver(IServiceProvider provider) + => _provider = provider ?? throw new ArgumentNullException(nameof(provider)); /// /// Returns a scope store compatible with the specified scope type or throws an diff --git a/src/OpenIddict.MongoDb/Resolvers/OpenIddictMongoDbTokenStoreResolver.cs b/src/OpenIddict.MongoDb/Resolvers/OpenIddictMongoDbTokenStoreResolver.cs index 60b1c23a..8230915e 100644 --- a/src/OpenIddict.MongoDb/Resolvers/OpenIddictMongoDbTokenStoreResolver.cs +++ b/src/OpenIddict.MongoDb/Resolvers/OpenIddictMongoDbTokenStoreResolver.cs @@ -18,8 +18,8 @@ public class OpenIddictMongoDbTokenStoreResolver : IOpenIddictTokenStoreResolver private readonly ConcurrentDictionary _cache = new ConcurrentDictionary(); private readonly IServiceProvider _provider; - public OpenIddictMongoDbTokenStoreResolver(IServiceProvider provider!!) - => _provider = provider; + public OpenIddictMongoDbTokenStoreResolver(IServiceProvider provider) + => _provider = provider ?? throw new ArgumentNullException(nameof(provider)); /// /// Returns a token store compatible with the specified token type or throws an diff --git a/src/OpenIddict.MongoDb/Stores/OpenIddictMongoDbApplicationStore.cs b/src/OpenIddict.MongoDb/Stores/OpenIddictMongoDbApplicationStore.cs index 2b398f79..f4122b48 100644 --- a/src/OpenIddict.MongoDb/Stores/OpenIddictMongoDbApplicationStore.cs +++ b/src/OpenIddict.MongoDb/Stores/OpenIddictMongoDbApplicationStore.cs @@ -23,11 +23,11 @@ public class OpenIddictMongoDbApplicationStore : IOpenIddictApplic where TApplication : OpenIddictMongoDbApplication { public OpenIddictMongoDbApplicationStore( - IOpenIddictMongoDbContext context!!, - IOptionsMonitor options!!) + IOpenIddictMongoDbContext context, + IOptionsMonitor options) { - Context = context; - Options = options; + Context = context ?? throw new ArgumentNullException(nameof(context)); + Options = options ?? throw new ArgumentNullException(nameof(options)); } /// @@ -51,8 +51,13 @@ public class OpenIddictMongoDbApplicationStore : IOpenIddictApplic /// public virtual async ValueTask CountAsync( - Func, IQueryable> query!!, CancellationToken cancellationToken) + Func, IQueryable> query, CancellationToken cancellationToken) { + if (query is null) + { + throw new ArgumentNullException(nameof(query)); + } + var database = await Context.GetDatabaseAsync(cancellationToken); var collection = database.GetCollection(Options.CurrentValue.ApplicationsCollectionName); @@ -60,8 +65,13 @@ public class OpenIddictMongoDbApplicationStore : IOpenIddictApplic } /// - public virtual async ValueTask CreateAsync(TApplication application!!, CancellationToken cancellationToken) + public virtual async ValueTask CreateAsync(TApplication application, CancellationToken cancellationToken) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + var database = await Context.GetDatabaseAsync(cancellationToken); var collection = database.GetCollection(Options.CurrentValue.ApplicationsCollectionName); @@ -69,8 +79,13 @@ public class OpenIddictMongoDbApplicationStore : IOpenIddictApplic } /// - public virtual async ValueTask DeleteAsync(TApplication application!!, CancellationToken cancellationToken) + public virtual async ValueTask DeleteAsync(TApplication application, CancellationToken cancellationToken) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + var database = await Context.GetDatabaseAsync(cancellationToken); var collection = database.GetCollection(Options.CurrentValue.ApplicationsCollectionName); @@ -120,7 +135,8 @@ public class OpenIddictMongoDbApplicationStore : IOpenIddictApplic } /// - public virtual IAsyncEnumerable FindByPostLogoutRedirectUriAsync(string address, CancellationToken cancellationToken) + public virtual IAsyncEnumerable FindByPostLogoutRedirectUriAsync( + string address, CancellationToken cancellationToken) { if (string.IsNullOrEmpty(address)) { @@ -143,7 +159,8 @@ public class OpenIddictMongoDbApplicationStore : IOpenIddictApplic } /// - public virtual IAsyncEnumerable FindByRedirectUriAsync(string address, CancellationToken cancellationToken) + public virtual IAsyncEnumerable FindByRedirectUriAsync( + string address, CancellationToken cancellationToken) { if (string.IsNullOrEmpty(address)) { @@ -167,9 +184,14 @@ public class OpenIddictMongoDbApplicationStore : IOpenIddictApplic /// public virtual async ValueTask GetAsync( - Func, TState, IQueryable> query!!, + Func, TState, IQueryable> query, TState state, CancellationToken cancellationToken) { + if (query is null) + { + throw new ArgumentNullException(nameof(query)); + } + var database = await Context.GetDatabaseAsync(cancellationToken); var collection = database.GetCollection(Options.CurrentValue.ApplicationsCollectionName); @@ -177,44 +199,129 @@ public class OpenIddictMongoDbApplicationStore : IOpenIddictApplic } /// - public virtual ValueTask GetClientIdAsync(TApplication application!!, CancellationToken cancellationToken) - => new(application.ClientId); + public virtual ValueTask GetClientIdAsync(TApplication application, CancellationToken cancellationToken) + { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + + return new(application.ClientId); + } /// - public virtual ValueTask GetClientSecretAsync(TApplication application!!, CancellationToken cancellationToken) - => new(application.ClientSecret); + public virtual ValueTask GetClientSecretAsync(TApplication application, CancellationToken cancellationToken) + { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + + return new(application.ClientSecret); + } /// - public virtual ValueTask GetClientTypeAsync(TApplication application!!, CancellationToken cancellationToken) - => new(application.Type); + public virtual ValueTask GetClientTypeAsync(TApplication application, CancellationToken cancellationToken) + { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + + return new(application.Type); + } /// - public virtual ValueTask GetConsentTypeAsync(TApplication application!!, CancellationToken cancellationToken) - => new(application.ConsentType); + public virtual ValueTask GetConsentTypeAsync(TApplication application, CancellationToken cancellationToken) + { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + + return new(application.ConsentType); + } /// - public virtual ValueTask GetDisplayNameAsync(TApplication application!!, CancellationToken cancellationToken) - => new(application.DisplayName); + public virtual ValueTask GetDisplayNameAsync(TApplication application, CancellationToken cancellationToken) + { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + + return new(application.DisplayName); + } /// - public virtual ValueTask> GetDisplayNamesAsync(TApplication application!!, CancellationToken cancellationToken) - => new(application.DisplayNames is { Count: > 0 } names ? names.ToImmutableDictionary() : ImmutableDictionary.Create()); + public virtual ValueTask> GetDisplayNamesAsync(TApplication application, CancellationToken cancellationToken) + { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + + if (application.DisplayNames is null || application.DisplayNames.Count == 0) + { + return new(ImmutableDictionary.Create()); + } + + return new(application.DisplayNames.ToImmutableDictionary()); + } /// - public virtual ValueTask GetIdAsync(TApplication application!!, CancellationToken cancellationToken) - => new(application.Id.ToString()); + public virtual ValueTask GetIdAsync(TApplication application, CancellationToken cancellationToken) + { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + + return new(application.Id.ToString()); + } /// - public virtual ValueTask> GetPermissionsAsync(TApplication application!!, CancellationToken cancellationToken) - => new(application.Permissions is { Count: > 0 } permissions ? permissions.ToImmutableArray() : ImmutableArray.Create()); + public virtual ValueTask> GetPermissionsAsync( + TApplication application, CancellationToken cancellationToken) + { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + + if (application.Permissions is null || application.Permissions.Count == 0) + { + return new(ImmutableArray.Create()); + } + + return new(application.Permissions.ToImmutableArray()); + } /// - public virtual ValueTask> GetPostLogoutRedirectUrisAsync(TApplication application!!, CancellationToken cancellationToken) - => new(application.PostLogoutRedirectUris is { Count: > 0 } addresses ? addresses.ToImmutableArray() : ImmutableArray.Create()); + public virtual ValueTask> GetPostLogoutRedirectUrisAsync( + TApplication application, CancellationToken cancellationToken) + { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + + if (application.PostLogoutRedirectUris is null || application.PostLogoutRedirectUris.Count == 0) + { + return new(ImmutableArray.Create()); + } + + return new(application.PostLogoutRedirectUris.ToImmutableArray()); + } /// - public virtual ValueTask> GetPropertiesAsync(TApplication application!!, CancellationToken cancellationToken) + public virtual ValueTask> GetPropertiesAsync(TApplication application, CancellationToken cancellationToken) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + if (application.Properties is null) { return new(ImmutableDictionary.Create()); @@ -232,12 +339,37 @@ public class OpenIddictMongoDbApplicationStore : IOpenIddictApplic } /// - public virtual ValueTask> GetRedirectUrisAsync(TApplication application!!, CancellationToken cancellationToken) - => new(application.RedirectUris is { Count: > 0 } addresses ? addresses.ToImmutableArray() : ImmutableArray.Create()); + public virtual ValueTask> GetRedirectUrisAsync( + TApplication application, CancellationToken cancellationToken) + { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + + if (application.RedirectUris is null || application.RedirectUris.Count == 0) + { + return new(ImmutableArray.Create()); + } + + return new(application.RedirectUris.ToImmutableArray()); + } /// - public virtual ValueTask> GetRequirementsAsync(TApplication application!!, CancellationToken cancellationToken) - => new(application.Requirements is { Count: > 0 } requirements ? requirements.ToImmutableArray() : ImmutableArray.Create()); + public virtual ValueTask> GetRequirementsAsync(TApplication application, CancellationToken cancellationToken) + { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + + if (application.Requirements is null || application.Requirements.Count == 0) + { + return new(ImmutableArray.Create()); + } + + return new(application.Requirements.ToImmutableArray()); + } /// public virtual ValueTask InstantiateAsync(CancellationToken cancellationToken) @@ -281,9 +413,14 @@ public class OpenIddictMongoDbApplicationStore : IOpenIddictApplic /// public virtual IAsyncEnumerable ListAsync( - Func, TState, IQueryable> query!!, + Func, TState, IQueryable> query, TState state, CancellationToken cancellationToken) { + if (query is null) + { + throw new ArgumentNullException(nameof(query)); + } + return ExecuteAsync(cancellationToken); async IAsyncEnumerable ExecuteAsync([EnumeratorCancellation] CancellationToken cancellationToken) @@ -299,62 +436,97 @@ public class OpenIddictMongoDbApplicationStore : IOpenIddictApplic } /// - public virtual ValueTask SetClientIdAsync(TApplication application!!, + public virtual ValueTask SetClientIdAsync(TApplication application, string? identifier, CancellationToken cancellationToken) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + application.ClientId = identifier; return default; } /// - public virtual ValueTask SetClientSecretAsync(TApplication application!!, + public virtual ValueTask SetClientSecretAsync(TApplication application, string? secret, CancellationToken cancellationToken) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + application.ClientSecret = secret; return default; } /// - public virtual ValueTask SetClientTypeAsync(TApplication application!!, + public virtual ValueTask SetClientTypeAsync(TApplication application, string? type, CancellationToken cancellationToken) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + application.Type = type; return default; } /// - public virtual ValueTask SetConsentTypeAsync(TApplication application!!, + public virtual ValueTask SetConsentTypeAsync(TApplication application, string? type, CancellationToken cancellationToken) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + application.ConsentType = type; return default; } /// - public virtual ValueTask SetDisplayNameAsync(TApplication application!!, + public virtual ValueTask SetDisplayNameAsync(TApplication application, string? name, CancellationToken cancellationToken) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + application.DisplayName = name; return default; } /// - public virtual ValueTask SetDisplayNamesAsync(TApplication application!!, + public virtual ValueTask SetDisplayNamesAsync(TApplication application, ImmutableDictionary names, CancellationToken cancellationToken) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + application.DisplayNames = names; return default; } /// - public virtual ValueTask SetPermissionsAsync(TApplication application!!, ImmutableArray permissions, CancellationToken cancellationToken) + public virtual ValueTask SetPermissionsAsync(TApplication application, ImmutableArray permissions, CancellationToken cancellationToken) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + if (permissions.IsDefaultOrEmpty) { application.Permissions = ImmutableList.Create(); @@ -368,9 +540,14 @@ public class OpenIddictMongoDbApplicationStore : IOpenIddictApplic } /// - public virtual ValueTask SetPostLogoutRedirectUrisAsync(TApplication application!!, + public virtual ValueTask SetPostLogoutRedirectUrisAsync(TApplication application, ImmutableArray addresses, CancellationToken cancellationToken) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + if (addresses.IsDefaultOrEmpty) { application.PostLogoutRedirectUris = ImmutableList.Create(); @@ -384,9 +561,14 @@ public class OpenIddictMongoDbApplicationStore : IOpenIddictApplic } /// - public virtual ValueTask SetPropertiesAsync(TApplication application!!, + public virtual ValueTask SetPropertiesAsync(TApplication application, ImmutableDictionary properties, CancellationToken cancellationToken) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + if (properties is not { Count: > 0 }) { application.Properties = null; @@ -418,9 +600,14 @@ public class OpenIddictMongoDbApplicationStore : IOpenIddictApplic } /// - public virtual ValueTask SetRedirectUrisAsync(TApplication application!!, + public virtual ValueTask SetRedirectUrisAsync(TApplication application, ImmutableArray addresses, CancellationToken cancellationToken) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + if (addresses.IsDefaultOrEmpty) { application.RedirectUris = ImmutableList.Create(); @@ -434,9 +621,14 @@ public class OpenIddictMongoDbApplicationStore : IOpenIddictApplic } /// - public virtual ValueTask SetRequirementsAsync(TApplication application!!, + public virtual ValueTask SetRequirementsAsync(TApplication application, ImmutableArray requirements, CancellationToken cancellationToken) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + if (requirements.IsDefaultOrEmpty) { application.Requirements = ImmutableList.Create(); @@ -450,8 +642,13 @@ public class OpenIddictMongoDbApplicationStore : IOpenIddictApplic } /// - public virtual async ValueTask UpdateAsync(TApplication application!!, CancellationToken cancellationToken) + public virtual async ValueTask UpdateAsync(TApplication application, CancellationToken cancellationToken) { + if (application is null) + { + throw new ArgumentNullException(nameof(application)); + } + // Generate a new concurrency token and attach it // to the application before persisting the changes. var timestamp = application.ConcurrencyToken; diff --git a/src/OpenIddict.MongoDb/Stores/OpenIddictMongoDbAuthorizationStore.cs b/src/OpenIddict.MongoDb/Stores/OpenIddictMongoDbAuthorizationStore.cs index c50331bb..21cf7f26 100644 --- a/src/OpenIddict.MongoDb/Stores/OpenIddictMongoDbAuthorizationStore.cs +++ b/src/OpenIddict.MongoDb/Stores/OpenIddictMongoDbAuthorizationStore.cs @@ -22,11 +22,11 @@ public class OpenIddictMongoDbAuthorizationStore : IOpenIddictAu where TAuthorization : OpenIddictMongoDbAuthorization { public OpenIddictMongoDbAuthorizationStore( - IOpenIddictMongoDbContext context!!, - IOptionsMonitor options!!) + IOpenIddictMongoDbContext context, + IOptionsMonitor options) { - Context = context; - Options = options; + Context = context ?? throw new ArgumentNullException(nameof(context)); + Options = options ?? throw new ArgumentNullException(nameof(options)); } /// @@ -50,8 +50,13 @@ public class OpenIddictMongoDbAuthorizationStore : IOpenIddictAu /// public virtual async ValueTask CountAsync( - Func, IQueryable> query!!, CancellationToken cancellationToken) + Func, IQueryable> query, CancellationToken cancellationToken) { + if (query is null) + { + throw new ArgumentNullException(nameof(query)); + } + var database = await Context.GetDatabaseAsync(cancellationToken); var collection = database.GetCollection(Options.CurrentValue.AuthorizationsCollectionName); @@ -59,8 +64,13 @@ public class OpenIddictMongoDbAuthorizationStore : IOpenIddictAu } /// - public virtual async ValueTask CreateAsync(TAuthorization authorization!!, CancellationToken cancellationToken) + public virtual async ValueTask CreateAsync(TAuthorization authorization, CancellationToken cancellationToken) { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + var database = await Context.GetDatabaseAsync(cancellationToken); var collection = database.GetCollection(Options.CurrentValue.AuthorizationsCollectionName); @@ -68,8 +78,13 @@ public class OpenIddictMongoDbAuthorizationStore : IOpenIddictAu } /// - public virtual async ValueTask DeleteAsync(TAuthorization authorization!!, CancellationToken cancellationToken) + public virtual async ValueTask DeleteAsync(TAuthorization authorization, CancellationToken cancellationToken) { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + var database = await Context.GetDatabaseAsync(cancellationToken); var collection = database.GetCollection(Options.CurrentValue.AuthorizationsCollectionName); @@ -306,8 +321,13 @@ public class OpenIddictMongoDbAuthorizationStore : IOpenIddictAu } /// - public virtual ValueTask GetApplicationIdAsync(TAuthorization authorization!!, CancellationToken cancellationToken) + public virtual ValueTask GetApplicationIdAsync(TAuthorization authorization, CancellationToken cancellationToken) { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + if (authorization.ApplicationId == ObjectId.Empty) { return new(result: null); @@ -318,9 +338,14 @@ public class OpenIddictMongoDbAuthorizationStore : IOpenIddictAu /// public virtual async ValueTask GetAsync( - Func, TState, IQueryable> query!!, + Func, TState, IQueryable> query, TState state, CancellationToken cancellationToken) { + if (query is null) + { + throw new ArgumentNullException(nameof(query)); + } + var database = await Context.GetDatabaseAsync(cancellationToken); var collection = database.GetCollection(Options.CurrentValue.AuthorizationsCollectionName); @@ -328,16 +353,40 @@ public class OpenIddictMongoDbAuthorizationStore : IOpenIddictAu } /// - public virtual ValueTask GetCreationDateAsync(TAuthorization authorization!!, CancellationToken cancellationToken) - => new(authorization.CreationDate is DateTime date ? DateTime.SpecifyKind(date, DateTimeKind.Utc) : null); + public virtual ValueTask GetCreationDateAsync(TAuthorization authorization, CancellationToken cancellationToken) + { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + + if (authorization.CreationDate is null) + { + return new(result: null); + } + + return new(DateTime.SpecifyKind(authorization.CreationDate.Value, DateTimeKind.Utc)); + } /// - public virtual ValueTask GetIdAsync(TAuthorization authorization!!, CancellationToken cancellationToken) - => new(authorization.Id.ToString()); + public virtual ValueTask GetIdAsync(TAuthorization authorization, CancellationToken cancellationToken) + { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + + return new(authorization.Id.ToString()); + } /// - public virtual ValueTask> GetPropertiesAsync(TAuthorization authorization!!, CancellationToken cancellationToken) + public virtual ValueTask> GetPropertiesAsync(TAuthorization authorization, CancellationToken cancellationToken) { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + if (authorization.Properties is null) { return new(ImmutableDictionary.Create()); @@ -355,20 +404,53 @@ public class OpenIddictMongoDbAuthorizationStore : IOpenIddictAu } /// - public virtual ValueTask> GetScopesAsync(TAuthorization authorization!!, CancellationToken cancellationToken) - => new(authorization.Scopes is { Count: > 0 } scopes ? scopes.ToImmutableArray() : ImmutableArray.Create()); + public virtual ValueTask> GetScopesAsync(TAuthorization authorization, CancellationToken cancellationToken) + { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + + if (authorization.Scopes is null || authorization.Scopes.Count == 0) + { + return new(ImmutableArray.Create()); + } + + return new(authorization.Scopes.ToImmutableArray()); + } /// - public virtual ValueTask GetStatusAsync(TAuthorization authorization!!, CancellationToken cancellationToken) - => new(authorization.Status); + public virtual ValueTask GetStatusAsync(TAuthorization authorization, CancellationToken cancellationToken) + { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + + return new(authorization.Status); + } /// - public virtual ValueTask GetSubjectAsync(TAuthorization authorization!!, CancellationToken cancellationToken) - => new(authorization.Subject); + public virtual ValueTask GetSubjectAsync(TAuthorization authorization, CancellationToken cancellationToken) + { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + + return new(authorization.Subject); + } /// - public virtual ValueTask GetTypeAsync(TAuthorization authorization!!, CancellationToken cancellationToken) - => new(authorization.Type); + public virtual ValueTask GetTypeAsync(TAuthorization authorization, CancellationToken cancellationToken) + { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + + return new(authorization.Type); + } /// public virtual ValueTask InstantiateAsync(CancellationToken cancellationToken) @@ -412,9 +494,14 @@ public class OpenIddictMongoDbAuthorizationStore : IOpenIddictAu /// public virtual IAsyncEnumerable ListAsync( - Func, TState, IQueryable> query!!, + Func, TState, IQueryable> query, TState state, CancellationToken cancellationToken) { + if (query is null) + { + throw new ArgumentNullException(nameof(query)); + } + return ExecuteAsync(cancellationToken); async IAsyncEnumerable ExecuteAsync([EnumeratorCancellation] CancellationToken cancellationToken) @@ -480,9 +567,14 @@ public class OpenIddictMongoDbAuthorizationStore : IOpenIddictAu } /// - public virtual ValueTask SetApplicationIdAsync(TAuthorization authorization!!, + public virtual ValueTask SetApplicationIdAsync(TAuthorization authorization, string? identifier, CancellationToken cancellationToken) { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + if (!string.IsNullOrEmpty(identifier)) { authorization.ApplicationId = ObjectId.Parse(identifier); @@ -497,18 +589,28 @@ public class OpenIddictMongoDbAuthorizationStore : IOpenIddictAu } /// - public virtual ValueTask SetCreationDateAsync(TAuthorization authorization!!, + public virtual ValueTask SetCreationDateAsync(TAuthorization authorization, DateTimeOffset? date, CancellationToken cancellationToken) { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + authorization.CreationDate = date?.UtcDateTime; return default; } /// - public virtual ValueTask SetPropertiesAsync(TAuthorization authorization!!, + public virtual ValueTask SetPropertiesAsync(TAuthorization authorization, ImmutableDictionary properties, CancellationToken cancellationToken) { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + if (properties is not { Count: > 0 }) { authorization.Properties = null; @@ -540,9 +642,14 @@ public class OpenIddictMongoDbAuthorizationStore : IOpenIddictAu } /// - public virtual ValueTask SetScopesAsync(TAuthorization authorization!!, + public virtual ValueTask SetScopesAsync(TAuthorization authorization, ImmutableArray scopes, CancellationToken cancellationToken) { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + if (scopes.IsDefaultOrEmpty) { authorization.Scopes = ImmutableList.Create(); @@ -556,32 +663,52 @@ public class OpenIddictMongoDbAuthorizationStore : IOpenIddictAu } /// - public virtual ValueTask SetStatusAsync(TAuthorization authorization!!, string? status, CancellationToken cancellationToken) + public virtual ValueTask SetStatusAsync(TAuthorization authorization, string? status, CancellationToken cancellationToken) { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + authorization.Status = status; return default; } /// - public virtual ValueTask SetSubjectAsync(TAuthorization authorization!!, string? subject, CancellationToken cancellationToken) + public virtual ValueTask SetSubjectAsync(TAuthorization authorization, string? subject, CancellationToken cancellationToken) { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + authorization.Subject = subject; return default; } /// - public virtual ValueTask SetTypeAsync(TAuthorization authorization!!, string? type, CancellationToken cancellationToken) + public virtual ValueTask SetTypeAsync(TAuthorization authorization, string? type, CancellationToken cancellationToken) { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + authorization.Type = type; return default; } /// - public virtual async ValueTask UpdateAsync(TAuthorization authorization!!, CancellationToken cancellationToken) + public virtual async ValueTask UpdateAsync(TAuthorization authorization, CancellationToken cancellationToken) { + if (authorization is null) + { + throw new ArgumentNullException(nameof(authorization)); + } + // Generate a new concurrency token and attach it // to the authorization before persisting the changes. var timestamp = authorization.ConcurrencyToken; diff --git a/src/OpenIddict.MongoDb/Stores/OpenIddictMongoDbScopeStore.cs b/src/OpenIddict.MongoDb/Stores/OpenIddictMongoDbScopeStore.cs index 0f61a160..d1e086fe 100644 --- a/src/OpenIddict.MongoDb/Stores/OpenIddictMongoDbScopeStore.cs +++ b/src/OpenIddict.MongoDb/Stores/OpenIddictMongoDbScopeStore.cs @@ -23,11 +23,11 @@ public class OpenIddictMongoDbScopeStore : IOpenIddictScopeStore where TScope : OpenIddictMongoDbScope { public OpenIddictMongoDbScopeStore( - IOpenIddictMongoDbContext context!!, - IOptionsMonitor options!!) + IOpenIddictMongoDbContext context, + IOptionsMonitor options) { - Context = context; - Options = options; + Context = context ?? throw new ArgumentNullException(nameof(context)); + Options = options ?? throw new ArgumentNullException(nameof(options)); } /// @@ -51,8 +51,13 @@ public class OpenIddictMongoDbScopeStore : IOpenIddictScopeStore /// public virtual async ValueTask CountAsync( - Func, IQueryable> query!!, CancellationToken cancellationToken) + Func, IQueryable> query, CancellationToken cancellationToken) { + if (query is null) + { + throw new ArgumentNullException(nameof(query)); + } + var database = await Context.GetDatabaseAsync(cancellationToken); var collection = database.GetCollection(Options.CurrentValue.ScopesCollectionName); @@ -60,8 +65,13 @@ public class OpenIddictMongoDbScopeStore : IOpenIddictScopeStore } /// - public virtual async ValueTask CreateAsync(TScope scope!!, CancellationToken cancellationToken) + public virtual async ValueTask CreateAsync(TScope scope, CancellationToken cancellationToken) { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + var database = await Context.GetDatabaseAsync(cancellationToken); var collection = database.GetCollection(Options.CurrentValue.ScopesCollectionName); @@ -69,8 +79,13 @@ public class OpenIddictMongoDbScopeStore : IOpenIddictScopeStore } /// - public virtual async ValueTask DeleteAsync(TScope scope!!, CancellationToken cancellationToken) + public virtual async ValueTask DeleteAsync(TScope scope, CancellationToken cancellationToken) { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + var database = await Context.GetDatabaseAsync(cancellationToken); var collection = database.GetCollection(Options.CurrentValue.ScopesCollectionName); @@ -113,7 +128,7 @@ public class OpenIddictMongoDbScopeStore : IOpenIddictScopeStore /// public virtual IAsyncEnumerable FindByNamesAsync(ImmutableArray names, CancellationToken cancellationToken) { - if (names.Any(string.IsNullOrEmpty)) + if (names.Any(name => string.IsNullOrEmpty(name))) { throw new ArgumentException(SR.GetResourceString(SR.ID0203), nameof(names)); } @@ -158,9 +173,14 @@ public class OpenIddictMongoDbScopeStore : IOpenIddictScopeStore /// public virtual async ValueTask GetAsync( - Func, TState, IQueryable> query!!, + Func, TState, IQueryable> query, TState state, CancellationToken cancellationToken) { + if (query is null) + { + throw new ArgumentNullException(nameof(query)); + } + var database = await Context.GetDatabaseAsync(cancellationToken); var collection = database.GetCollection(Options.CurrentValue.ScopesCollectionName); @@ -168,32 +188,89 @@ public class OpenIddictMongoDbScopeStore : IOpenIddictScopeStore } /// - public virtual ValueTask GetDescriptionAsync(TScope scope!!, CancellationToken cancellationToken) - => new(scope.Description); + public virtual ValueTask GetDescriptionAsync(TScope scope, CancellationToken cancellationToken) + { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + + return new(scope.Description); + } /// - public virtual ValueTask> GetDescriptionsAsync(TScope scope!!, CancellationToken cancellationToken) - => new(scope.Descriptions is { Count: > 0 } descriptions ? descriptions.ToImmutableDictionary() : ImmutableDictionary.Create()); + public virtual ValueTask> GetDescriptionsAsync(TScope scope, CancellationToken cancellationToken) + { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + + if (scope.Descriptions is null || scope.Descriptions.Count == 0) + { + return new(ImmutableDictionary.Create()); + } + + return new(scope.Descriptions.ToImmutableDictionary()); + } /// - public virtual ValueTask GetDisplayNameAsync(TScope scope!!, CancellationToken cancellationToken) - => new(scope.DisplayName); + public virtual ValueTask GetDisplayNameAsync(TScope scope, CancellationToken cancellationToken) + { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + + return new(scope.DisplayName); + } /// - public virtual ValueTask> GetDisplayNamesAsync(TScope scope!!, CancellationToken cancellationToken) - => new(scope.DisplayNames is { Count: > 0 } names ? names.ToImmutableDictionary() : ImmutableDictionary.Create()); + public virtual ValueTask> GetDisplayNamesAsync(TScope scope, CancellationToken cancellationToken) + { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + + if (scope.DisplayNames is null || scope.DisplayNames.Count == 0) + { + return new(ImmutableDictionary.Create()); + } + + return new(scope.DisplayNames.ToImmutableDictionary()); + } /// - public virtual ValueTask GetIdAsync(TScope scope!!, CancellationToken cancellationToken) - => new(scope.Id.ToString()); + public virtual ValueTask GetIdAsync(TScope scope, CancellationToken cancellationToken) + { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + + return new(scope.Id.ToString()); + } /// - public virtual ValueTask GetNameAsync(TScope scope!!, CancellationToken cancellationToken) - => new(scope.Name); + public virtual ValueTask GetNameAsync(TScope scope, CancellationToken cancellationToken) + { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + + return new(scope.Name); + } /// - public virtual ValueTask> GetPropertiesAsync(TScope scope!!, CancellationToken cancellationToken) + public virtual ValueTask> GetPropertiesAsync(TScope scope, CancellationToken cancellationToken) { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + if (scope.Properties is null) { return new(ImmutableDictionary.Create()); @@ -211,8 +288,20 @@ public class OpenIddictMongoDbScopeStore : IOpenIddictScopeStore } /// - public virtual ValueTask> GetResourcesAsync(TScope scope!!, CancellationToken cancellationToken) - => new(scope.Resources is { Count: > 0 } resources ? resources.ToImmutableArray() : ImmutableArray.Create()); + public virtual ValueTask> GetResourcesAsync(TScope scope, CancellationToken cancellationToken) + { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + + if (scope.Resources is null || scope.Resources.Count == 0) + { + return new(ImmutableArray.Create()); + } + + return new(scope.Resources.ToImmutableArray()); + } /// public virtual ValueTask InstantiateAsync(CancellationToken cancellationToken) @@ -256,9 +345,14 @@ public class OpenIddictMongoDbScopeStore : IOpenIddictScopeStore /// public virtual IAsyncEnumerable ListAsync( - Func, TState, IQueryable> query!!, + Func, TState, IQueryable> query, TState state, CancellationToken cancellationToken) { + if (query is null) + { + throw new ArgumentNullException(nameof(query)); + } + return ExecuteAsync(cancellationToken); async IAsyncEnumerable ExecuteAsync([EnumeratorCancellation] CancellationToken cancellationToken) @@ -274,51 +368,81 @@ public class OpenIddictMongoDbScopeStore : IOpenIddictScopeStore } /// - public virtual ValueTask SetDescriptionAsync(TScope scope!!, string? description, CancellationToken cancellationToken) + public virtual ValueTask SetDescriptionAsync(TScope scope, string? description, CancellationToken cancellationToken) { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + scope.Description = description; return default; } /// - public virtual ValueTask SetDescriptionsAsync(TScope scope!!, + public virtual ValueTask SetDescriptionsAsync(TScope scope, ImmutableDictionary descriptions, CancellationToken cancellationToken) { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + scope.Descriptions = descriptions; return default; } /// - public virtual ValueTask SetDisplayNamesAsync(TScope scope!!, + public virtual ValueTask SetDisplayNamesAsync(TScope scope, ImmutableDictionary names, CancellationToken cancellationToken) { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + scope.DisplayNames = names; return default; } /// - public virtual ValueTask SetDisplayNameAsync(TScope scope!!, string? name, CancellationToken cancellationToken) + public virtual ValueTask SetDisplayNameAsync(TScope scope, string? name, CancellationToken cancellationToken) { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + scope.DisplayName = name; return default; } /// - public virtual ValueTask SetNameAsync(TScope scope!!, string? name, CancellationToken cancellationToken) + public virtual ValueTask SetNameAsync(TScope scope, string? name, CancellationToken cancellationToken) { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + scope.Name = name; return default; } /// - public virtual ValueTask SetPropertiesAsync(TScope scope!!, + public virtual ValueTask SetPropertiesAsync(TScope scope, ImmutableDictionary properties, CancellationToken cancellationToken) { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + if (properties is not { Count: > 0 }) { scope.Properties = null; @@ -350,8 +474,13 @@ public class OpenIddictMongoDbScopeStore : IOpenIddictScopeStore } /// - public virtual ValueTask SetResourcesAsync(TScope scope!!, ImmutableArray resources, CancellationToken cancellationToken) + public virtual ValueTask SetResourcesAsync(TScope scope, ImmutableArray resources, CancellationToken cancellationToken) { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + if (resources.IsDefaultOrEmpty) { scope.Resources = ImmutableList.Create(); @@ -365,8 +494,13 @@ public class OpenIddictMongoDbScopeStore : IOpenIddictScopeStore } /// - public virtual async ValueTask UpdateAsync(TScope scope!!, CancellationToken cancellationToken) + public virtual async ValueTask UpdateAsync(TScope scope, CancellationToken cancellationToken) { + if (scope is null) + { + throw new ArgumentNullException(nameof(scope)); + } + // Generate a new concurrency token and attach it // to the scope before persisting the changes. var timestamp = scope.ConcurrencyToken; diff --git a/src/OpenIddict.MongoDb/Stores/OpenIddictMongoDbTokenStore.cs b/src/OpenIddict.MongoDb/Stores/OpenIddictMongoDbTokenStore.cs index 65c638e4..19041271 100644 --- a/src/OpenIddict.MongoDb/Stores/OpenIddictMongoDbTokenStore.cs +++ b/src/OpenIddict.MongoDb/Stores/OpenIddictMongoDbTokenStore.cs @@ -22,11 +22,11 @@ public class OpenIddictMongoDbTokenStore : IOpenIddictTokenStore where TToken : OpenIddictMongoDbToken { public OpenIddictMongoDbTokenStore( - IOpenIddictMongoDbContext context!!, - IOptionsMonitor options!!) + IOpenIddictMongoDbContext context, + IOptionsMonitor options) { - Context = context; - Options = options; + Context = context ?? throw new ArgumentNullException(nameof(context)); + Options = options ?? throw new ArgumentNullException(nameof(options)); } /// @@ -50,8 +50,13 @@ public class OpenIddictMongoDbTokenStore : IOpenIddictTokenStore /// public virtual async ValueTask CountAsync( - Func, IQueryable> query!!, CancellationToken cancellationToken) + Func, IQueryable> query, CancellationToken cancellationToken) { + if (query is null) + { + throw new ArgumentNullException(nameof(query)); + } + var database = await Context.GetDatabaseAsync(cancellationToken); var collection = database.GetCollection(Options.CurrentValue.TokensCollectionName); @@ -59,8 +64,13 @@ public class OpenIddictMongoDbTokenStore : IOpenIddictTokenStore } /// - public virtual async ValueTask CreateAsync(TToken token!!, CancellationToken cancellationToken) + public virtual async ValueTask CreateAsync(TToken token, CancellationToken cancellationToken) { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + var database = await Context.GetDatabaseAsync(cancellationToken); var collection = database.GetCollection(Options.CurrentValue.TokensCollectionName); @@ -68,8 +78,13 @@ public class OpenIddictMongoDbTokenStore : IOpenIddictTokenStore } /// - public virtual async ValueTask DeleteAsync(TToken token!!, CancellationToken cancellationToken) + public virtual async ValueTask DeleteAsync(TToken token, CancellationToken cancellationToken) { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + var database = await Context.GetDatabaseAsync(cancellationToken); var collection = database.GetCollection(Options.CurrentValue.TokensCollectionName); @@ -288,8 +303,13 @@ public class OpenIddictMongoDbTokenStore : IOpenIddictTokenStore } /// - public virtual ValueTask GetApplicationIdAsync(TToken token!!, CancellationToken cancellationToken) + public virtual ValueTask GetApplicationIdAsync(TToken token, CancellationToken cancellationToken) { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + if (token.ApplicationId == ObjectId.Empty) { return new(result: null); @@ -300,9 +320,14 @@ public class OpenIddictMongoDbTokenStore : IOpenIddictTokenStore /// public virtual async ValueTask GetAsync( - Func, TState, IQueryable> query!!, + Func, TState, IQueryable> query, TState state, CancellationToken cancellationToken) { + if (query is null) + { + throw new ArgumentNullException(nameof(query)); + } + var database = await Context.GetDatabaseAsync(cancellationToken); var collection = database.GetCollection(Options.CurrentValue.TokensCollectionName); @@ -310,8 +335,13 @@ public class OpenIddictMongoDbTokenStore : IOpenIddictTokenStore } /// - public virtual ValueTask GetAuthorizationIdAsync(TToken token!!, CancellationToken cancellationToken) + public virtual ValueTask GetAuthorizationIdAsync(TToken token, CancellationToken cancellationToken) { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + if (token.AuthorizationId == ObjectId.Empty) { return new(result: null); @@ -321,24 +351,67 @@ public class OpenIddictMongoDbTokenStore : IOpenIddictTokenStore } /// - public virtual ValueTask GetCreationDateAsync(TToken token!!, CancellationToken cancellationToken) - => new(token.CreationDate is DateTime date ? DateTime.SpecifyKind(date, DateTimeKind.Utc) : null); + public virtual ValueTask GetCreationDateAsync(TToken token, CancellationToken cancellationToken) + { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + + if (token.CreationDate is null) + { + return new(result: null); + } + + return new(DateTime.SpecifyKind(token.CreationDate.Value, DateTimeKind.Utc)); + } /// - public virtual ValueTask GetExpirationDateAsync(TToken token!!, CancellationToken cancellationToken) - => new(token.ExpirationDate is DateTime date ? DateTime.SpecifyKind(date, DateTimeKind.Utc) : null); + public virtual ValueTask GetExpirationDateAsync(TToken token, CancellationToken cancellationToken) + { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + + if (token.ExpirationDate is null) + { + return new(result: null); + } + + return new(DateTime.SpecifyKind(token.ExpirationDate.Value, DateTimeKind.Utc)); + } /// - public virtual ValueTask GetIdAsync(TToken token!!, CancellationToken cancellationToken) - => new(token.Id.ToString()); + public virtual ValueTask GetIdAsync(TToken token, CancellationToken cancellationToken) + { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + + return new(token.Id.ToString()); + } /// - public virtual ValueTask GetPayloadAsync(TToken token!!, CancellationToken cancellationToken) - => new(token.Payload); + public virtual ValueTask GetPayloadAsync(TToken token, CancellationToken cancellationToken) + { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + + return new(token.Payload); + } /// - public virtual ValueTask> GetPropertiesAsync(TToken token!!, CancellationToken cancellationToken) + public virtual ValueTask> GetPropertiesAsync(TToken token, CancellationToken cancellationToken) { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + if (token.Properties is null) { return new(ImmutableDictionary.Create()); @@ -356,24 +429,64 @@ public class OpenIddictMongoDbTokenStore : IOpenIddictTokenStore } /// - public virtual ValueTask GetRedemptionDateAsync(TToken token!!, CancellationToken cancellationToken) - => new(token.RedemptionDate is DateTime date ? DateTime.SpecifyKind(date, DateTimeKind.Utc) : null); + public virtual ValueTask GetRedemptionDateAsync(TToken token, CancellationToken cancellationToken) + { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + + if (token.RedemptionDate is null) + { + return new(result: null); + } + + return new(DateTime.SpecifyKind(token.RedemptionDate.Value, DateTimeKind.Utc)); + } /// - public virtual ValueTask GetReferenceIdAsync(TToken token!!, CancellationToken cancellationToken) - => new(token.ReferenceId); + public virtual ValueTask GetReferenceIdAsync(TToken token, CancellationToken cancellationToken) + { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + + return new(token.ReferenceId); + } /// - public virtual ValueTask GetStatusAsync(TToken token!!, CancellationToken cancellationToken) - => new(token.Status); + public virtual ValueTask GetStatusAsync(TToken token, CancellationToken cancellationToken) + { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + + return new(token.Status); + } /// - public virtual ValueTask GetSubjectAsync(TToken token!!, CancellationToken cancellationToken) - => new(token.Subject); + public virtual ValueTask GetSubjectAsync(TToken token, CancellationToken cancellationToken) + { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + + return new(token.Subject); + } /// - public virtual ValueTask GetTypeAsync(TToken token!!, CancellationToken cancellationToken) - => new(token.Type); + public virtual ValueTask GetTypeAsync(TToken token, CancellationToken cancellationToken) + { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + + return new(token.Type); + } /// public virtual ValueTask InstantiateAsync(CancellationToken cancellationToken) @@ -417,9 +530,14 @@ public class OpenIddictMongoDbTokenStore : IOpenIddictTokenStore /// public virtual IAsyncEnumerable ListAsync( - Func, TState, IQueryable> query!!, + Func, TState, IQueryable> query, TState state, CancellationToken cancellationToken) { + if (query is null) + { + throw new ArgumentNullException(nameof(query)); + } + return ExecuteAsync(cancellationToken); async IAsyncEnumerable ExecuteAsync([EnumeratorCancellation] CancellationToken cancellationToken) @@ -486,8 +604,13 @@ public class OpenIddictMongoDbTokenStore : IOpenIddictTokenStore } /// - public virtual ValueTask SetApplicationIdAsync(TToken token!!, string? identifier, CancellationToken cancellationToken) + public virtual ValueTask SetApplicationIdAsync(TToken token, string? identifier, CancellationToken cancellationToken) { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + if (!string.IsNullOrEmpty(identifier)) { token.ApplicationId = ObjectId.Parse(identifier); @@ -502,8 +625,13 @@ public class OpenIddictMongoDbTokenStore : IOpenIddictTokenStore } /// - public virtual ValueTask SetAuthorizationIdAsync(TToken token!!, string? identifier, CancellationToken cancellationToken) + public virtual ValueTask SetAuthorizationIdAsync(TToken token, string? identifier, CancellationToken cancellationToken) { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + if (!string.IsNullOrEmpty(identifier)) { token.AuthorizationId = ObjectId.Parse(identifier); @@ -518,33 +646,53 @@ public class OpenIddictMongoDbTokenStore : IOpenIddictTokenStore } /// - public virtual ValueTask SetCreationDateAsync(TToken token!!, DateTimeOffset? date, CancellationToken cancellationToken) + public virtual ValueTask SetCreationDateAsync(TToken token, DateTimeOffset? date, CancellationToken cancellationToken) { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + token.CreationDate = date?.UtcDateTime; return default; } /// - public virtual ValueTask SetExpirationDateAsync(TToken token!!, DateTimeOffset? date, CancellationToken cancellationToken) + public virtual ValueTask SetExpirationDateAsync(TToken token, DateTimeOffset? date, CancellationToken cancellationToken) { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + token.ExpirationDate = date?.UtcDateTime; return default; } /// - public virtual ValueTask SetPayloadAsync(TToken token!!, string? payload, CancellationToken cancellationToken) + public virtual ValueTask SetPayloadAsync(TToken token, string? payload, CancellationToken cancellationToken) { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + token.Payload = payload; return default; } /// - public virtual ValueTask SetPropertiesAsync(TToken token!!, + public virtual ValueTask SetPropertiesAsync(TToken token, ImmutableDictionary properties, CancellationToken cancellationToken) { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + if (properties is not { Count: > 0 }) { token.Properties = null; @@ -576,48 +724,78 @@ public class OpenIddictMongoDbTokenStore : IOpenIddictTokenStore } /// - public virtual ValueTask SetRedemptionDateAsync(TToken token!!, DateTimeOffset? date, CancellationToken cancellationToken) + public virtual ValueTask SetRedemptionDateAsync(TToken token, DateTimeOffset? date, CancellationToken cancellationToken) { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + token.RedemptionDate = date?.UtcDateTime; return default; } /// - public virtual ValueTask SetReferenceIdAsync(TToken token!!, string? identifier, CancellationToken cancellationToken) + public virtual ValueTask SetReferenceIdAsync(TToken token, string? identifier, CancellationToken cancellationToken) { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + token.ReferenceId = identifier; return default; } /// - public virtual ValueTask SetStatusAsync(TToken token!!, string? status, CancellationToken cancellationToken) + public virtual ValueTask SetStatusAsync(TToken token, string? status, CancellationToken cancellationToken) { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + token.Status = status; return default; } /// - public virtual ValueTask SetSubjectAsync(TToken token!!, string? subject, CancellationToken cancellationToken) + public virtual ValueTask SetSubjectAsync(TToken token, string? subject, CancellationToken cancellationToken) { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + token.Subject = subject; return default; } /// - public virtual ValueTask SetTypeAsync(TToken token!!, string? type, CancellationToken cancellationToken) + public virtual ValueTask SetTypeAsync(TToken token, string? type, CancellationToken cancellationToken) { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + token.Type = type; return default; } /// - public virtual async ValueTask UpdateAsync(TToken token!!, CancellationToken cancellationToken) + public virtual async ValueTask UpdateAsync(TToken token, CancellationToken cancellationToken) { + if (token is null) + { + throw new ArgumentNullException(nameof(token)); + } + // Generate a new concurrency token and attach it // to the token before persisting the changes. var timestamp = token.ConcurrencyToken; diff --git a/src/OpenIddict.Quartz/OpenIddictQuartzBuilder.cs b/src/OpenIddict.Quartz/OpenIddictQuartzBuilder.cs index f6ea2245..086db9d7 100644 --- a/src/OpenIddict.Quartz/OpenIddictQuartzBuilder.cs +++ b/src/OpenIddict.Quartz/OpenIddictQuartzBuilder.cs @@ -18,8 +18,8 @@ public class OpenIddictQuartzBuilder /// Initializes a new instance of . /// /// The services collection. - public OpenIddictQuartzBuilder(IServiceCollection services!!) - => Services = services; + public OpenIddictQuartzBuilder(IServiceCollection services) + => Services = services ?? throw new ArgumentNullException(nameof(services)); /// /// Gets the services collection. @@ -33,8 +33,13 @@ public class OpenIddictQuartzBuilder /// The delegate used to configure the OpenIddict options. /// This extension can be safely called multiple times. /// The . - public OpenIddictQuartzBuilder Configure(Action configuration!!) + public OpenIddictQuartzBuilder Configure(Action configuration) { + if (configuration is null) + { + throw new ArgumentNullException(nameof(configuration)); + } + Services.Configure(configuration); return this; diff --git a/src/OpenIddict.Quartz/OpenIddictQuartzConfiguration.cs b/src/OpenIddict.Quartz/OpenIddictQuartzConfiguration.cs index 9a051257..f4bb8021 100644 --- a/src/OpenIddict.Quartz/OpenIddictQuartzConfiguration.cs +++ b/src/OpenIddict.Quartz/OpenIddictQuartzConfiguration.cs @@ -14,8 +14,13 @@ namespace OpenIddict.Quartz; public class OpenIddictQuartzConfiguration : IConfigureOptions { /// - public void Configure(QuartzOptions options!!) + public void Configure(QuartzOptions options) { + if (options is null) + { + throw new ArgumentNullException(nameof(options)); + } + options.AddJob(builder => { builder.StoreDurably() diff --git a/src/OpenIddict.Quartz/OpenIddictQuartzExtensions.cs b/src/OpenIddict.Quartz/OpenIddictQuartzExtensions.cs index 90be5848..d65f3f10 100644 --- a/src/OpenIddict.Quartz/OpenIddictQuartzExtensions.cs +++ b/src/OpenIddict.Quartz/OpenIddictQuartzExtensions.cs @@ -21,8 +21,13 @@ public static class OpenIddictQuartzExtensions /// The services builder used by OpenIddict to register new services. /// This extension can be safely called multiple times. /// The . - public static OpenIddictQuartzBuilder UseQuartz(this OpenIddictCoreBuilder builder!!) + public static OpenIddictQuartzBuilder UseQuartz(this OpenIddictCoreBuilder builder) { + if (builder is null) + { + throw new ArgumentNullException(nameof(builder)); + } + builder.Services.AddQuartz(); // The OpenIddict job is registered as a service to allow @@ -44,8 +49,18 @@ public static class OpenIddictQuartzExtensions /// This extension can be safely called multiple times. /// The . public static OpenIddictCoreBuilder UseQuartz( - this OpenIddictCoreBuilder builder!!, Action configuration!!) + this OpenIddictCoreBuilder builder, Action configuration) { + if (builder is null) + { + throw new ArgumentNullException(nameof(builder)); + } + + if (configuration is null) + { + throw new ArgumentNullException(nameof(configuration)); + } + configuration(builder.UseQuartz()); return builder; diff --git a/src/OpenIddict.Quartz/OpenIddictQuartzJob.cs b/src/OpenIddict.Quartz/OpenIddictQuartzJob.cs index be1d289d..26536d6a 100644 --- a/src/OpenIddict.Quartz/OpenIddictQuartzJob.cs +++ b/src/OpenIddict.Quartz/OpenIddictQuartzJob.cs @@ -28,10 +28,10 @@ public class OpenIddictQuartzJob : IJob /// /// The OpenIddict Quartz.NET options. /// The service provider. - public OpenIddictQuartzJob(IOptionsMonitor options!!, IServiceProvider provider!!) + public OpenIddictQuartzJob(IOptionsMonitor options, IServiceProvider provider) { - _options = options; - _provider = provider; + _options = options ?? throw new ArgumentNullException(nameof(options)); + _provider = provider ?? throw new ArgumentNullException(nameof(provider)); } /// @@ -42,8 +42,13 @@ public class OpenIddictQuartzJob : IJob group: typeof(OpenIddictQuartzJob).Assembly.GetName().Name!); /// - public async Task Execute(IJobExecutionContext context!!) + public async Task Execute(IJobExecutionContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + List? exceptions = null; // Note: this job is registered as a transient service. As such, it cannot directly depend on scoped services diff --git a/src/OpenIddict.Server.AspNetCore/OpenIddictServerAspNetCoreBuilder.cs b/src/OpenIddict.Server.AspNetCore/OpenIddictServerAspNetCoreBuilder.cs index b03706c7..68861785 100644 --- a/src/OpenIddict.Server.AspNetCore/OpenIddictServerAspNetCoreBuilder.cs +++ b/src/OpenIddict.Server.AspNetCore/OpenIddictServerAspNetCoreBuilder.cs @@ -21,8 +21,8 @@ public class OpenIddictServerAspNetCoreBuilder /// Initializes a new instance of . /// /// The services collection. - public OpenIddictServerAspNetCoreBuilder(IServiceCollection services!!) - => Services = services; + public OpenIddictServerAspNetCoreBuilder(IServiceCollection services) + => Services = services ?? throw new ArgumentNullException(nameof(services)); /// /// Gets the services collection. @@ -36,8 +36,13 @@ public class OpenIddictServerAspNetCoreBuilder /// The delegate used to configure the OpenIddict options. /// This extension can be safely called multiple times. /// The . - public OpenIddictServerAspNetCoreBuilder Configure(Action configuration!!) + public OpenIddictServerAspNetCoreBuilder Configure(Action configuration) { + if (configuration is null) + { + throw new ArgumentNullException(nameof(configuration)); + } + Services.Configure(configuration); return this; @@ -162,8 +167,15 @@ public class OpenIddictServerAspNetCoreBuilder /// /// The caching policy. /// The . - public OpenIddictServerAspNetCoreBuilder SetAuthorizationRequestCachingPolicy(DistributedCacheEntryOptions policy!!) - => Configure(options => options.AuthorizationRequestCachingPolicy = policy); + public OpenIddictServerAspNetCoreBuilder SetAuthorizationRequestCachingPolicy(DistributedCacheEntryOptions policy) + { + if (policy is null) + { + throw new ArgumentNullException(nameof(policy)); + } + + return Configure(options => options.AuthorizationRequestCachingPolicy = policy); + } /// /// Sets the caching policy used by the logout endpoint. @@ -171,8 +183,15 @@ public class OpenIddictServerAspNetCoreBuilder /// /// The caching policy. /// The . - public OpenIddictServerAspNetCoreBuilder SetLogoutRequestCachingPolicy(DistributedCacheEntryOptions policy!!) - => Configure(options => options.LogoutRequestCachingPolicy = policy); + public OpenIddictServerAspNetCoreBuilder SetLogoutRequestCachingPolicy(DistributedCacheEntryOptions policy) + { + if (policy is null) + { + throw new ArgumentNullException(nameof(policy)); + } + + return Configure(options => options.LogoutRequestCachingPolicy = policy); + } /// [EditorBrowsable(EditorBrowsableState.Never)] diff --git a/src/OpenIddict.Server.AspNetCore/OpenIddictServerAspNetCoreConfiguration.cs b/src/OpenIddict.Server.AspNetCore/OpenIddictServerAspNetCoreConfiguration.cs index 739510be..9545ab36 100644 --- a/src/OpenIddict.Server.AspNetCore/OpenIddictServerAspNetCoreConfiguration.cs +++ b/src/OpenIddict.Server.AspNetCore/OpenIddictServerAspNetCoreConfiguration.cs @@ -20,8 +20,13 @@ public class OpenIddictServerAspNetCoreConfiguration : IConfigureOptions /// The options instance to initialize. - public void Configure(AuthenticationOptions options!!) + public void Configure(AuthenticationOptions options) { + if (options is null) + { + throw new ArgumentNullException(nameof(options)); + } + // If a handler was already registered and the type doesn't correspond to the OpenIddict handler, throw an exception. if (options.SchemeMap.TryGetValue(OpenIddictServerAspNetCoreDefaults.AuthenticationScheme, out var builder) && builder.HandlerType != typeof(OpenIddictServerAspNetCoreHandler)) @@ -33,8 +38,13 @@ public class OpenIddictServerAspNetCoreConfiguration : IConfigureOptions /// The name of the options instance to configure, if applicable. /// The options instance to initialize. - public void PostConfigure(string name, AuthenticationOptions options!!) + public void PostConfigure(string name, AuthenticationOptions options) { + if (options is null) + { + throw new ArgumentNullException(nameof(options)); + } + if (!TryValidate(options.SchemeMap, options.DefaultAuthenticateScheme) || !TryValidate(options.SchemeMap, options.DefaultChallengeScheme) || !TryValidate(options.SchemeMap, options.DefaultForbidScheme) || @@ -74,8 +89,13 @@ public class OpenIddictServerAspNetCoreConfiguration : IConfigureOptions /// The name of the options instance to configure, if applicable. /// The options instance to initialize. - public void PostConfigure(string name, OpenIddictServerAspNetCoreOptions options!!) + public void PostConfigure(string name, OpenIddictServerAspNetCoreOptions options) { + if (options is null) + { + throw new ArgumentNullException(nameof(options)); + } + if (options.EnableErrorPassthrough && options.EnableStatusCodePagesIntegration) { throw new InvalidOperationException(SR.GetResourceString(SR.ID0110)); diff --git a/src/OpenIddict.Server.AspNetCore/OpenIddictServerAspNetCoreExtensions.cs b/src/OpenIddict.Server.AspNetCore/OpenIddictServerAspNetCoreExtensions.cs index 373fad2f..7a871d84 100644 --- a/src/OpenIddict.Server.AspNetCore/OpenIddictServerAspNetCoreExtensions.cs +++ b/src/OpenIddict.Server.AspNetCore/OpenIddictServerAspNetCoreExtensions.cs @@ -22,8 +22,13 @@ public static class OpenIddictServerAspNetCoreExtensions /// The services builder used by OpenIddict to register new services. /// This extension can be safely called multiple times. /// The . - public static OpenIddictServerAspNetCoreBuilder UseAspNetCore(this OpenIddictServerBuilder builder!!) + public static OpenIddictServerAspNetCoreBuilder UseAspNetCore(this OpenIddictServerBuilder builder) { + if (builder is null) + { + throw new ArgumentNullException(nameof(builder)); + } + builder.Services.AddAuthentication(); builder.Services.TryAddScoped(); @@ -68,8 +73,18 @@ public static class OpenIddictServerAspNetCoreExtensions /// This extension can be safely called multiple times. /// The . public static OpenIddictServerBuilder UseAspNetCore( - this OpenIddictServerBuilder builder!!, Action configuration!!) + this OpenIddictServerBuilder builder, Action configuration) { + if (builder is null) + { + throw new ArgumentNullException(nameof(builder)); + } + + if (configuration is null) + { + throw new ArgumentNullException(nameof(configuration)); + } + configuration(builder.UseAspNetCore()); return builder; diff --git a/src/OpenIddict.Server.AspNetCore/OpenIddictServerAspNetCoreHandler.cs b/src/OpenIddict.Server.AspNetCore/OpenIddictServerAspNetCoreHandler.cs index e9eece65..60502667 100644 --- a/src/OpenIddict.Server.AspNetCore/OpenIddictServerAspNetCoreHandler.cs +++ b/src/OpenIddict.Server.AspNetCore/OpenIddictServerAspNetCoreHandler.cs @@ -28,16 +28,16 @@ public class OpenIddictServerAspNetCoreHandler : AuthenticationHandler class. /// public OpenIddictServerAspNetCoreHandler( - IOpenIddictServerDispatcher dispatcher!!, - IOpenIddictServerFactory factory!!, - IOptionsMonitor options!!, - ILoggerFactory logger!!, - UrlEncoder encoder!!, - ISystemClock clock!!) + IOpenIddictServerDispatcher dispatcher, + IOpenIddictServerFactory factory, + IOptionsMonitor options, + ILoggerFactory logger, + UrlEncoder encoder, + ISystemClock clock) : base(options, logger, encoder, clock) { - _dispatcher = dispatcher; - _factory = factory; + _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); + _factory = factory ?? throw new ArgumentNullException(nameof(factory)); } /// @@ -338,8 +338,13 @@ public class OpenIddictServerAspNetCoreHandler : AuthenticationHandler HandleChallengeAsync(properties); /// - public async Task SignInAsync(ClaimsPrincipal user!!, AuthenticationProperties? properties) + public async Task SignInAsync(ClaimsPrincipal user, AuthenticationProperties? properties) { + if (user is null) + { + throw new ArgumentNullException(nameof(user)); + } + var transaction = Context.Features.Get()?.Transaction ?? throw new InvalidOperationException(SR.GetResourceString(SR.ID0112)); diff --git a/src/OpenIddict.Server.AspNetCore/OpenIddictServerAspNetCoreHandlerFilters.cs b/src/OpenIddict.Server.AspNetCore/OpenIddictServerAspNetCoreHandlerFilters.cs index 49dc2364..9a29dd83 100644 --- a/src/OpenIddict.Server.AspNetCore/OpenIddictServerAspNetCoreHandlerFilters.cs +++ b/src/OpenIddict.Server.AspNetCore/OpenIddictServerAspNetCoreHandlerFilters.cs @@ -23,11 +23,18 @@ public static class OpenIddictServerAspNetCoreHandlerFilters { private readonly IOptionsMonitor _options; - public RequireAuthorizationRequestCachingEnabled(IOptionsMonitor options!!) - => _options = options; - - public ValueTask IsActiveAsync(BaseContext context!!) - => new(_options.CurrentValue.EnableAuthorizationRequestCaching); + public RequireAuthorizationRequestCachingEnabled(IOptionsMonitor options) + => _options = options ?? throw new ArgumentNullException(nameof(options)); + + public ValueTask IsActiveAsync(BaseContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(_options.CurrentValue.EnableAuthorizationRequestCaching); + } } /// @@ -38,11 +45,18 @@ public static class OpenIddictServerAspNetCoreHandlerFilters { private readonly IOptionsMonitor _options; - public RequireAuthorizationEndpointPassthroughEnabled(IOptionsMonitor options!!) - => _options = options; + public RequireAuthorizationEndpointPassthroughEnabled(IOptionsMonitor options) + => _options = options ?? throw new ArgumentNullException(nameof(options)); + + public ValueTask IsActiveAsync(BaseContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } - public ValueTask IsActiveAsync(BaseContext context!!) - => new(_options.CurrentValue.EnableAuthorizationEndpointPassthrough); + return new(_options.CurrentValue.EnableAuthorizationEndpointPassthrough); + } } /// @@ -52,11 +66,18 @@ public static class OpenIddictServerAspNetCoreHandlerFilters { private readonly IOptionsMonitor _options; - public RequireErrorPassthroughEnabled(IOptionsMonitor options!!) - => _options = options; + public RequireErrorPassthroughEnabled(IOptionsMonitor options) + => _options = options ?? throw new ArgumentNullException(nameof(options)); + + public ValueTask IsActiveAsync(BaseContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } - public ValueTask IsActiveAsync(BaseContext context!!) - => new(_options.CurrentValue.EnableErrorPassthrough); + return new(_options.CurrentValue.EnableErrorPassthrough); + } } /// @@ -64,8 +85,15 @@ public static class OpenIddictServerAspNetCoreHandlerFilters /// public class RequireHttpRequest : IOpenIddictServerHandlerFilter { - public ValueTask IsActiveAsync(BaseContext context!!) - => new(context.Transaction.GetHttpRequest() is not null); + public ValueTask IsActiveAsync(BaseContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(context.Transaction.GetHttpRequest() is not null); + } } /// @@ -75,11 +103,18 @@ public static class OpenIddictServerAspNetCoreHandlerFilters { private readonly IOptionsMonitor _options; - public RequireLogoutRequestCachingEnabled(IOptionsMonitor options!!) - => _options = options; + public RequireLogoutRequestCachingEnabled(IOptionsMonitor options) + => _options = options ?? throw new ArgumentNullException(nameof(options)); - public ValueTask IsActiveAsync(BaseContext context!!) - => new(_options.CurrentValue.EnableLogoutRequestCaching); + public ValueTask IsActiveAsync(BaseContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(_options.CurrentValue.EnableLogoutRequestCaching); + } } /// @@ -90,11 +125,18 @@ public static class OpenIddictServerAspNetCoreHandlerFilters { private readonly IOptionsMonitor _options; - public RequireLogoutEndpointPassthroughEnabled(IOptionsMonitor options!!) - => _options = options; + public RequireLogoutEndpointPassthroughEnabled(IOptionsMonitor options) + => _options = options ?? throw new ArgumentNullException(nameof(options)); + + public ValueTask IsActiveAsync(BaseContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } - public ValueTask IsActiveAsync(BaseContext context!!) - => new(_options.CurrentValue.EnableLogoutEndpointPassthrough); + return new(_options.CurrentValue.EnableLogoutEndpointPassthrough); + } } /// @@ -104,11 +146,18 @@ public static class OpenIddictServerAspNetCoreHandlerFilters { private readonly IOptionsMonitor _options; - public RequireStatusCodePagesIntegrationEnabled(IOptionsMonitor options!!) - => _options = options; + public RequireStatusCodePagesIntegrationEnabled(IOptionsMonitor options) + => _options = options ?? throw new ArgumentNullException(nameof(options)); - public ValueTask IsActiveAsync(BaseContext context!!) - => new(_options.CurrentValue.EnableStatusCodePagesIntegration); + public ValueTask IsActiveAsync(BaseContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(_options.CurrentValue.EnableStatusCodePagesIntegration); + } } /// @@ -118,11 +167,18 @@ public static class OpenIddictServerAspNetCoreHandlerFilters { private readonly IOptionsMonitor _options; - public RequireTransportSecurityRequirementEnabled(IOptionsMonitor options!!) - => _options = options; + public RequireTransportSecurityRequirementEnabled(IOptionsMonitor options) + => _options = options ?? throw new ArgumentNullException(nameof(options)); + + public ValueTask IsActiveAsync(BaseContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } - public ValueTask IsActiveAsync(BaseContext context!!) - => new(!_options.CurrentValue.DisableTransportSecurityRequirement); + return new(!_options.CurrentValue.DisableTransportSecurityRequirement); + } } /// @@ -133,11 +189,18 @@ public static class OpenIddictServerAspNetCoreHandlerFilters { private readonly IOptionsMonitor _options; - public RequireTokenEndpointPassthroughEnabled(IOptionsMonitor options!!) - => _options = options; + public RequireTokenEndpointPassthroughEnabled(IOptionsMonitor options) + => _options = options ?? throw new ArgumentNullException(nameof(options)); + + public ValueTask IsActiveAsync(BaseContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } - public ValueTask IsActiveAsync(BaseContext context!!) - => new(_options.CurrentValue.EnableTokenEndpointPassthrough); + return new(_options.CurrentValue.EnableTokenEndpointPassthrough); + } } /// @@ -148,11 +211,18 @@ public static class OpenIddictServerAspNetCoreHandlerFilters { private readonly IOptionsMonitor _options; - public RequireUserinfoEndpointPassthroughEnabled(IOptionsMonitor options!!) - => _options = options; + public RequireUserinfoEndpointPassthroughEnabled(IOptionsMonitor options) + => _options = options ?? throw new ArgumentNullException(nameof(options)); - public ValueTask IsActiveAsync(BaseContext context!!) - => new(_options.CurrentValue.EnableUserinfoEndpointPassthrough); + public ValueTask IsActiveAsync(BaseContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(_options.CurrentValue.EnableUserinfoEndpointPassthrough); + } } /// @@ -163,10 +233,17 @@ public static class OpenIddictServerAspNetCoreHandlerFilters { private readonly IOptionsMonitor _options; - public RequireVerificationEndpointPassthroughEnabled(IOptionsMonitor options!!) - => _options = options; + public RequireVerificationEndpointPassthroughEnabled(IOptionsMonitor options) + => _options = options ?? throw new ArgumentNullException(nameof(options)); + + public ValueTask IsActiveAsync(BaseContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } - public ValueTask IsActiveAsync(BaseContext context!!) - => new(_options.CurrentValue.EnableVerificationEndpointPassthrough); + return new(_options.CurrentValue.EnableVerificationEndpointPassthrough); + } } } diff --git a/src/OpenIddict.Server.AspNetCore/OpenIddictServerAspNetCoreHandlers.Authentication.cs b/src/OpenIddict.Server.AspNetCore/OpenIddictServerAspNetCoreHandlers.Authentication.cs index ce829ccc..814f3926 100644 --- a/src/OpenIddict.Server.AspNetCore/OpenIddictServerAspNetCoreHandlers.Authentication.cs +++ b/src/OpenIddict.Server.AspNetCore/OpenIddictServerAspNetCoreHandlers.Authentication.cs @@ -64,8 +64,8 @@ public static partial class OpenIddictServerAspNetCoreHandlers public RestoreCachedRequestParameters() => throw new InvalidOperationException(SR.GetResourceString(SR.ID0116)); - public RestoreCachedRequestParameters(IDistributedCache cache!!) - => _cache = cache; + public RestoreCachedRequestParameters(IDistributedCache cache) + => _cache = cache ?? throw new ArgumentNullException(nameof(cache)); /// /// Gets the default descriptor definition assigned to this handler. @@ -80,8 +80,13 @@ public static partial class OpenIddictServerAspNetCoreHandlers .Build(); /// - public async ValueTask HandleAsync(ExtractAuthorizationRequestContext context!!) + public async ValueTask HandleAsync(ExtractAuthorizationRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.Request is not null, SR.GetResourceString(SR.ID4008)); // If a request_id parameter can be found in the authorization request, @@ -156,10 +161,10 @@ public static partial class OpenIddictServerAspNetCoreHandlers public CacheRequestParameters( IDistributedCache cache, - IOptionsMonitor options!!) + IOptionsMonitor options) { - _cache = cache; - _options = options; + _cache = cache ?? throw new ArgumentNullException(nameof(cache)); + _options = options ?? throw new ArgumentNullException(nameof(options)); } /// @@ -175,14 +180,22 @@ public static partial class OpenIddictServerAspNetCoreHandlers .Build(); /// - public async ValueTask HandleAsync(ExtractAuthorizationRequestContext context!!) + public async ValueTask HandleAsync(ExtractAuthorizationRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.Request is not null, SR.GetResourceString(SR.ID4008)); // This handler only applies to ASP.NET Core requests. If the HTTP context cannot be resolved, // this may indicate that the request was incorrectly processed by another server stack. - var request = context.Transaction.GetHttpRequest() ?? + var request = context.Transaction.GetHttpRequest(); + if (request is null) + { throw new InvalidOperationException(SR.GetResourceString(SR.ID0114)); + } // Don't cache the request if the request doesn't include any parameter. // If a request_id parameter can be found in the authorization request, @@ -263,8 +276,8 @@ public static partial class OpenIddictServerAspNetCoreHandlers public RemoveCachedRequest() => throw new InvalidOperationException(SR.GetResourceString(SR.ID0116)); - public RemoveCachedRequest(IDistributedCache cache!!) - => _cache = cache; + public RemoveCachedRequest(IDistributedCache cache) + => _cache = cache ?? throw new ArgumentNullException(nameof(cache)); /// /// Gets the default descriptor definition assigned to this handler. @@ -279,8 +292,13 @@ public static partial class OpenIddictServerAspNetCoreHandlers .Build(); /// - public ValueTask HandleAsync(ApplyAuthorizationResponseContext context!!) + public ValueTask HandleAsync(ApplyAuthorizationResponseContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + if (string.IsNullOrEmpty(context.Request?.RequestId)) { return default; @@ -319,8 +337,13 @@ public static partial class OpenIddictServerAspNetCoreHandlers .Build(); /// - public async ValueTask HandleAsync(ApplyAuthorizationResponseContext context!!) + public async ValueTask HandleAsync(ApplyAuthorizationResponseContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // This handler only applies to ASP.NET Core requests. If the HTTP context cannot be resolved, // this may indicate that the request was incorrectly processed by another server stack. var response = context.Transaction.GetHttpRequest()?.HttpContext.Response ?? @@ -400,8 +423,13 @@ public static partial class OpenIddictServerAspNetCoreHandlers .Build(); /// - public ValueTask HandleAsync(ApplyAuthorizationResponseContext context!!) + public ValueTask HandleAsync(ApplyAuthorizationResponseContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // This handler only applies to ASP.NET Core requests. If the HTTP context cannot be resolved, // this may indicate that the request was incorrectly processed by another server stack. var response = context.Transaction.GetHttpRequest()?.HttpContext.Response ?? @@ -466,8 +494,13 @@ public static partial class OpenIddictServerAspNetCoreHandlers .Build(); /// - public ValueTask HandleAsync(ApplyAuthorizationResponseContext context!!) + public ValueTask HandleAsync(ApplyAuthorizationResponseContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // This handler only applies to ASP.NET Core requests. If the HTTP context cannot be resolved, // this may indicate that the request was incorrectly processed by another server stack. var response = context.Transaction.GetHttpRequest()?.HttpContext.Response ?? diff --git a/src/OpenIddict.Server.AspNetCore/OpenIddictServerAspNetCoreHandlers.Device.cs b/src/OpenIddict.Server.AspNetCore/OpenIddictServerAspNetCoreHandlers.Device.cs index d3ac363e..afd9d7c3 100644 --- a/src/OpenIddict.Server.AspNetCore/OpenIddictServerAspNetCoreHandlers.Device.cs +++ b/src/OpenIddict.Server.AspNetCore/OpenIddictServerAspNetCoreHandlers.Device.cs @@ -69,8 +69,13 @@ public static partial class OpenIddictServerAspNetCoreHandlers .Build(); /// - public ValueTask HandleAsync(ApplyVerificationResponseContext context!!) + public ValueTask HandleAsync(ApplyVerificationResponseContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // This handler only applies to ASP.NET Core requests. If the HTTP context cannot be resolved, // this may indicate that the request was incorrectly processed by another server stack. var response = context.Transaction.GetHttpRequest()?.HttpContext.Response ?? diff --git a/src/OpenIddict.Server.AspNetCore/OpenIddictServerAspNetCoreHandlers.Session.cs b/src/OpenIddict.Server.AspNetCore/OpenIddictServerAspNetCoreHandlers.Session.cs index 0bfa4927..904c81ee 100644 --- a/src/OpenIddict.Server.AspNetCore/OpenIddictServerAspNetCoreHandlers.Session.cs +++ b/src/OpenIddict.Server.AspNetCore/OpenIddictServerAspNetCoreHandlers.Session.cs @@ -61,8 +61,8 @@ public static partial class OpenIddictServerAspNetCoreHandlers public RestoreCachedRequestParameters() => throw new InvalidOperationException(SR.GetResourceString(SR.ID0116)); - public RestoreCachedRequestParameters(IDistributedCache cache!!) - => _cache = cache; + public RestoreCachedRequestParameters(IDistributedCache cache) + => _cache = cache ?? throw new ArgumentNullException(nameof(cache)); /// /// Gets the default descriptor definition assigned to this handler. @@ -77,8 +77,13 @@ public static partial class OpenIddictServerAspNetCoreHandlers .Build(); /// - public async ValueTask HandleAsync(ExtractLogoutRequestContext context!!) + public async ValueTask HandleAsync(ExtractLogoutRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.Request is not null, SR.GetResourceString(SR.ID4008)); // If a request_id parameter can be found in the logout request, @@ -153,10 +158,10 @@ public static partial class OpenIddictServerAspNetCoreHandlers public CacheRequestParameters( IDistributedCache cache, - IOptionsMonitor options!!) + IOptionsMonitor options) { - _cache = cache; - _options = options; + _cache = cache ?? throw new ArgumentNullException(nameof(cache)); + _options = options ?? throw new ArgumentNullException(nameof(options)); } /// @@ -172,14 +177,22 @@ public static partial class OpenIddictServerAspNetCoreHandlers .Build(); /// - public async ValueTask HandleAsync(ExtractLogoutRequestContext context!!) + public async ValueTask HandleAsync(ExtractLogoutRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.Request is not null, SR.GetResourceString(SR.ID4008)); // This handler only applies to ASP.NET Core requests. If the HTTP context cannot be resolved, // this may indicate that the request was incorrectly processed by another server stack. - var request = context.Transaction.GetHttpRequest() ?? + var request = context.Transaction.GetHttpRequest(); + if (request is null) + { throw new InvalidOperationException(SR.GetResourceString(SR.ID0114)); + } // Don't cache the request if the request doesn't include any parameter. // If a request_id parameter can be found in the logout request, @@ -260,8 +273,8 @@ public static partial class OpenIddictServerAspNetCoreHandlers public RemoveCachedRequest() => throw new InvalidOperationException(SR.GetResourceString(SR.ID0116)); - public RemoveCachedRequest(IDistributedCache cache!!) - => _cache = cache; + public RemoveCachedRequest(IDistributedCache cache) + => _cache = cache ?? throw new ArgumentNullException(nameof(cache)); /// /// Gets the default descriptor definition assigned to this handler. @@ -276,8 +289,13 @@ public static partial class OpenIddictServerAspNetCoreHandlers .Build(); /// - public ValueTask HandleAsync(ApplyLogoutResponseContext context!!) + public ValueTask HandleAsync(ApplyLogoutResponseContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + if (string.IsNullOrEmpty(context.Request?.RequestId)) { return default; @@ -311,8 +329,13 @@ public static partial class OpenIddictServerAspNetCoreHandlers .Build(); /// - public ValueTask HandleAsync(ApplyLogoutResponseContext context!!) + public ValueTask HandleAsync(ApplyLogoutResponseContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // This handler only applies to ASP.NET Core requests. If the HTTP context cannot be resolved, // this may indicate that the request was incorrectly processed by another server stack. var response = context.Transaction.GetHttpRequest()?.HttpContext.Response ?? @@ -376,8 +399,13 @@ public static partial class OpenIddictServerAspNetCoreHandlers .Build(); /// - public ValueTask HandleAsync(ApplyLogoutResponseContext context!!) + public ValueTask HandleAsync(ApplyLogoutResponseContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // This handler only applies to ASP.NET Core requests. If the HTTP context cannot be resolved, // this may indicate that the request was incorrectly processed by another server stack. var response = context.Transaction.GetHttpRequest()?.HttpContext.Response ?? diff --git a/src/OpenIddict.Server.AspNetCore/OpenIddictServerAspNetCoreHandlers.cs b/src/OpenIddict.Server.AspNetCore/OpenIddictServerAspNetCoreHandlers.cs index 2645e1f4..599de079 100644 --- a/src/OpenIddict.Server.AspNetCore/OpenIddictServerAspNetCoreHandlers.cs +++ b/src/OpenIddict.Server.AspNetCore/OpenIddictServerAspNetCoreHandlers.cs @@ -75,8 +75,13 @@ public static partial class OpenIddictServerAspNetCoreHandlers .Build(); /// - public ValueTask HandleAsync(ProcessRequestContext context!!) + public ValueTask HandleAsync(ProcessRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // This handler only applies to ASP.NET Core requests. If the HTTP context cannot be resolved, // this may indicate that the request was incorrectly processed by another server stack. var request = context.Transaction.GetHttpRequest() ?? @@ -95,7 +100,7 @@ public static partial class OpenIddictServerAspNetCoreHandlers Matches(request, context.Options.VerificationEndpointUris) ? OpenIddictServerEndpointType.Verification : OpenIddictServerEndpointType.Unknown; - if (context.EndpointType != OpenIddictServerEndpointType.Unknown) + if (context.EndpointType is not OpenIddictServerEndpointType.Unknown) { context.Logger.LogInformation(SR.GetResourceString(SR.ID6053), context.EndpointType); } @@ -173,8 +178,13 @@ public static partial class OpenIddictServerAspNetCoreHandlers .Build(); /// - public ValueTask HandleAsync(ProcessRequestContext context!!) + public ValueTask HandleAsync(ProcessRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // This handler only applies to ASP.NET Core requests. If the HTTP context cannot be resolved, // this may indicate that the request was incorrectly processed by another server stack. var request = context.Transaction.GetHttpRequest() ?? @@ -233,8 +243,13 @@ public static partial class OpenIddictServerAspNetCoreHandlers .Build(); /// - public ValueTask HandleAsync(ProcessRequestContext context!!) + public ValueTask HandleAsync(ProcessRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // This handler only applies to ASP.NET Core requests. If the HTTP context cannot be resolved, // this may indicate that the request was incorrectly processed by another server stack. var request = context.Transaction.GetHttpRequest() ?? @@ -280,8 +295,13 @@ public static partial class OpenIddictServerAspNetCoreHandlers .Build(); /// - public ValueTask HandleAsync(ProcessChallengeContext context!!) + public ValueTask HandleAsync(ProcessChallengeContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var properties = context.Transaction.GetProperty(typeof(AuthenticationProperties).FullName!); if (properties is null) { @@ -354,8 +374,13 @@ public static partial class OpenIddictServerAspNetCoreHandlers .Build(); /// - public ValueTask HandleAsync(ProcessSignInContext context!!) + public ValueTask HandleAsync(ProcessSignInContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var properties = context.Transaction.GetProperty(typeof(AuthenticationProperties).FullName!); if (properties is null) { @@ -404,8 +429,13 @@ public static partial class OpenIddictServerAspNetCoreHandlers .Build(); /// - public ValueTask HandleAsync(ProcessSignOutContext context!!) + public ValueTask HandleAsync(ProcessSignOutContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var properties = context.Transaction.GetProperty(typeof(AuthenticationProperties).FullName!); if (properties is null) { @@ -453,8 +483,13 @@ public static partial class OpenIddictServerAspNetCoreHandlers .Build(); /// - public ValueTask HandleAsync(TContext context!!) + public ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // This handler only applies to ASP.NET Core requests. If the HTTP context cannot be resolved, // this may indicate that the request was incorrectly processed by another server stack. var request = context.Transaction.GetHttpRequest() ?? @@ -499,8 +534,13 @@ public static partial class OpenIddictServerAspNetCoreHandlers .Build(); /// - public async ValueTask HandleAsync(TContext context!!) + public async ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // This handler only applies to ASP.NET Core requests. If the HTTP context cannot be resolved, // this may indicate that the request was incorrectly processed by another server stack. var request = context.Transaction.GetHttpRequest() ?? @@ -574,8 +614,13 @@ public static partial class OpenIddictServerAspNetCoreHandlers .Build(); /// - public async ValueTask HandleAsync(TContext context!!) + public async ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // This handler only applies to ASP.NET Core requests. If the HTTP context cannot be resolved, // this may indicate that the request was incorrectly processed by another server stack. var request = context.Transaction.GetHttpRequest() ?? @@ -645,8 +690,13 @@ public static partial class OpenIddictServerAspNetCoreHandlers .Build(); /// - public ValueTask HandleAsync(TContext context!!) + public ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.Transaction.Request is not null, SR.GetResourceString(SR.ID4008)); // This handler only applies to ASP.NET Core requests. If the HTTP context cannot be resolved, @@ -739,8 +789,13 @@ public static partial class OpenIddictServerAspNetCoreHandlers .Build(); /// - public ValueTask HandleAsync(TContext context!!) + public ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // This handler only applies to ASP.NET Core requests. If the HTTP context cannot be resolved, // this may indicate that the request was incorrectly processed by another server stack. var request = context.Transaction.GetHttpRequest() ?? @@ -782,8 +837,13 @@ public static partial class OpenIddictServerAspNetCoreHandlers .Build(); /// - public ValueTask HandleAsync(TContext context!!) + public ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + context.SkipRequest(); return default; @@ -808,8 +868,13 @@ public static partial class OpenIddictServerAspNetCoreHandlers .Build(); /// - public ValueTask HandleAsync(TContext context!!) + public ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // This handler only applies to ASP.NET Core requests. If the HTTP context cannot be resolved, // this may indicate that the request was incorrectly processed by another server stack. var response = context.Transaction.GetHttpRequest()?.HttpContext.Response ?? @@ -857,8 +922,13 @@ public static partial class OpenIddictServerAspNetCoreHandlers .Build(); /// - public ValueTask HandleAsync(TContext context!!) + public ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // This handler only applies to ASP.NET Core requests. If the HTTP context cannot be resolved, // this may indicate that the request was incorrectly processed by another server stack. var response = context.Transaction.GetHttpRequest()?.HttpContext.Response ?? @@ -881,8 +951,8 @@ public static partial class OpenIddictServerAspNetCoreHandlers { private readonly IOptionsMonitor _options; - public AttachWwwAuthenticateHeader(IOptionsMonitor options!!) - => _options = options; + public AttachWwwAuthenticateHeader(IOptionsMonitor options) + => _options = options ?? throw new ArgumentNullException(nameof(options)); /// /// Gets the default descriptor definition assigned to this handler. @@ -896,8 +966,13 @@ public static partial class OpenIddictServerAspNetCoreHandlers .Build(); /// - public ValueTask HandleAsync(TContext context!!) + public ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // This handler only applies to ASP.NET Core requests. If the HTTP context cannot be resolved, // this may indicate that the request was incorrectly processed by another server stack. var response = context.Transaction.GetHttpRequest()?.HttpContext.Response ?? @@ -1002,8 +1077,13 @@ public static partial class OpenIddictServerAspNetCoreHandlers .Build(); /// - public ValueTask HandleAsync(TContext context!!) + public ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // This handler only applies to ASP.NET Core requests. If the HTTP context cannot be resolved, // this may indicate that the request was incorrectly processed by another server stack. var response = context.Transaction.GetHttpRequest()?.HttpContext.Response ?? @@ -1040,8 +1120,13 @@ public static partial class OpenIddictServerAspNetCoreHandlers .Build(); /// - public async ValueTask HandleAsync(TContext context!!) + public async ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.Transaction.Response is not null, SR.GetResourceString(SR.ID4007)); // This handler only applies to ASP.NET Core requests. If the HTTP context cannot be resolved, @@ -1094,8 +1179,13 @@ public static partial class OpenIddictServerAspNetCoreHandlers .Build(); /// - public ValueTask HandleAsync(TContext context!!) + public ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.Transaction.Response is not null, SR.GetResourceString(SR.ID4007)); if (string.IsNullOrEmpty(context.Transaction.Response.Error)) @@ -1129,8 +1219,13 @@ public static partial class OpenIddictServerAspNetCoreHandlers .Build(); /// - public ValueTask HandleAsync(TContext context!!) + public ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // This handler only applies to ASP.NET Core requests. If the HTTP context cannot be resolved, // this may indicate that the request was incorrectly processed by another server stack. var response = context.Transaction.GetHttpRequest()?.HttpContext.Response ?? @@ -1180,8 +1275,13 @@ public static partial class OpenIddictServerAspNetCoreHandlers .Build(); /// - public async ValueTask HandleAsync(TContext context!!) + public async ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // This handler only applies to ASP.NET Core requests. If the HTTP context cannot be resolved, // this may indicate that the request was incorrectly processed by another server stack. var response = context.Transaction.GetHttpRequest()?.HttpContext.Response ?? @@ -1249,8 +1349,13 @@ public static partial class OpenIddictServerAspNetCoreHandlers .Build(); /// - public ValueTask HandleAsync(TContext context!!) + public ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + context.Logger.LogInformation(SR.GetResourceString(SR.ID6145)); context.HandleRequest(); diff --git a/src/OpenIddict.Server.AspNetCore/OpenIddictServerAspNetCoreHelpers.cs b/src/OpenIddict.Server.AspNetCore/OpenIddictServerAspNetCoreHelpers.cs index bb99ebf2..94198355 100644 --- a/src/OpenIddict.Server.AspNetCore/OpenIddictServerAspNetCoreHelpers.cs +++ b/src/OpenIddict.Server.AspNetCore/OpenIddictServerAspNetCoreHelpers.cs @@ -19,32 +19,68 @@ public static class OpenIddictServerAspNetCoreHelpers /// /// The transaction instance. /// The instance or if it couldn't be found. - public static HttpRequest? GetHttpRequest(this OpenIddictServerTransaction transaction!!) - => transaction.Properties.TryGetValue(typeof(HttpRequest).FullName!, out object? property) && - property is WeakReference reference && - reference.TryGetTarget(out HttpRequest? request) ? request : null; + public static HttpRequest? GetHttpRequest(this OpenIddictServerTransaction transaction) + { + if (transaction is null) + { + throw new ArgumentNullException(nameof(transaction)); + } + + if (!transaction.Properties.TryGetValue(typeof(HttpRequest).FullName!, out object? property)) + { + return null; + } + + if (property is WeakReference reference && reference.TryGetTarget(out HttpRequest? request)) + { + return request; + } + + return null; + } /// /// Retrieves the instance stored in . /// /// The context instance. /// The . - public static OpenIddictServerEndpointType GetOpenIddictServerEndpointType(this HttpContext context!!) - => context.Features.Get()?.Transaction?.EndpointType ?? default; + public static OpenIddictServerEndpointType GetOpenIddictServerEndpointType(this HttpContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return context.Features.Get()?.Transaction?.EndpointType ?? default; + } /// /// Retrieves the instance stored in . /// /// The context instance. - /// The instance or if it couldn't be found. - public static OpenIddictRequest? GetOpenIddictServerRequest(this HttpContext context!!) - => context.Features.Get()?.Transaction?.Request; + /// The instance or null if it couldn't be found. + public static OpenIddictRequest? GetOpenIddictServerRequest(this HttpContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return context.Features.Get()?.Transaction?.Request; + } /// /// Retrieves the instance stored in . /// /// The context instance. - /// The instance or if it couldn't be found. - public static OpenIddictResponse? GetOpenIddictServerResponse(this HttpContext context!!) - => context.Features.Get()?.Transaction?.Response; + /// The instance or null if it couldn't be found. + public static OpenIddictResponse? GetOpenIddictServerResponse(this HttpContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return context.Features.Get()?.Transaction?.Response; + } } diff --git a/src/OpenIddict.Server.DataProtection/OpenIddictServerDataProtectionBuilder.cs b/src/OpenIddict.Server.DataProtection/OpenIddictServerDataProtectionBuilder.cs index a394574c..8a084c5b 100644 --- a/src/OpenIddict.Server.DataProtection/OpenIddictServerDataProtectionBuilder.cs +++ b/src/OpenIddict.Server.DataProtection/OpenIddictServerDataProtectionBuilder.cs @@ -20,8 +20,8 @@ public class OpenIddictServerDataProtectionBuilder /// Initializes a new instance of . /// /// The services collection. - public OpenIddictServerDataProtectionBuilder(IServiceCollection services!!) - => Services = services; + public OpenIddictServerDataProtectionBuilder(IServiceCollection services) + => Services = services ?? throw new ArgumentNullException(nameof(services)); /// /// Gets the services collection. @@ -35,8 +35,13 @@ public class OpenIddictServerDataProtectionBuilder /// The delegate used to configure the OpenIddict options. /// This extension can be safely called multiple times. /// The . - public OpenIddictServerDataProtectionBuilder Configure(Action configuration!!) + public OpenIddictServerDataProtectionBuilder Configure(Action configuration) { + if (configuration is null) + { + throw new ArgumentNullException(nameof(configuration)); + } + Services.Configure(configuration); return this; @@ -48,16 +53,30 @@ public class OpenIddictServerDataProtectionBuilder /// /// The data protection provider used to create token protectors. /// The . - public OpenIddictServerDataProtectionBuilder UseDataProtectionProvider(IDataProtectionProvider provider!!) - => Configure(options => options.DataProtectionProvider = provider); + public OpenIddictServerDataProtectionBuilder UseDataProtectionProvider(IDataProtectionProvider provider) + { + if (provider is null) + { + throw new ArgumentNullException(nameof(provider)); + } + + return Configure(options => options.DataProtectionProvider = provider); + } /// /// Configures OpenIddict to use a specific formatter instead of relying on the default instance. /// /// The formatter used to read and write tokens. /// The . - public OpenIddictServerDataProtectionBuilder UseFormatter(IOpenIddictServerDataProtectionFormatter formatter!!) - => Configure(options => options.Formatter = formatter); + public OpenIddictServerDataProtectionBuilder UseFormatter(IOpenIddictServerDataProtectionFormatter formatter) + { + if (formatter is null) + { + throw new ArgumentNullException(nameof(formatter)); + } + + return Configure(options => options.Formatter = formatter); + } /// /// Configures OpenIddict to use the default token format (JWT) when issuing new access tokens. diff --git a/src/OpenIddict.Server.DataProtection/OpenIddictServerDataProtectionConfiguration.cs b/src/OpenIddict.Server.DataProtection/OpenIddictServerDataProtectionConfiguration.cs index 82247cb5..27f05bd0 100644 --- a/src/OpenIddict.Server.DataProtection/OpenIddictServerDataProtectionConfiguration.cs +++ b/src/OpenIddict.Server.DataProtection/OpenIddictServerDataProtectionConfiguration.cs @@ -21,11 +21,16 @@ public class OpenIddictServerDataProtectionConfiguration : IConfigureOptions class. /// /// The ASP.NET Core Data Protection provider. - public OpenIddictServerDataProtectionConfiguration(IDataProtectionProvider dataProtectionProvider!!) + public OpenIddictServerDataProtectionConfiguration(IDataProtectionProvider dataProtectionProvider) => _dataProtectionProvider = dataProtectionProvider; - public void Configure(OpenIddictServerOptions options!!) + public void Configure(OpenIddictServerOptions options) { + if (options is null) + { + throw new ArgumentNullException(nameof(options)); + } + // Register the built-in event handlers used by the OpenIddict Data Protection server components. options.Handlers.AddRange(OpenIddictServerDataProtectionHandlers.DefaultHandlers); } @@ -36,8 +41,13 @@ public class OpenIddictServerDataProtectionConfiguration : IConfigureOptions /// The name of the options instance to configure, if applicable. /// The options instance to initialize. - public void PostConfigure(string name, OpenIddictServerDataProtectionOptions options!!) + public void PostConfigure(string name, OpenIddictServerDataProtectionOptions options) { + if (options is null) + { + throw new ArgumentNullException(nameof(options)); + } + options.DataProtectionProvider ??= _dataProtectionProvider; } } diff --git a/src/OpenIddict.Server.DataProtection/OpenIddictServerDataProtectionExtensions.cs b/src/OpenIddict.Server.DataProtection/OpenIddictServerDataProtectionExtensions.cs index 35289e5f..df131355 100644 --- a/src/OpenIddict.Server.DataProtection/OpenIddictServerDataProtectionExtensions.cs +++ b/src/OpenIddict.Server.DataProtection/OpenIddictServerDataProtectionExtensions.cs @@ -23,8 +23,13 @@ public static class OpenIddictServerDataProtectionExtensions /// The services builder used by OpenIddict to register new services. /// This extension can be safely called multiple times. /// The . - public static OpenIddictServerDataProtectionBuilder UseDataProtection(this OpenIddictServerBuilder builder!!) + public static OpenIddictServerDataProtectionBuilder UseDataProtection(this OpenIddictServerBuilder builder) { + if (builder is null) + { + throw new ArgumentNullException(nameof(builder)); + } + builder.Services.AddDataProtection(); // Register the built-in server event handlers used by the OpenIddict Data Protection components. @@ -50,8 +55,18 @@ public static class OpenIddictServerDataProtectionExtensions /// This extension can be safely called multiple times. /// The . public static OpenIddictServerBuilder UseDataProtection( - this OpenIddictServerBuilder builder!!, Action configuration!!) + this OpenIddictServerBuilder builder, Action configuration) { + if (builder is null) + { + throw new ArgumentNullException(nameof(builder)); + } + + if (configuration is null) + { + throw new ArgumentNullException(nameof(configuration)); + } + configuration(builder.UseDataProtection()); return builder; diff --git a/src/OpenIddict.Server.DataProtection/OpenIddictServerDataProtectionFormatter.cs b/src/OpenIddict.Server.DataProtection/OpenIddictServerDataProtectionFormatter.cs index 6e035820..2768c1e5 100644 --- a/src/OpenIddict.Server.DataProtection/OpenIddictServerDataProtectionFormatter.cs +++ b/src/OpenIddict.Server.DataProtection/OpenIddictServerDataProtectionFormatter.cs @@ -15,8 +15,13 @@ namespace OpenIddict.Server.DataProtection; public class OpenIddictServerDataProtectionFormatter : IOpenIddictServerDataProtectionFormatter { - public ClaimsPrincipal ReadToken(BinaryReader reader!!) + public ClaimsPrincipal ReadToken(BinaryReader reader) { + if (reader is null) + { + throw new ArgumentNullException(nameof(reader)); + } + var (principal, properties) = Read(reader); // Tokens serialized using the ASP.NET Core Data Protection stack are compound @@ -186,8 +191,18 @@ public class OpenIddictServerDataProtectionFormatter : IOpenIddictServerDataProt } } - public void WriteToken(BinaryWriter writer!!, ClaimsPrincipal principal!!) + public void WriteToken(BinaryWriter writer, ClaimsPrincipal principal) { + if (writer is null) + { + throw new ArgumentNullException(nameof(writer)); + } + + if (principal is null) + { + throw new ArgumentNullException(nameof(principal)); + } + var properties = new Dictionary(); // Unlike ASP.NET Core Data Protection-based tokens, tokens serialized using the new format @@ -303,8 +318,18 @@ public class OpenIddictServerDataProtectionFormatter : IOpenIddictServerDataProt } } - static void WriteClaim(BinaryWriter writer!!, Claim claim!!) + static void WriteClaim(BinaryWriter writer, Claim claim) { + if (writer is null) + { + throw new ArgumentNullException(nameof(writer)); + } + + if (claim is null) + { + throw new ArgumentNullException(nameof(claim)); + } + WriteWithDefault(writer, claim.Type, claim.Subject?.NameClaimType ?? ClaimsIdentity.DefaultNameClaimType); writer.Write(claim.Value); WriteWithDefault(writer, claim.ValueType, ClaimValueTypes.String); diff --git a/src/OpenIddict.Server.DataProtection/OpenIddictServerDataProtectionHandlers.Protection.cs b/src/OpenIddict.Server.DataProtection/OpenIddictServerDataProtectionHandlers.Protection.cs index c6826581..7eccd5f2 100644 --- a/src/OpenIddict.Server.DataProtection/OpenIddictServerDataProtectionHandlers.Protection.cs +++ b/src/OpenIddict.Server.DataProtection/OpenIddictServerDataProtectionHandlers.Protection.cs @@ -38,8 +38,8 @@ public static partial class OpenIddictServerDataProtectionHandlers { private readonly IOptionsMonitor _options; - public ValidateDataProtectionToken(IOptionsMonitor options!!) - => _options = options; + public ValidateDataProtectionToken(IOptionsMonitor options) + => _options = options ?? throw new ArgumentNullException(nameof(options)); /// /// Gets the default descriptor definition assigned to this handler. @@ -238,8 +238,8 @@ public static partial class OpenIddictServerDataProtectionHandlers { private readonly IOptionsMonitor _options; - public GenerateDataProtectionToken(IOptionsMonitor options!!) - => _options = options; + public GenerateDataProtectionToken(IOptionsMonitor options) + => _options = options ?? throw new ArgumentNullException(nameof(options)); /// /// Gets the default descriptor definition assigned to this handler. @@ -252,8 +252,13 @@ public static partial class OpenIddictServerDataProtectionHandlers .Build(); /// - public ValueTask HandleAsync(GenerateTokenContext context!!) + public ValueTask HandleAsync(GenerateTokenContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // If an access token was already attached by another handler, don't overwrite it. if (!string.IsNullOrEmpty(context.Token)) { diff --git a/src/OpenIddict.Server.Owin/OpenIddictServerOwinBuilder.cs b/src/OpenIddict.Server.Owin/OpenIddictServerOwinBuilder.cs index 3612d1f7..77ca4e02 100644 --- a/src/OpenIddict.Server.Owin/OpenIddictServerOwinBuilder.cs +++ b/src/OpenIddict.Server.Owin/OpenIddictServerOwinBuilder.cs @@ -21,8 +21,8 @@ public class OpenIddictServerOwinBuilder /// Initializes a new instance of . /// /// The services collection. - public OpenIddictServerOwinBuilder(IServiceCollection services!!) - => Services = services; + public OpenIddictServerOwinBuilder(IServiceCollection services) + => Services = services ?? throw new ArgumentNullException(nameof(services)); /// /// Gets the services collection. @@ -36,8 +36,13 @@ public class OpenIddictServerOwinBuilder /// The delegate used to configure the OpenIddict options. /// This extension can be safely called multiple times. /// The . - public OpenIddictServerOwinBuilder Configure(Action configuration!!) + public OpenIddictServerOwinBuilder Configure(Action configuration) { + if (configuration is null) + { + throw new ArgumentNullException(nameof(configuration)); + } + Services.Configure(configuration); return this; @@ -151,8 +156,15 @@ public class OpenIddictServerOwinBuilder /// /// The caching policy. /// The . - public OpenIddictServerOwinBuilder SetAuthorizationRequestCachingPolicy(DistributedCacheEntryOptions policy!!) - => Configure(options => options.AuthorizationRequestCachingPolicy = policy); + public OpenIddictServerOwinBuilder SetAuthorizationRequestCachingPolicy(DistributedCacheEntryOptions policy) + { + if (policy is null) + { + throw new ArgumentNullException(nameof(policy)); + } + + return Configure(options => options.AuthorizationRequestCachingPolicy = policy); + } /// /// Sets the caching policy used by the logout endpoint. @@ -160,8 +172,15 @@ public class OpenIddictServerOwinBuilder /// /// The caching policy. /// The . - public OpenIddictServerOwinBuilder SetLogoutRequestCachingPolicy(DistributedCacheEntryOptions policy!!) - => Configure(options => options.LogoutRequestCachingPolicy = policy); + public OpenIddictServerOwinBuilder SetLogoutRequestCachingPolicy(DistributedCacheEntryOptions policy) + { + if (policy is null) + { + throw new ArgumentNullException(nameof(policy)); + } + + return Configure(options => options.LogoutRequestCachingPolicy = policy); + } /// [EditorBrowsable(EditorBrowsableState.Never)] diff --git a/src/OpenIddict.Server.Owin/OpenIddictServerOwinConfiguration.cs b/src/OpenIddict.Server.Owin/OpenIddictServerOwinConfiguration.cs index 7c80efba..cf15a8c2 100644 --- a/src/OpenIddict.Server.Owin/OpenIddictServerOwinConfiguration.cs +++ b/src/OpenIddict.Server.Owin/OpenIddictServerOwinConfiguration.cs @@ -14,14 +14,24 @@ namespace OpenIddict.Server.Owin; public class OpenIddictServerOwinConfiguration : IConfigureOptions, IPostConfigureOptions { - public void Configure(OpenIddictServerOptions options!!) + public void Configure(OpenIddictServerOptions options) { + if (options is null) + { + throw new ArgumentNullException(nameof(options)); + } + // Register the built-in event handlers used by the OpenIddict OWIN server components. options.Handlers.AddRange(OpenIddictServerOwinHandlers.DefaultHandlers); } - public void PostConfigure(string name, OpenIddictServerOwinOptions options!!) + public void PostConfigure(string name, OpenIddictServerOwinOptions options) { + if (options is null) + { + throw new ArgumentNullException(nameof(options)); + } + if (options.AuthenticationMode is AuthenticationMode.Active) { throw new InvalidOperationException(SR.GetResourceString(SR.ID0119)); diff --git a/src/OpenIddict.Server.Owin/OpenIddictServerOwinExtensions.cs b/src/OpenIddict.Server.Owin/OpenIddictServerOwinExtensions.cs index 92f38d17..608e3ad9 100644 --- a/src/OpenIddict.Server.Owin/OpenIddictServerOwinExtensions.cs +++ b/src/OpenIddict.Server.Owin/OpenIddictServerOwinExtensions.cs @@ -22,8 +22,13 @@ public static class OpenIddictServerOwinExtensions /// The services builder used by OpenIddict to register new services. /// This extension can be safely called multiple times. /// The . - public static OpenIddictServerOwinBuilder UseOwin(this OpenIddictServerBuilder builder!!) + public static OpenIddictServerOwinBuilder UseOwin(this OpenIddictServerBuilder builder) { + if (builder is null) + { + throw new ArgumentNullException(nameof(builder)); + } + builder.Services.AddWebEncoders(); // Note: unlike regular OWIN middleware, the OpenIddict server middleware is registered @@ -66,8 +71,18 @@ public static class OpenIddictServerOwinExtensions /// This extension can be safely called multiple times. /// The . public static OpenIddictServerBuilder UseOwin( - this OpenIddictServerBuilder builder!!, Action configuration!!) + this OpenIddictServerBuilder builder, Action configuration) { + if (builder is null) + { + throw new ArgumentNullException(nameof(builder)); + } + + if (configuration is null) + { + throw new ArgumentNullException(nameof(configuration)); + } + configuration(builder.UseOwin()); return builder; diff --git a/src/OpenIddict.Server.Owin/OpenIddictServerOwinHandler.cs b/src/OpenIddict.Server.Owin/OpenIddictServerOwinHandler.cs index df2cd310..b1328849 100644 --- a/src/OpenIddict.Server.Owin/OpenIddictServerOwinHandler.cs +++ b/src/OpenIddict.Server.Owin/OpenIddictServerOwinHandler.cs @@ -25,11 +25,11 @@ public class OpenIddictServerOwinHandler : AuthenticationHandlerThe OpenIddict server dispatcher used by this instance. /// The OpenIddict server factory used by this instance. public OpenIddictServerOwinHandler( - IOpenIddictServerDispatcher dispatcher!!, - IOpenIddictServerFactory factory!!) + IOpenIddictServerDispatcher dispatcher, + IOpenIddictServerFactory factory) { - _dispatcher = dispatcher; - _factory = factory; + _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); + _factory = factory ?? throw new ArgumentNullException(nameof(factory)); } /// diff --git a/src/OpenIddict.Server.Owin/OpenIddictServerOwinHandlerFilters.cs b/src/OpenIddict.Server.Owin/OpenIddictServerOwinHandlerFilters.cs index 5a4536d0..dd3179d3 100644 --- a/src/OpenIddict.Server.Owin/OpenIddictServerOwinHandlerFilters.cs +++ b/src/OpenIddict.Server.Owin/OpenIddictServerOwinHandlerFilters.cs @@ -21,11 +21,18 @@ public static class OpenIddictServerOwinHandlerFilters { private readonly IOptionsMonitor _options; - public RequireAuthorizationRequestCachingEnabled(IOptionsMonitor options!!) - => _options = options; - - public ValueTask IsActiveAsync(BaseContext context!!) - => new(_options.CurrentValue.EnableAuthorizationRequestCaching); + public RequireAuthorizationRequestCachingEnabled(IOptionsMonitor options) + => _options = options ?? throw new ArgumentNullException(nameof(options)); + + public ValueTask IsActiveAsync(BaseContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(_options.CurrentValue.EnableAuthorizationRequestCaching); + } } /// @@ -36,11 +43,18 @@ public static class OpenIddictServerOwinHandlerFilters { private readonly IOptionsMonitor _options; - public RequireAuthorizationEndpointPassthroughEnabled(IOptionsMonitor options!!) - => _options = options; + public RequireAuthorizationEndpointPassthroughEnabled(IOptionsMonitor options) + => _options = options ?? throw new ArgumentNullException(nameof(options)); + + public ValueTask IsActiveAsync(BaseContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } - public ValueTask IsActiveAsync(BaseContext context!!) - => new(_options.CurrentValue.EnableAuthorizationEndpointPassthrough); + return new(_options.CurrentValue.EnableAuthorizationEndpointPassthrough); + } } /// @@ -50,11 +64,18 @@ public static class OpenIddictServerOwinHandlerFilters { private readonly IOptionsMonitor _options; - public RequireErrorPassthroughEnabled(IOptionsMonitor options!!) - => _options = options; + public RequireErrorPassthroughEnabled(IOptionsMonitor options) + => _options = options ?? throw new ArgumentNullException(nameof(options)); + + public ValueTask IsActiveAsync(BaseContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } - public ValueTask IsActiveAsync(BaseContext context!!) - => new(_options.CurrentValue.EnableErrorPassthrough); + return new(_options.CurrentValue.EnableErrorPassthrough); + } } /// @@ -64,11 +85,18 @@ public static class OpenIddictServerOwinHandlerFilters { private readonly IOptionsMonitor _options; - public RequireLogoutRequestCachingEnabled(IOptionsMonitor options!!) - => _options = options; + public RequireLogoutRequestCachingEnabled(IOptionsMonitor options) + => _options = options ?? throw new ArgumentNullException(nameof(options)); - public ValueTask IsActiveAsync(BaseContext context!!) - => new(_options.CurrentValue.EnableLogoutRequestCaching); + public ValueTask IsActiveAsync(BaseContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(_options.CurrentValue.EnableLogoutRequestCaching); + } } /// @@ -79,11 +107,18 @@ public static class OpenIddictServerOwinHandlerFilters { private readonly IOptionsMonitor _options; - public RequireLogoutEndpointPassthroughEnabled(IOptionsMonitor options!!) - => _options = options; + public RequireLogoutEndpointPassthroughEnabled(IOptionsMonitor options) + => _options = options ?? throw new ArgumentNullException(nameof(options)); + + public ValueTask IsActiveAsync(BaseContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } - public ValueTask IsActiveAsync(BaseContext context!!) - => new(_options.CurrentValue.EnableLogoutEndpointPassthrough); + return new(_options.CurrentValue.EnableLogoutEndpointPassthrough); + } } /// @@ -91,8 +126,15 @@ public static class OpenIddictServerOwinHandlerFilters /// public class RequireOwinRequest : IOpenIddictServerHandlerFilter { - public ValueTask IsActiveAsync(BaseContext context!!) - => new(context.Transaction.GetOwinRequest() is not null); + public ValueTask IsActiveAsync(BaseContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(context.Transaction.GetOwinRequest() is not null); + } } /// @@ -102,11 +144,18 @@ public static class OpenIddictServerOwinHandlerFilters { private readonly IOptionsMonitor _options; - public RequireTransportSecurityRequirementEnabled(IOptionsMonitor options!!) - => _options = options; + public RequireTransportSecurityRequirementEnabled(IOptionsMonitor options) + => _options = options ?? throw new ArgumentNullException(nameof(options)); - public ValueTask IsActiveAsync(BaseContext context!!) - => new(!_options.CurrentValue.DisableTransportSecurityRequirement); + public ValueTask IsActiveAsync(BaseContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(!_options.CurrentValue.DisableTransportSecurityRequirement); + } } /// @@ -117,11 +166,18 @@ public static class OpenIddictServerOwinHandlerFilters { private readonly IOptionsMonitor _options; - public RequireTokenEndpointPassthroughEnabled(IOptionsMonitor options!!) - => _options = options; + public RequireTokenEndpointPassthroughEnabled(IOptionsMonitor options) + => _options = options ?? throw new ArgumentNullException(nameof(options)); + + public ValueTask IsActiveAsync(BaseContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } - public ValueTask IsActiveAsync(BaseContext context!!) - => new(_options.CurrentValue.EnableTokenEndpointPassthrough); + return new(_options.CurrentValue.EnableTokenEndpointPassthrough); + } } /// @@ -132,11 +188,18 @@ public static class OpenIddictServerOwinHandlerFilters { private readonly IOptionsMonitor _options; - public RequireUserinfoEndpointPassthroughEnabled(IOptionsMonitor options!!) - => _options = options; + public RequireUserinfoEndpointPassthroughEnabled(IOptionsMonitor options) + => _options = options ?? throw new ArgumentNullException(nameof(options)); - public ValueTask IsActiveAsync(BaseContext context!!) - => new(_options.CurrentValue.EnableUserinfoEndpointPassthrough); + public ValueTask IsActiveAsync(BaseContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(_options.CurrentValue.EnableUserinfoEndpointPassthrough); + } } /// @@ -147,10 +210,17 @@ public static class OpenIddictServerOwinHandlerFilters { private readonly IOptionsMonitor _options; - public RequireVerificationEndpointPassthroughEnabled(IOptionsMonitor options!!) - => _options = options; + public RequireVerificationEndpointPassthroughEnabled(IOptionsMonitor options) + => _options = options ?? throw new ArgumentNullException(nameof(options)); + + public ValueTask IsActiveAsync(BaseContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } - public ValueTask IsActiveAsync(BaseContext context!!) - => new(_options.CurrentValue.EnableVerificationEndpointPassthrough); + return new(_options.CurrentValue.EnableVerificationEndpointPassthrough); + } } } diff --git a/src/OpenIddict.Server.Owin/OpenIddictServerOwinHandlers.Authentication.cs b/src/OpenIddict.Server.Owin/OpenIddictServerOwinHandlers.Authentication.cs index c465aa28..bc7cb726 100644 --- a/src/OpenIddict.Server.Owin/OpenIddictServerOwinHandlers.Authentication.cs +++ b/src/OpenIddict.Server.Owin/OpenIddictServerOwinHandlers.Authentication.cs @@ -61,8 +61,8 @@ public static partial class OpenIddictServerOwinHandlers public RestoreCachedRequestParameters() => throw new InvalidOperationException(SR.GetResourceString(SR.ID0116)); - public RestoreCachedRequestParameters(IDistributedCache cache!!) - => _cache = cache; + public RestoreCachedRequestParameters(IDistributedCache cache) + => _cache = cache ?? throw new ArgumentNullException(nameof(cache)); /// /// Gets the default descriptor definition assigned to this handler. @@ -77,8 +77,13 @@ public static partial class OpenIddictServerOwinHandlers .Build(); /// - public async ValueTask HandleAsync(ExtractAuthorizationRequestContext context!!) + public async ValueTask HandleAsync(ExtractAuthorizationRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.Request is not null, SR.GetResourceString(SR.ID4008)); // If a request_id parameter can be found in the authorization request, @@ -153,10 +158,10 @@ public static partial class OpenIddictServerOwinHandlers public CacheRequestParameters( IDistributedCache cache, - IOptionsMonitor options!!) + IOptionsMonitor options) { - _cache = cache; - _options = options; + _cache = cache ?? throw new ArgumentNullException(nameof(cache)); + _options = options ?? throw new ArgumentNullException(nameof(options)); } /// @@ -172,8 +177,13 @@ public static partial class OpenIddictServerOwinHandlers .Build(); /// - public async ValueTask HandleAsync(ExtractAuthorizationRequestContext context!!) + public async ValueTask HandleAsync(ExtractAuthorizationRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.Request is not null, SR.GetResourceString(SR.ID4008)); // This handler only applies to OWIN requests. If The OWIN request cannot be resolved, @@ -255,8 +265,8 @@ public static partial class OpenIddictServerOwinHandlers public RemoveCachedRequest() => throw new InvalidOperationException(SR.GetResourceString(SR.ID0116)); - public RemoveCachedRequest(IDistributedCache cache!!) - => _cache = cache; + public RemoveCachedRequest(IDistributedCache cache) + => _cache = cache ?? throw new ArgumentNullException(nameof(cache)); /// /// Gets the default descriptor definition assigned to this handler. @@ -271,8 +281,13 @@ public static partial class OpenIddictServerOwinHandlers .Build(); /// - public ValueTask HandleAsync(ApplyAuthorizationResponseContext context!!) + public ValueTask HandleAsync(ApplyAuthorizationResponseContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + if (string.IsNullOrEmpty(context.Request?.RequestId)) { return default; @@ -311,12 +326,20 @@ public static partial class OpenIddictServerOwinHandlers .Build(); /// - public async ValueTask HandleAsync(ApplyAuthorizationResponseContext context!!) + public async ValueTask HandleAsync(ApplyAuthorizationResponseContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // This handler only applies to OWIN requests. If The OWIN request cannot be resolved, // this may indicate that the request was incorrectly processed by another server stack. - var response = context.Transaction.GetOwinRequest()?.Context.Response ?? + var response = context.Transaction.GetOwinRequest()?.Context.Response; + if (response is null) + { throw new InvalidOperationException(SR.GetResourceString(SR.ID0120)); + } if (string.IsNullOrEmpty(context.RedirectUri) || !string.Equals(context.ResponseMode, ResponseModes.FormPost, StringComparison.Ordinal)) @@ -392,12 +415,20 @@ public static partial class OpenIddictServerOwinHandlers .Build(); /// - public ValueTask HandleAsync(ApplyAuthorizationResponseContext context!!) + public ValueTask HandleAsync(ApplyAuthorizationResponseContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // This handler only applies to OWIN requests. If The OWIN request cannot be resolved, // this may indicate that the request was incorrectly processed by another server stack. - var response = context.Transaction.GetOwinRequest()?.Context.Response ?? + var response = context.Transaction.GetOwinRequest()?.Context.Response; + if (response is null) + { throw new InvalidOperationException(SR.GetResourceString(SR.ID0120)); + } if (string.IsNullOrEmpty(context.RedirectUri) || !string.Equals(context.ResponseMode, ResponseModes.Query, StringComparison.Ordinal)) @@ -448,12 +479,20 @@ public static partial class OpenIddictServerOwinHandlers .Build(); /// - public ValueTask HandleAsync(ApplyAuthorizationResponseContext context!!) + public ValueTask HandleAsync(ApplyAuthorizationResponseContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // This handler only applies to OWIN requests. If The OWIN request cannot be resolved, // this may indicate that the request was incorrectly processed by another server stack. - var response = context.Transaction.GetOwinRequest()?.Context.Response ?? + var response = context.Transaction.GetOwinRequest()?.Context.Response; + if (response is null) + { throw new InvalidOperationException(SR.GetResourceString(SR.ID0120)); + } if (string.IsNullOrEmpty(context.RedirectUri) || !string.Equals(context.ResponseMode, ResponseModes.Fragment, StringComparison.Ordinal)) diff --git a/src/OpenIddict.Server.Owin/OpenIddictServerOwinHandlers.Device.cs b/src/OpenIddict.Server.Owin/OpenIddictServerOwinHandlers.Device.cs index d3cf300c..82bcd6d6 100644 --- a/src/OpenIddict.Server.Owin/OpenIddictServerOwinHandlers.Device.cs +++ b/src/OpenIddict.Server.Owin/OpenIddictServerOwinHandlers.Device.cs @@ -68,8 +68,13 @@ public static partial class OpenIddictServerOwinHandlers .Build(); /// - public ValueTask HandleAsync(ApplyVerificationResponseContext context!!) + public ValueTask HandleAsync(ApplyVerificationResponseContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // This handler only applies to OWIN requests. If The OWIN request cannot be resolved, // this may indicate that the request was incorrectly processed by another server stack. var response = context.Transaction.GetOwinRequest()?.Context.Response ?? diff --git a/src/OpenIddict.Server.Owin/OpenIddictServerOwinHandlers.Session.cs b/src/OpenIddict.Server.Owin/OpenIddictServerOwinHandlers.Session.cs index bb2a9e32..c8f23b4e 100644 --- a/src/OpenIddict.Server.Owin/OpenIddictServerOwinHandlers.Session.cs +++ b/src/OpenIddict.Server.Owin/OpenIddictServerOwinHandlers.Session.cs @@ -59,8 +59,8 @@ public static partial class OpenIddictServerOwinHandlers public RestoreCachedRequestParameters() => throw new InvalidOperationException(SR.GetResourceString(SR.ID0116)); - public RestoreCachedRequestParameters(IDistributedCache cache!!) - => _cache = cache; + public RestoreCachedRequestParameters(IDistributedCache cache) + => _cache = cache ?? throw new ArgumentNullException(nameof(cache)); /// /// Gets the default descriptor definition assigned to this handler. @@ -75,8 +75,13 @@ public static partial class OpenIddictServerOwinHandlers .Build(); /// - public async ValueTask HandleAsync(ExtractLogoutRequestContext context!!) + public async ValueTask HandleAsync(ExtractLogoutRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.Request is not null, SR.GetResourceString(SR.ID4008)); // If a request_id parameter can be found in the logout request, @@ -151,10 +156,10 @@ public static partial class OpenIddictServerOwinHandlers public CacheRequestParameters( IDistributedCache cache, - IOptionsMonitor options!!) + IOptionsMonitor options) { - _cache = cache; - _options = options; + _cache = cache ?? throw new ArgumentNullException(nameof(cache)); + _options = options ?? throw new ArgumentNullException(nameof(options)); } /// @@ -170,8 +175,13 @@ public static partial class OpenIddictServerOwinHandlers .Build(); /// - public async ValueTask HandleAsync(ExtractLogoutRequestContext context!!) + public async ValueTask HandleAsync(ExtractLogoutRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.Request is not null, SR.GetResourceString(SR.ID4008)); // This handler only applies to OWIN requests. If The OWIN request cannot be resolved, @@ -253,8 +263,8 @@ public static partial class OpenIddictServerOwinHandlers public RemoveCachedRequest() => throw new InvalidOperationException(SR.GetResourceString(SR.ID0116)); - public RemoveCachedRequest(IDistributedCache cache!!) - => _cache = cache; + public RemoveCachedRequest(IDistributedCache cache) + => _cache = cache ?? throw new ArgumentNullException(nameof(cache)); /// /// Gets the default descriptor definition assigned to this handler. @@ -269,8 +279,13 @@ public static partial class OpenIddictServerOwinHandlers .Build(); /// - public ValueTask HandleAsync(ApplyLogoutResponseContext context!!) + public ValueTask HandleAsync(ApplyLogoutResponseContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + if (string.IsNullOrEmpty(context.Request?.RequestId)) { return default; @@ -304,12 +319,20 @@ public static partial class OpenIddictServerOwinHandlers .Build(); /// - public ValueTask HandleAsync(ApplyLogoutResponseContext context!!) + public ValueTask HandleAsync(ApplyLogoutResponseContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // This handler only applies to OWIN requests. If The OWIN request cannot be resolved, // this may indicate that the request was incorrectly processed by another server stack. - var response = context.Transaction.GetOwinRequest()?.Context.Response ?? + var response = context.Transaction.GetOwinRequest()?.Context.Response; + if (response is null) + { throw new InvalidOperationException(SR.GetResourceString(SR.ID0120)); + } if (string.IsNullOrEmpty(context.PostLogoutRedirectUri)) { @@ -359,12 +382,20 @@ public static partial class OpenIddictServerOwinHandlers .Build(); /// - public ValueTask HandleAsync(ApplyLogoutResponseContext context!!) + public ValueTask HandleAsync(ApplyLogoutResponseContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // This handler only applies to OWIN requests. If The OWIN request cannot be resolved, // this may indicate that the request was incorrectly processed by another server stack. - var response = context.Transaction.GetOwinRequest()?.Context.Response ?? + var response = context.Transaction.GetOwinRequest()?.Context.Response; + if (response is null) + { throw new InvalidOperationException(SR.GetResourceString(SR.ID0120)); + } // Note: this handler only executes if no post_logout_redirect_uri was specified // and if the response doesn't correspond to an error, that must be handled locally. diff --git a/src/OpenIddict.Server.Owin/OpenIddictServerOwinHandlers.cs b/src/OpenIddict.Server.Owin/OpenIddictServerOwinHandlers.cs index 5bc324da..409d88bf 100644 --- a/src/OpenIddict.Server.Owin/OpenIddictServerOwinHandlers.cs +++ b/src/OpenIddict.Server.Owin/OpenIddictServerOwinHandlers.cs @@ -62,8 +62,13 @@ public static partial class OpenIddictServerOwinHandlers .Build(); /// - public ValueTask HandleAsync(ProcessRequestContext context!!) + public ValueTask HandleAsync(ProcessRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // This handler only applies to OWIN requests. If The OWIN request cannot be resolved, // this may indicate that the request was incorrectly processed by another server stack. var request = context.Transaction.GetOwinRequest() ?? @@ -82,7 +87,7 @@ public static partial class OpenIddictServerOwinHandlers Matches(request, context.Options.VerificationEndpointUris) ? OpenIddictServerEndpointType.Verification : OpenIddictServerEndpointType.Unknown; - if (context.EndpointType != OpenIddictServerEndpointType.Unknown) + if (context.EndpointType is not OpenIddictServerEndpointType.Unknown) { context.Logger.LogInformation(SR.GetResourceString(SR.ID6053), context.EndpointType); } @@ -160,8 +165,13 @@ public static partial class OpenIddictServerOwinHandlers .Build(); /// - public ValueTask HandleAsync(ProcessRequestContext context!!) + public ValueTask HandleAsync(ProcessRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // This handler only applies to OWIN requests. If The OWIN request cannot be resolved, // this may indicate that the request was incorrectly processed by another server stack. var request = context.Transaction.GetOwinRequest() ?? @@ -220,8 +230,13 @@ public static partial class OpenIddictServerOwinHandlers .Build(); /// - public ValueTask HandleAsync(ProcessRequestContext context!!) + public ValueTask HandleAsync(ProcessRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // This handler only applies to OWIN requests. If The OWIN request cannot be resolved, // this may indicate that the request was incorrectly processed by another server stack. var request = context.Transaction.GetOwinRequest() ?? @@ -267,8 +282,13 @@ public static partial class OpenIddictServerOwinHandlers .Build(); /// - public ValueTask HandleAsync(ProcessChallengeContext context!!) + public ValueTask HandleAsync(ProcessChallengeContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var properties = context.Transaction.GetProperty(typeof(AuthenticationProperties).FullName!); if (properties is null) { @@ -321,8 +341,13 @@ public static partial class OpenIddictServerOwinHandlers .Build(); /// - public ValueTask HandleAsync(TContext context!!) + public ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // This handler only applies to OWIN requests. If The OWIN request cannot be resolved, // this may indicate that the request was incorrectly processed by another server stack. var request = context.Transaction.GetOwinRequest() ?? @@ -367,8 +392,13 @@ public static partial class OpenIddictServerOwinHandlers .Build(); /// - public async ValueTask HandleAsync(TContext context!!) + public async ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // This handler only applies to OWIN requests. If The OWIN request cannot be resolved, // this may indicate that the request was incorrectly processed by another server stack. var request = context.Transaction.GetOwinRequest() ?? @@ -442,8 +472,13 @@ public static partial class OpenIddictServerOwinHandlers .Build(); /// - public async ValueTask HandleAsync(TContext context!!) + public async ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // This handler only applies to OWIN requests. If The OWIN request cannot be resolved, // this may indicate that the request was incorrectly processed by another server stack. var request = context.Transaction.GetOwinRequest() ?? @@ -513,8 +548,13 @@ public static partial class OpenIddictServerOwinHandlers .Build(); /// - public ValueTask HandleAsync(TContext context!!) + public ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.Transaction.Request is not null, SR.GetResourceString(SR.ID4008)); // This handler only applies to OWIN requests. If The OWIN request cannot be resolved, @@ -607,8 +647,13 @@ public static partial class OpenIddictServerOwinHandlers .Build(); /// - public ValueTask HandleAsync(TContext context!!) + public ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.Transaction.Request is not null, SR.GetResourceString(SR.ID4008)); // This handler only applies to OWIN requests. If The OWIN request cannot be resolved, @@ -650,8 +695,13 @@ public static partial class OpenIddictServerOwinHandlers .Build(); /// - public ValueTask HandleAsync(TContext context!!) + public ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + context.SkipRequest(); return default; @@ -676,8 +726,13 @@ public static partial class OpenIddictServerOwinHandlers .Build(); /// - public ValueTask HandleAsync(TContext context!!) + public ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.Transaction.Response is not null, SR.GetResourceString(SR.ID4007)); // This handler only applies to OWIN requests. If The OWIN request cannot be resolved, @@ -725,8 +780,13 @@ public static partial class OpenIddictServerOwinHandlers .Build(); /// - public ValueTask HandleAsync(TContext context!!) + public ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // This handler only applies to OWIN requests. If The OWIN request cannot be resolved, // this may indicate that the request was incorrectly processed by another server stack. var response = context.Transaction.GetOwinRequest()?.Context.Response ?? @@ -749,8 +809,8 @@ public static partial class OpenIddictServerOwinHandlers { private readonly IOptionsMonitor _options; - public AttachWwwAuthenticateHeader(IOptionsMonitor options!!) - => _options = options; + public AttachWwwAuthenticateHeader(IOptionsMonitor options) + => _options = options ?? throw new ArgumentNullException(nameof(options)); /// /// Gets the default descriptor definition assigned to this handler. @@ -764,8 +824,13 @@ public static partial class OpenIddictServerOwinHandlers .Build(); /// - public ValueTask HandleAsync(TContext context!!) + public ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.Transaction.Response is not null, SR.GetResourceString(SR.ID4007)); // This handler only applies to OWIN requests. If The OWIN request cannot be resolved, @@ -870,8 +935,13 @@ public static partial class OpenIddictServerOwinHandlers .Build(); /// - public ValueTask HandleAsync(TContext context!!) + public ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // This handler only applies to OWIN requests. If The OWIN request cannot be resolved, // this may indicate that the request was incorrectly processed by another server stack. var response = context.Transaction.GetOwinRequest()?.Context.Response ?? @@ -908,8 +978,13 @@ public static partial class OpenIddictServerOwinHandlers .Build(); /// - public async ValueTask HandleAsync(TContext context!!) + public async ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.Transaction.Response is not null, SR.GetResourceString(SR.ID4007)); // This handler only applies to OWIN requests. If The OWIN request cannot be resolved, @@ -962,8 +1037,13 @@ public static partial class OpenIddictServerOwinHandlers .Build(); /// - public ValueTask HandleAsync(TContext context!!) + public ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.Transaction.Response is not null, SR.GetResourceString(SR.ID4007)); if (string.IsNullOrEmpty(context.Transaction.Response.Error)) @@ -999,8 +1079,13 @@ public static partial class OpenIddictServerOwinHandlers .Build(); /// - public async ValueTask HandleAsync(TContext context!!) + public async ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.Transaction.Response is not null, SR.GetResourceString(SR.ID4007)); // This handler only applies to OWIN requests. If The OWIN request cannot be resolved, @@ -1068,8 +1153,13 @@ public static partial class OpenIddictServerOwinHandlers .Build(); /// - public ValueTask HandleAsync(TContext context!!) + public ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + context.Logger.LogInformation(SR.GetResourceString(SR.ID6145)); context.HandleRequest(); diff --git a/src/OpenIddict.Server.Owin/OpenIddictServerOwinHelpers.cs b/src/OpenIddict.Server.Owin/OpenIddictServerOwinHelpers.cs index dd2b8223..a4af54ae 100644 --- a/src/OpenIddict.Server.Owin/OpenIddictServerOwinHelpers.cs +++ b/src/OpenIddict.Server.Owin/OpenIddictServerOwinHelpers.cs @@ -21,40 +21,83 @@ public static class OpenIddictServerOwinHelpers /// /// The application builder used to register middleware instances. /// The . - public static IAppBuilder UseOpenIddictServer(this IAppBuilder app!!) - => app.Use(); + public static IAppBuilder UseOpenIddictServer(this IAppBuilder app) + { + if (app is null) + { + throw new ArgumentNullException(nameof(app)); + } + + return app.Use(); + } /// /// Retrieves the instance stored in the properties. /// /// The transaction instance. /// The instance or if it couldn't be found. - public static IOwinRequest? GetOwinRequest(this OpenIddictServerTransaction transaction!!) - => transaction.Properties.TryGetValue(typeof(IOwinRequest).FullName!, out object? property) && - property is WeakReference reference && - reference.TryGetTarget(out IOwinRequest? request) ? request : null; + public static IOwinRequest? GetOwinRequest(this OpenIddictServerTransaction transaction) + { + if (transaction is null) + { + throw new ArgumentNullException(nameof(transaction)); + } + + if (!transaction.Properties.TryGetValue(typeof(IOwinRequest).FullName!, out object? property)) + { + return null; + } + + if (property is WeakReference reference && reference.TryGetTarget(out IOwinRequest? request)) + { + return request; + } + + return null; + } /// /// Retrieves the instance stored in . /// /// The context instance. /// The . - public static OpenIddictServerEndpointType GetOpenIddictServerEndpointType(this IOwinContext context!!) - => context.Get(typeof(OpenIddictServerTransaction).FullName)?.EndpointType ?? default; + public static OpenIddictServerEndpointType GetOpenIddictServerEndpointType(this IOwinContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return context.Get(typeof(OpenIddictServerTransaction).FullName)?.EndpointType ?? default; + } /// /// Retrieves the instance stored in . /// /// The context instance. - /// The instance or if it couldn't be found. - public static OpenIddictRequest? GetOpenIddictServerRequest(this IOwinContext context!!) - => context.Get(typeof(OpenIddictServerTransaction).FullName)?.Request; + /// The instance or null if it couldn't be found. + public static OpenIddictRequest? GetOpenIddictServerRequest(this IOwinContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return context.Get(typeof(OpenIddictServerTransaction).FullName)?.Request; + } /// /// Retrieves the instance stored in . /// /// The context instance. - /// The instance or if it couldn't be found. - public static OpenIddictResponse? GetOpenIddictServerResponse(this IOwinContext context!!) - => context.Get(typeof(OpenIddictServerTransaction).FullName)?.Response; + /// The instance or null if it couldn't be found. + public static OpenIddictResponse? GetOpenIddictServerResponse(this IOwinContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return context.Get(typeof(OpenIddictServerTransaction).FullName)?.Response; + } } diff --git a/src/OpenIddict.Server.Owin/OpenIddictServerOwinMiddleware.cs b/src/OpenIddict.Server.Owin/OpenIddictServerOwinMiddleware.cs index f6a3acc7..61387aa4 100644 --- a/src/OpenIddict.Server.Owin/OpenIddictServerOwinMiddleware.cs +++ b/src/OpenIddict.Server.Owin/OpenIddictServerOwinMiddleware.cs @@ -29,13 +29,13 @@ public class OpenIddictServerOwinMiddleware : AuthenticationMiddlewareThe OpenIddict server factory. public OpenIddictServerOwinMiddleware( OwinMiddleware? next, - IOptionsMonitor options!!, - IOpenIddictServerDispatcher dispatcher!!, - IOpenIddictServerFactory factory!!) + IOptionsMonitor options, + IOpenIddictServerDispatcher dispatcher, + IOpenIddictServerFactory factory) : base(next, options.CurrentValue) { - _dispatcher = dispatcher; - _factory = factory; + _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); + _factory = factory ?? throw new ArgumentNullException(nameof(factory)); } /// diff --git a/src/OpenIddict.Server.Owin/OpenIddictServerOwinMiddlewareFactory.cs b/src/OpenIddict.Server.Owin/OpenIddictServerOwinMiddlewareFactory.cs index 20b42032..d80eb5dd 100644 --- a/src/OpenIddict.Server.Owin/OpenIddictServerOwinMiddlewareFactory.cs +++ b/src/OpenIddict.Server.Owin/OpenIddictServerOwinMiddlewareFactory.cs @@ -33,8 +33,13 @@ public class OpenIddictServerOwinMiddlewareFactory : OwinMiddleware /// /// A that can be used to monitor the asynchronous operation. /// - public override Task Invoke(IOwinContext context!!) + public override Task Invoke(IOwinContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var provider = context.Get(typeof(IServiceProvider).FullName) ?? throw new InvalidOperationException(SR.GetResourceString(SR.ID0121)); diff --git a/src/OpenIddict.Server/OpenIddictServerBuilder.cs b/src/OpenIddict.Server/OpenIddictServerBuilder.cs index 3d751669..4f0c9f2f 100644 --- a/src/OpenIddict.Server/OpenIddictServerBuilder.cs +++ b/src/OpenIddict.Server/OpenIddictServerBuilder.cs @@ -25,8 +25,8 @@ public class OpenIddictServerBuilder /// Initializes a new instance of . /// /// The services collection. - public OpenIddictServerBuilder(IServiceCollection services!!) - => Services = services; + public OpenIddictServerBuilder(IServiceCollection services) + => Services = services ?? throw new ArgumentNullException(nameof(services)); /// /// Gets the services collection. @@ -42,9 +42,14 @@ public class OpenIddictServerBuilder /// The . [EditorBrowsable(EditorBrowsableState.Advanced)] public OpenIddictServerBuilder AddEventHandler( - Action> configuration!!) + Action> configuration) where TContext : OpenIddictServerEvents.BaseContext { + if (configuration is null) + { + throw new ArgumentNullException(nameof(configuration)); + } + // Note: handlers registered using this API are assumed to be custom handlers by default. var builder = OpenIddictServerHandlerDescriptor.CreateBuilder() .SetType(OpenIddictServerHandlerType.Custom); @@ -60,8 +65,13 @@ public class OpenIddictServerBuilder /// The handler descriptor. /// The . [EditorBrowsable(EditorBrowsableState.Advanced)] - public OpenIddictServerBuilder AddEventHandler(OpenIddictServerHandlerDescriptor descriptor!!) + public OpenIddictServerBuilder AddEventHandler(OpenIddictServerHandlerDescriptor descriptor) { + if (descriptor is null) + { + throw new ArgumentNullException(nameof(descriptor)); + } + // Register the handler in the services collection. Services.Add(descriptor.ServiceDescriptor); @@ -74,8 +84,13 @@ public class OpenIddictServerBuilder /// The descriptor corresponding to the handler to remove. /// The . [EditorBrowsable(EditorBrowsableState.Advanced)] - public OpenIddictServerBuilder RemoveEventHandler(OpenIddictServerHandlerDescriptor descriptor!!) + public OpenIddictServerBuilder RemoveEventHandler(OpenIddictServerHandlerDescriptor descriptor) { + if (descriptor is null) + { + throw new ArgumentNullException(nameof(descriptor)); + } + Services.RemoveAll(descriptor.ServiceDescriptor.ServiceType); Services.PostConfigure(options => @@ -98,8 +113,13 @@ public class OpenIddictServerBuilder /// The delegate used to configure the OpenIddict options. /// This extension can be safely called multiple times. /// The . - public OpenIddictServerBuilder Configure(Action configuration!!) + public OpenIddictServerBuilder Configure(Action configuration) { + if (configuration is null) + { + throw new ArgumentNullException(nameof(configuration)); + } + Services.Configure(configuration); return this; @@ -119,16 +139,28 @@ public class OpenIddictServerBuilder /// /// The encrypting credentials. /// The . - public OpenIddictServerBuilder AddEncryptionCredentials(EncryptingCredentials credentials!!) - => Configure(options => options.EncryptionCredentials.Add(credentials)); + public OpenIddictServerBuilder AddEncryptionCredentials(EncryptingCredentials credentials) + { + if (credentials is null) + { + throw new ArgumentNullException(nameof(credentials)); + } + + return Configure(options => options.EncryptionCredentials.Add(credentials)); + } /// /// Registers an encryption key. /// /// The security key. /// The . - public OpenIddictServerBuilder AddEncryptionKey(SecurityKey key!!) + public OpenIddictServerBuilder AddEncryptionKey(SecurityKey key) { + if (key is null) + { + throw new ArgumentNullException(nameof(key)); + } + // If the encryption key is an asymmetric security key, ensure it has a private key. if (key is AsymmetricSecurityKey asymmetricSecurityKey && asymmetricSecurityKey.PrivateKeyStatus is PrivateKeyStatus.DoesNotExist) @@ -170,8 +202,13 @@ public class OpenIddictServerBuilder /// The . [SuppressMessage("Reliability", "CA2000:Dispose objects before losing scope", Justification = "The X.509 certificate is attached to the server options.")] - public OpenIddictServerBuilder AddDevelopmentEncryptionCertificate(X500DistinguishedName subject!!) + public OpenIddictServerBuilder AddDevelopmentEncryptionCertificate(X500DistinguishedName subject) { + if (subject is null) + { + throw new ArgumentNullException(nameof(subject)); + } + using var store = new X509Store(StoreName.My, StoreLocation.CurrentUser); store.Open(OpenFlags.ReadWrite); @@ -326,8 +363,13 @@ public class OpenIddictServerBuilder /// /// The encryption certificate. /// The . - public OpenIddictServerBuilder AddEncryptionCertificate(X509Certificate2 certificate!!) + public OpenIddictServerBuilder AddEncryptionCertificate(X509Certificate2 certificate) { + if (certificate is null) + { + throw new ArgumentNullException(nameof(certificate)); + } + // If the certificate is a X.509v3 certificate that specifies at least one // key usage, ensure that the certificate key can be used for key encryption. if (certificate.Version >= 3) @@ -373,9 +415,14 @@ public class OpenIddictServerBuilder /// An enumeration of flags indicating how and where to store the private key of the certificate. /// The . public OpenIddictServerBuilder AddEncryptionCertificate( - Assembly assembly!!, string resource, + Assembly assembly, string resource, string? password, X509KeyStorageFlags flags) { + if (assembly is null) + { + throw new ArgumentNullException(nameof(assembly)); + } + if (string.IsNullOrEmpty(resource)) { throw new ArgumentException(SR.GetResourceString(SR.ID0062), nameof(resource)); @@ -415,8 +462,13 @@ public class OpenIddictServerBuilder /// The . [SuppressMessage("Reliability", "CA2000:Dispose objects before losing scope", Justification = "The X.509 certificate is attached to the server options.")] - public OpenIddictServerBuilder AddEncryptionCertificate(Stream stream!!, string? password, X509KeyStorageFlags flags) + public OpenIddictServerBuilder AddEncryptionCertificate(Stream stream, string? password, X509KeyStorageFlags flags) { + if (stream is null) + { + throw new ArgumentNullException(nameof(stream)); + } + using var buffer = new MemoryStream(); stream.CopyTo(buffer); @@ -479,16 +531,28 @@ public class OpenIddictServerBuilder /// /// The signing credentials. /// The . - public OpenIddictServerBuilder AddSigningCredentials(SigningCredentials credentials!!) - => Configure(options => options.SigningCredentials.Add(credentials)); + public OpenIddictServerBuilder AddSigningCredentials(SigningCredentials credentials) + { + if (credentials is null) + { + throw new ArgumentNullException(nameof(credentials)); + } + + return Configure(options => options.SigningCredentials.Add(credentials)); + } /// /// Registers a signing key. /// /// The security key. /// The . - public OpenIddictServerBuilder AddSigningKey(SecurityKey key!!) + public OpenIddictServerBuilder AddSigningKey(SecurityKey key) { + if (key is null) + { + throw new ArgumentNullException(nameof(key)); + } + // If the signing key is an asymmetric security key, ensure it has a private key. if (key is AsymmetricSecurityKey asymmetricSecurityKey && asymmetricSecurityKey.PrivateKeyStatus is PrivateKeyStatus.DoesNotExist) @@ -548,8 +612,13 @@ public class OpenIddictServerBuilder /// The . [SuppressMessage("Reliability", "CA2000:Dispose objects before losing scope", Justification = "The X.509 certificate is attached to the server options.")] - public OpenIddictServerBuilder AddDevelopmentSigningCertificate(X500DistinguishedName subject!!) + public OpenIddictServerBuilder AddDevelopmentSigningCertificate(X500DistinguishedName subject) { + if (subject is null) + { + throw new ArgumentNullException(nameof(subject)); + } + using var store = new X509Store(StoreName.My, StoreLocation.CurrentUser); store.Open(OpenFlags.ReadWrite); @@ -722,8 +791,13 @@ public class OpenIddictServerBuilder /// /// The signing certificate. /// The . - public OpenIddictServerBuilder AddSigningCertificate(X509Certificate2 certificate!!) + public OpenIddictServerBuilder AddSigningCertificate(X509Certificate2 certificate) { + if (certificate is null) + { + throw new ArgumentNullException(nameof(certificate)); + } + // If the certificate is a X.509v3 certificate that specifies at least // one key usage, ensure that the certificate key can be used for signing. if (certificate.Version >= 3) @@ -769,9 +843,14 @@ public class OpenIddictServerBuilder /// An enumeration of flags indicating how and where to store the private key of the certificate. /// The . public OpenIddictServerBuilder AddSigningCertificate( - Assembly assembly!!, string resource, + Assembly assembly, string resource, string? password, X509KeyStorageFlags flags) { + if (assembly is null) + { + throw new ArgumentNullException(nameof(assembly)); + } + if (string.IsNullOrEmpty(resource)) { throw new ArgumentException(SR.GetResourceString(SR.ID0062), nameof(resource)); @@ -811,8 +890,13 @@ public class OpenIddictServerBuilder /// The . [SuppressMessage("Reliability", "CA2000:Dispose objects before losing scope", Justification = "The X.509 certificate is attached to the server options.")] - public OpenIddictServerBuilder AddSigningCertificate(Stream stream!!, string? password, X509KeyStorageFlags flags) + public OpenIddictServerBuilder AddSigningCertificate(Stream stream, string? password, X509KeyStorageFlags flags) { + if (stream is null) + { + throw new ArgumentNullException(nameof(stream)); + } + using var buffer = new MemoryStream(); stream.CopyTo(buffer); @@ -1010,8 +1094,15 @@ public class OpenIddictServerBuilder /// /// The addresses associated to the endpoint. /// The . - public OpenIddictServerBuilder SetAuthorizationEndpointUris(params string[] addresses!!) - => SetAuthorizationEndpointUris(addresses.Select(address => new Uri(address, UriKind.RelativeOrAbsolute)).ToArray()); + public OpenIddictServerBuilder SetAuthorizationEndpointUris(params string[] addresses) + { + if (addresses is null) + { + throw new ArgumentNullException(nameof(addresses)); + } + + return SetAuthorizationEndpointUris(addresses.Select(address => new Uri(address, UriKind.RelativeOrAbsolute)).ToArray()); + } /// /// Sets the relative or absolute URLs associated to the authorization endpoint. @@ -1020,8 +1111,13 @@ public class OpenIddictServerBuilder /// /// The addresses associated to the endpoint. /// The . - public OpenIddictServerBuilder SetAuthorizationEndpointUris(params Uri[] addresses!!) + public OpenIddictServerBuilder SetAuthorizationEndpointUris(params Uri[] addresses) { + if (addresses is null) + { + throw new ArgumentNullException(nameof(addresses)); + } + if (addresses.Any(address => !address.IsWellFormedOriginalString())) { throw new ArgumentException(SR.GetResourceString(SR.ID0072), nameof(addresses)); @@ -1046,8 +1142,15 @@ public class OpenIddictServerBuilder /// /// The addresses associated to the endpoint. /// The . - public OpenIddictServerBuilder SetConfigurationEndpointUris(params string[] addresses!!) - => SetConfigurationEndpointUris(addresses.Select(address => new Uri(address, UriKind.RelativeOrAbsolute)).ToArray()); + public OpenIddictServerBuilder SetConfigurationEndpointUris(params string[] addresses) + { + if (addresses is null) + { + throw new ArgumentNullException(nameof(addresses)); + } + + return SetConfigurationEndpointUris(addresses.Select(address => new Uri(address, UriKind.RelativeOrAbsolute)).ToArray()); + } /// /// Sets the relative or absolute URLs associated to the configuration endpoint. @@ -1056,8 +1159,13 @@ public class OpenIddictServerBuilder /// /// The addresses associated to the endpoint. /// The . - public OpenIddictServerBuilder SetConfigurationEndpointUris(params Uri[] addresses!!) + public OpenIddictServerBuilder SetConfigurationEndpointUris(params Uri[] addresses) { + if (addresses is null) + { + throw new ArgumentNullException(nameof(addresses)); + } + if (addresses.Any(address => !address.IsWellFormedOriginalString())) { throw new ArgumentException(SR.GetResourceString(SR.ID0072), nameof(addresses)); @@ -1082,8 +1190,15 @@ public class OpenIddictServerBuilder /// /// The addresses associated to the endpoint. /// The . - public OpenIddictServerBuilder SetCryptographyEndpointUris(params string[] addresses!!) - => SetCryptographyEndpointUris(addresses.Select(address => new Uri(address, UriKind.RelativeOrAbsolute)).ToArray()); + public OpenIddictServerBuilder SetCryptographyEndpointUris(params string[] addresses) + { + if (addresses is null) + { + throw new ArgumentNullException(nameof(addresses)); + } + + return SetCryptographyEndpointUris(addresses.Select(address => new Uri(address, UriKind.RelativeOrAbsolute)).ToArray()); + } /// /// Sets the relative or absolute URLs associated to the cryptography endpoint. @@ -1092,8 +1207,13 @@ public class OpenIddictServerBuilder /// /// The addresses associated to the endpoint. /// The . - public OpenIddictServerBuilder SetCryptographyEndpointUris(params Uri[] addresses!!) + public OpenIddictServerBuilder SetCryptographyEndpointUris(params Uri[] addresses) { + if (addresses is null) + { + throw new ArgumentNullException(nameof(addresses)); + } + if (addresses.Any(address => !address.IsWellFormedOriginalString())) { throw new ArgumentException(SR.GetResourceString(SR.ID0072), nameof(addresses)); @@ -1118,8 +1238,15 @@ public class OpenIddictServerBuilder /// /// The addresses associated to the endpoint. /// The . - public OpenIddictServerBuilder SetDeviceEndpointUris(params string[] addresses!!) - => SetDeviceEndpointUris(addresses.Select(address => new Uri(address, UriKind.RelativeOrAbsolute)).ToArray()); + public OpenIddictServerBuilder SetDeviceEndpointUris(params string[] addresses) + { + if (addresses is null) + { + throw new ArgumentNullException(nameof(addresses)); + } + + return SetDeviceEndpointUris(addresses.Select(address => new Uri(address, UriKind.RelativeOrAbsolute)).ToArray()); + } /// /// Sets the relative or absolute URLs associated to the device endpoint. @@ -1128,8 +1255,13 @@ public class OpenIddictServerBuilder /// /// The addresses associated to the endpoint. /// The . - public OpenIddictServerBuilder SetDeviceEndpointUris(params Uri[] addresses!!) + public OpenIddictServerBuilder SetDeviceEndpointUris(params Uri[] addresses) { + if (addresses is null) + { + throw new ArgumentNullException(nameof(addresses)); + } + if (addresses.Any(address => !address.IsWellFormedOriginalString())) { throw new ArgumentException(SR.GetResourceString(SR.ID0072), nameof(addresses)); @@ -1154,8 +1286,15 @@ public class OpenIddictServerBuilder /// /// The addresses associated to the endpoint. /// The . - public OpenIddictServerBuilder SetIntrospectionEndpointUris(params string[] addresses!!) - => SetIntrospectionEndpointUris(addresses.Select(address => new Uri(address, UriKind.RelativeOrAbsolute)).ToArray()); + public OpenIddictServerBuilder SetIntrospectionEndpointUris(params string[] addresses) + { + if (addresses is null) + { + throw new ArgumentNullException(nameof(addresses)); + } + + return SetIntrospectionEndpointUris(addresses.Select(address => new Uri(address, UriKind.RelativeOrAbsolute)).ToArray()); + } /// /// Sets the relative or absolute URLs associated to the introspection endpoint. @@ -1164,8 +1303,13 @@ public class OpenIddictServerBuilder /// /// The addresses associated to the endpoint. /// The . - public OpenIddictServerBuilder SetIntrospectionEndpointUris(params Uri[] addresses!!) + public OpenIddictServerBuilder SetIntrospectionEndpointUris(params Uri[] addresses) { + if (addresses is null) + { + throw new ArgumentNullException(nameof(addresses)); + } + if (addresses.Any(address => !address.IsWellFormedOriginalString())) { throw new ArgumentException(SR.GetResourceString(SR.ID0072), nameof(addresses)); @@ -1190,8 +1334,15 @@ public class OpenIddictServerBuilder /// /// The addresses associated to the endpoint. /// The . - public OpenIddictServerBuilder SetLogoutEndpointUris(params string[] addresses!!) - => SetLogoutEndpointUris(addresses.Select(address => new Uri(address, UriKind.RelativeOrAbsolute)).ToArray()); + public OpenIddictServerBuilder SetLogoutEndpointUris(params string[] addresses) + { + if (addresses is null) + { + throw new ArgumentNullException(nameof(addresses)); + } + + return SetLogoutEndpointUris(addresses.Select(address => new Uri(address, UriKind.RelativeOrAbsolute)).ToArray()); + } /// /// Sets the relative or absolute URLs associated to the logout endpoint. @@ -1200,8 +1351,13 @@ public class OpenIddictServerBuilder /// /// The addresses associated to the endpoint. /// The . - public OpenIddictServerBuilder SetLogoutEndpointUris(params Uri[] addresses!!) + public OpenIddictServerBuilder SetLogoutEndpointUris(params Uri[] addresses) { + if (addresses is null) + { + throw new ArgumentNullException(nameof(addresses)); + } + if (addresses.Any(address => !address.IsWellFormedOriginalString())) { throw new ArgumentException(SR.GetResourceString(SR.ID0072), nameof(addresses)); @@ -1226,8 +1382,15 @@ public class OpenIddictServerBuilder /// /// The addresses associated to the endpoint. /// The . - public OpenIddictServerBuilder SetRevocationEndpointUris(params string[] addresses!!) - => SetRevocationEndpointUris(addresses.Select(address => new Uri(address, UriKind.RelativeOrAbsolute)).ToArray()); + public OpenIddictServerBuilder SetRevocationEndpointUris(params string[] addresses) + { + if (addresses is null) + { + throw new ArgumentNullException(nameof(addresses)); + } + + return SetRevocationEndpointUris(addresses.Select(address => new Uri(address, UriKind.RelativeOrAbsolute)).ToArray()); + } /// /// Sets the relative or absolute URLs associated to the revocation endpoint. @@ -1236,8 +1399,13 @@ public class OpenIddictServerBuilder /// /// The addresses associated to the endpoint. /// The . - public OpenIddictServerBuilder SetRevocationEndpointUris(params Uri[] addresses!!) + public OpenIddictServerBuilder SetRevocationEndpointUris(params Uri[] addresses) { + if (addresses is null) + { + throw new ArgumentNullException(nameof(addresses)); + } + if (addresses.Any(address => !address.IsWellFormedOriginalString())) { throw new ArgumentException(SR.GetResourceString(SR.ID0072), nameof(addresses)); @@ -1262,8 +1430,15 @@ public class OpenIddictServerBuilder /// /// The addresses associated to the endpoint. /// The . - public OpenIddictServerBuilder SetTokenEndpointUris(params string[] addresses!!) - => SetTokenEndpointUris(addresses.Select(address => new Uri(address, UriKind.RelativeOrAbsolute)).ToArray()); + public OpenIddictServerBuilder SetTokenEndpointUris(params string[] addresses) + { + if (addresses is null) + { + throw new ArgumentNullException(nameof(addresses)); + } + + return SetTokenEndpointUris(addresses.Select(address => new Uri(address, UriKind.RelativeOrAbsolute)).ToArray()); + } /// /// Sets the relative or absolute URLs associated to the token endpoint. @@ -1272,8 +1447,13 @@ public class OpenIddictServerBuilder /// /// The addresses associated to the endpoint. /// The . - public OpenIddictServerBuilder SetTokenEndpointUris(params Uri[] addresses!!) + public OpenIddictServerBuilder SetTokenEndpointUris(params Uri[] addresses) { + if (addresses is null) + { + throw new ArgumentNullException(nameof(addresses)); + } + if (addresses.Any(address => !address.IsWellFormedOriginalString())) { throw new ArgumentException(SR.GetResourceString(SR.ID0072), nameof(addresses)); @@ -1298,8 +1478,15 @@ public class OpenIddictServerBuilder /// /// The addresses associated to the endpoint. /// The . - public OpenIddictServerBuilder SetUserinfoEndpointUris(params string[] addresses!!) - => SetUserinfoEndpointUris(addresses.Select(address => new Uri(address, UriKind.RelativeOrAbsolute)).ToArray()); + public OpenIddictServerBuilder SetUserinfoEndpointUris(params string[] addresses) + { + if (addresses is null) + { + throw new ArgumentNullException(nameof(addresses)); + } + + return SetUserinfoEndpointUris(addresses.Select(address => new Uri(address, UriKind.RelativeOrAbsolute)).ToArray()); + } /// /// Sets the relative or absolute URLs associated to the userinfo endpoint. @@ -1308,8 +1495,13 @@ public class OpenIddictServerBuilder /// /// The addresses associated to the endpoint. /// The . - public OpenIddictServerBuilder SetUserinfoEndpointUris(params Uri[] addresses!!) + public OpenIddictServerBuilder SetUserinfoEndpointUris(params Uri[] addresses) { + if (addresses is null) + { + throw new ArgumentNullException(nameof(addresses)); + } + if (addresses.Any(address => !address.IsWellFormedOriginalString())) { throw new ArgumentException(SR.GetResourceString(SR.ID0072), nameof(addresses)); @@ -1334,8 +1526,15 @@ public class OpenIddictServerBuilder /// /// The addresses associated to the endpoint. /// The . - public OpenIddictServerBuilder SetVerificationEndpointUris(params string[] addresses!!) - => SetVerificationEndpointUris(addresses.Select(address => new Uri(address, UriKind.RelativeOrAbsolute)).ToArray()); + public OpenIddictServerBuilder SetVerificationEndpointUris(params string[] addresses) + { + if (addresses is null) + { + throw new ArgumentNullException(nameof(addresses)); + } + + return SetVerificationEndpointUris(addresses.Select(address => new Uri(address, UriKind.RelativeOrAbsolute)).ToArray()); + } /// /// Sets the relative or absolute URLs associated to the verification endpoint. @@ -1344,8 +1543,13 @@ public class OpenIddictServerBuilder /// /// The addresses associated to the endpoint. /// The . - public OpenIddictServerBuilder SetVerificationEndpointUris(params Uri[] addresses!!) + public OpenIddictServerBuilder SetVerificationEndpointUris(params Uri[] addresses) { + if (addresses is null) + { + throw new ArgumentNullException(nameof(addresses)); + } + if (addresses.Any(address => !address.IsWellFormedOriginalString())) { throw new ArgumentException(SR.GetResourceString(SR.ID0072), nameof(addresses)); @@ -1465,9 +1669,14 @@ public class OpenIddictServerBuilder /// /// The supported claims. /// The . - public OpenIddictServerBuilder RegisterClaims(params string[] claims!!) + public OpenIddictServerBuilder RegisterClaims(params string[] claims) { - if (claims.Any(string.IsNullOrEmpty)) + if (claims is null) + { + throw new ArgumentNullException(nameof(claims)); + } + + if (claims.Any(claim => string.IsNullOrEmpty(claim))) { throw new ArgumentException(SR.GetResourceString(SR.ID0073), nameof(claims)); } @@ -1481,9 +1690,14 @@ public class OpenIddictServerBuilder /// /// The supported scopes. /// The . - public OpenIddictServerBuilder RegisterScopes(params string[] scopes!!) + public OpenIddictServerBuilder RegisterScopes(params string[] scopes) { - if (scopes.Any(string.IsNullOrEmpty)) + if (scopes is null) + { + throw new ArgumentNullException(nameof(scopes)); + } + + if (scopes.Any(scope => string.IsNullOrEmpty(scope))) { throw new ArgumentException(SR.GetResourceString(SR.ID0074), nameof(scopes)); } @@ -1581,8 +1795,15 @@ public class OpenIddictServerBuilder /// /// The issuer address. /// The . - public OpenIddictServerBuilder SetIssuer(Uri address!!) - => Configure(options => options.Issuer = address); + public OpenIddictServerBuilder SetIssuer(Uri address) + { + if (address is null) + { + throw new ArgumentNullException(nameof(address)); + } + + return Configure(options => options.Issuer = address); + } /// /// Configures OpenIddict to use reference tokens, so that the access token payloads diff --git a/src/OpenIddict.Server/OpenIddictServerConfiguration.cs b/src/OpenIddict.Server/OpenIddictServerConfiguration.cs index afc48590..d0f0a2fb 100644 --- a/src/OpenIddict.Server/OpenIddictServerConfiguration.cs +++ b/src/OpenIddict.Server/OpenIddictServerConfiguration.cs @@ -21,8 +21,13 @@ public class OpenIddictServerConfiguration : IPostConfigureOptions /// The name of the options instance to configure, if applicable. /// The options instance to initialize. - public void PostConfigure(string name, OpenIddictServerOptions options!!) + public void PostConfigure(string name, OpenIddictServerOptions options) { + if (options is null) + { + throw new ArgumentNullException(nameof(options)); + } + // Explicitly disable all the features that are implicitly excluded when the degraded mode is active. if (options.EnableDegradedMode) { diff --git a/src/OpenIddict.Server/OpenIddictServerDispatcher.cs b/src/OpenIddict.Server/OpenIddictServerDispatcher.cs index 63e49ad8..e3f0594d 100644 --- a/src/OpenIddict.Server/OpenIddictServerDispatcher.cs +++ b/src/OpenIddict.Server/OpenIddictServerDispatcher.cs @@ -19,17 +19,22 @@ public class OpenIddictServerDispatcher : IOpenIddictServerDispatcher /// Creates a new instance of the class. /// public OpenIddictServerDispatcher( - ILogger logger!!, - IOptionsMonitor options!!, - IServiceProvider provider!!) + ILogger logger, + IOptionsMonitor options, + IServiceProvider provider) { - _logger = logger; - _options = options; - _provider = provider; + _logger = logger ?? throw new ArgumentNullException(nameof(logger)); + _options = options ?? throw new ArgumentNullException(nameof(options)); + _provider = provider ?? throw new ArgumentNullException(nameof(provider)); } - public async ValueTask DispatchAsync(TContext context!!) where TContext : BaseContext + public async ValueTask DispatchAsync(TContext context) where TContext : BaseContext { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + await foreach (var handler in GetHandlersAsync()) { try diff --git a/src/OpenIddict.Server/OpenIddictServerEvents.cs b/src/OpenIddict.Server/OpenIddictServerEvents.cs index 3cc5a484..37c7e014 100644 --- a/src/OpenIddict.Server/OpenIddictServerEvents.cs +++ b/src/OpenIddict.Server/OpenIddictServerEvents.cs @@ -21,8 +21,8 @@ public static partial class OpenIddictServerEvents /// /// Creates a new instance of the class. /// - protected BaseContext(OpenIddictServerTransaction transaction!!) - => Transaction = transaction; + protected BaseContext(OpenIddictServerTransaction transaction) + => Transaction = transaction ?? throw new ArgumentNullException(nameof(transaction)); /// /// Gets the environment associated with the current request being processed. diff --git a/src/OpenIddict.Server/OpenIddictServerExtensions.cs b/src/OpenIddict.Server/OpenIddictServerExtensions.cs index 6b26056e..d2f2cd24 100644 --- a/src/OpenIddict.Server/OpenIddictServerExtensions.cs +++ b/src/OpenIddict.Server/OpenIddictServerExtensions.cs @@ -22,8 +22,13 @@ public static class OpenIddictServerExtensions /// The services builder used by OpenIddict to register new services. /// This extension can be safely called multiple times. /// The . - public static OpenIddictServerBuilder AddServer(this OpenIddictBuilder builder!!) + public static OpenIddictServerBuilder AddServer(this OpenIddictBuilder builder) { + if (builder is null) + { + throw new ArgumentNullException(nameof(builder)); + } + builder.Services.AddLogging(); builder.Services.AddOptions(); @@ -89,8 +94,18 @@ public static class OpenIddictServerExtensions /// The configuration delegate used to configure the server services. /// This extension can be safely called multiple times. /// The . - public static OpenIddictBuilder AddServer(this OpenIddictBuilder builder!!, Action configuration!!) + public static OpenIddictBuilder AddServer(this OpenIddictBuilder builder, Action configuration) { + if (builder is null) + { + throw new ArgumentNullException(nameof(builder)); + } + + if (configuration is null) + { + throw new ArgumentNullException(nameof(configuration)); + } + configuration(builder.AddServer()); return builder; diff --git a/src/OpenIddict.Server/OpenIddictServerFactory.cs b/src/OpenIddict.Server/OpenIddictServerFactory.cs index 2e2ee4e1..b3223325 100644 --- a/src/OpenIddict.Server/OpenIddictServerFactory.cs +++ b/src/OpenIddict.Server/OpenIddictServerFactory.cs @@ -18,11 +18,11 @@ public class OpenIddictServerFactory : IOpenIddictServerFactory /// Creates a new instance of the class. /// public OpenIddictServerFactory( - ILogger logger!!, - IOptionsMonitor options!!) + ILogger logger, + IOptionsMonitor options) { - _logger = logger; - _options = options; + _logger = logger ?? throw new ArgumentNullException(nameof(logger)); + _options = options ?? throw new ArgumentNullException(nameof(options)); } public ValueTask CreateTransactionAsync() diff --git a/src/OpenIddict.Server/OpenIddictServerHandler.cs b/src/OpenIddict.Server/OpenIddictServerHandler.cs index 6232d198..90b59e9c 100644 --- a/src/OpenIddict.Server/OpenIddictServerHandler.cs +++ b/src/OpenIddict.Server/OpenIddictServerHandler.cs @@ -18,8 +18,8 @@ public class OpenIddictServerHandler : IOpenIddictServerHandler /// The event handler delegate. - public OpenIddictServerHandler(Func handler!!) - => _handler = handler; + public OpenIddictServerHandler(Func handler) + => _handler = handler ?? throw new ArgumentNullException(nameof(handler)); /// /// Processes the event. @@ -28,5 +28,6 @@ public class OpenIddictServerHandler : IOpenIddictServerHandler /// A that can be used to monitor the asynchronous operation. /// - public ValueTask HandleAsync(TContext context!!) => _handler(context); + public ValueTask HandleAsync(TContext context) + => _handler(context ?? throw new ArgumentNullException(nameof(context))); } diff --git a/src/OpenIddict.Server/OpenIddictServerHandlerDescriptor.cs b/src/OpenIddict.Server/OpenIddictServerHandlerDescriptor.cs index 5c46c80b..660f3800 100644 --- a/src/OpenIddict.Server/OpenIddictServerHandlerDescriptor.cs +++ b/src/OpenIddict.Server/OpenIddictServerHandlerDescriptor.cs @@ -72,8 +72,13 @@ public class OpenIddictServerHandlerDescriptor /// /// The event handler filter type. /// The builder instance, so that calls can be easily chained. - public Builder AddFilter(Type type!!) + public Builder AddFilter(Type type) { + if (type is null) + { + throw new ArgumentNullException(nameof(type)); + } + if (!typeof(IOpenIddictServerHandlerFilter<>).MakeGenericType(typeof(TContext)).IsAssignableFrom(type)) { throw new InvalidOperationException(SR.GetResourceString(SR.ID0104)); @@ -99,8 +104,13 @@ public class OpenIddictServerHandlerDescriptor /// The existing descriptor properties are copied from. /// All the properties previously set on this instance are automatically replaced. /// The builder instance, so that calls can be easily chained. - public Builder Import(OpenIddictServerHandlerDescriptor descriptor!!) + public Builder Import(OpenIddictServerHandlerDescriptor descriptor) { + if (descriptor is null) + { + throw new ArgumentNullException(nameof(descriptor)); + } + if (descriptor.ContextType != typeof(TContext)) { throw new InvalidOperationException(SR.GetResourceString(SR.ID0284)); @@ -120,8 +130,13 @@ public class OpenIddictServerHandlerDescriptor /// /// The service descriptor. /// The builder instance, so that calls can be easily chained. - public Builder SetServiceDescriptor(ServiceDescriptor descriptor!!) + public Builder SetServiceDescriptor(ServiceDescriptor descriptor) { + if (descriptor is null) + { + throw new ArgumentNullException(nameof(descriptor)); + } + var type = descriptor.ServiceType; if (!typeof(IOpenIddictServerHandler<>).MakeGenericType(typeof(TContext)).IsAssignableFrom(type)) { @@ -167,8 +182,15 @@ public class OpenIddictServerHandlerDescriptor /// /// The handler instance. /// The builder instance, so that calls can be easily chained. - public Builder UseInlineHandler(Func handler!!) - => UseSingletonHandler(new OpenIddictServerHandler(handler)); + public Builder UseInlineHandler(Func handler) + { + if (handler is null) + { + throw new ArgumentNullException(nameof(handler)); + } + + return UseSingletonHandler(new OpenIddictServerHandler(handler)); + } /// /// Configures the descriptor to use the specified scoped handler. @@ -186,10 +208,17 @@ public class OpenIddictServerHandlerDescriptor /// The handler type. /// The factory used to create the handler. /// The builder instance, so that calls can be easily chained. - public Builder UseScopedHandler(Func factory!!) + public Builder UseScopedHandler(Func factory) where THandler : IOpenIddictServerHandler - => SetServiceDescriptor(new ServiceDescriptor( + { + if (factory is null) + { + throw new ArgumentNullException(nameof(factory)); + } + + return SetServiceDescriptor(new ServiceDescriptor( typeof(THandler), factory, ServiceLifetime.Scoped)); + } /// /// Configures the descriptor to use the specified singleton handler. @@ -207,10 +236,17 @@ public class OpenIddictServerHandlerDescriptor /// The handler type. /// The factory used to create the handler. /// The builder instance, so that calls can be easily chained. - public Builder UseSingletonHandler(Func factory!!) + public Builder UseSingletonHandler(Func factory) where THandler : IOpenIddictServerHandler - => SetServiceDescriptor(new ServiceDescriptor( + { + if (factory is null) + { + throw new ArgumentNullException(nameof(factory)); + } + + return SetServiceDescriptor(new ServiceDescriptor( typeof(THandler), factory, ServiceLifetime.Singleton)); + } /// /// Configures the descriptor to use the specified singleton handler. @@ -218,9 +254,16 @@ public class OpenIddictServerHandlerDescriptor /// The handler type. /// The handler instance. /// The builder instance, so that calls can be easily chained. - public Builder UseSingletonHandler(THandler handler!!) + public Builder UseSingletonHandler(THandler handler) where THandler : IOpenIddictServerHandler - => SetServiceDescriptor(new ServiceDescriptor(typeof(THandler), handler)); + { + if (handler is null) + { + throw new ArgumentNullException(nameof(handler)); + } + + return SetServiceDescriptor(new ServiceDescriptor(typeof(THandler), handler)); + } /// /// Build a new descriptor instance, based on the parameters that were previously set. diff --git a/src/OpenIddict.Server/OpenIddictServerHandlerFilters.cs b/src/OpenIddict.Server/OpenIddictServerHandlerFilters.cs index ea15802f..baaa6126 100644 --- a/src/OpenIddict.Server/OpenIddictServerHandlerFilters.cs +++ b/src/OpenIddict.Server/OpenIddictServerHandlerFilters.cs @@ -16,8 +16,15 @@ public static class OpenIddictServerHandlerFilters /// public class RequireAccessTokenGenerated : IOpenIddictServerHandlerFilter { - public ValueTask IsActiveAsync(ProcessSignInContext context!!) - => new(context.GenerateAccessToken); + public ValueTask IsActiveAsync(ProcessSignInContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(context.GenerateAccessToken); + } } /// @@ -25,8 +32,15 @@ public static class OpenIddictServerHandlerFilters /// public class RequireAccessTokenValidated : IOpenIddictServerHandlerFilter { - public ValueTask IsActiveAsync(ProcessAuthenticationContext context!!) - => new(context.ValidateAccessToken); + public ValueTask IsActiveAsync(ProcessAuthenticationContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(context.ValidateAccessToken); + } } /// @@ -34,8 +48,15 @@ public static class OpenIddictServerHandlerFilters /// public class RequireAuthorizationCodeGenerated : IOpenIddictServerHandlerFilter { - public ValueTask IsActiveAsync(ProcessSignInContext context!!) - => new(context.GenerateAuthorizationCode); + public ValueTask IsActiveAsync(ProcessSignInContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(context.GenerateAuthorizationCode); + } } /// @@ -43,8 +64,15 @@ public static class OpenIddictServerHandlerFilters /// public class RequireAuthorizationCodeValidated : IOpenIddictServerHandlerFilter { - public ValueTask IsActiveAsync(ProcessAuthenticationContext context!!) - => new(context.ValidateAuthorizationCode); + public ValueTask IsActiveAsync(ProcessAuthenticationContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(context.ValidateAuthorizationCode); + } } /// @@ -52,8 +80,15 @@ public static class OpenIddictServerHandlerFilters /// public class RequireAuthorizationRequest : IOpenIddictServerHandlerFilter { - public ValueTask IsActiveAsync(BaseContext context!!) - => new(context.EndpointType is OpenIddictServerEndpointType.Authorization); + public ValueTask IsActiveAsync(BaseContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(context.EndpointType is OpenIddictServerEndpointType.Authorization); + } } /// @@ -61,8 +96,15 @@ public static class OpenIddictServerHandlerFilters /// public class RequireAuthorizationStorageEnabled : IOpenIddictServerHandlerFilter { - public ValueTask IsActiveAsync(BaseContext context!!) - => new(!context.Options.DisableAuthorizationStorage); + public ValueTask IsActiveAsync(BaseContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(!context.Options.DisableAuthorizationStorage); + } } /// @@ -70,8 +112,15 @@ public static class OpenIddictServerHandlerFilters /// public class RequireClientIdParameter : IOpenIddictServerHandlerFilter { - public ValueTask IsActiveAsync(BaseContext context!!) - => new(!string.IsNullOrEmpty(context.Transaction.Request?.ClientId)); + public ValueTask IsActiveAsync(BaseContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(!string.IsNullOrEmpty(context.Transaction.Request?.ClientId)); + } } /// @@ -79,8 +128,15 @@ public static class OpenIddictServerHandlerFilters /// public class RequireConfigurationRequest : IOpenIddictServerHandlerFilter { - public ValueTask IsActiveAsync(BaseContext context!!) - => new(context.EndpointType is OpenIddictServerEndpointType.Configuration); + public ValueTask IsActiveAsync(BaseContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(context.EndpointType is OpenIddictServerEndpointType.Configuration); + } } /// @@ -88,8 +144,15 @@ public static class OpenIddictServerHandlerFilters /// public class RequireCryptographyRequest : IOpenIddictServerHandlerFilter { - public ValueTask IsActiveAsync(BaseContext context!!) - => new(context.EndpointType is OpenIddictServerEndpointType.Cryptography); + public ValueTask IsActiveAsync(BaseContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(context.EndpointType is OpenIddictServerEndpointType.Cryptography); + } } /// @@ -97,8 +160,15 @@ public static class OpenIddictServerHandlerFilters /// public class RequireDegradedModeDisabled : IOpenIddictServerHandlerFilter { - public ValueTask IsActiveAsync(BaseContext context!!) - => new(!context.Options.EnableDegradedMode); + public ValueTask IsActiveAsync(BaseContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(!context.Options.EnableDegradedMode); + } } /// @@ -106,8 +176,15 @@ public static class OpenIddictServerHandlerFilters /// public class RequireDeviceCodeGenerated : IOpenIddictServerHandlerFilter { - public ValueTask IsActiveAsync(ProcessSignInContext context!!) - => new(context.GenerateDeviceCode); + public ValueTask IsActiveAsync(ProcessSignInContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(context.GenerateDeviceCode); + } } /// @@ -115,8 +192,15 @@ public static class OpenIddictServerHandlerFilters /// public class RequireDeviceCodeValidated : IOpenIddictServerHandlerFilter { - public ValueTask IsActiveAsync(ProcessAuthenticationContext context!!) - => new(context.ValidateDeviceCode); + public ValueTask IsActiveAsync(ProcessAuthenticationContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(context.ValidateDeviceCode); + } } /// @@ -124,8 +208,15 @@ public static class OpenIddictServerHandlerFilters /// public class RequireDeviceRequest : IOpenIddictServerHandlerFilter { - public ValueTask IsActiveAsync(BaseContext context!!) - => new(context.EndpointType is OpenIddictServerEndpointType.Device); + public ValueTask IsActiveAsync(BaseContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(context.EndpointType is OpenIddictServerEndpointType.Device); + } } /// @@ -133,8 +224,15 @@ public static class OpenIddictServerHandlerFilters /// public class RequireEndpointPermissionsEnabled : IOpenIddictServerHandlerFilter { - public ValueTask IsActiveAsync(BaseContext context!!) - => new(!context.Options.IgnoreEndpointPermissions); + public ValueTask IsActiveAsync(BaseContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(!context.Options.IgnoreEndpointPermissions); + } } /// @@ -142,8 +240,15 @@ public static class OpenIddictServerHandlerFilters /// public class RequireGenericTokenValidated : IOpenIddictServerHandlerFilter { - public ValueTask IsActiveAsync(ProcessAuthenticationContext context!!) - => new(context.ValidateGenericToken); + public ValueTask IsActiveAsync(ProcessAuthenticationContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(context.ValidateGenericToken); + } } /// @@ -151,8 +256,15 @@ public static class OpenIddictServerHandlerFilters /// public class RequireGrantTypePermissionsEnabled : IOpenIddictServerHandlerFilter { - public ValueTask IsActiveAsync(BaseContext context!!) - => new(!context.Options.IgnoreGrantTypePermissions); + public ValueTask IsActiveAsync(BaseContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(!context.Options.IgnoreGrantTypePermissions); + } } /// @@ -160,8 +272,15 @@ public static class OpenIddictServerHandlerFilters /// public class RequireIdentityTokenGenerated : IOpenIddictServerHandlerFilter { - public ValueTask IsActiveAsync(ProcessSignInContext context!!) - => new(context.GenerateIdentityToken); + public ValueTask IsActiveAsync(ProcessSignInContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(context.GenerateIdentityToken); + } } /// @@ -169,8 +288,15 @@ public static class OpenIddictServerHandlerFilters /// public class RequireIdentityTokenValidated : IOpenIddictServerHandlerFilter { - public ValueTask IsActiveAsync(ProcessAuthenticationContext context!!) - => new(context.ValidateIdentityToken); + public ValueTask IsActiveAsync(ProcessAuthenticationContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(context.ValidateIdentityToken); + } } /// @@ -178,8 +304,15 @@ public static class OpenIddictServerHandlerFilters /// public class RequireIntrospectionRequest : IOpenIddictServerHandlerFilter { - public ValueTask IsActiveAsync(BaseContext context!!) - => new(context.EndpointType is OpenIddictServerEndpointType.Introspection); + public ValueTask IsActiveAsync(BaseContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(context.EndpointType is OpenIddictServerEndpointType.Introspection); + } } /// @@ -187,8 +320,15 @@ public static class OpenIddictServerHandlerFilters /// public class RequireLogoutRequest : IOpenIddictServerHandlerFilter { - public ValueTask IsActiveAsync(BaseContext context!!) - => new(context.EndpointType is OpenIddictServerEndpointType.Logout); + public ValueTask IsActiveAsync(BaseContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(context.EndpointType is OpenIddictServerEndpointType.Logout); + } } /// @@ -196,8 +336,15 @@ public static class OpenIddictServerHandlerFilters /// public class RequirePostLogoutRedirectUriParameter : IOpenIddictServerHandlerFilter { - public ValueTask IsActiveAsync(BaseContext context!!) - => new(!string.IsNullOrEmpty(context.Transaction.Request?.PostLogoutRedirectUri)); + public ValueTask IsActiveAsync(BaseContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(!string.IsNullOrEmpty(context.Transaction.Request?.PostLogoutRedirectUri)); + } } /// @@ -205,8 +352,15 @@ public static class OpenIddictServerHandlerFilters /// public class RequireReferenceAccessTokensEnabled : IOpenIddictServerHandlerFilter { - public ValueTask IsActiveAsync(BaseContext context!!) - => new(context.Options.UseReferenceAccessTokens); + public ValueTask IsActiveAsync(BaseContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(context.Options.UseReferenceAccessTokens); + } } /// @@ -214,8 +368,15 @@ public static class OpenIddictServerHandlerFilters /// public class RequireReferenceRefreshTokensEnabled : IOpenIddictServerHandlerFilter { - public ValueTask IsActiveAsync(BaseContext context!!) - => new(context.Options.UseReferenceRefreshTokens); + public ValueTask IsActiveAsync(BaseContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(context.Options.UseReferenceRefreshTokens); + } } /// @@ -223,8 +384,15 @@ public static class OpenIddictServerHandlerFilters /// public class RequireRefreshTokenGenerated : IOpenIddictServerHandlerFilter { - public ValueTask IsActiveAsync(ProcessSignInContext context!!) - => new(context.GenerateRefreshToken); + public ValueTask IsActiveAsync(ProcessSignInContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(context.GenerateRefreshToken); + } } /// @@ -232,8 +400,15 @@ public static class OpenIddictServerHandlerFilters /// public class RequireRefreshTokenValidated : IOpenIddictServerHandlerFilter { - public ValueTask IsActiveAsync(ProcessAuthenticationContext context!!) - => new(context.ValidateRefreshToken); + public ValueTask IsActiveAsync(ProcessAuthenticationContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(context.ValidateRefreshToken); + } } /// @@ -241,8 +416,15 @@ public static class OpenIddictServerHandlerFilters /// public class RequireResponseTypePermissionsEnabled : IOpenIddictServerHandlerFilter { - public ValueTask IsActiveAsync(BaseContext context!!) - => new(!context.Options.IgnoreResponseTypePermissions); + public ValueTask IsActiveAsync(BaseContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(!context.Options.IgnoreResponseTypePermissions); + } } /// @@ -250,8 +432,15 @@ public static class OpenIddictServerHandlerFilters /// public class RequireRevocationRequest : IOpenIddictServerHandlerFilter { - public ValueTask IsActiveAsync(BaseContext context!!) - => new(context.EndpointType is OpenIddictServerEndpointType.Revocation); + public ValueTask IsActiveAsync(BaseContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(context.EndpointType is OpenIddictServerEndpointType.Revocation); + } } /// @@ -259,8 +448,15 @@ public static class OpenIddictServerHandlerFilters /// public class RequireScopePermissionsEnabled : IOpenIddictServerHandlerFilter { - public ValueTask IsActiveAsync(BaseContext context!!) - => new(!context.Options.IgnoreScopePermissions); + public ValueTask IsActiveAsync(BaseContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(!context.Options.IgnoreScopePermissions); + } } /// @@ -268,8 +464,15 @@ public static class OpenIddictServerHandlerFilters /// public class RequireScopeValidationEnabled : IOpenIddictServerHandlerFilter { - public ValueTask IsActiveAsync(BaseContext context!!) - => new(!context.Options.DisableScopeValidation); + public ValueTask IsActiveAsync(BaseContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(!context.Options.DisableScopeValidation); + } } /// @@ -277,8 +480,15 @@ public static class OpenIddictServerHandlerFilters /// public class RequireSlidingRefreshTokenExpirationEnabled : IOpenIddictServerHandlerFilter { - public ValueTask IsActiveAsync(BaseContext context!!) - => new(!context.Options.DisableSlidingRefreshTokenExpiration); + public ValueTask IsActiveAsync(BaseContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(!context.Options.DisableSlidingRefreshTokenExpiration); + } } /// @@ -286,8 +496,15 @@ public static class OpenIddictServerHandlerFilters /// public class RequireTokenEntryCreated : IOpenIddictServerHandlerFilter { - public ValueTask IsActiveAsync(GenerateTokenContext context!!) - => new(context.CreateTokenEntry); + public ValueTask IsActiveAsync(GenerateTokenContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(context.CreateTokenEntry); + } } /// @@ -295,8 +512,15 @@ public static class OpenIddictServerHandlerFilters /// public class RequireTokenLifetimeValidationEnabled : IOpenIddictServerHandlerFilter { - public ValueTask IsActiveAsync(ValidateTokenContext context!!) - => new(!context.DisableLifetimeValidation); + public ValueTask IsActiveAsync(ValidateTokenContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(!context.DisableLifetimeValidation); + } } /// @@ -304,8 +528,15 @@ public static class OpenIddictServerHandlerFilters /// public class RequireTokenPayloadPersisted : IOpenIddictServerHandlerFilter { - public ValueTask IsActiveAsync(GenerateTokenContext context!!) - => new(context.PersistTokenPayload); + public ValueTask IsActiveAsync(GenerateTokenContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(context.PersistTokenPayload); + } } /// @@ -313,8 +544,15 @@ public static class OpenIddictServerHandlerFilters /// public class RequireTokenRequest : IOpenIddictServerHandlerFilter { - public ValueTask IsActiveAsync(BaseContext context!!) - => new(context.EndpointType is OpenIddictServerEndpointType.Token); + public ValueTask IsActiveAsync(BaseContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(context.EndpointType is OpenIddictServerEndpointType.Token); + } } /// @@ -322,8 +560,15 @@ public static class OpenIddictServerHandlerFilters /// public class RequireTokenStorageEnabled : IOpenIddictServerHandlerFilter { - public ValueTask IsActiveAsync(BaseContext context!!) - => new(!context.Options.DisableTokenStorage); + public ValueTask IsActiveAsync(BaseContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(!context.Options.DisableTokenStorage); + } } /// @@ -331,8 +576,15 @@ public static class OpenIddictServerHandlerFilters /// public class RequireUserCodeGenerated : IOpenIddictServerHandlerFilter { - public ValueTask IsActiveAsync(ProcessSignInContext context!!) - => new(context.GenerateUserCode); + public ValueTask IsActiveAsync(ProcessSignInContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(context.GenerateUserCode); + } } /// @@ -340,8 +592,15 @@ public static class OpenIddictServerHandlerFilters /// public class RequireUserCodeValidated : IOpenIddictServerHandlerFilter { - public ValueTask IsActiveAsync(ProcessAuthenticationContext context!!) - => new(context.ValidateUserCode); + public ValueTask IsActiveAsync(ProcessAuthenticationContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(context.ValidateUserCode); + } } /// @@ -349,8 +608,15 @@ public static class OpenIddictServerHandlerFilters /// public class RequireUserinfoRequest : IOpenIddictServerHandlerFilter { - public ValueTask IsActiveAsync(BaseContext context!!) - => new(context.EndpointType is OpenIddictServerEndpointType.Userinfo); + public ValueTask IsActiveAsync(BaseContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(context.EndpointType is OpenIddictServerEndpointType.Userinfo); + } } /// @@ -358,7 +624,14 @@ public static class OpenIddictServerHandlerFilters /// public class RequireVerificationRequest : IOpenIddictServerHandlerFilter { - public ValueTask IsActiveAsync(BaseContext context!!) - => new(context.EndpointType is OpenIddictServerEndpointType.Verification); + public ValueTask IsActiveAsync(BaseContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(context.EndpointType is OpenIddictServerEndpointType.Verification); + } } } diff --git a/src/OpenIddict.Server/OpenIddictServerHandlers.Authentication.cs b/src/OpenIddict.Server/OpenIddictServerHandlers.Authentication.cs index 34e75f54..ac794dc4 100644 --- a/src/OpenIddict.Server/OpenIddictServerHandlers.Authentication.cs +++ b/src/OpenIddict.Server/OpenIddictServerHandlers.Authentication.cs @@ -66,8 +66,8 @@ public static partial class OpenIddictServerHandlers { private readonly IOpenIddictServerDispatcher _dispatcher; - public ExtractAuthorizationRequest(IOpenIddictServerDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public ExtractAuthorizationRequest(IOpenIddictServerDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -81,8 +81,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessRequestContext context!!) + public async ValueTask HandleAsync(ProcessRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var notification = new ExtractAuthorizationRequestContext(context.Transaction); await _dispatcher.DispatchAsync(notification); @@ -123,8 +128,8 @@ public static partial class OpenIddictServerHandlers { private readonly IOpenIddictServerDispatcher _dispatcher; - public ValidateAuthorizationRequest(IOpenIddictServerDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public ValidateAuthorizationRequest(IOpenIddictServerDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -138,8 +143,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessRequestContext context!!) + public async ValueTask HandleAsync(ProcessRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var notification = new ValidateAuthorizationRequestContext(context.Transaction); await _dispatcher.DispatchAsync(notification); @@ -184,8 +194,8 @@ public static partial class OpenIddictServerHandlers { private readonly IOpenIddictServerDispatcher _dispatcher; - public HandleAuthorizationRequest(IOpenIddictServerDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public HandleAuthorizationRequest(IOpenIddictServerDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -199,8 +209,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessRequestContext context!!) + public async ValueTask HandleAsync(ProcessRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var notification = new HandleAuthorizationRequestContext(context.Transaction); await _dispatcher.DispatchAsync(notification); @@ -276,8 +291,8 @@ public static partial class OpenIddictServerHandlers { private readonly IOpenIddictServerDispatcher _dispatcher; - public ApplyAuthorizationResponse(IOpenIddictServerDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public ApplyAuthorizationResponse(IOpenIddictServerDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -291,8 +306,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(TContext context!!) + public async ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var notification = new ApplyAuthorizationResponseContext(context.Transaction); await _dispatcher.DispatchAsync(notification); @@ -328,8 +348,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ValidateAuthorizationRequestContext context!!) + public ValueTask HandleAsync(ValidateAuthorizationRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // Reject requests using the unsupported request parameter. if (!string.IsNullOrEmpty(context.Request.Request)) { @@ -363,8 +388,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ValidateAuthorizationRequestContext context!!) + public ValueTask HandleAsync(ValidateAuthorizationRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // Reject requests using the unsupported request_uri parameter. if (!string.IsNullOrEmpty(context.Request.RequestUri)) { @@ -398,8 +428,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ValidateAuthorizationRequestContext context!!) + public ValueTask HandleAsync(ValidateAuthorizationRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // client_id is a required parameter and MUST cause an error when missing. // See http://openid.net/specs/openid-connect-core-1_0.html#AuthRequest. if (string.IsNullOrEmpty(context.ClientId)) @@ -434,8 +469,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ValidateAuthorizationRequestContext context!!) + public ValueTask HandleAsync(ValidateAuthorizationRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // While redirect_uri was not mandatory in OAuth 2.0, this parameter // is now declared as REQUIRED and MUST cause an error when missing. // See http://openid.net/specs/openid-connect-core-1_0.html#AuthRequest. @@ -534,8 +574,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ValidateAuthorizationRequestContext context!!) + public ValueTask HandleAsync(ValidateAuthorizationRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // Reject requests missing the mandatory response_type parameter. if (string.IsNullOrEmpty(context.Request.ResponseType)) { @@ -624,8 +669,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ValidateAuthorizationRequestContext context!!) + public ValueTask HandleAsync(ValidateAuthorizationRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // response_mode=query (explicit or not) and a response_type containing id_token // or token are not considered as a safe combination and MUST be rejected. // See http://openid.net/specs/oauth-v2-multiple-response-types-1_0.html#Security. @@ -701,8 +751,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ValidateAuthorizationRequestContext context!!) + public ValueTask HandleAsync(ValidateAuthorizationRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // Reject authorization requests containing the id_token response_type if no openid scope has been received. if (context.Request.HasResponseType(ResponseTypes.IdToken) && !context.Request.HasScope(Scopes.OpenId)) { @@ -747,8 +802,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ValidateAuthorizationRequestContext context!!) + public ValueTask HandleAsync(ValidateAuthorizationRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // Reject OpenID Connect implicit/hybrid requests missing the mandatory nonce parameter. // See http://openid.net/specs/openid-connect-core-1_0.html#AuthRequest, // http://openid.net/specs/openid-connect-implicit-1_0.html#RequestParameters @@ -791,8 +851,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ValidateAuthorizationRequestContext context!!) + public ValueTask HandleAsync(ValidateAuthorizationRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // Reject requests specifying prompt=none with consent/login or select_account. if (context.Request.HasPrompt(Prompts.None) && (context.Request.HasPrompt(Prompts.Consent) || context.Request.HasPrompt(Prompts.Login) || @@ -828,8 +893,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ValidateAuthorizationRequestContext context!!) + public ValueTask HandleAsync(ValidateAuthorizationRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // If OpenIddict was configured to require PKCE, reject the request if the code challenge // is missing and if an authorization code was requested by the client application. if (context.Options.RequireProofKeyForCodeExchange && @@ -936,8 +1006,8 @@ public static partial class OpenIddictServerHandlers public ValidateClientId() => throw new InvalidOperationException(SR.GetResourceString(SR.ID0016)); - public ValidateClientId(IOpenIddictApplicationManager applicationManager!!) - => _applicationManager = applicationManager; + public ValidateClientId(IOpenIddictApplicationManager applicationManager) + => _applicationManager = applicationManager ?? throw new ArgumentNullException(nameof(applicationManager)); /// /// Gets the default descriptor definition assigned to this handler. @@ -951,8 +1021,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ValidateAuthorizationRequestContext context!!) + public async ValueTask HandleAsync(ValidateAuthorizationRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(!string.IsNullOrEmpty(context.ClientId), SR.FormatID4000(Parameters.ClientId)); var application = await _applicationManager.FindByClientIdAsync(context.ClientId); @@ -982,8 +1057,8 @@ public static partial class OpenIddictServerHandlers public ValidateClientType() => throw new InvalidOperationException(SR.GetResourceString(SR.ID0016)); - public ValidateClientType(IOpenIddictApplicationManager applicationManager!!) - => _applicationManager = applicationManager; + public ValidateClientType(IOpenIddictApplicationManager applicationManager) + => _applicationManager = applicationManager ?? throw new ArgumentNullException(nameof(applicationManager)); /// /// Gets the default descriptor definition assigned to this handler. @@ -997,8 +1072,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ValidateAuthorizationRequestContext context!!) + public async ValueTask HandleAsync(ValidateAuthorizationRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(!string.IsNullOrEmpty(context.ClientId), SR.FormatID4000(Parameters.ClientId)); var application = await _applicationManager.FindByClientIdAsync(context.ClientId) ?? @@ -1039,8 +1119,8 @@ public static partial class OpenIddictServerHandlers public ValidateClientRedirectUri() => throw new InvalidOperationException(SR.GetResourceString(SR.ID0016)); - public ValidateClientRedirectUri(IOpenIddictApplicationManager applicationManager!!) - => _applicationManager = applicationManager; + public ValidateClientRedirectUri(IOpenIddictApplicationManager applicationManager) + => _applicationManager = applicationManager ?? throw new ArgumentNullException(nameof(applicationManager)); /// /// Gets the default descriptor definition assigned to this handler. @@ -1054,8 +1134,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ValidateAuthorizationRequestContext context!!) + public async ValueTask HandleAsync(ValidateAuthorizationRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(!string.IsNullOrEmpty(context.ClientId), SR.FormatID4000(Parameters.ClientId)); var application = await _applicationManager.FindByClientIdAsync(context.ClientId) ?? @@ -1131,8 +1216,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ValidateAuthorizationRequestContext context!!) + public async ValueTask HandleAsync(ValidateAuthorizationRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // If all the specified scopes are registered in the options, avoid making a database lookup. var scopes = new HashSet(context.Request.GetScopes(), StringComparer.Ordinal); scopes.ExceptWith(context.Options.Scopes); @@ -1182,8 +1272,8 @@ public static partial class OpenIddictServerHandlers public ValidateEndpointPermissions() => throw new InvalidOperationException(SR.GetResourceString(SR.ID0016)); - public ValidateEndpointPermissions(IOpenIddictApplicationManager applicationManager!!) - => _applicationManager = applicationManager; + public ValidateEndpointPermissions(IOpenIddictApplicationManager applicationManager) + => _applicationManager = applicationManager ?? throw new ArgumentNullException(nameof(applicationManager)); /// /// Gets the default descriptor definition assigned to this handler. @@ -1198,8 +1288,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ValidateAuthorizationRequestContext context!!) + public async ValueTask HandleAsync(ValidateAuthorizationRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(!string.IsNullOrEmpty(context.ClientId), SR.FormatID4000(Parameters.ClientId)); var application = await _applicationManager.FindByClientIdAsync(context.ClientId) ?? @@ -1230,8 +1325,8 @@ public static partial class OpenIddictServerHandlers public ValidateGrantTypePermissions() => throw new InvalidOperationException(SR.GetResourceString(SR.ID0016)); - public ValidateGrantTypePermissions(IOpenIddictApplicationManager applicationManager!!) - => _applicationManager = applicationManager; + public ValidateGrantTypePermissions(IOpenIddictApplicationManager applicationManager) + => _applicationManager = applicationManager ?? throw new ArgumentNullException(nameof(applicationManager)); /// /// Gets the default descriptor definition assigned to this handler. @@ -1246,8 +1341,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ValidateAuthorizationRequestContext context!!) + public async ValueTask HandleAsync(ValidateAuthorizationRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(!string.IsNullOrEmpty(context.ClientId), SR.FormatID4000(Parameters.ClientId)); var application = await _applicationManager.FindByClientIdAsync(context.ClientId) ?? @@ -1323,8 +1423,8 @@ public static partial class OpenIddictServerHandlers public ValidateResponseTypePermissions() => throw new InvalidOperationException(SR.GetResourceString(SR.ID0016)); - public ValidateResponseTypePermissions(IOpenIddictApplicationManager applicationManager!!) - => _applicationManager = applicationManager; + public ValidateResponseTypePermissions(IOpenIddictApplicationManager applicationManager) + => _applicationManager = applicationManager ?? throw new ArgumentNullException(nameof(applicationManager)); /// /// Gets the default descriptor definition assigned to this handler. @@ -1339,8 +1439,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ValidateAuthorizationRequestContext context!!) + public async ValueTask HandleAsync(ValidateAuthorizationRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(!string.IsNullOrEmpty(context.ClientId), SR.FormatID4000(Parameters.ClientId)); var application = await _applicationManager.FindByClientIdAsync(context.ClientId) ?? @@ -1398,8 +1503,8 @@ public static partial class OpenIddictServerHandlers public ValidateScopePermissions() => throw new InvalidOperationException(SR.GetResourceString(SR.ID0016)); - public ValidateScopePermissions(IOpenIddictApplicationManager applicationManager!!) - => _applicationManager = applicationManager; + public ValidateScopePermissions(IOpenIddictApplicationManager applicationManager) + => _applicationManager = applicationManager ?? throw new ArgumentNullException(nameof(applicationManager)); /// /// Gets the default descriptor definition assigned to this handler. @@ -1414,8 +1519,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ValidateAuthorizationRequestContext context!!) + public async ValueTask HandleAsync(ValidateAuthorizationRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(!string.IsNullOrEmpty(context.ClientId), SR.FormatID4000(Parameters.ClientId)); var application = await _applicationManager.FindByClientIdAsync(context.ClientId) ?? @@ -1457,8 +1567,8 @@ public static partial class OpenIddictServerHandlers public ValidateProofKeyForCodeExchangeRequirement() => throw new InvalidOperationException(SR.GetResourceString(SR.ID0016)); - public ValidateProofKeyForCodeExchangeRequirement(IOpenIddictApplicationManager applicationManager!!) - => _applicationManager = applicationManager; + public ValidateProofKeyForCodeExchangeRequirement(IOpenIddictApplicationManager applicationManager) + => _applicationManager = applicationManager ?? throw new ArgumentNullException(nameof(applicationManager)); /// /// Gets the default descriptor definition assigned to this handler. @@ -1472,8 +1582,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ValidateAuthorizationRequestContext context!!) + public async ValueTask HandleAsync(ValidateAuthorizationRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(!string.IsNullOrEmpty(context.ClientId), SR.FormatID4000(Parameters.ClientId)); // If a code_challenge was provided or if no authorization code is requested, the request is always @@ -1517,8 +1632,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ApplyAuthorizationResponseContext context!!) + public ValueTask HandleAsync(ApplyAuthorizationResponseContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + if (context.Request is null) { return default; @@ -1555,8 +1675,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ApplyAuthorizationResponseContext context!!) + public ValueTask HandleAsync(ApplyAuthorizationResponseContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + if (context.Request is null) { return default; @@ -1592,8 +1717,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ApplyAuthorizationResponseContext context!!) + public ValueTask HandleAsync(ApplyAuthorizationResponseContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // If the user agent is expected to be redirected to the client application, attach the request // state to the authorization response to help the client mitigate CSRF/session fixation attacks. // @@ -1624,8 +1754,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ApplyAuthorizationResponseContext context!!) + public ValueTask HandleAsync(ApplyAuthorizationResponseContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // If the user agent is expected to be redirected to the client application, attach the // issuer address to the authorization response to help the client detect mix-up attacks. // diff --git a/src/OpenIddict.Server/OpenIddictServerHandlers.Device.cs b/src/OpenIddict.Server/OpenIddictServerHandlers.Device.cs index e3622a3f..47597554 100644 --- a/src/OpenIddict.Server/OpenIddictServerHandlers.Device.cs +++ b/src/OpenIddict.Server/OpenIddictServerHandlers.Device.cs @@ -65,8 +65,8 @@ public static partial class OpenIddictServerHandlers { private readonly IOpenIddictServerDispatcher _dispatcher; - public ExtractDeviceRequest(IOpenIddictServerDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public ExtractDeviceRequest(IOpenIddictServerDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -80,8 +80,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessRequestContext context!!) + public async ValueTask HandleAsync(ProcessRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var notification = new ExtractDeviceRequestContext(context.Transaction); await _dispatcher.DispatchAsync(notification); @@ -122,8 +127,8 @@ public static partial class OpenIddictServerHandlers { private readonly IOpenIddictServerDispatcher _dispatcher; - public ValidateDeviceRequest(IOpenIddictServerDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public ValidateDeviceRequest(IOpenIddictServerDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -137,8 +142,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessRequestContext context!!) + public async ValueTask HandleAsync(ProcessRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var notification = new ValidateDeviceRequestContext(context.Transaction); await _dispatcher.DispatchAsync(notification); @@ -174,8 +184,8 @@ public static partial class OpenIddictServerHandlers { private readonly IOpenIddictServerDispatcher _dispatcher; - public HandleDeviceRequest(IOpenIddictServerDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public HandleDeviceRequest(IOpenIddictServerDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -189,8 +199,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessRequestContext context!!) + public async ValueTask HandleAsync(ProcessRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var notification = new HandleDeviceRequestContext(context.Transaction); await _dispatcher.DispatchAsync(notification); @@ -270,8 +285,8 @@ public static partial class OpenIddictServerHandlers { private readonly IOpenIddictServerDispatcher _dispatcher; - public ApplyDeviceResponse(IOpenIddictServerDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public ApplyDeviceResponse(IOpenIddictServerDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -285,8 +300,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(TContext context!!) + public async ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var notification = new ApplyDeviceResponseContext(context.Transaction); await _dispatcher.DispatchAsync(notification); @@ -322,8 +342,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ValidateDeviceRequestContext context!!) + public ValueTask HandleAsync(ValidateDeviceRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // client_id is a required parameter and MUST cause an error when missing. // See https://tools.ietf.org/html/rfc8628#section-3.1 for more information. if (string.IsNullOrEmpty(context.ClientId)) @@ -358,8 +383,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ValidateDeviceRequestContext context!!) + public ValueTask HandleAsync(ValidateDeviceRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // Reject device requests that specify scope=offline_access if the refresh token flow is not enabled. if (context.Request.HasScope(Scopes.OfflineAccess) && !context.Options.GrantTypes.Contains(GrantTypes.RefreshToken)) { @@ -408,8 +438,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ValidateDeviceRequestContext context!!) + public async ValueTask HandleAsync(ValidateDeviceRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // If all the specified scopes are registered in the options, avoid making a database lookup. var scopes = new HashSet(context.Request.GetScopes(), StringComparer.Ordinal); scopes.ExceptWith(context.Options.Scopes); @@ -459,8 +494,8 @@ public static partial class OpenIddictServerHandlers public ValidateClientId() => throw new InvalidOperationException(SR.GetResourceString(SR.ID0016)); - public ValidateClientId(IOpenIddictApplicationManager applicationManager!!) - => _applicationManager = applicationManager; + public ValidateClientId(IOpenIddictApplicationManager applicationManager) + => _applicationManager = applicationManager ?? throw new ArgumentNullException(nameof(applicationManager)); /// /// Gets the default descriptor definition assigned to this handler. @@ -475,8 +510,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ValidateDeviceRequestContext context!!) + public async ValueTask HandleAsync(ValidateDeviceRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(!string.IsNullOrEmpty(context.ClientId), SR.FormatID4000(Parameters.ClientId)); // Retrieve the application details corresponding to the requested client_id. @@ -507,8 +547,8 @@ public static partial class OpenIddictServerHandlers public ValidateClientType() => throw new InvalidOperationException(SR.GetResourceString(SR.ID0016)); - public ValidateClientType(IOpenIddictApplicationManager applicationManager!!) - => _applicationManager = applicationManager; + public ValidateClientType(IOpenIddictApplicationManager applicationManager) + => _applicationManager = applicationManager ?? throw new ArgumentNullException(nameof(applicationManager)); /// /// Gets the default descriptor definition assigned to this handler. @@ -523,8 +563,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ValidateDeviceRequestContext context!!) + public async ValueTask HandleAsync(ValidateDeviceRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(!string.IsNullOrEmpty(context.ClientId), SR.FormatID4000(Parameters.ClientId)); var application = await _applicationManager.FindByClientIdAsync(context.ClientId) ?? @@ -573,8 +618,8 @@ public static partial class OpenIddictServerHandlers public ValidateClientSecret() => throw new InvalidOperationException(SR.GetResourceString(SR.ID0016)); - public ValidateClientSecret(IOpenIddictApplicationManager applicationManager!!) - => _applicationManager = applicationManager; + public ValidateClientSecret(IOpenIddictApplicationManager applicationManager) + => _applicationManager = applicationManager ?? throw new ArgumentNullException(nameof(applicationManager)); /// /// Gets the default descriptor definition assigned to this handler. @@ -589,8 +634,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ValidateDeviceRequestContext context!!) + public async ValueTask HandleAsync(ValidateDeviceRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(!string.IsNullOrEmpty(context.ClientId), SR.FormatID4000(Parameters.ClientId)); var application = await _applicationManager.FindByClientIdAsync(context.ClientId) ?? @@ -629,8 +679,8 @@ public static partial class OpenIddictServerHandlers public ValidateEndpointPermissions() => throw new InvalidOperationException(SR.GetResourceString(SR.ID0016)); - public ValidateEndpointPermissions(IOpenIddictApplicationManager applicationManager!!) - => _applicationManager = applicationManager; + public ValidateEndpointPermissions(IOpenIddictApplicationManager applicationManager) + => _applicationManager = applicationManager ?? throw new ArgumentNullException(nameof(applicationManager)); /// /// Gets the default descriptor definition assigned to this handler. @@ -646,8 +696,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ValidateDeviceRequestContext context!!) + public async ValueTask HandleAsync(ValidateDeviceRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(!string.IsNullOrEmpty(context.ClientId), SR.FormatID4000(Parameters.ClientId)); var application = await _applicationManager.FindByClientIdAsync(context.ClientId) ?? @@ -678,8 +733,8 @@ public static partial class OpenIddictServerHandlers public ValidateGrantTypePermissions() => throw new InvalidOperationException(SR.GetResourceString(SR.ID0016)); - public ValidateGrantTypePermissions(IOpenIddictApplicationManager applicationManager!!) - => _applicationManager = applicationManager; + public ValidateGrantTypePermissions(IOpenIddictApplicationManager applicationManager) + => _applicationManager = applicationManager ?? throw new ArgumentNullException(nameof(applicationManager)); /// /// Gets the default descriptor definition assigned to this handler. @@ -694,8 +749,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ValidateDeviceRequestContext context!!) + public async ValueTask HandleAsync(ValidateDeviceRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(!string.IsNullOrEmpty(context.ClientId), SR.FormatID4000(Parameters.ClientId)); var application = await _applicationManager.FindByClientIdAsync(context.ClientId) ?? @@ -742,8 +802,8 @@ public static partial class OpenIddictServerHandlers public ValidateScopePermissions() => throw new InvalidOperationException(SR.GetResourceString(SR.ID0016)); - public ValidateScopePermissions(IOpenIddictApplicationManager applicationManager!!) - => _applicationManager = applicationManager; + public ValidateScopePermissions(IOpenIddictApplicationManager applicationManager) + => _applicationManager = applicationManager ?? throw new ArgumentNullException(nameof(applicationManager)); /// /// Gets the default descriptor definition assigned to this handler. @@ -759,8 +819,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ValidateDeviceRequestContext context!!) + public async ValueTask HandleAsync(ValidateDeviceRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(!string.IsNullOrEmpty(context.ClientId), SR.FormatID4000(Parameters.ClientId)); var application = await _applicationManager.FindByClientIdAsync(context.ClientId) ?? @@ -798,8 +863,8 @@ public static partial class OpenIddictServerHandlers { private readonly IOpenIddictServerDispatcher _dispatcher; - public ExtractVerificationRequest(IOpenIddictServerDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public ExtractVerificationRequest(IOpenIddictServerDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -813,8 +878,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessRequestContext context!!) + public async ValueTask HandleAsync(ProcessRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var notification = new ExtractVerificationRequestContext(context.Transaction); await _dispatcher.DispatchAsync(notification); @@ -855,8 +925,8 @@ public static partial class OpenIddictServerHandlers { private readonly IOpenIddictServerDispatcher _dispatcher; - public ValidateVerificationRequest(IOpenIddictServerDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public ValidateVerificationRequest(IOpenIddictServerDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -870,8 +940,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessRequestContext context!!) + public async ValueTask HandleAsync(ProcessRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var notification = new ValidateVerificationRequestContext(context.Transaction); await _dispatcher.DispatchAsync(notification); @@ -907,8 +982,8 @@ public static partial class OpenIddictServerHandlers { private readonly IOpenIddictServerDispatcher _dispatcher; - public HandleVerificationRequest(IOpenIddictServerDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public HandleVerificationRequest(IOpenIddictServerDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -922,8 +997,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessRequestContext context!!) + public async ValueTask HandleAsync(ProcessRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var notification = new HandleVerificationRequestContext(context.Transaction); await _dispatcher.DispatchAsync(notification); @@ -999,8 +1079,8 @@ public static partial class OpenIddictServerHandlers { private readonly IOpenIddictServerDispatcher _dispatcher; - public ApplyVerificationResponse(IOpenIddictServerDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public ApplyVerificationResponse(IOpenIddictServerDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -1014,8 +1094,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(TContext context!!) + public async ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var notification = new ApplyVerificationResponseContext(context.Transaction); await _dispatcher.DispatchAsync(notification); @@ -1042,8 +1127,8 @@ public static partial class OpenIddictServerHandlers { private readonly IOpenIddictServerDispatcher _dispatcher; - public AttachUserCodePrincipal(IOpenIddictServerDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public AttachUserCodePrincipal(IOpenIddictServerDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -1056,8 +1141,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(HandleVerificationRequestContext context!!) + public async ValueTask HandleAsync(HandleVerificationRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // Note: the user_code may not be present (e.g when the user typed // the verification_uri manually without the user code appended). // In this case, ignore the missing token so that a view can be diff --git a/src/OpenIddict.Server/OpenIddictServerHandlers.Discovery.cs b/src/OpenIddict.Server/OpenIddictServerHandlers.Discovery.cs index f9ab7b44..429b7ebf 100644 --- a/src/OpenIddict.Server/OpenIddictServerHandlers.Discovery.cs +++ b/src/OpenIddict.Server/OpenIddictServerHandlers.Discovery.cs @@ -64,8 +64,8 @@ public static partial class OpenIddictServerHandlers { private readonly IOpenIddictServerDispatcher _dispatcher; - public ExtractConfigurationRequest(IOpenIddictServerDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public ExtractConfigurationRequest(IOpenIddictServerDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -79,8 +79,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessRequestContext context!!) + public async ValueTask HandleAsync(ProcessRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var notification = new ExtractConfigurationRequestContext(context.Transaction); await _dispatcher.DispatchAsync(notification); @@ -121,8 +126,8 @@ public static partial class OpenIddictServerHandlers { private readonly IOpenIddictServerDispatcher _dispatcher; - public ValidateConfigurationRequest(IOpenIddictServerDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public ValidateConfigurationRequest(IOpenIddictServerDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -136,8 +141,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessRequestContext context!!) + public async ValueTask HandleAsync(ProcessRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var notification = new ValidateConfigurationRequestContext(context.Transaction); await _dispatcher.DispatchAsync(notification); @@ -173,8 +183,8 @@ public static partial class OpenIddictServerHandlers { private readonly IOpenIddictServerDispatcher _dispatcher; - public HandleConfigurationRequest(IOpenIddictServerDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public HandleConfigurationRequest(IOpenIddictServerDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -188,8 +198,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessRequestContext context!!) + public async ValueTask HandleAsync(ProcessRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var notification = new HandleConfigurationRequestContext(context.Transaction); await _dispatcher.DispatchAsync(notification); @@ -254,8 +269,8 @@ public static partial class OpenIddictServerHandlers { private readonly IOpenIddictServerDispatcher _dispatcher; - public ApplyConfigurationResponse(IOpenIddictServerDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public ApplyConfigurationResponse(IOpenIddictServerDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -269,8 +284,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(TContext context!!) + public async ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var notification = new ApplyConfigurationResponseContext(context.Transaction); await _dispatcher.DispatchAsync(notification); @@ -306,8 +326,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(HandleConfigurationRequestContext context!!) + public ValueTask HandleAsync(HandleConfigurationRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // Note: while OpenIddict allows specifying multiple endpoint addresses, the OAuth 2.0 // and OpenID Connect discovery specifications only allow a single address per endpoint. @@ -392,8 +417,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(HandleConfigurationRequestContext context!!) + public ValueTask HandleAsync(HandleConfigurationRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + context.GrantTypes.UnionWith(context.Options.GrantTypes); return default; @@ -416,8 +446,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(HandleConfigurationRequestContext context!!) + public ValueTask HandleAsync(HandleConfigurationRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + context.ResponseModes.UnionWith(context.Options.ResponseModes); return default; @@ -440,8 +475,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(HandleConfigurationRequestContext context!!) + public ValueTask HandleAsync(HandleConfigurationRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + context.ResponseTypes.UnionWith(context.Options.ResponseTypes); return default; @@ -465,8 +505,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(HandleConfigurationRequestContext context!!) + public ValueTask HandleAsync(HandleConfigurationRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + if (context.IntrospectionEndpoint is not null) { context.IntrospectionEndpointAuthenticationMethods.Add(ClientAuthenticationMethods.ClientSecretBasic); @@ -506,8 +551,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(HandleConfigurationRequestContext context!!) + public ValueTask HandleAsync(HandleConfigurationRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + context.CodeChallengeMethods.UnionWith(context.Options.CodeChallengeMethods); return default; @@ -530,8 +580,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(HandleConfigurationRequestContext context!!) + public ValueTask HandleAsync(HandleConfigurationRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + context.Scopes.UnionWith(context.Options.Scopes); return default; @@ -554,8 +609,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(HandleConfigurationRequestContext context!!) + public ValueTask HandleAsync(HandleConfigurationRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + context.Claims.UnionWith(context.Options.Claims); return default; @@ -578,8 +638,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(HandleConfigurationRequestContext context!!) + public ValueTask HandleAsync(HandleConfigurationRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + context.SubjectTypes.Add(SubjectTypes.Public); return default; @@ -602,8 +667,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(HandleConfigurationRequestContext context!!) + public ValueTask HandleAsync(HandleConfigurationRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + foreach (var credentials in context.Options.SigningCredentials) { // Try to resolve the JWA algorithm short name. @@ -663,8 +733,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(HandleConfigurationRequestContext context!!) + public ValueTask HandleAsync(HandleConfigurationRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // Note: the optional claims/request/request_uri parameters are not yet supported // by OpenIddict, so "false" is returned to encourage clients not to use them. context.Metadata[Metadata.ClaimsParameterSupported] = false; @@ -687,8 +762,8 @@ public static partial class OpenIddictServerHandlers { private readonly IOpenIddictServerDispatcher _dispatcher; - public ExtractCryptographyRequest(IOpenIddictServerDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public ExtractCryptographyRequest(IOpenIddictServerDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -702,8 +777,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessRequestContext context!!) + public async ValueTask HandleAsync(ProcessRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var notification = new ExtractCryptographyRequestContext(context.Transaction); await _dispatcher.DispatchAsync(notification); @@ -744,8 +824,8 @@ public static partial class OpenIddictServerHandlers { private readonly IOpenIddictServerDispatcher _dispatcher; - public ValidateCryptographyRequest(IOpenIddictServerDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public ValidateCryptographyRequest(IOpenIddictServerDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -759,8 +839,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessRequestContext context!!) + public async ValueTask HandleAsync(ProcessRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var notification = new ValidateCryptographyRequestContext(context.Transaction); await _dispatcher.DispatchAsync(notification); @@ -796,8 +881,8 @@ public static partial class OpenIddictServerHandlers { private readonly IOpenIddictServerDispatcher _dispatcher; - public HandleCryptographyRequest(IOpenIddictServerDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public HandleCryptographyRequest(IOpenIddictServerDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -811,8 +896,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessRequestContext context!!) + public async ValueTask HandleAsync(ProcessRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var notification = new HandleCryptographyRequestContext(context.Transaction); await _dispatcher.DispatchAsync(notification); @@ -919,8 +1009,8 @@ public static partial class OpenIddictServerHandlers { private readonly IOpenIddictServerDispatcher _dispatcher; - public ApplyCryptographyResponse(IOpenIddictServerDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public ApplyCryptographyResponse(IOpenIddictServerDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -934,8 +1024,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(TContext context!!) + public async ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var notification = new ApplyCryptographyResponseContext(context.Transaction); await _dispatcher.DispatchAsync(notification); @@ -971,8 +1066,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(HandleCryptographyRequestContext context!!) + public ValueTask HandleAsync(HandleCryptographyRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + foreach (var credentials in context.Options.SigningCredentials) { #if SUPPORTS_ECDSA diff --git a/src/OpenIddict.Server/OpenIddictServerHandlers.Exchange.cs b/src/OpenIddict.Server/OpenIddictServerHandlers.Exchange.cs index fb695f06..43a74ef0 100644 --- a/src/OpenIddict.Server/OpenIddictServerHandlers.Exchange.cs +++ b/src/OpenIddict.Server/OpenIddictServerHandlers.Exchange.cs @@ -78,8 +78,8 @@ public static partial class OpenIddictServerHandlers { private readonly IOpenIddictServerDispatcher _dispatcher; - public ExtractTokenRequest(IOpenIddictServerDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public ExtractTokenRequest(IOpenIddictServerDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -93,8 +93,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessRequestContext context!!) + public async ValueTask HandleAsync(ProcessRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var notification = new ExtractTokenRequestContext(context.Transaction); await _dispatcher.DispatchAsync(notification); @@ -135,8 +140,8 @@ public static partial class OpenIddictServerHandlers { private readonly IOpenIddictServerDispatcher _dispatcher; - public ValidateTokenRequest(IOpenIddictServerDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public ValidateTokenRequest(IOpenIddictServerDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -150,8 +155,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessRequestContext context!!) + public async ValueTask HandleAsync(ProcessRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var notification = new ValidateTokenRequestContext(context.Transaction); await _dispatcher.DispatchAsync(notification); @@ -191,8 +201,8 @@ public static partial class OpenIddictServerHandlers { private readonly IOpenIddictServerDispatcher _dispatcher; - public HandleTokenRequest(IOpenIddictServerDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public HandleTokenRequest(IOpenIddictServerDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -206,8 +216,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessRequestContext context!!) + public async ValueTask HandleAsync(ProcessRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var notification = new HandleTokenRequestContext(context.Transaction); await _dispatcher.DispatchAsync(notification); @@ -283,8 +298,8 @@ public static partial class OpenIddictServerHandlers { private readonly IOpenIddictServerDispatcher _dispatcher; - public ApplyTokenResponse(IOpenIddictServerDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public ApplyTokenResponse(IOpenIddictServerDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -298,8 +313,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(TContext context!!) + public async ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var notification = new ApplyTokenResponseContext(context.Transaction); await _dispatcher.DispatchAsync(notification); @@ -335,8 +355,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ValidateTokenRequestContext context!!) + public ValueTask HandleAsync(ValidateTokenRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // Reject token requests missing the mandatory grant_type parameter. if (string.IsNullOrEmpty(context.Request.GrantType)) { @@ -395,8 +420,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ValidateTokenRequestContext context!!) + public ValueTask HandleAsync(ValidateTokenRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + if (!string.IsNullOrEmpty(context.ClientId)) { return default; @@ -440,8 +470,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ValidateTokenRequestContext context!!) + public ValueTask HandleAsync(ValidateTokenRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // Reject grant_type=authorization_code requests missing the authorization code. // See https://tools.ietf.org/html/rfc6749#section-4.1.3 for more information. if (context.Request.IsAuthorizationCodeGrantType() && string.IsNullOrEmpty(context.Request.Code)) @@ -477,8 +512,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ValidateTokenRequestContext context!!) + public ValueTask HandleAsync(ValidateTokenRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // Reject grant_type=client_credentials requests missing the client credentials. // See https://tools.ietf.org/html/rfc6749#section-4.4.1 for more information. if (context.Request.IsClientCredentialsGrantType() && (string.IsNullOrEmpty(context.Request.ClientId) || @@ -513,8 +553,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ValidateTokenRequestContext context!!) + public ValueTask HandleAsync(ValidateTokenRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // Reject grant_type=urn:ietf:params:oauth:grant-type:device_code requests missing the device code. // See https://tools.ietf.org/html/rfc8628#section-3.4 for more information. if (context.Request.IsDeviceCodeGrantType() && string.IsNullOrEmpty(context.Request.DeviceCode)) @@ -548,8 +593,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ValidateTokenRequestContext context!!) + public ValueTask HandleAsync(ValidateTokenRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // Reject grant_type=refresh_token requests missing the refresh token. // See https://tools.ietf.org/html/rfc6749#section-6 for more information. if (context.Request.IsRefreshTokenGrantType() && string.IsNullOrEmpty(context.Request.RefreshToken)) @@ -585,8 +635,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ValidateTokenRequestContext context!!) + public ValueTask HandleAsync(ValidateTokenRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // Reject grant_type=password requests missing username or password. // See https://tools.ietf.org/html/rfc6749#section-4.3.2 for more information. if (context.Request.IsPasswordGrantType() && (string.IsNullOrEmpty(context.Request.Username) || @@ -622,8 +677,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ValidateTokenRequestContext context!!) + public ValueTask HandleAsync(ValidateTokenRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + if (!context.Request.IsAuthorizationCodeGrantType()) { return default; @@ -682,8 +742,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ValidateTokenRequestContext context!!) + public async ValueTask HandleAsync(ValidateTokenRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // If all the specified scopes are registered in the options, avoid making a database lookup. var scopes = new HashSet(context.Request.GetScopes(), StringComparer.Ordinal); scopes.ExceptWith(context.Options.Scopes); @@ -733,8 +798,8 @@ public static partial class OpenIddictServerHandlers public ValidateClientId() => throw new InvalidOperationException(SR.GetResourceString(SR.ID0016)); - public ValidateClientId(IOpenIddictApplicationManager applicationManager!!) - => _applicationManager = applicationManager; + public ValidateClientId(IOpenIddictApplicationManager applicationManager) + => _applicationManager = applicationManager ?? throw new ArgumentNullException(nameof(applicationManager)); /// /// Gets the default descriptor definition assigned to this handler. @@ -749,8 +814,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ValidateTokenRequestContext context!!) + public async ValueTask HandleAsync(ValidateTokenRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(!string.IsNullOrEmpty(context.ClientId), SR.FormatID4000(Parameters.ClientId)); // Retrieve the application details corresponding to the requested client_id. @@ -781,8 +851,8 @@ public static partial class OpenIddictServerHandlers public ValidateClientType() => throw new InvalidOperationException(SR.GetResourceString(SR.ID0016)); - public ValidateClientType(IOpenIddictApplicationManager applicationManager!!) - => _applicationManager = applicationManager; + public ValidateClientType(IOpenIddictApplicationManager applicationManager) + => _applicationManager = applicationManager ?? throw new ArgumentNullException(nameof(applicationManager)); /// /// Gets the default descriptor definition assigned to this handler. @@ -797,8 +867,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ValidateTokenRequestContext context!!) + public async ValueTask HandleAsync(ValidateTokenRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(!string.IsNullOrEmpty(context.ClientId), SR.FormatID4000(Parameters.ClientId)); var application = await _applicationManager.FindByClientIdAsync(context.ClientId) ?? @@ -860,8 +935,8 @@ public static partial class OpenIddictServerHandlers public ValidateClientSecret() => throw new InvalidOperationException(SR.GetResourceString(SR.ID0016)); - public ValidateClientSecret(IOpenIddictApplicationManager applicationManager!!) - => _applicationManager = applicationManager; + public ValidateClientSecret(IOpenIddictApplicationManager applicationManager) + => _applicationManager = applicationManager ?? throw new ArgumentNullException(nameof(applicationManager)); /// /// Gets the default descriptor definition assigned to this handler. @@ -876,8 +951,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ValidateTokenRequestContext context!!) + public async ValueTask HandleAsync(ValidateTokenRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(!string.IsNullOrEmpty(context.ClientId), SR.FormatID4000(Parameters.ClientId)); var application = await _applicationManager.FindByClientIdAsync(context.ClientId) ?? @@ -916,8 +996,8 @@ public static partial class OpenIddictServerHandlers public ValidateEndpointPermissions() => throw new InvalidOperationException(SR.GetResourceString(SR.ID0016)); - public ValidateEndpointPermissions(IOpenIddictApplicationManager applicationManager!!) - => _applicationManager = applicationManager; + public ValidateEndpointPermissions(IOpenIddictApplicationManager applicationManager) + => _applicationManager = applicationManager ?? throw new ArgumentNullException(nameof(applicationManager)); /// /// Gets the default descriptor definition assigned to this handler. @@ -933,8 +1013,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ValidateTokenRequestContext context!!) + public async ValueTask HandleAsync(ValidateTokenRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(!string.IsNullOrEmpty(context.ClientId), SR.FormatID4000(Parameters.ClientId)); var application = await _applicationManager.FindByClientIdAsync(context.ClientId) ?? @@ -966,8 +1051,8 @@ public static partial class OpenIddictServerHandlers public ValidateGrantTypePermissions() => throw new InvalidOperationException(SR.GetResourceString(SR.ID0016)); - public ValidateGrantTypePermissions(IOpenIddictApplicationManager applicationManager!!) - => _applicationManager = applicationManager; + public ValidateGrantTypePermissions(IOpenIddictApplicationManager applicationManager) + => _applicationManager = applicationManager ?? throw new ArgumentNullException(nameof(applicationManager)); /// /// Gets the default descriptor definition assigned to this handler. @@ -983,8 +1068,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ValidateTokenRequestContext context!!) + public async ValueTask HandleAsync(ValidateTokenRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(!string.IsNullOrEmpty(context.ClientId), SR.FormatID4000(Parameters.ClientId)); var application = await _applicationManager.FindByClientIdAsync(context.ClientId) ?? @@ -1031,8 +1121,8 @@ public static partial class OpenIddictServerHandlers public ValidateScopePermissions() => throw new InvalidOperationException(SR.GetResourceString(SR.ID0016)); - public ValidateScopePermissions(IOpenIddictApplicationManager applicationManager!!) - => _applicationManager = applicationManager; + public ValidateScopePermissions(IOpenIddictApplicationManager applicationManager) + => _applicationManager = applicationManager ?? throw new ArgumentNullException(nameof(applicationManager)); /// /// Gets the default descriptor definition assigned to this handler. @@ -1048,8 +1138,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ValidateTokenRequestContext context!!) + public async ValueTask HandleAsync(ValidateTokenRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(!string.IsNullOrEmpty(context.ClientId), SR.FormatID4000(Parameters.ClientId)); var application = await _applicationManager.FindByClientIdAsync(context.ClientId) ?? @@ -1091,8 +1186,8 @@ public static partial class OpenIddictServerHandlers public ValidateProofKeyForCodeExchangeRequirement() => throw new InvalidOperationException(SR.GetResourceString(SR.ID0016)); - public ValidateProofKeyForCodeExchangeRequirement(IOpenIddictApplicationManager applicationManager!!) - => _applicationManager = applicationManager; + public ValidateProofKeyForCodeExchangeRequirement(IOpenIddictApplicationManager applicationManager) + => _applicationManager = applicationManager ?? throw new ArgumentNullException(nameof(applicationManager)); /// /// Gets the default descriptor definition assigned to this handler. @@ -1107,8 +1202,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ValidateTokenRequestContext context!!) + public async ValueTask HandleAsync(ValidateTokenRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + if (!context.Request.IsAuthorizationCodeGrantType()) { return; @@ -1148,8 +1248,8 @@ public static partial class OpenIddictServerHandlers { private readonly IOpenIddictServerDispatcher _dispatcher; - public ValidateToken(IOpenIddictServerDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public ValidateToken(IOpenIddictServerDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -1162,8 +1262,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ValidateTokenRequestContext context!!) + public async ValueTask HandleAsync(ValidateTokenRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + if (!context.Request.IsAuthorizationCodeGrantType() && !context.Request.IsDeviceCodeGrantType() && !context.Request.IsRefreshTokenGrantType()) @@ -1223,8 +1328,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ValidateTokenRequestContext context!!) + public ValueTask HandleAsync(ValidateTokenRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + if (!context.Request.IsAuthorizationCodeGrantType() && !context.Request.IsDeviceCodeGrantType() && !context.Request.IsRefreshTokenGrantType()) @@ -1310,8 +1420,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ValidateTokenRequestContext context!!) + public ValueTask HandleAsync(ValidateTokenRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + if (!context.Request.IsAuthorizationCodeGrantType()) { return default; @@ -1376,8 +1491,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ValidateTokenRequestContext context!!) + public ValueTask HandleAsync(ValidateTokenRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + if (!context.Request.IsAuthorizationCodeGrantType()) { return default; @@ -1490,8 +1610,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ValidateTokenRequestContext context!!) + public ValueTask HandleAsync(ValidateTokenRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + if (!context.Request.IsAuthorizationCodeGrantType() && !context.Request.IsRefreshTokenGrantType()) { return default; @@ -1557,8 +1682,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(HandleTokenRequestContext context!!) + public ValueTask HandleAsync(HandleTokenRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + if (!context.Request.IsAuthorizationCodeGrantType() && !context.Request.IsRefreshTokenGrantType()) { return default; @@ -1590,8 +1720,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ApplyTokenResponseContext context!!) + public ValueTask HandleAsync(ApplyTokenResponseContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + if (string.IsNullOrEmpty(context.Error)) { return default; diff --git a/src/OpenIddict.Server/OpenIddictServerHandlers.Introspection.cs b/src/OpenIddict.Server/OpenIddictServerHandlers.Introspection.cs index 572597cb..c4ffce6c 100644 --- a/src/OpenIddict.Server/OpenIddictServerHandlers.Introspection.cs +++ b/src/OpenIddict.Server/OpenIddictServerHandlers.Introspection.cs @@ -63,8 +63,8 @@ public static partial class OpenIddictServerHandlers { private readonly IOpenIddictServerDispatcher _dispatcher; - public ExtractIntrospectionRequest(IOpenIddictServerDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public ExtractIntrospectionRequest(IOpenIddictServerDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -78,8 +78,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessRequestContext context!!) + public async ValueTask HandleAsync(ProcessRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var notification = new ExtractIntrospectionRequestContext(context.Transaction); await _dispatcher.DispatchAsync(notification); @@ -120,8 +125,8 @@ public static partial class OpenIddictServerHandlers { private readonly IOpenIddictServerDispatcher _dispatcher; - public ValidateIntrospectionRequest(IOpenIddictServerDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public ValidateIntrospectionRequest(IOpenIddictServerDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -135,8 +140,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessRequestContext context!!) + public async ValueTask HandleAsync(ProcessRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var notification = new ValidateIntrospectionRequestContext(context.Transaction); await _dispatcher.DispatchAsync(notification); @@ -176,8 +186,8 @@ public static partial class OpenIddictServerHandlers { private readonly IOpenIddictServerDispatcher _dispatcher; - public HandleIntrospectionRequest(IOpenIddictServerDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public HandleIntrospectionRequest(IOpenIddictServerDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -191,8 +201,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessRequestContext context!!) + public async ValueTask HandleAsync(ProcessRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var notification = new HandleIntrospectionRequestContext(context.Transaction); await _dispatcher.DispatchAsync(notification); @@ -274,8 +289,8 @@ public static partial class OpenIddictServerHandlers { private readonly IOpenIddictServerDispatcher _dispatcher; - public ApplyIntrospectionResponse(IOpenIddictServerDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public ApplyIntrospectionResponse(IOpenIddictServerDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -289,8 +304,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(TContext context!!) + public async ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var notification = new ApplyIntrospectionResponseContext(context.Transaction); await _dispatcher.DispatchAsync(notification); @@ -326,8 +346,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ValidateIntrospectionRequestContext context!!) + public ValueTask HandleAsync(ValidateIntrospectionRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // Reject introspection requests missing the mandatory token parameter. if (string.IsNullOrEmpty(context.Request.Token)) { @@ -361,8 +386,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ValidateIntrospectionRequestContext context!!) + public ValueTask HandleAsync(ValidateIntrospectionRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // At this stage, reject the introspection request unless the client identification requirement was disabled. if (!context.Options.AcceptAnonymousClients && string.IsNullOrEmpty(context.ClientId)) { @@ -390,8 +420,8 @@ public static partial class OpenIddictServerHandlers public ValidateClientId() => throw new InvalidOperationException(SR.GetResourceString(SR.ID0016)); - public ValidateClientId(IOpenIddictApplicationManager applicationManager!!) - => _applicationManager = applicationManager; + public ValidateClientId(IOpenIddictApplicationManager applicationManager) + => _applicationManager = applicationManager ?? throw new ArgumentNullException(nameof(applicationManager)); /// /// Gets the default descriptor definition assigned to this handler. @@ -406,8 +436,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ValidateIntrospectionRequestContext context!!) + public async ValueTask HandleAsync(ValidateIntrospectionRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(!string.IsNullOrEmpty(context.ClientId), SR.FormatID4000(Parameters.ClientId)); // Retrieve the application details corresponding to the requested client_id. @@ -438,8 +473,8 @@ public static partial class OpenIddictServerHandlers public ValidateClientType() => throw new InvalidOperationException(SR.GetResourceString(SR.ID0016)); - public ValidateClientType(IOpenIddictApplicationManager applicationManager!!) - => _applicationManager = applicationManager; + public ValidateClientType(IOpenIddictApplicationManager applicationManager) + => _applicationManager = applicationManager ?? throw new ArgumentNullException(nameof(applicationManager)); /// /// Gets the default descriptor definition assigned to this handler. @@ -454,8 +489,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ValidateIntrospectionRequestContext context!!) + public async ValueTask HandleAsync(ValidateIntrospectionRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(!string.IsNullOrEmpty(context.ClientId), SR.FormatID4000(Parameters.ClientId)); var application = await _applicationManager.FindByClientIdAsync(context.ClientId) ?? @@ -504,8 +544,8 @@ public static partial class OpenIddictServerHandlers public ValidateClientSecret() => throw new InvalidOperationException(SR.GetResourceString(SR.ID0016)); - public ValidateClientSecret(IOpenIddictApplicationManager applicationManager!!) - => _applicationManager = applicationManager; + public ValidateClientSecret(IOpenIddictApplicationManager applicationManager) + => _applicationManager = applicationManager ?? throw new ArgumentNullException(nameof(applicationManager)); /// /// Gets the default descriptor definition assigned to this handler. @@ -520,8 +560,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ValidateIntrospectionRequestContext context!!) + public async ValueTask HandleAsync(ValidateIntrospectionRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(!string.IsNullOrEmpty(context.ClientId), SR.FormatID4000(Parameters.ClientId)); var application = await _applicationManager.FindByClientIdAsync(context.ClientId) ?? @@ -560,8 +605,8 @@ public static partial class OpenIddictServerHandlers public ValidateEndpointPermissions() => throw new InvalidOperationException(SR.GetResourceString(SR.ID0016)); - public ValidateEndpointPermissions(IOpenIddictApplicationManager applicationManager!!) - => _applicationManager = applicationManager; + public ValidateEndpointPermissions(IOpenIddictApplicationManager applicationManager) + => _applicationManager = applicationManager ?? throw new ArgumentNullException(nameof(applicationManager)); /// /// Gets the default descriptor definition assigned to this handler. @@ -577,8 +622,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ValidateIntrospectionRequestContext context!!) + public async ValueTask HandleAsync(ValidateIntrospectionRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(!string.IsNullOrEmpty(context.ClientId), SR.FormatID4000(Parameters.ClientId)); var application = await _applicationManager.FindByClientIdAsync(context.ClientId) ?? @@ -606,8 +656,8 @@ public static partial class OpenIddictServerHandlers { private readonly IOpenIddictServerDispatcher _dispatcher; - public ValidateToken(IOpenIddictServerDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public ValidateToken(IOpenIddictServerDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -620,8 +670,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ValidateIntrospectionRequestContext context!!) + public async ValueTask HandleAsync(ValidateIntrospectionRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var notification = new ProcessAuthenticationContext(context.Transaction); await _dispatcher.DispatchAsync(notification); @@ -671,8 +726,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ValidateIntrospectionRequestContext context!!) + public ValueTask HandleAsync(ValidateIntrospectionRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.Principal is { Identity: ClaimsIdentity }, SR.GetResourceString(SR.ID4006)); if (!context.Principal.HasTokenType(TokenTypeHints.AccessToken) && @@ -713,8 +773,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ValidateIntrospectionRequestContext context!!) + public ValueTask HandleAsync(ValidateIntrospectionRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(!string.IsNullOrEmpty(context.ClientId), SR.FormatID4000(Parameters.ClientId)); Debug.Assert(context.Principal is { Identity: ClaimsIdentity }, SR.GetResourceString(SR.ID4006)); @@ -774,8 +839,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(HandleIntrospectionRequestContext context!!) + public ValueTask HandleAsync(HandleIntrospectionRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var notification = context.Transaction.GetProperty( typeof(ValidateIntrospectionRequestContext).FullName!) ?? throw new InvalidOperationException(SR.GetResourceString(SR.ID0007)); @@ -804,8 +874,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(HandleIntrospectionRequestContext context!!) + public ValueTask HandleAsync(HandleIntrospectionRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.Principal is { Identity: ClaimsIdentity }, SR.GetResourceString(SR.ID4006)); context.TokenId = context.Principal.GetClaim(Claims.JwtId); @@ -842,8 +917,8 @@ public static partial class OpenIddictServerHandlers public AttachApplicationClaims() => throw new InvalidOperationException(SR.GetResourceString(SR.ID0016)); - public AttachApplicationClaims(IOpenIddictApplicationManager applicationManager!!) - => _applicationManager = applicationManager; + public AttachApplicationClaims(IOpenIddictApplicationManager applicationManager) + => _applicationManager = applicationManager ?? throw new ArgumentNullException(nameof(applicationManager)); /// /// Gets the default descriptor definition assigned to this handler. @@ -858,8 +933,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(HandleIntrospectionRequestContext context!!) + public async ValueTask HandleAsync(HandleIntrospectionRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(!string.IsNullOrEmpty(context.Request.ClientId), SR.FormatID4000(Parameters.ClientId)); Debug.Assert(context.Principal is { Identity: ClaimsIdentity }, SR.GetResourceString(SR.ID4006)); @@ -1011,8 +1091,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ApplyIntrospectionResponseContext context!!) + public ValueTask HandleAsync(ApplyIntrospectionResponseContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + if (string.IsNullOrEmpty(context.Error)) { return default; diff --git a/src/OpenIddict.Server/OpenIddictServerHandlers.Protection.cs b/src/OpenIddict.Server/OpenIddictServerHandlers.Protection.cs index 617f826e..9bd5c7d1 100644 --- a/src/OpenIddict.Server/OpenIddictServerHandlers.Protection.cs +++ b/src/OpenIddict.Server/OpenIddictServerHandlers.Protection.cs @@ -60,8 +60,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ValidateTokenContext context!!) + public ValueTask HandleAsync(ValidateTokenContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var parameters = context.Options.TokenValidationParameters.Clone(); parameters.ValidIssuer ??= context.Issuer?.AbsoluteUri; parameters.ValidateIssuer = !string.IsNullOrEmpty(parameters.ValidIssuer); @@ -122,8 +127,8 @@ public static partial class OpenIddictServerHandlers public ValidateReferenceTokenIdentifier() => throw new InvalidOperationException(SR.GetResourceString(SR.ID0016)); - public ValidateReferenceTokenIdentifier(IOpenIddictTokenManager tokenManager!!) - => _tokenManager = tokenManager; + public ValidateReferenceTokenIdentifier(IOpenIddictTokenManager tokenManager) + => _tokenManager = tokenManager ?? throw new ArgumentNullException(nameof(tokenManager)); /// /// Gets the default descriptor definition assigned to this handler. @@ -137,8 +142,13 @@ public static partial class OpenIddictServerHandlers .SetType(OpenIddictServerHandlerType.BuiltIn) .Build(); - public async ValueTask HandleAsync(ValidateTokenContext context!!) + public async ValueTask HandleAsync(ValidateTokenContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var token = context.Token.Length switch { // 12 may correspond to a normalized user code and 43 to any @@ -245,8 +255,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ValidateTokenContext context!!) + public async ValueTask HandleAsync(ValidateTokenContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // If a principal was already attached, don't overwrite it. if (context.Principal is not null) { @@ -391,8 +406,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ValidateTokenContext context!!) + public ValueTask HandleAsync(ValidateTokenContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + if (context.Principal is null) { return default; @@ -431,8 +451,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ValidateTokenContext context!!) + public ValueTask HandleAsync(ValidateTokenContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + if (context.Principal is null) { return default; @@ -523,8 +548,8 @@ public static partial class OpenIddictServerHandlers public RestoreReferenceTokenProperties() => throw new InvalidOperationException(SR.GetResourceString(SR.ID0016)); - public RestoreReferenceTokenProperties(IOpenIddictTokenManager tokenManager!!) - => _tokenManager = tokenManager; + public RestoreReferenceTokenProperties(IOpenIddictTokenManager tokenManager) + => _tokenManager = tokenManager ?? throw new ArgumentNullException(nameof(tokenManager)); /// /// Gets the default descriptor definition assigned to this handler. @@ -538,8 +563,13 @@ public static partial class OpenIddictServerHandlers .SetType(OpenIddictServerHandlerType.BuiltIn) .Build(); - public async ValueTask HandleAsync(ValidateTokenContext context!!) + public async ValueTask HandleAsync(ValidateTokenContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + if (context.Principal is null || string.IsNullOrEmpty(context.TokenId)) { return; @@ -573,8 +603,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ValidateTokenContext context!!) + public ValueTask HandleAsync(ValidateTokenContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + if (context.Principal is null) { context.Reject( @@ -646,8 +681,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ValidateTokenContext context!!) + public ValueTask HandleAsync(ValidateTokenContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.Principal is { Identity: ClaimsIdentity }, SR.GetResourceString(SR.ID4006)); var date = context.Principal.GetExpirationDate(); @@ -694,8 +734,8 @@ public static partial class OpenIddictServerHandlers public ValidateTokenEntry() => throw new InvalidOperationException(SR.GetResourceString(SR.ID0016)); - public ValidateTokenEntry(IOpenIddictTokenManager tokenManager!!) - => _tokenManager = tokenManager; + public ValidateTokenEntry(IOpenIddictTokenManager tokenManager) + => _tokenManager = tokenManager ?? throw new ArgumentNullException(nameof(tokenManager)); /// /// Gets the default descriptor definition assigned to this handler. @@ -709,8 +749,13 @@ public static partial class OpenIddictServerHandlers .SetType(OpenIddictServerHandlerType.BuiltIn) .Build(); - public async ValueTask HandleAsync(ValidateTokenContext context!!) + public async ValueTask HandleAsync(ValidateTokenContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.Principal is { Identity: ClaimsIdentity }, SR.GetResourceString(SR.ID4006)); // Extract the token identifier from the authentication principal. @@ -892,8 +937,8 @@ public static partial class OpenIddictServerHandlers public ValidateAuthorizationEntry() => throw new InvalidOperationException(SR.GetResourceString(SR.ID0016)); - public ValidateAuthorizationEntry(IOpenIddictAuthorizationManager authorizationManager!!) - => _authorizationManager = authorizationManager; + public ValidateAuthorizationEntry(IOpenIddictAuthorizationManager authorizationManager) + => _authorizationManager = authorizationManager ?? throw new ArgumentNullException(nameof(authorizationManager)); /// /// Gets the default descriptor definition assigned to this handler. @@ -907,8 +952,13 @@ public static partial class OpenIddictServerHandlers .SetType(OpenIddictServerHandlerType.BuiltIn) .Build(); - public async ValueTask HandleAsync(ValidateTokenContext context!!) + public async ValueTask HandleAsync(ValidateTokenContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.Principal is { Identity: ClaimsIdentity }, SR.GetResourceString(SR.ID4006)); var identifier = context.Principal.GetAuthorizationId(); @@ -962,8 +1012,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(GenerateTokenContext context!!) + public ValueTask HandleAsync(GenerateTokenContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + context.SecurityTokenHandler = context.Options.JsonWebTokenHandler; context.EncryptionCredentials = context.TokenType switch @@ -1004,8 +1059,8 @@ public static partial class OpenIddictServerHandlers IOpenIddictApplicationManager applicationManager, IOpenIddictTokenManager tokenManager) { - _applicationManager = applicationManager; - _tokenManager = tokenManager; + _applicationManager = applicationManager ?? throw new ArgumentNullException(nameof(applicationManager)); + _tokenManager = tokenManager ?? throw new ArgumentNullException(nameof(tokenManager)); } /// @@ -1022,8 +1077,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(GenerateTokenContext context!!) + public async ValueTask HandleAsync(GenerateTokenContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var descriptor = new OpenIddictTokenDescriptor { AuthorizationId = context.Principal.GetAuthorizationId(), @@ -1091,8 +1151,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(GenerateTokenContext context!!) + public ValueTask HandleAsync(GenerateTokenContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // If a token was already attached by another handler, don't overwrite it. if (!string.IsNullOrEmpty(context.Token)) { @@ -1203,8 +1268,8 @@ public static partial class OpenIddictServerHandlers public ConvertReferenceToken() => throw new InvalidOperationException(SR.GetResourceString(SR.ID0016)); - public ConvertReferenceToken(IOpenIddictTokenManager tokenManager!!) - => _tokenManager = tokenManager; + public ConvertReferenceToken(IOpenIddictTokenManager tokenManager) + => _tokenManager = tokenManager ?? throw new ArgumentNullException(nameof(tokenManager)); /// /// Gets the default descriptor definition assigned to this handler. @@ -1220,8 +1285,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(GenerateTokenContext context!!) + public async ValueTask HandleAsync(GenerateTokenContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var identifier = context.Principal.GetTokenId(); if (string.IsNullOrEmpty(identifier)) { @@ -1313,8 +1383,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(GenerateTokenContext context!!) + public ValueTask HandleAsync(GenerateTokenContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // To make user codes easier to read and type by humans, a dash is automatically // appended before each new block of 4 integers. These dashes are expected to be // stripped from the user codes when receiving them at the verification endpoint. diff --git a/src/OpenIddict.Server/OpenIddictServerHandlers.Revocation.cs b/src/OpenIddict.Server/OpenIddictServerHandlers.Revocation.cs index 9c3962a7..4bd81442 100644 --- a/src/OpenIddict.Server/OpenIddictServerHandlers.Revocation.cs +++ b/src/OpenIddict.Server/OpenIddictServerHandlers.Revocation.cs @@ -56,8 +56,8 @@ public static partial class OpenIddictServerHandlers { private readonly IOpenIddictServerDispatcher _dispatcher; - public ExtractRevocationRequest(IOpenIddictServerDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public ExtractRevocationRequest(IOpenIddictServerDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -71,8 +71,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessRequestContext context!!) + public async ValueTask HandleAsync(ProcessRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var notification = new ExtractRevocationRequestContext(context.Transaction); await _dispatcher.DispatchAsync(notification); @@ -113,8 +118,8 @@ public static partial class OpenIddictServerHandlers { private readonly IOpenIddictServerDispatcher _dispatcher; - public ValidateRevocationRequest(IOpenIddictServerDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public ValidateRevocationRequest(IOpenIddictServerDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -128,8 +133,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessRequestContext context!!) + public async ValueTask HandleAsync(ProcessRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var notification = new ValidateRevocationRequestContext(context.Transaction); await _dispatcher.DispatchAsync(notification); @@ -169,8 +179,8 @@ public static partial class OpenIddictServerHandlers { private readonly IOpenIddictServerDispatcher _dispatcher; - public HandleRevocationRequest(IOpenIddictServerDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public HandleRevocationRequest(IOpenIddictServerDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -184,8 +194,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessRequestContext context!!) + public async ValueTask HandleAsync(ProcessRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var notification = new HandleRevocationRequestContext(context.Transaction); await _dispatcher.DispatchAsync(notification); @@ -221,8 +236,8 @@ public static partial class OpenIddictServerHandlers { private readonly IOpenIddictServerDispatcher _dispatcher; - public ApplyRevocationResponse(IOpenIddictServerDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public ApplyRevocationResponse(IOpenIddictServerDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -236,8 +251,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(TContext context!!) + public async ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var notification = new ApplyRevocationResponseContext(context.Transaction); await _dispatcher.DispatchAsync(notification); @@ -273,8 +293,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ValidateRevocationRequestContext context!!) + public ValueTask HandleAsync(ValidateRevocationRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // Reject revocation requests missing the mandatory token parameter. if (string.IsNullOrEmpty(context.Request.Token)) { @@ -308,8 +333,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ValidateRevocationRequestContext context!!) + public ValueTask HandleAsync(ValidateRevocationRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // At this stage, reject the revocation request unless the client identification requirement was disabled. if (!context.Options.AcceptAnonymousClients && string.IsNullOrEmpty(context.ClientId)) { @@ -337,8 +367,8 @@ public static partial class OpenIddictServerHandlers public ValidateClientId() => throw new InvalidOperationException(SR.GetResourceString(SR.ID0016)); - public ValidateClientId(IOpenIddictApplicationManager applicationManager!!) - => _applicationManager = applicationManager; + public ValidateClientId(IOpenIddictApplicationManager applicationManager) + => _applicationManager = applicationManager ?? throw new ArgumentNullException(nameof(applicationManager)); /// /// Gets the default descriptor definition assigned to this handler. @@ -353,8 +383,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ValidateRevocationRequestContext context!!) + public async ValueTask HandleAsync(ValidateRevocationRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(!string.IsNullOrEmpty(context.ClientId), SR.FormatID4000(Parameters.ClientId)); // Retrieve the application details corresponding to the requested client_id. @@ -385,8 +420,8 @@ public static partial class OpenIddictServerHandlers public ValidateClientType() => throw new InvalidOperationException(SR.GetResourceString(SR.ID0016)); - public ValidateClientType(IOpenIddictApplicationManager applicationManager!!) - => _applicationManager = applicationManager; + public ValidateClientType(IOpenIddictApplicationManager applicationManager) + => _applicationManager = applicationManager ?? throw new ArgumentNullException(nameof(applicationManager)); /// /// Gets the default descriptor definition assigned to this handler. @@ -401,8 +436,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ValidateRevocationRequestContext context!!) + public async ValueTask HandleAsync(ValidateRevocationRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(!string.IsNullOrEmpty(context.ClientId), SR.FormatID4000(Parameters.ClientId)); var application = await _applicationManager.FindByClientIdAsync(context.ClientId) ?? @@ -451,8 +491,8 @@ public static partial class OpenIddictServerHandlers public ValidateClientSecret() => throw new InvalidOperationException(SR.GetResourceString(SR.ID0016)); - public ValidateClientSecret(IOpenIddictApplicationManager applicationManager!!) - => _applicationManager = applicationManager; + public ValidateClientSecret(IOpenIddictApplicationManager applicationManager) + => _applicationManager = applicationManager ?? throw new ArgumentNullException(nameof(applicationManager)); /// /// Gets the default descriptor definition assigned to this handler. @@ -467,8 +507,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ValidateRevocationRequestContext context!!) + public async ValueTask HandleAsync(ValidateRevocationRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(!string.IsNullOrEmpty(context.ClientId), SR.FormatID4000(Parameters.ClientId)); var application = await _applicationManager.FindByClientIdAsync(context.ClientId) ?? @@ -507,8 +552,8 @@ public static partial class OpenIddictServerHandlers public ValidateEndpointPermissions() => throw new InvalidOperationException(SR.GetResourceString(SR.ID0016)); - public ValidateEndpointPermissions(IOpenIddictApplicationManager applicationManager!!) - => _applicationManager = applicationManager; + public ValidateEndpointPermissions(IOpenIddictApplicationManager applicationManager) + => _applicationManager = applicationManager ?? throw new ArgumentNullException(nameof(applicationManager)); /// /// Gets the default descriptor definition assigned to this handler. @@ -524,8 +569,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ValidateRevocationRequestContext context!!) + public async ValueTask HandleAsync(ValidateRevocationRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(!string.IsNullOrEmpty(context.ClientId), SR.FormatID4000(Parameters.ClientId)); var application = await _applicationManager.FindByClientIdAsync(context.ClientId) ?? @@ -553,8 +603,8 @@ public static partial class OpenIddictServerHandlers { private readonly IOpenIddictServerDispatcher _dispatcher; - public ValidateToken(IOpenIddictServerDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public ValidateToken(IOpenIddictServerDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -567,8 +617,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ValidateRevocationRequestContext context!!) + public async ValueTask HandleAsync(ValidateRevocationRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var notification = new ProcessAuthenticationContext(context.Transaction); await _dispatcher.DispatchAsync(notification); @@ -618,8 +673,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ValidateRevocationRequestContext context!!) + public ValueTask HandleAsync(ValidateRevocationRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.Principal is { Identity: ClaimsIdentity }, SR.GetResourceString(SR.ID4006)); if (!context.Principal.HasTokenType(TokenTypeHints.AccessToken) && @@ -660,8 +720,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ValidateRevocationRequestContext context!!) + public ValueTask HandleAsync(ValidateRevocationRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(!string.IsNullOrEmpty(context.ClientId), SR.FormatID4000(Parameters.ClientId)); Debug.Assert(context.Principal is { Identity: ClaimsIdentity }, SR.GetResourceString(SR.ID4006)); @@ -721,8 +786,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(HandleRevocationRequestContext context!!) + public ValueTask HandleAsync(HandleRevocationRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var notification = context.Transaction.GetProperty( typeof(ValidateRevocationRequestContext).FullName!) ?? throw new InvalidOperationException(SR.GetResourceString(SR.ID0007)); @@ -745,8 +815,8 @@ public static partial class OpenIddictServerHandlers public RevokeToken() => throw new InvalidOperationException(SR.GetResourceString(SR.ID0016)); - public RevokeToken(IOpenIddictTokenManager tokenManager!!) - => _tokenManager = tokenManager; + public RevokeToken(IOpenIddictTokenManager tokenManager) + => _tokenManager = tokenManager ?? throw new ArgumentNullException(nameof(tokenManager)); /// /// Gets the default descriptor definition assigned to this handler. @@ -760,8 +830,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(HandleRevocationRequestContext context!!) + public async ValueTask HandleAsync(HandleRevocationRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.Principal is { Identity: ClaimsIdentity }, SR.GetResourceString(SR.ID4006)); // Extract the token identifier from the authentication principal. @@ -820,8 +895,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ApplyRevocationResponseContext context!!) + public ValueTask HandleAsync(ApplyRevocationResponseContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + if (string.IsNullOrEmpty(context.Error)) { return default; diff --git a/src/OpenIddict.Server/OpenIddictServerHandlers.Session.cs b/src/OpenIddict.Server/OpenIddictServerHandlers.Session.cs index c7294e7c..b028d00c 100644 --- a/src/OpenIddict.Server/OpenIddictServerHandlers.Session.cs +++ b/src/OpenIddict.Server/OpenIddictServerHandlers.Session.cs @@ -44,8 +44,8 @@ public static partial class OpenIddictServerHandlers { private readonly IOpenIddictServerDispatcher _dispatcher; - public ExtractLogoutRequest(IOpenIddictServerDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public ExtractLogoutRequest(IOpenIddictServerDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -59,8 +59,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessRequestContext context!!) + public async ValueTask HandleAsync(ProcessRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var notification = new ExtractLogoutRequestContext(context.Transaction); await _dispatcher.DispatchAsync(notification); @@ -101,8 +106,8 @@ public static partial class OpenIddictServerHandlers { private readonly IOpenIddictServerDispatcher _dispatcher; - public ValidateLogoutRequest(IOpenIddictServerDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public ValidateLogoutRequest(IOpenIddictServerDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -116,8 +121,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessRequestContext context!!) + public async ValueTask HandleAsync(ProcessRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var notification = new ValidateLogoutRequestContext(context.Transaction); await _dispatcher.DispatchAsync(notification); @@ -157,8 +167,8 @@ public static partial class OpenIddictServerHandlers { private readonly IOpenIddictServerDispatcher _dispatcher; - public HandleLogoutRequest(IOpenIddictServerDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public HandleLogoutRequest(IOpenIddictServerDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -172,8 +182,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessRequestContext context!!) + public async ValueTask HandleAsync(ProcessRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var notification = new HandleLogoutRequestContext(context.Transaction); await _dispatcher.DispatchAsync(notification); @@ -248,8 +263,8 @@ public static partial class OpenIddictServerHandlers { private readonly IOpenIddictServerDispatcher _dispatcher; - public ApplyLogoutResponse(IOpenIddictServerDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public ApplyLogoutResponse(IOpenIddictServerDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -263,8 +278,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(TContext context!!) + public async ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var notification = new ApplyLogoutResponseContext(context.Transaction); await _dispatcher.DispatchAsync(notification); @@ -300,8 +320,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ValidateLogoutRequestContext context!!) + public ValueTask HandleAsync(ValidateLogoutRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + if (string.IsNullOrEmpty(context.PostLogoutRedirectUri)) { return default; @@ -346,8 +371,8 @@ public static partial class OpenIddictServerHandlers public ValidateClientPostLogoutRedirectUri() => throw new InvalidOperationException(SR.GetResourceString(SR.ID0016)); - public ValidateClientPostLogoutRedirectUri(IOpenIddictApplicationManager applicationManager!!) - => _applicationManager = applicationManager; + public ValidateClientPostLogoutRedirectUri(IOpenIddictApplicationManager applicationManager) + => _applicationManager = applicationManager ?? throw new ArgumentNullException(nameof(applicationManager)); /// /// Gets the default descriptor definition assigned to this handler. @@ -362,8 +387,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ValidateLogoutRequestContext context!!) + public async ValueTask HandleAsync(ValidateLogoutRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(!string.IsNullOrEmpty(context.PostLogoutRedirectUri), SR.FormatID4000(Parameters.PostLogoutRedirectUri)); if (!await ValidatePostLogoutRedirectUriAsync(context.PostLogoutRedirectUri)) @@ -414,8 +444,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ApplyLogoutResponseContext context!!) + public ValueTask HandleAsync(ApplyLogoutResponseContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + if (context.Request is null) { return default; @@ -451,8 +486,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ApplyLogoutResponseContext context!!) + public ValueTask HandleAsync(ApplyLogoutResponseContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // Attach the request state to the logout response. if (string.IsNullOrEmpty(context.Response.State)) { diff --git a/src/OpenIddict.Server/OpenIddictServerHandlers.Userinfo.cs b/src/OpenIddict.Server/OpenIddictServerHandlers.Userinfo.cs index 184e22e8..dd2b9d93 100644 --- a/src/OpenIddict.Server/OpenIddictServerHandlers.Userinfo.cs +++ b/src/OpenIddict.Server/OpenIddictServerHandlers.Userinfo.cs @@ -46,8 +46,8 @@ public static partial class OpenIddictServerHandlers { private readonly IOpenIddictServerDispatcher _dispatcher; - public ExtractUserinfoRequest(IOpenIddictServerDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public ExtractUserinfoRequest(IOpenIddictServerDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -61,8 +61,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessRequestContext context!!) + public async ValueTask HandleAsync(ProcessRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var notification = new ExtractUserinfoRequestContext(context.Transaction); await _dispatcher.DispatchAsync(notification); @@ -103,8 +108,8 @@ public static partial class OpenIddictServerHandlers { private readonly IOpenIddictServerDispatcher _dispatcher; - public ValidateUserinfoRequest(IOpenIddictServerDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public ValidateUserinfoRequest(IOpenIddictServerDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -118,8 +123,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessRequestContext context!!) + public async ValueTask HandleAsync(ProcessRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var notification = new ValidateUserinfoRequestContext(context.Transaction); await _dispatcher.DispatchAsync(notification); @@ -159,8 +169,8 @@ public static partial class OpenIddictServerHandlers { private readonly IOpenIddictServerDispatcher _dispatcher; - public HandleUserinfoRequest(IOpenIddictServerDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public HandleUserinfoRequest(IOpenIddictServerDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -174,8 +184,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessRequestContext context!!) + public async ValueTask HandleAsync(ProcessRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var notification = new HandleUserinfoRequestContext(context.Transaction); await _dispatcher.DispatchAsync(notification); @@ -246,8 +261,8 @@ public static partial class OpenIddictServerHandlers { private readonly IOpenIddictServerDispatcher _dispatcher; - public ApplyUserinfoResponse(IOpenIddictServerDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public ApplyUserinfoResponse(IOpenIddictServerDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -261,8 +276,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(TContext context!!) + public async ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var notification = new ApplyUserinfoResponseContext(context.Transaction); await _dispatcher.DispatchAsync(notification); @@ -298,8 +318,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ValidateUserinfoRequestContext context!!) + public ValueTask HandleAsync(ValidateUserinfoRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + if (string.IsNullOrEmpty(context.Request.AccessToken)) { context.Logger.LogInformation(SR.GetResourceString(SR.ID6131), Parameters.AccessToken); @@ -323,8 +348,8 @@ public static partial class OpenIddictServerHandlers { private readonly IOpenIddictServerDispatcher _dispatcher; - public ValidateToken(IOpenIddictServerDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public ValidateToken(IOpenIddictServerDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -337,8 +362,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ValidateUserinfoRequestContext context!!) + public async ValueTask HandleAsync(ValidateUserinfoRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var notification = new ProcessAuthenticationContext(context.Transaction); await _dispatcher.DispatchAsync(notification); @@ -389,8 +419,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(HandleUserinfoRequestContext context!!) + public ValueTask HandleAsync(HandleUserinfoRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var notification = context.Transaction.GetProperty( typeof(ValidateUserinfoRequestContext).FullName!) ?? throw new InvalidOperationException(SR.GetResourceString(SR.ID0007)); @@ -419,8 +454,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(HandleUserinfoRequestContext context!!) + public ValueTask HandleAsync(HandleUserinfoRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.Principal is { Identity: ClaimsIdentity }, SR.GetResourceString(SR.ID4006)); // Note: when receiving an access token, its audiences list cannot be used for the "aud" claim @@ -448,8 +488,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(HandleUserinfoRequestContext context!!) + public ValueTask HandleAsync(HandleUserinfoRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.Principal is { Identity: ClaimsIdentity }, SR.GetResourceString(SR.ID4006)); context.Subject = context.Principal.GetClaim(Claims.Subject); diff --git a/src/OpenIddict.Server/OpenIddictServerHandlers.cs b/src/OpenIddict.Server/OpenIddictServerHandlers.cs index 1e2cbb5a..a5b76179 100644 --- a/src/OpenIddict.Server/OpenIddictServerHandlers.cs +++ b/src/OpenIddict.Server/OpenIddictServerHandlers.cs @@ -114,8 +114,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ProcessAuthenticationContext context!!) + public ValueTask HandleAsync(ProcessAuthenticationContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + switch (context.EndpointType) { case OpenIddictServerEndpointType.Authorization: @@ -153,8 +158,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ProcessAuthenticationContext context!!) + public ValueTask HandleAsync(ProcessAuthenticationContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + (context.ExtractAccessToken, context.RequireAccessToken, context.ValidateAccessToken) = context.EndpointType switch @@ -248,8 +258,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ProcessAuthenticationContext context!!) + public ValueTask HandleAsync(ProcessAuthenticationContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + context.AccessToken = context.EndpointType switch { OpenIddictServerEndpointType.Userinfo when context.ExtractAccessToken @@ -328,8 +343,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ProcessAuthenticationContext context!!) + public ValueTask HandleAsync(ProcessAuthenticationContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + if ((context.RequireAccessToken && string.IsNullOrEmpty(context.AccessToken)) || (context.RequireAuthorizationCode && string.IsNullOrEmpty(context.AuthorizationCode)) || (context.RequireDeviceCode && string.IsNullOrEmpty(context.DeviceCode)) || @@ -357,8 +377,8 @@ public static partial class OpenIddictServerHandlers { private readonly IOpenIddictServerDispatcher _dispatcher; - public ValidateAccessToken(IOpenIddictServerDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public ValidateAccessToken(IOpenIddictServerDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -372,8 +392,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessAuthenticationContext context!!) + public async ValueTask HandleAsync(ProcessAuthenticationContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + if (context.AccessTokenPrincipal is not null || string.IsNullOrEmpty(context.AccessToken)) { return; @@ -419,8 +444,8 @@ public static partial class OpenIddictServerHandlers { private readonly IOpenIddictServerDispatcher _dispatcher; - public ValidateAuthorizationCode(IOpenIddictServerDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public ValidateAuthorizationCode(IOpenIddictServerDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -434,8 +459,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessAuthenticationContext context!!) + public async ValueTask HandleAsync(ProcessAuthenticationContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + if (context.AuthorizationCodePrincipal is not null || string.IsNullOrEmpty(context.AuthorizationCode)) { return; @@ -481,8 +511,8 @@ public static partial class OpenIddictServerHandlers { private readonly IOpenIddictServerDispatcher _dispatcher; - public ValidateDeviceCode(IOpenIddictServerDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public ValidateDeviceCode(IOpenIddictServerDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -496,8 +526,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessAuthenticationContext context!!) + public async ValueTask HandleAsync(ProcessAuthenticationContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + if (context.DeviceCodePrincipal is not null || string.IsNullOrEmpty(context.DeviceCode)) { return; @@ -543,8 +578,8 @@ public static partial class OpenIddictServerHandlers { private readonly IOpenIddictServerDispatcher _dispatcher; - public ValidateGenericToken(IOpenIddictServerDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public ValidateGenericToken(IOpenIddictServerDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -558,8 +593,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessAuthenticationContext context!!) + public async ValueTask HandleAsync(ProcessAuthenticationContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + if (context.GenericTokenPrincipal is not null || string.IsNullOrEmpty(context.GenericToken)) { return; @@ -612,8 +652,8 @@ public static partial class OpenIddictServerHandlers { private readonly IOpenIddictServerDispatcher _dispatcher; - public ValidateIdentityToken(IOpenIddictServerDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public ValidateIdentityToken(IOpenIddictServerDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -627,8 +667,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessAuthenticationContext context!!) + public async ValueTask HandleAsync(ProcessAuthenticationContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + if (context.IdentityTokenPrincipal is not null || string.IsNullOrEmpty(context.IdentityToken)) { return; @@ -677,8 +722,8 @@ public static partial class OpenIddictServerHandlers { private readonly IOpenIddictServerDispatcher _dispatcher; - public ValidateRefreshToken(IOpenIddictServerDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public ValidateRefreshToken(IOpenIddictServerDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -692,8 +737,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessAuthenticationContext context!!) + public async ValueTask HandleAsync(ProcessAuthenticationContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + if (context.RefreshTokenPrincipal is not null || string.IsNullOrEmpty(context.RefreshToken)) { return; @@ -739,8 +789,8 @@ public static partial class OpenIddictServerHandlers { private readonly IOpenIddictServerDispatcher _dispatcher; - public ValidateUserCode(IOpenIddictServerDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public ValidateUserCode(IOpenIddictServerDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -754,8 +804,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessAuthenticationContext context!!) + public async ValueTask HandleAsync(ProcessAuthenticationContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + if (context.UserCodePrincipal is not null || string.IsNullOrEmpty(context.UserCode)) { return; @@ -810,8 +865,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ProcessChallengeContext context!!) + public ValueTask HandleAsync(ProcessChallengeContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + if (context.EndpointType is not (OpenIddictServerEndpointType.Authorization or OpenIddictServerEndpointType.Token or OpenIddictServerEndpointType.Userinfo or @@ -840,8 +900,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ProcessChallengeContext context!!) + public ValueTask HandleAsync(ProcessChallengeContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + if (!context.Parameters.ContainsKey(Parameters.Error)) { context.Parameters[Parameters.Error] = context.EndpointType switch @@ -898,8 +963,8 @@ public static partial class OpenIddictServerHandlers public RejectDeviceCodeEntry() => throw new InvalidOperationException(SR.GetResourceString(SR.ID0016)); - public RejectDeviceCodeEntry(IOpenIddictTokenManager tokenManager!!) - => _tokenManager = tokenManager; + public RejectDeviceCodeEntry(IOpenIddictTokenManager tokenManager) + => _tokenManager = tokenManager ?? throw new ArgumentNullException(nameof(tokenManager)); /// /// Gets the default descriptor definition assigned to this handler. @@ -914,9 +979,14 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessChallengeContext context!!) + public async ValueTask HandleAsync(ProcessChallengeContext context) { - if (context.EndpointType != OpenIddictServerEndpointType.Verification) + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + if (context.EndpointType is not OpenIddictServerEndpointType.Verification) { return; } @@ -952,8 +1022,8 @@ public static partial class OpenIddictServerHandlers public RejectUserCodeEntry() => throw new InvalidOperationException(SR.GetResourceString(SR.ID0016)); - public RejectUserCodeEntry(IOpenIddictTokenManager tokenManager!!) - => _tokenManager = tokenManager; + public RejectUserCodeEntry(IOpenIddictTokenManager tokenManager) + => _tokenManager = tokenManager ?? throw new ArgumentNullException(nameof(tokenManager)); /// /// Gets the default descriptor definition assigned to this handler. @@ -968,9 +1038,14 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessChallengeContext context!!) + public async ValueTask HandleAsync(ProcessChallengeContext context) { - if (context.EndpointType != OpenIddictServerEndpointType.Verification) + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + if (context.EndpointType is not OpenIddictServerEndpointType.Verification) { return; } @@ -1012,8 +1087,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ProcessChallengeContext context!!) + public ValueTask HandleAsync(ProcessChallengeContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + if (context.Parameters.Count > 0) { foreach (var parameter in context.Parameters) @@ -1043,8 +1123,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ProcessSignInContext context!!) + public ValueTask HandleAsync(ProcessSignInContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + if (context.EndpointType is not (OpenIddictServerEndpointType.Authorization or OpenIddictServerEndpointType.Device or OpenIddictServerEndpointType.Token or @@ -1107,8 +1192,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ProcessSignInContext context!!) + public ValueTask HandleAsync(ProcessSignInContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.Principal is { Identity: ClaimsIdentity }, SR.GetResourceString(SR.ID4006)); switch (context.EndpointType) @@ -1190,8 +1280,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ProcessSignInContext context!!) + public ValueTask HandleAsync(ProcessSignInContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.Principal is { Identity: ClaimsIdentity }, SR.GetResourceString(SR.ID4006)); // Always include the "openid" scope when the developer doesn't explicitly call SetScopes. @@ -1222,8 +1317,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ProcessSignInContext context!!) + public ValueTask HandleAsync(ProcessSignInContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.Principal is { Identity: ClaimsIdentity }, SR.GetResourceString(SR.ID4006)); // Add the validated client_id to the list of authorized presenters, @@ -1253,8 +1353,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ProcessSignInContext context!!) + public ValueTask HandleAsync(ProcessSignInContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.Principal is { Identity: ClaimsIdentity }, SR.GetResourceString(SR.ID4006)); // When a "resources" property cannot be found in the ticket, infer it from the "audiences" property. @@ -1288,8 +1393,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ProcessSignInContext context!!) + public ValueTask HandleAsync(ProcessSignInContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.Principal is { Identity: ClaimsIdentity }, SR.GetResourceString(SR.ID4006)); (context.GenerateAccessToken, context.IncludeAccessToken) = context.EndpointType switch @@ -1377,11 +1487,11 @@ public static partial class OpenIddictServerHandlers public AttachAuthorization() => throw new InvalidOperationException(SR.GetResourceString(SR.ID0016)); public AttachAuthorization( - IOpenIddictApplicationManager applicationManager!!, - IOpenIddictAuthorizationManager authorizationManager!!) + IOpenIddictApplicationManager applicationManager, + IOpenIddictAuthorizationManager authorizationManager) { - _applicationManager = applicationManager; - _authorizationManager = authorizationManager; + _applicationManager = applicationManager ?? throw new ArgumentNullException(nameof(applicationManager)); + _authorizationManager = authorizationManager ?? throw new ArgumentNullException(nameof(authorizationManager)); } /// @@ -1397,8 +1507,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessSignInContext context!!) + public async ValueTask HandleAsync(ProcessSignInContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.Principal is { Identity: ClaimsIdentity }, SR.GetResourceString(SR.ID4006)); // If no authorization code, device code or refresh token is returned, don't create an authorization. @@ -1472,8 +1587,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ProcessSignInContext context!!) + public ValueTask HandleAsync(ProcessSignInContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.Principal is { Identity: ClaimsIdentity }, SR.GetResourceString(SR.ID4006)); // Create a new principal containing only the filtered claims. @@ -1585,8 +1705,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ProcessSignInContext context!!) + public ValueTask HandleAsync(ProcessSignInContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.Principal is { Identity: ClaimsIdentity }, SR.GetResourceString(SR.ID4006)); // Create a new principal containing only the filtered claims. @@ -1666,8 +1791,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ProcessSignInContext context!!) + public ValueTask HandleAsync(ProcessSignInContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.Principal is { Identity: ClaimsIdentity }, SR.GetResourceString(SR.ID4006)); // Create a new principal containing only the filtered claims. @@ -1734,8 +1864,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ProcessSignInContext context!!) + public ValueTask HandleAsync(ProcessSignInContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.Principal is { Identity: ClaimsIdentity }, SR.GetResourceString(SR.ID4006)); // Create a new principal containing only the filtered claims. @@ -1813,8 +1948,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ProcessSignInContext context!!) + public ValueTask HandleAsync(ProcessSignInContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.Principal is { Identity: ClaimsIdentity }, SR.GetResourceString(SR.ID4006)); // Replace the principal by a new one containing only the filtered claims. @@ -1921,8 +2061,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ProcessSignInContext context!!) + public ValueTask HandleAsync(ProcessSignInContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.Principal is { Identity: ClaimsIdentity }, SR.GetResourceString(SR.ID4006)); // Create a new principal containing only the filtered claims. @@ -1978,8 +2123,8 @@ public static partial class OpenIddictServerHandlers public RedeemTokenEntry() => throw new InvalidOperationException(SR.GetResourceString(SR.ID0016)); - public RedeemTokenEntry(IOpenIddictTokenManager tokenManager!!) - => _tokenManager = tokenManager; + public RedeemTokenEntry(IOpenIddictTokenManager tokenManager) + => _tokenManager = tokenManager ?? throw new ArgumentNullException(nameof(tokenManager)); /// /// Gets the default descriptor definition assigned to this handler. @@ -1994,8 +2139,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessSignInContext context!!) + public async ValueTask HandleAsync(ProcessSignInContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + switch (context.EndpointType) { case OpenIddictServerEndpointType.Token when context.Request.IsAuthorizationCodeGrantType(): @@ -2035,8 +2185,8 @@ public static partial class OpenIddictServerHandlers { private readonly IOpenIddictServerDispatcher _dispatcher; - public GenerateAccessToken(IOpenIddictServerDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public GenerateAccessToken(IOpenIddictServerDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -2050,8 +2200,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessSignInContext context!!) + public async ValueTask HandleAsync(ProcessSignInContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var notification = new GenerateTokenContext(context.Transaction) { ClientId = context.ClientId, @@ -2097,8 +2252,8 @@ public static partial class OpenIddictServerHandlers { private readonly IOpenIddictServerDispatcher _dispatcher; - public GenerateAuthorizationCode(IOpenIddictServerDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public GenerateAuthorizationCode(IOpenIddictServerDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -2112,8 +2267,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessSignInContext context!!) + public async ValueTask HandleAsync(ProcessSignInContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var notification = new GenerateTokenContext(context.Transaction) { ClientId = context.ClientId, @@ -2157,8 +2317,8 @@ public static partial class OpenIddictServerHandlers { private readonly IOpenIddictServerDispatcher _dispatcher; - public GenerateDeviceCode(IOpenIddictServerDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public GenerateDeviceCode(IOpenIddictServerDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -2172,8 +2332,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessSignInContext context!!) + public async ValueTask HandleAsync(ProcessSignInContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var notification = new GenerateTokenContext(context.Transaction) { ClientId = context.ClientId, @@ -2224,8 +2389,8 @@ public static partial class OpenIddictServerHandlers { private readonly IOpenIddictServerDispatcher _dispatcher; - public GenerateRefreshToken(IOpenIddictServerDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public GenerateRefreshToken(IOpenIddictServerDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -2239,8 +2404,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessSignInContext context!!) + public async ValueTask HandleAsync(ProcessSignInContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var notification = new GenerateTokenContext(context.Transaction) { ClientId = context.ClientId, @@ -2297,8 +2467,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ProcessSignInContext context!!) + public ValueTask HandleAsync(ProcessSignInContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + if (context.UserCodePrincipal is null) { throw new InvalidOperationException(SR.GetResourceString(SR.ID0020)); @@ -2324,8 +2499,8 @@ public static partial class OpenIddictServerHandlers public UpdateReferenceDeviceCodeEntry() => throw new InvalidOperationException(SR.GetResourceString(SR.ID0016)); - public UpdateReferenceDeviceCodeEntry(IOpenIddictTokenManager tokenManager!!) - => _tokenManager = tokenManager; + public UpdateReferenceDeviceCodeEntry(IOpenIddictTokenManager tokenManager) + => _tokenManager = tokenManager ?? throw new ArgumentNullException(nameof(tokenManager)); /// /// Gets the default descriptor definition assigned to this handler. @@ -2341,9 +2516,14 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessSignInContext context!!) + public async ValueTask HandleAsync(ProcessSignInContext context) { - if (context.EndpointType != OpenIddictServerEndpointType.Verification || string.IsNullOrEmpty(context.DeviceCode)) + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + if (context.EndpointType is not OpenIddictServerEndpointType.Verification || string.IsNullOrEmpty(context.DeviceCode)) { return; } @@ -2401,8 +2581,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ProcessSignInContext context!!) + public ValueTask HandleAsync(ProcessSignInContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + if (context.IdentityTokenPrincipal is null) { throw new InvalidOperationException(SR.GetResourceString(SR.ID0022)); @@ -2510,8 +2695,8 @@ public static partial class OpenIddictServerHandlers { private readonly IOpenIddictServerDispatcher _dispatcher; - public GenerateUserCode(IOpenIddictServerDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public GenerateUserCode(IOpenIddictServerDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -2525,8 +2710,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessSignInContext context!!) + public async ValueTask HandleAsync(ProcessSignInContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var notification = new GenerateTokenContext(context.Transaction) { ClientId = context.ClientId, @@ -2570,8 +2760,8 @@ public static partial class OpenIddictServerHandlers { private readonly IOpenIddictServerDispatcher _dispatcher; - public GenerateIdentityToken(IOpenIddictServerDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public GenerateIdentityToken(IOpenIddictServerDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -2585,8 +2775,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessSignInContext context!!) + public async ValueTask HandleAsync(ProcessSignInContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var notification = new GenerateTokenContext(context.Transaction) { ClientId = context.ClientId, @@ -2640,8 +2835,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ProcessSignInContext context!!) + public ValueTask HandleAsync(ProcessSignInContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + if (context.IncludeAccessToken) { context.Response.AccessToken = context.AccessToken; @@ -2782,9 +2982,14 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ProcessSignOutContext context!!) + public ValueTask HandleAsync(ProcessSignOutContext context) { - if (context.EndpointType != OpenIddictServerEndpointType.Logout) + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + if (context.EndpointType is not OpenIddictServerEndpointType.Logout) { throw new InvalidOperationException(SR.GetResourceString(SR.ID0024)); } @@ -2809,8 +3014,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ProcessSignOutContext context!!) + public ValueTask HandleAsync(ProcessSignOutContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + if (context.Parameters.Count > 0) { foreach (var parameter in context.Parameters) @@ -2839,8 +3049,13 @@ public static partial class OpenIddictServerHandlers .Build(); /// - public ValueTask HandleAsync(ProcessErrorContext context!!) + public ValueTask HandleAsync(ProcessErrorContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + context.Response.Error = context.Error; context.Response.ErrorDescription = context.ErrorDescription; context.Response.ErrorUri = context.ErrorUri; diff --git a/src/OpenIddict.Server/OpenIddictServerHelpers.cs b/src/OpenIddict.Server/OpenIddictServerHelpers.cs index 55f38bff..7c693a66 100644 --- a/src/OpenIddict.Server/OpenIddictServerHelpers.cs +++ b/src/OpenIddict.Server/OpenIddictServerHelpers.cs @@ -19,8 +19,13 @@ public static class OpenIddictServerHelpers /// The property name. /// The property value or if it couldn't be found. public static TProperty? GetProperty( - this OpenIddictServerTransaction transaction!!, string name) where TProperty : class + this OpenIddictServerTransaction transaction, string name) where TProperty : class { + if (transaction is null) + { + throw new ArgumentNullException(nameof(transaction)); + } + if (string.IsNullOrEmpty(name)) { throw new ArgumentException(SR.GetResourceString(SR.ID0106), nameof(name)); @@ -43,9 +48,14 @@ public static class OpenIddictServerHelpers /// The property value. /// The server transaction, so that calls can be easily chained. public static OpenIddictServerTransaction SetProperty( - this OpenIddictServerTransaction transaction!!, + this OpenIddictServerTransaction transaction, string name, TProperty? value) where TProperty : class { + if (transaction is null) + { + throw new ArgumentNullException(nameof(transaction)); + } + if (string.IsNullOrEmpty(name)) { throw new ArgumentException(SR.GetResourceString(SR.ID0106), nameof(name)); diff --git a/src/OpenIddict.Server/OpenIddictServerOptions.cs b/src/OpenIddict.Server/OpenIddictServerOptions.cs index 3ba95a07..b93f1385 100644 --- a/src/OpenIddict.Server/OpenIddictServerOptions.cs +++ b/src/OpenIddict.Server/OpenIddictServerOptions.cs @@ -240,7 +240,7 @@ public class OpenIddictServerOptions /// Note: the list is automatically sorted based on the order assigned to each handler descriptor. /// As such, it MUST NOT be mutated after options initialization to preserve the exact order. /// - public List Handlers { get; } = new(DefaultHandlers); + public List Handlers { get; } = new(OpenIddictServerHandlers.DefaultHandlers); /// /// Gets or sets a boolean determining whether client identification is optional. diff --git a/src/OpenIddict.Validation.AspNetCore/OpenIddictValidationAspNetCoreBuilder.cs b/src/OpenIddict.Validation.AspNetCore/OpenIddictValidationAspNetCoreBuilder.cs index c10b3023..ee0f1d49 100644 --- a/src/OpenIddict.Validation.AspNetCore/OpenIddictValidationAspNetCoreBuilder.cs +++ b/src/OpenIddict.Validation.AspNetCore/OpenIddictValidationAspNetCoreBuilder.cs @@ -19,8 +19,8 @@ public class OpenIddictValidationAspNetCoreBuilder /// Initializes a new instance of . /// /// The services collection. - public OpenIddictValidationAspNetCoreBuilder(IServiceCollection services!!) - => Services = services; + public OpenIddictValidationAspNetCoreBuilder(IServiceCollection services) + => Services = services ?? throw new ArgumentNullException(nameof(services)); /// /// Gets the services collection. @@ -34,8 +34,13 @@ public class OpenIddictValidationAspNetCoreBuilder /// The delegate used to configure the OpenIddict options. /// This extension can be safely called multiple times. /// The . - public OpenIddictValidationAspNetCoreBuilder Configure(Action configuration!!) + public OpenIddictValidationAspNetCoreBuilder Configure(Action configuration) { + if (configuration is null) + { + throw new ArgumentNullException(nameof(configuration)); + } + Services.Configure(configuration); return this; diff --git a/src/OpenIddict.Validation.AspNetCore/OpenIddictValidationAspNetCoreConfiguration.cs b/src/OpenIddict.Validation.AspNetCore/OpenIddictValidationAspNetCoreConfiguration.cs index 366dba20..404515e5 100644 --- a/src/OpenIddict.Validation.AspNetCore/OpenIddictValidationAspNetCoreConfiguration.cs +++ b/src/OpenIddict.Validation.AspNetCore/OpenIddictValidationAspNetCoreConfiguration.cs @@ -19,8 +19,13 @@ public class OpenIddictValidationAspNetCoreConfiguration : IConfigureOptions /// The options instance to initialize. - public void Configure(AuthenticationOptions options!!) + public void Configure(AuthenticationOptions options) { + if (options is null) + { + throw new ArgumentNullException(nameof(options)); + } + // If a handler was already registered and the type doesn't correspond to the OpenIddict handler, throw an exception. if (options.SchemeMap.TryGetValue(OpenIddictValidationAspNetCoreDefaults.AuthenticationScheme, out var builder) && builder.HandlerType != typeof(OpenIddictValidationAspNetCoreHandler)) @@ -32,8 +37,13 @@ public class OpenIddictValidationAspNetCoreConfiguration : IConfigureOptions /// The name of the options instance to configure, if applicable. /// The options instance to initialize. - public void PostConfigure(string name, AuthenticationOptions options!!) + public void PostConfigure(string name, AuthenticationOptions options) { + if (options is null) + { + throw new ArgumentNullException(nameof(options)); + } + if (!TryValidate(options.SchemeMap, options.DefaultSignInScheme) || !TryValidate(options.SchemeMap, options.DefaultSignOutScheme)) { diff --git a/src/OpenIddict.Validation.AspNetCore/OpenIddictValidationAspNetCoreExtensions.cs b/src/OpenIddict.Validation.AspNetCore/OpenIddictValidationAspNetCoreExtensions.cs index 27d4e335..29a56854 100644 --- a/src/OpenIddict.Validation.AspNetCore/OpenIddictValidationAspNetCoreExtensions.cs +++ b/src/OpenIddict.Validation.AspNetCore/OpenIddictValidationAspNetCoreExtensions.cs @@ -22,8 +22,13 @@ public static class OpenIddictValidationAspNetCoreExtensions /// The services builder used by OpenIddict to register new services. /// This extension can be safely called multiple times. /// The . - public static OpenIddictValidationAspNetCoreBuilder UseAspNetCore(this OpenIddictValidationBuilder builder!!) + public static OpenIddictValidationAspNetCoreBuilder UseAspNetCore(this OpenIddictValidationBuilder builder) { + if (builder is null) + { + throw new ArgumentNullException(nameof(builder)); + } + builder.Services.AddAuthentication(); builder.Services.TryAddScoped(); @@ -56,8 +61,18 @@ public static class OpenIddictValidationAspNetCoreExtensions /// This extension can be safely called multiple times. /// The . public static OpenIddictValidationBuilder UseAspNetCore( - this OpenIddictValidationBuilder builder!!, Action configuration!!) + this OpenIddictValidationBuilder builder, Action configuration) { + if (builder is null) + { + throw new ArgumentNullException(nameof(builder)); + } + + if (configuration is null) + { + throw new ArgumentNullException(nameof(configuration)); + } + configuration(builder.UseAspNetCore()); return builder; diff --git a/src/OpenIddict.Validation.AspNetCore/OpenIddictValidationAspNetCoreHandler.cs b/src/OpenIddict.Validation.AspNetCore/OpenIddictValidationAspNetCoreHandler.cs index 16bbab3a..2287413a 100644 --- a/src/OpenIddict.Validation.AspNetCore/OpenIddictValidationAspNetCoreHandler.cs +++ b/src/OpenIddict.Validation.AspNetCore/OpenIddictValidationAspNetCoreHandler.cs @@ -25,16 +25,16 @@ public class OpenIddictValidationAspNetCoreHandler : AuthenticationHandler class. /// public OpenIddictValidationAspNetCoreHandler( - IOpenIddictValidationDispatcher dispatcher!!, - IOpenIddictValidationFactory factory!!, - IOptionsMonitor options!!, - ILoggerFactory logger!!, - UrlEncoder encoder!!, - ISystemClock clock!!) + IOpenIddictValidationDispatcher dispatcher, + IOpenIddictValidationFactory factory, + IOptionsMonitor options, + ILoggerFactory logger, + UrlEncoder encoder, + ISystemClock clock) : base(options, logger, encoder, clock) { - _dispatcher = dispatcher; - _factory = factory; + _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); + _factory = factory ?? throw new ArgumentNullException(nameof(factory)); } /// diff --git a/src/OpenIddict.Validation.AspNetCore/OpenIddictValidationAspNetCoreHandlerFilters.cs b/src/OpenIddict.Validation.AspNetCore/OpenIddictValidationAspNetCoreHandlerFilters.cs index a761a72b..6cd2a238 100644 --- a/src/OpenIddict.Validation.AspNetCore/OpenIddictValidationAspNetCoreHandlerFilters.cs +++ b/src/OpenIddict.Validation.AspNetCore/OpenIddictValidationAspNetCoreHandlerFilters.cs @@ -20,7 +20,14 @@ public static class OpenIddictValidationAspNetCoreHandlerFilters /// public class RequireHttpRequest : IOpenIddictValidationHandlerFilter { - public ValueTask IsActiveAsync(BaseContext context!!) - => new(context.Transaction.GetHttpRequest() is not null); + public ValueTask IsActiveAsync(BaseContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(context.Transaction.GetHttpRequest() is not null); + } } } diff --git a/src/OpenIddict.Validation.AspNetCore/OpenIddictValidationAspNetCoreHandlers.cs b/src/OpenIddict.Validation.AspNetCore/OpenIddictValidationAspNetCoreHandlers.cs index 69856b5e..19ab53d0 100644 --- a/src/OpenIddict.Validation.AspNetCore/OpenIddictValidationAspNetCoreHandlers.cs +++ b/src/OpenIddict.Validation.AspNetCore/OpenIddictValidationAspNetCoreHandlers.cs @@ -77,8 +77,13 @@ public static partial class OpenIddictValidationAspNetCoreHandlers .Build(); /// - public ValueTask HandleAsync(ProcessRequestContext context!!) + public ValueTask HandleAsync(ProcessRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // This handler only applies to ASP.NET Core requests. If the HTTP context cannot be resolved, // this may indicate that the request was incorrectly processed by another server stack. var request = context.Transaction.GetHttpRequest() ?? @@ -137,8 +142,13 @@ public static partial class OpenIddictValidationAspNetCoreHandlers .Build(); /// - public ValueTask HandleAsync(ProcessAuthenticationContext context!!) + public ValueTask HandleAsync(ProcessAuthenticationContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // If a token was already resolved, don't overwrite it. if (!string.IsNullOrEmpty(context.AccessToken)) { @@ -183,8 +193,13 @@ public static partial class OpenIddictValidationAspNetCoreHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessAuthenticationContext context!!) + public async ValueTask HandleAsync(ProcessAuthenticationContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // If a token was already resolved, don't overwrite it. if (!string.IsNullOrEmpty(context.AccessToken)) { @@ -233,8 +248,13 @@ public static partial class OpenIddictValidationAspNetCoreHandlers .Build(); /// - public ValueTask HandleAsync(ProcessAuthenticationContext context!!) + public ValueTask HandleAsync(ProcessAuthenticationContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // If a token was already resolved, don't overwrite it. if (!string.IsNullOrEmpty(context.AccessToken)) { @@ -277,8 +297,13 @@ public static partial class OpenIddictValidationAspNetCoreHandlers .Build(); /// - public ValueTask HandleAsync(ProcessChallengeContext context!!) + public ValueTask HandleAsync(ProcessChallengeContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var properties = context.Transaction.GetProperty(typeof(AuthenticationProperties).FullName!); if (properties is null) { @@ -350,8 +375,13 @@ public static partial class OpenIddictValidationAspNetCoreHandlers .Build(); /// - public ValueTask HandleAsync(TContext context!!) + public ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.Transaction.Response is not null, SR.GetResourceString(SR.ID4007)); // This handler only applies to ASP.NET Core requests. If the HTTP context cannot be resolved, @@ -392,8 +422,13 @@ public static partial class OpenIddictValidationAspNetCoreHandlers .Build(); /// - public ValueTask HandleAsync(TContext context!!) + public ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // This handler only applies to ASP.NET Core requests. If the HTTP context cannot be resolved, // this may indicate that the request was incorrectly processed by another server stack. var response = context.Transaction.GetHttpRequest()?.HttpContext.Response ?? @@ -416,8 +451,8 @@ public static partial class OpenIddictValidationAspNetCoreHandlers { private readonly IOptionsMonitor _options; - public AttachWwwAuthenticateHeader(IOptionsMonitor options!!) - => _options = options; + public AttachWwwAuthenticateHeader(IOptionsMonitor options) + => _options = options ?? throw new ArgumentNullException(nameof(options)); /// /// Gets the default descriptor definition assigned to this handler. @@ -431,8 +466,13 @@ public static partial class OpenIddictValidationAspNetCoreHandlers .Build(); /// - public ValueTask HandleAsync(TContext context!!) + public ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.Transaction.Response is not null, SR.GetResourceString(SR.ID4007)); // This handler only applies to ASP.NET Core requests. If the HTTP context cannot be resolved, @@ -528,8 +568,13 @@ public static partial class OpenIddictValidationAspNetCoreHandlers .Build(); /// - public ValueTask HandleAsync(TContext context!!) + public ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // This handler only applies to ASP.NET Core requests. If the HTTP context cannot be resolved, // this may indicate that the request was incorrectly processed by another server stack. var response = context.Transaction.GetHttpRequest()?.HttpContext.Response ?? @@ -566,8 +611,13 @@ public static partial class OpenIddictValidationAspNetCoreHandlers .Build(); /// - public async ValueTask HandleAsync(TContext context!!) + public async ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.Transaction.Response is not null, SR.GetResourceString(SR.ID4007)); // This handler only applies to ASP.NET Core requests. If the HTTP context cannot be resolved, diff --git a/src/OpenIddict.Validation.AspNetCore/OpenIddictValidationAspNetCoreHelpers.cs b/src/OpenIddict.Validation.AspNetCore/OpenIddictValidationAspNetCoreHelpers.cs index 8cf56756..ba115bd1 100644 --- a/src/OpenIddict.Validation.AspNetCore/OpenIddictValidationAspNetCoreHelpers.cs +++ b/src/OpenIddict.Validation.AspNetCore/OpenIddictValidationAspNetCoreHelpers.cs @@ -19,32 +19,68 @@ public static class OpenIddictValidationAspNetCoreHelpers /// /// The transaction instance. /// The instance or if it couldn't be found. - public static HttpRequest? GetHttpRequest(this OpenIddictValidationTransaction transaction!!) - => transaction.Properties.TryGetValue(typeof(HttpRequest).FullName!, out object? property) && - property is WeakReference reference && - reference.TryGetTarget(out HttpRequest? request) ? request : null; + public static HttpRequest? GetHttpRequest(this OpenIddictValidationTransaction transaction) + { + if (transaction is null) + { + throw new ArgumentNullException(nameof(transaction)); + } + + if (!transaction.Properties.TryGetValue(typeof(HttpRequest).FullName!, out object? property)) + { + return null; + } + + if (property is WeakReference reference && reference.TryGetTarget(out HttpRequest? request)) + { + return request; + } + + return null; + } /// /// Retrieves the instance stored in . /// /// The context instance. /// The . - public static OpenIddictValidationEndpointType GetOpenIddictValidationEndpointType(this HttpContext context!!) - => context.Features.Get()?.Transaction?.EndpointType ?? default; + public static OpenIddictValidationEndpointType GetOpenIddictValidationEndpointType(this HttpContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return context.Features.Get()?.Transaction?.EndpointType ?? default; + } /// /// Retrieves the instance stored in . /// /// The context instance. - /// The instance or if it couldn't be found. - public static OpenIddictRequest? GetOpenIddictValidationRequest(this HttpContext context!!) - => context.Features.Get()?.Transaction?.Request; + /// The instance or null if it couldn't be found. + public static OpenIddictRequest? GetOpenIddictValidationRequest(this HttpContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return context.Features.Get()?.Transaction?.Request; + } /// /// Retrieves the instance stored in . /// /// The context instance. - /// The instance or if it couldn't be found. - public static OpenIddictResponse? GetOpenIddictValidationResponse(this HttpContext context!!) - => context.Features.Get()?.Transaction?.Response; + /// The instance or null if it couldn't be found. + public static OpenIddictResponse? GetOpenIddictValidationResponse(this HttpContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return context.Features.Get()?.Transaction?.Response; + } } diff --git a/src/OpenIddict.Validation.DataProtection/OpenIddictValidationDataProtectionBuilder.cs b/src/OpenIddict.Validation.DataProtection/OpenIddictValidationDataProtectionBuilder.cs index 698bba3e..4f7bc1db 100644 --- a/src/OpenIddict.Validation.DataProtection/OpenIddictValidationDataProtectionBuilder.cs +++ b/src/OpenIddict.Validation.DataProtection/OpenIddictValidationDataProtectionBuilder.cs @@ -20,8 +20,8 @@ public class OpenIddictValidationDataProtectionBuilder /// Initializes a new instance of . /// /// The services collection. - public OpenIddictValidationDataProtectionBuilder(IServiceCollection services!!) - => Services = services; + public OpenIddictValidationDataProtectionBuilder(IServiceCollection services) + => Services = services ?? throw new ArgumentNullException(nameof(services)); /// /// Gets the services collection. @@ -35,8 +35,13 @@ public class OpenIddictValidationDataProtectionBuilder /// The delegate used to configure the OpenIddict options. /// This extension can be safely called multiple times. /// The . - public OpenIddictValidationDataProtectionBuilder Configure(Action configuration!!) + public OpenIddictValidationDataProtectionBuilder Configure(Action configuration) { + if (configuration is null) + { + throw new ArgumentNullException(nameof(configuration)); + } + Services.Configure(configuration); return this; @@ -48,16 +53,30 @@ public class OpenIddictValidationDataProtectionBuilder /// /// The data protection provider used to create token protectors. /// The . - public OpenIddictValidationDataProtectionBuilder UseDataProtectionProvider(IDataProtectionProvider provider!!) - => Configure(options => options.DataProtectionProvider = provider); + public OpenIddictValidationDataProtectionBuilder UseDataProtectionProvider(IDataProtectionProvider provider) + { + if (provider is null) + { + throw new ArgumentNullException(nameof(provider)); + } + + return Configure(options => options.DataProtectionProvider = provider); + } /// /// Configures OpenIddict to use a specific formatter instead of relying on the default instance. /// /// The formatter used to read tokens. /// The . - public OpenIddictValidationDataProtectionBuilder UseFormatter(IOpenIddictValidationDataProtectionFormatter formatter!!) - => Configure(options => options.Formatter = formatter); + public OpenIddictValidationDataProtectionBuilder UseFormatter(IOpenIddictValidationDataProtectionFormatter formatter) + { + if (formatter is null) + { + throw new ArgumentNullException(nameof(formatter)); + } + + return Configure(options => options.Formatter = formatter); + } /// [EditorBrowsable(EditorBrowsableState.Never)] diff --git a/src/OpenIddict.Validation.DataProtection/OpenIddictValidationDataProtectionConfiguration.cs b/src/OpenIddict.Validation.DataProtection/OpenIddictValidationDataProtectionConfiguration.cs index ecdbe7b1..c8d4b5e1 100644 --- a/src/OpenIddict.Validation.DataProtection/OpenIddictValidationDataProtectionConfiguration.cs +++ b/src/OpenIddict.Validation.DataProtection/OpenIddictValidationDataProtectionConfiguration.cs @@ -21,11 +21,16 @@ public class OpenIddictValidationDataProtectionConfiguration : IConfigureOptions /// Creates a new instance of the class. /// /// The ASP.NET Core Data Protection provider. - public OpenIddictValidationDataProtectionConfiguration(IDataProtectionProvider dataProtectionProvider!!) + public OpenIddictValidationDataProtectionConfiguration(IDataProtectionProvider dataProtectionProvider) => _dataProtectionProvider = dataProtectionProvider; - public void Configure(OpenIddictValidationOptions options!!) + public void Configure(OpenIddictValidationOptions options) { + if (options is null) + { + throw new ArgumentNullException(nameof(options)); + } + // Register the built-in event handlers used by the OpenIddict Data Protection validation components. options.Handlers.AddRange(OpenIddictValidationDataProtectionHandlers.DefaultHandlers); } @@ -36,6 +41,13 @@ public class OpenIddictValidationDataProtectionConfiguration : IConfigureOptions /// /// The name of the options instance to configure, if applicable. /// The options instance to initialize. - public void PostConfigure(string name, OpenIddictValidationDataProtectionOptions options!!) - => options.DataProtectionProvider ??= _dataProtectionProvider; + public void PostConfigure(string name, OpenIddictValidationDataProtectionOptions options) + { + if (options is null) + { + throw new ArgumentNullException(nameof(options)); + } + + options.DataProtectionProvider ??= _dataProtectionProvider; + } } diff --git a/src/OpenIddict.Validation.DataProtection/OpenIddictValidationDataProtectionExtensions.cs b/src/OpenIddict.Validation.DataProtection/OpenIddictValidationDataProtectionExtensions.cs index d062f8a9..47abc50e 100644 --- a/src/OpenIddict.Validation.DataProtection/OpenIddictValidationDataProtectionExtensions.cs +++ b/src/OpenIddict.Validation.DataProtection/OpenIddictValidationDataProtectionExtensions.cs @@ -22,8 +22,13 @@ public static class OpenIddictValidationDataProtectionExtensions /// The services builder used by OpenIddict to register new services. /// This extension can be safely called multiple times. /// The . - public static OpenIddictValidationDataProtectionBuilder UseDataProtection(this OpenIddictValidationBuilder builder!!) + public static OpenIddictValidationDataProtectionBuilder UseDataProtection(this OpenIddictValidationBuilder builder) { + if (builder is null) + { + throw new ArgumentNullException(nameof(builder)); + } + builder.Services.AddDataProtection(); // Register the built-in validation event handlers used by the OpenIddict Data Protection components. @@ -48,8 +53,18 @@ public static class OpenIddictValidationDataProtectionExtensions /// This extension can be safely called multiple times. /// The . public static OpenIddictValidationBuilder UseDataProtection( - this OpenIddictValidationBuilder builder!!, Action configuration!!) + this OpenIddictValidationBuilder builder, Action configuration) { + if (builder is null) + { + throw new ArgumentNullException(nameof(builder)); + } + + if (configuration is null) + { + throw new ArgumentNullException(nameof(configuration)); + } + configuration(builder.UseDataProtection()); return builder; diff --git a/src/OpenIddict.Validation.DataProtection/OpenIddictValidationDataProtectionFormatter.cs b/src/OpenIddict.Validation.DataProtection/OpenIddictValidationDataProtectionFormatter.cs index e423976e..360831f0 100644 --- a/src/OpenIddict.Validation.DataProtection/OpenIddictValidationDataProtectionFormatter.cs +++ b/src/OpenIddict.Validation.DataProtection/OpenIddictValidationDataProtectionFormatter.cs @@ -13,8 +13,13 @@ namespace OpenIddict.Validation.DataProtection; public class OpenIddictValidationDataProtectionFormatter : IOpenIddictValidationDataProtectionFormatter { - public ClaimsPrincipal ReadToken(BinaryReader reader!!) + public ClaimsPrincipal ReadToken(BinaryReader reader) { + if (reader is null) + { + throw new ArgumentNullException(nameof(reader)); + } + var (principal, properties) = Read(reader); // Tokens serialized using the ASP.NET Core Data Protection stack are compound diff --git a/src/OpenIddict.Validation.DataProtection/OpenIddictValidationDataProtectionHandlers.Protection.cs b/src/OpenIddict.Validation.DataProtection/OpenIddictValidationDataProtectionHandlers.Protection.cs index dd7e82ee..15bfd330 100644 --- a/src/OpenIddict.Validation.DataProtection/OpenIddictValidationDataProtectionHandlers.Protection.cs +++ b/src/OpenIddict.Validation.DataProtection/OpenIddictValidationDataProtectionHandlers.Protection.cs @@ -33,8 +33,8 @@ public static partial class OpenIddictValidationDataProtectionHandlers { private readonly IOptionsMonitor _options; - public ValidateDataProtectionToken(IOptionsMonitor options!!) - => _options = options; + public ValidateDataProtectionToken(IOptionsMonitor options) + => _options = options ?? throw new ArgumentNullException(nameof(options)); /// /// Gets the default descriptor definition assigned to this handler. diff --git a/src/OpenIddict.Validation.Owin/OpenIddictValidationOwinBuilder.cs b/src/OpenIddict.Validation.Owin/OpenIddictValidationOwinBuilder.cs index 0961d24d..20af2ae5 100644 --- a/src/OpenIddict.Validation.Owin/OpenIddictValidationOwinBuilder.cs +++ b/src/OpenIddict.Validation.Owin/OpenIddictValidationOwinBuilder.cs @@ -19,8 +19,8 @@ public class OpenIddictValidationOwinBuilder /// Initializes a new instance of . /// /// The services collection. - public OpenIddictValidationOwinBuilder(IServiceCollection services!!) - => Services = services; + public OpenIddictValidationOwinBuilder(IServiceCollection services) + => Services = services ?? throw new ArgumentNullException(nameof(services)); /// /// Gets the services collection. @@ -34,8 +34,13 @@ public class OpenIddictValidationOwinBuilder /// The delegate used to configure the OpenIddict options. /// This extension can be safely called multiple times. /// The . - public OpenIddictValidationOwinBuilder Configure(Action configuration!!) + public OpenIddictValidationOwinBuilder Configure(Action configuration) { + if (configuration is null) + { + throw new ArgumentNullException(nameof(configuration)); + } + Services.Configure(configuration); return this; diff --git a/src/OpenIddict.Validation.Owin/OpenIddictValidationOwinConfiguration.cs b/src/OpenIddict.Validation.Owin/OpenIddictValidationOwinConfiguration.cs index 9c8d3a2c..fb033ae1 100644 --- a/src/OpenIddict.Validation.Owin/OpenIddictValidationOwinConfiguration.cs +++ b/src/OpenIddict.Validation.Owin/OpenIddictValidationOwinConfiguration.cs @@ -13,8 +13,13 @@ namespace OpenIddict.Validation.Owin; /// public class OpenIddictValidationOwinConfiguration : IConfigureOptions { - public void Configure(OpenIddictValidationOptions options!!) + public void Configure(OpenIddictValidationOptions options) { + if (options is null) + { + throw new ArgumentNullException(nameof(options)); + } + // Register the built-in event handlers used by the OpenIddict OWIN validation components. options.Handlers.AddRange(OpenIddictValidationOwinHandlers.DefaultHandlers); } diff --git a/src/OpenIddict.Validation.Owin/OpenIddictValidationOwinExtensions.cs b/src/OpenIddict.Validation.Owin/OpenIddictValidationOwinExtensions.cs index 65235164..fe5f6bfe 100644 --- a/src/OpenIddict.Validation.Owin/OpenIddictValidationOwinExtensions.cs +++ b/src/OpenIddict.Validation.Owin/OpenIddictValidationOwinExtensions.cs @@ -22,8 +22,13 @@ public static class OpenIddictValidationOwinExtensions /// The services builder used by OpenIddict to register new services. /// This extension can be safely called multiple times. /// The . - public static OpenIddictValidationOwinBuilder UseOwin(this OpenIddictValidationBuilder builder!!) + public static OpenIddictValidationOwinBuilder UseOwin(this OpenIddictValidationBuilder builder) { + if (builder is null) + { + throw new ArgumentNullException(nameof(builder)); + } + // Note: unlike regular OWIN middleware, the OpenIddict validation middleware is registered // as a scoped service in the DI container. This allows containers that support middleware // resolution (like Autofac) to use it without requiring additional configuration. @@ -54,8 +59,18 @@ public static class OpenIddictValidationOwinExtensions /// This extension can be safely called multiple times. /// The . public static OpenIddictValidationBuilder UseOwin( - this OpenIddictValidationBuilder builder!!, Action configuration!!) + this OpenIddictValidationBuilder builder, Action configuration) { + if (builder is null) + { + throw new ArgumentNullException(nameof(builder)); + } + + if (configuration is null) + { + throw new ArgumentNullException(nameof(configuration)); + } + configuration(builder.UseOwin()); return builder; diff --git a/src/OpenIddict.Validation.Owin/OpenIddictValidationOwinHandler.cs b/src/OpenIddict.Validation.Owin/OpenIddictValidationOwinHandler.cs index 1d1dc478..b31ebb7b 100644 --- a/src/OpenIddict.Validation.Owin/OpenIddictValidationOwinHandler.cs +++ b/src/OpenIddict.Validation.Owin/OpenIddictValidationOwinHandler.cs @@ -24,11 +24,11 @@ public class OpenIddictValidationOwinHandler : AuthenticationHandlerThe OpenIddict validation provider used by this instance. /// The OpenIddict validation factory used by this instance. public OpenIddictValidationOwinHandler( - IOpenIddictValidationDispatcher dispatcher!!, - IOpenIddictValidationFactory factory!!) + IOpenIddictValidationDispatcher dispatcher, + IOpenIddictValidationFactory factory) { - _dispatcher = dispatcher; - _factory = factory; + _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); + _factory = factory ?? throw new ArgumentNullException(nameof(factory)); } /// diff --git a/src/OpenIddict.Validation.Owin/OpenIddictValidationOwinHandlerFilters.cs b/src/OpenIddict.Validation.Owin/OpenIddictValidationOwinHandlerFilters.cs index 47d3b355..91fcb70e 100644 --- a/src/OpenIddict.Validation.Owin/OpenIddictValidationOwinHandlerFilters.cs +++ b/src/OpenIddict.Validation.Owin/OpenIddictValidationOwinHandlerFilters.cs @@ -18,7 +18,14 @@ public static class OpenIddictValidationOwinHandlerFilters /// public class RequireOwinRequest : IOpenIddictValidationHandlerFilter { - public ValueTask IsActiveAsync(BaseContext context!!) - => new(context.Transaction.GetOwinRequest() is not null); + public ValueTask IsActiveAsync(BaseContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(context.Transaction.GetOwinRequest() is not null); + } } } diff --git a/src/OpenIddict.Validation.Owin/OpenIddictValidationOwinHandlers.cs b/src/OpenIddict.Validation.Owin/OpenIddictValidationOwinHandlers.cs index 6dfd50f7..28433e01 100644 --- a/src/OpenIddict.Validation.Owin/OpenIddictValidationOwinHandlers.cs +++ b/src/OpenIddict.Validation.Owin/OpenIddictValidationOwinHandlers.cs @@ -72,8 +72,13 @@ public static partial class OpenIddictValidationOwinHandlers .Build(); /// - public ValueTask HandleAsync(ProcessRequestContext context!!) + public ValueTask HandleAsync(ProcessRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // This handler only applies to OWIN requests. If The OWIN request cannot be resolved, // this may indicate that the request was incorrectly processed by another server stack. var request = context.Transaction.GetOwinRequest() ?? @@ -132,8 +137,13 @@ public static partial class OpenIddictValidationOwinHandlers .Build(); /// - public ValueTask HandleAsync(ProcessAuthenticationContext context!!) + public ValueTask HandleAsync(ProcessAuthenticationContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // If a token was already resolved, don't overwrite it. if (!string.IsNullOrEmpty(context.AccessToken)) { @@ -178,8 +188,13 @@ public static partial class OpenIddictValidationOwinHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessAuthenticationContext context!!) + public async ValueTask HandleAsync(ProcessAuthenticationContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // If a token was already resolved, don't overwrite it. if (!string.IsNullOrEmpty(context.AccessToken)) { @@ -229,8 +244,13 @@ public static partial class OpenIddictValidationOwinHandlers .Build(); /// - public ValueTask HandleAsync(ProcessAuthenticationContext context!!) + public ValueTask HandleAsync(ProcessAuthenticationContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // If a token was already resolved, don't overwrite it. if (!string.IsNullOrEmpty(context.AccessToken)) { @@ -274,8 +294,13 @@ public static partial class OpenIddictValidationOwinHandlers .Build(); /// - public ValueTask HandleAsync(ProcessChallengeContext context!!) + public ValueTask HandleAsync(ProcessChallengeContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var properties = context.Transaction.GetProperty(typeof(AuthenticationProperties).FullName!); if (properties is null) { @@ -328,8 +353,13 @@ public static partial class OpenIddictValidationOwinHandlers .Build(); /// - public ValueTask HandleAsync(TContext context!!) + public ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.Transaction.Response is not null, SR.GetResourceString(SR.ID4007)); // This handler only applies to OWIN requests. If The OWIN request cannot be resolved, @@ -370,8 +400,13 @@ public static partial class OpenIddictValidationOwinHandlers .Build(); /// - public ValueTask HandleAsync(TContext context!!) + public ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // This handler only applies to OWIN requests. If The OWIN request cannot be resolved, // this may indicate that the request was incorrectly processed by another server stack. var response = context.Transaction.GetOwinRequest()?.Context.Response ?? @@ -394,8 +429,8 @@ public static partial class OpenIddictValidationOwinHandlers { private readonly IOptionsMonitor _options; - public AttachWwwAuthenticateHeader(IOptionsMonitor options!!) - => _options = options; + public AttachWwwAuthenticateHeader(IOptionsMonitor options) + => _options = options ?? throw new ArgumentNullException(nameof(options)); /// /// Gets the default descriptor definition assigned to this handler. @@ -409,8 +444,13 @@ public static partial class OpenIddictValidationOwinHandlers .Build(); /// - public ValueTask HandleAsync(TContext context!!) + public ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.Transaction.Response is not null, SR.GetResourceString(SR.ID4007)); // This handler only applies to OWIN requests. If The OWIN request cannot be resolved, @@ -511,8 +551,13 @@ public static partial class OpenIddictValidationOwinHandlers .Build(); /// - public ValueTask HandleAsync(TContext context!!) + public ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // This handler only applies to OWIN requests. If The OWIN request cannot be resolved, // this may indicate that the request was incorrectly processed by another server stack. var response = context.Transaction.GetOwinRequest()?.Context.Response ?? @@ -549,8 +594,13 @@ public static partial class OpenIddictValidationOwinHandlers .Build(); /// - public async ValueTask HandleAsync(TContext context!!) + public async ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.Transaction.Response is not null, SR.GetResourceString(SR.ID4007)); // This handler only applies to OWIN requests. If The OWIN request cannot be resolved, diff --git a/src/OpenIddict.Validation.Owin/OpenIddictValidationOwinHelpers.cs b/src/OpenIddict.Validation.Owin/OpenIddictValidationOwinHelpers.cs index 9cfd3231..45dc5d33 100644 --- a/src/OpenIddict.Validation.Owin/OpenIddictValidationOwinHelpers.cs +++ b/src/OpenIddict.Validation.Owin/OpenIddictValidationOwinHelpers.cs @@ -21,40 +21,83 @@ public static class OpenIddictValidationOwinHelpers /// /// The application builder used to register middleware instances. /// The . - public static IAppBuilder UseOpenIddictValidation(this IAppBuilder app!!) - => app.Use(); + public static IAppBuilder UseOpenIddictValidation(this IAppBuilder app) + { + if (app is null) + { + throw new ArgumentNullException(nameof(app)); + } + + return app.Use(); + } /// /// Retrieves the instance stored in the properties. /// /// The transaction instance. /// The instance or if it couldn't be found. - public static IOwinRequest? GetOwinRequest(this OpenIddictValidationTransaction transaction!!) - => transaction.Properties.TryGetValue(typeof(IOwinRequest).FullName!, out object? property) && - property is WeakReference reference && - reference.TryGetTarget(out IOwinRequest? request) ? request : null; + public static IOwinRequest? GetOwinRequest(this OpenIddictValidationTransaction transaction) + { + if (transaction is null) + { + throw new ArgumentNullException(nameof(transaction)); + } + + if (!transaction.Properties.TryGetValue(typeof(IOwinRequest).FullName!, out object? property)) + { + return null; + } + + if (property is WeakReference reference && reference.TryGetTarget(out IOwinRequest? request)) + { + return request; + } + + return null; + } /// /// Retrieves the instance stored in . /// /// The context instance. /// The . - public static OpenIddictValidationEndpointType GetOpenIddictValidationEndpointType(this IOwinContext context!!) - => context.Get(typeof(OpenIddictValidationTransaction).FullName)?.EndpointType ?? default; + public static OpenIddictValidationEndpointType GetOpenIddictValidationEndpointType(this IOwinContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return context.Get(typeof(OpenIddictValidationTransaction).FullName)?.EndpointType ?? default; + } /// /// Retrieves the instance stored in . /// /// The context instance. - /// The instance or if it couldn't be found. - public static OpenIddictRequest? GetOpenIddictValidationRequest(this IOwinContext context!!) - => context.Get(typeof(OpenIddictValidationTransaction).FullName)?.Request; + /// The instance or null if it couldn't be found. + public static OpenIddictRequest? GetOpenIddictValidationRequest(this IOwinContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return context.Get(typeof(OpenIddictValidationTransaction).FullName)?.Request; + } /// /// Retrieves the instance stored in . /// /// The context instance. - /// The instance or if it couldn't be found. - public static OpenIddictResponse? GetOpenIddictValidationResponse(this IOwinContext context!!) - => context.Get(typeof(OpenIddictValidationTransaction).FullName)?.Response; + /// The instance or null if it couldn't be found. + public static OpenIddictResponse? GetOpenIddictValidationResponse(this IOwinContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return context.Get(typeof(OpenIddictValidationTransaction).FullName)?.Response; + } } diff --git a/src/OpenIddict.Validation.Owin/OpenIddictValidationOwinMiddleware.cs b/src/OpenIddict.Validation.Owin/OpenIddictValidationOwinMiddleware.cs index 346a450d..9ce506b9 100644 --- a/src/OpenIddict.Validation.Owin/OpenIddictValidationOwinMiddleware.cs +++ b/src/OpenIddict.Validation.Owin/OpenIddictValidationOwinMiddleware.cs @@ -29,13 +29,13 @@ public class OpenIddictValidationOwinMiddleware : AuthenticationMiddlewareThe OpenIddict validation factory. public OpenIddictValidationOwinMiddleware( OwinMiddleware? next, - IOptionsMonitor options!!, - IOpenIddictValidationDispatcher dispatcher!!, - IOpenIddictValidationFactory factory!!) + IOptionsMonitor options, + IOpenIddictValidationDispatcher dispatcher, + IOpenIddictValidationFactory factory) : base(next, options.CurrentValue) { - _dispatcher = dispatcher; - _factory = factory; + _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); + _factory = factory ?? throw new ArgumentNullException(nameof(factory)); } /// diff --git a/src/OpenIddict.Validation.Owin/OpenIddictValidationOwinMiddlewareFactory.cs b/src/OpenIddict.Validation.Owin/OpenIddictValidationOwinMiddlewareFactory.cs index 11403181..a15a4761 100644 --- a/src/OpenIddict.Validation.Owin/OpenIddictValidationOwinMiddlewareFactory.cs +++ b/src/OpenIddict.Validation.Owin/OpenIddictValidationOwinMiddlewareFactory.cs @@ -33,8 +33,13 @@ public class OpenIddictValidationOwinMiddlewareFactory : OwinMiddleware /// /// A that can be used to monitor the asynchronous operation. /// - public override Task Invoke(IOwinContext context!!) + public override Task Invoke(IOwinContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var provider = context.Get(typeof(IServiceProvider).FullName) ?? throw new InvalidOperationException(SR.GetResourceString(SR.ID0168)); diff --git a/src/OpenIddict.Validation.ServerIntegration/OpenIddictValidationServerIntegrationBuilder.cs b/src/OpenIddict.Validation.ServerIntegration/OpenIddictValidationServerIntegrationBuilder.cs index cfa21024..be160ea1 100644 --- a/src/OpenIddict.Validation.ServerIntegration/OpenIddictValidationServerIntegrationBuilder.cs +++ b/src/OpenIddict.Validation.ServerIntegration/OpenIddictValidationServerIntegrationBuilder.cs @@ -18,8 +18,8 @@ public class OpenIddictValidationServerIntegrationBuilder /// Initializes a new instance of . /// /// The services collection. - public OpenIddictValidationServerIntegrationBuilder(IServiceCollection services!!) - => Services = services; + public OpenIddictValidationServerIntegrationBuilder(IServiceCollection services) + => Services = services ?? throw new ArgumentNullException(nameof(services)); /// /// Gets the services collection. @@ -33,9 +33,13 @@ public class OpenIddictValidationServerIntegrationBuilder /// The delegate used to configure the OpenIddict options. /// This extension can be safely called multiple times. /// The . - public OpenIddictValidationServerIntegrationBuilder Configure( - Action configuration!!) + public OpenIddictValidationServerIntegrationBuilder Configure(Action configuration) { + if (configuration is null) + { + throw new ArgumentNullException(nameof(configuration)); + } + Services.Configure(configuration); return this; diff --git a/src/OpenIddict.Validation.ServerIntegration/OpenIddictValidationServerIntegrationConfiguration.cs b/src/OpenIddict.Validation.ServerIntegration/OpenIddictValidationServerIntegrationConfiguration.cs index aebf87c3..078d9c83 100644 --- a/src/OpenIddict.Validation.ServerIntegration/OpenIddictValidationServerIntegrationConfiguration.cs +++ b/src/OpenIddict.Validation.ServerIntegration/OpenIddictValidationServerIntegrationConfiguration.cs @@ -21,16 +21,21 @@ public class OpenIddictValidationServerIntegrationConfiguration : IConfigureOpti /// Creates a new instance of the class. /// /// The OpenIddict server options. - public OpenIddictValidationServerIntegrationConfiguration(IOptionsMonitor options!!) - => _options = options; + public OpenIddictValidationServerIntegrationConfiguration(IOptionsMonitor options) + => _options = options ?? throw new ArgumentNullException(nameof(options)); /// /// Populates the default OpenIddict validation/server integration options /// and ensures that the configuration is in a consistent and valid state. /// /// The options instance to initialize. - public void Configure(OpenIddictValidationOptions options!!) + public void Configure(OpenIddictValidationOptions options) { + if (options is null) + { + throw new ArgumentNullException(nameof(options)); + } + // Note: the issuer may be null. In this case, it will be usually provided by // a validation handler registered by the host (e.g ASP.NET Core or OWIN/Katana). options.Configuration = new OpenIddictConfiguration @@ -57,8 +62,13 @@ public class OpenIddictValidationServerIntegrationConfiguration : IConfigureOpti /// /// The name of the options instance to configure, if applicable. /// The options instance to initialize. - public void PostConfigure(string name, OpenIddictValidationOptions options!!) + public void PostConfigure(string name, OpenIddictValidationOptions options) { + if (options is null) + { + throw new ArgumentNullException(nameof(options)); + } + if (options.ValidationType != OpenIddictValidationType.Direct) { throw new InvalidOperationException(SR.GetResourceString(SR.ID0170)); diff --git a/src/OpenIddict.Validation.ServerIntegration/OpenIddictValidationServerIntegrationExtensions.cs b/src/OpenIddict.Validation.ServerIntegration/OpenIddictValidationServerIntegrationExtensions.cs index ef8457b8..bd8b74be 100644 --- a/src/OpenIddict.Validation.ServerIntegration/OpenIddictValidationServerIntegrationExtensions.cs +++ b/src/OpenIddict.Validation.ServerIntegration/OpenIddictValidationServerIntegrationExtensions.cs @@ -23,8 +23,13 @@ public static class OpenIddictValidationServerIntegrationExtensions /// The services builder used by OpenIddict to register new services. /// This extension can be safely called multiple times. /// The . - public static OpenIddictValidationServerIntegrationBuilder UseLocalServer(this OpenIddictValidationBuilder builder!!) + public static OpenIddictValidationServerIntegrationBuilder UseLocalServer(this OpenIddictValidationBuilder builder) { + if (builder is null) + { + throw new ArgumentNullException(nameof(builder)); + } + // Note: TryAddEnumerable() is used here to ensure the initializers are registered only once. builder.Services.TryAddEnumerable(new[] { @@ -44,8 +49,18 @@ public static class OpenIddictValidationServerIntegrationExtensions /// This extension can be safely called multiple times. /// The . public static OpenIddictValidationBuilder UseLocalServer( - this OpenIddictValidationBuilder builder!!, Action configuration!!) + this OpenIddictValidationBuilder builder, Action configuration) { + if (builder is null) + { + throw new ArgumentNullException(nameof(builder)); + } + + if (configuration is null) + { + throw new ArgumentNullException(nameof(configuration)); + } + configuration(builder.UseLocalServer()); return builder; diff --git a/src/OpenIddict.Validation.SystemNetHttp/OpenIddictValidationSystemNetHttpBuilder.cs b/src/OpenIddict.Validation.SystemNetHttp/OpenIddictValidationSystemNetHttpBuilder.cs index e31175ab..6ce2d98c 100644 --- a/src/OpenIddict.Validation.SystemNetHttp/OpenIddictValidationSystemNetHttpBuilder.cs +++ b/src/OpenIddict.Validation.SystemNetHttp/OpenIddictValidationSystemNetHttpBuilder.cs @@ -19,8 +19,8 @@ public class OpenIddictValidationSystemNetHttpBuilder /// Initializes a new instance of . /// /// The services collection. - public OpenIddictValidationSystemNetHttpBuilder(IServiceCollection services!!) - => Services = services; + public OpenIddictValidationSystemNetHttpBuilder(IServiceCollection services) + => Services = services ?? throw new ArgumentNullException(nameof(services)); /// /// Gets the services collection. @@ -34,8 +34,13 @@ public class OpenIddictValidationSystemNetHttpBuilder /// The delegate used to configure the OpenIddict options. /// This extension can be safely called multiple times. /// The . - public OpenIddictValidationSystemNetHttpBuilder Configure(Action configuration!!) + public OpenIddictValidationSystemNetHttpBuilder Configure(Action configuration) { + if (configuration is null) + { + throw new ArgumentNullException(nameof(configuration)); + } + Services.Configure(configuration); return this; diff --git a/src/OpenIddict.Validation.SystemNetHttp/OpenIddictValidationSystemNetHttpConfiguration.cs b/src/OpenIddict.Validation.SystemNetHttp/OpenIddictValidationSystemNetHttpConfiguration.cs index 30a0524d..4af295a0 100644 --- a/src/OpenIddict.Validation.SystemNetHttp/OpenIddictValidationSystemNetHttpConfiguration.cs +++ b/src/OpenIddict.Validation.SystemNetHttp/OpenIddictValidationSystemNetHttpConfiguration.cs @@ -21,12 +21,17 @@ public class OpenIddictValidationSystemNetHttpConfiguration : IConfigureOptions< #if !SUPPORTS_SERVICE_PROVIDER_IN_HTTP_MESSAGE_HANDLER_BUILDER private readonly IServiceProvider _provider; - public OpenIddictValidationSystemNetHttpConfiguration(IServiceProvider provider!!) - => _provider = provider; + public OpenIddictValidationSystemNetHttpConfiguration(IServiceProvider provider) + => _provider = provider ?? throw new ArgumentNullException(nameof(provider)); #endif - public void Configure(OpenIddictValidationOptions options!!) + public void Configure(OpenIddictValidationOptions options) { + if (options is null) + { + throw new ArgumentNullException(nameof(options)); + } + // Register the built-in event handlers used by the OpenIddict System.Net.Http validation components. options.Handlers.AddRange(OpenIddictValidationSystemNetHttpHandlers.DefaultHandlers); } @@ -34,8 +39,13 @@ public class OpenIddictValidationSystemNetHttpConfiguration : IConfigureOptions< public void Configure(HttpClientFactoryOptions options) => Debug.Fail("This infrastructure method shouldn't be called."); - public void Configure(string name, HttpClientFactoryOptions options!!) + public void Configure(string name, HttpClientFactoryOptions options) { + if (options is null) + { + throw new ArgumentNullException(nameof(options)); + } + var assembly = typeof(OpenIddictValidationSystemNetHttpOptions).Assembly.GetName(); if (!string.Equals(name, assembly.Name, StringComparison.Ordinal)) diff --git a/src/OpenIddict.Validation.SystemNetHttp/OpenIddictValidationSystemNetHttpExtensions.cs b/src/OpenIddict.Validation.SystemNetHttp/OpenIddictValidationSystemNetHttpExtensions.cs index 305760a8..92398e04 100644 --- a/src/OpenIddict.Validation.SystemNetHttp/OpenIddictValidationSystemNetHttpExtensions.cs +++ b/src/OpenIddict.Validation.SystemNetHttp/OpenIddictValidationSystemNetHttpExtensions.cs @@ -23,8 +23,13 @@ public static class OpenIddictValidationSystemNetHttpExtensions /// The services builder used by OpenIddict to register new services. /// This extension can be safely called multiple times. /// The . - public static OpenIddictValidationSystemNetHttpBuilder UseSystemNetHttp(this OpenIddictValidationBuilder builder!!) + public static OpenIddictValidationSystemNetHttpBuilder UseSystemNetHttp(this OpenIddictValidationBuilder builder) { + if (builder is null) + { + throw new ArgumentNullException(nameof(builder)); + } + builder.Services.AddHttpClient(); // Register the built-in validation event handlers used by the OpenIddict System.Net.Http components. @@ -52,8 +57,18 @@ public static class OpenIddictValidationSystemNetHttpExtensions /// This extension can be safely called multiple times. /// The . public static OpenIddictValidationBuilder UseSystemNetHttp( - this OpenIddictValidationBuilder builder!!, Action configuration!!) + this OpenIddictValidationBuilder builder, Action configuration) { + if (builder is null) + { + throw new ArgumentNullException(nameof(builder)); + } + + if (configuration is null) + { + throw new ArgumentNullException(nameof(configuration)); + } + configuration(builder.UseSystemNetHttp()); return builder; diff --git a/src/OpenIddict.Validation.SystemNetHttp/OpenIddictValidationSystemNetHttpHandlerFilters.cs b/src/OpenIddict.Validation.SystemNetHttp/OpenIddictValidationSystemNetHttpHandlerFilters.cs index f301c92b..6a84f0d9 100644 --- a/src/OpenIddict.Validation.SystemNetHttp/OpenIddictValidationSystemNetHttpHandlerFilters.cs +++ b/src/OpenIddict.Validation.SystemNetHttp/OpenIddictValidationSystemNetHttpHandlerFilters.cs @@ -16,8 +16,16 @@ public static class OpenIddictValidationSystemNetHttpHandlerFilters /// public class RequireHttpMetadataAddress : IOpenIddictValidationHandlerFilter { - public ValueTask IsActiveAsync(BaseExternalContext context!!) - => new(string.Equals(context.Address?.Scheme, Uri.UriSchemeHttp, StringComparison.OrdinalIgnoreCase) || - string.Equals(context.Address?.Scheme, Uri.UriSchemeHttps, StringComparison.OrdinalIgnoreCase)); + public ValueTask IsActiveAsync(BaseExternalContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new( + string.Equals(context.Address?.Scheme, Uri.UriSchemeHttp, StringComparison.OrdinalIgnoreCase) || + string.Equals(context.Address?.Scheme, Uri.UriSchemeHttps, StringComparison.OrdinalIgnoreCase)); + } } } diff --git a/src/OpenIddict.Validation.SystemNetHttp/OpenIddictValidationSystemNetHttpHandlers.Introspection.cs b/src/OpenIddict.Validation.SystemNetHttp/OpenIddictValidationSystemNetHttpHandlers.Introspection.cs index 231d2b6a..967bf1e9 100644 --- a/src/OpenIddict.Validation.SystemNetHttp/OpenIddictValidationSystemNetHttpHandlers.Introspection.cs +++ b/src/OpenIddict.Validation.SystemNetHttp/OpenIddictValidationSystemNetHttpHandlers.Introspection.cs @@ -48,8 +48,13 @@ public static partial class OpenIddictValidationSystemNetHttpHandlers .Build(); /// - public async ValueTask HandleAsync(PrepareIntrospectionRequestContext context!!) + public async ValueTask HandleAsync(PrepareIntrospectionRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.Request is not null, SR.GetResourceString(SR.ID4008)); // This handler only applies to System.Net.Http requests. If the HTTP request cannot be resolved, diff --git a/src/OpenIddict.Validation.SystemNetHttp/OpenIddictValidationSystemNetHttpHandlers.cs b/src/OpenIddict.Validation.SystemNetHttp/OpenIddictValidationSystemNetHttpHandlers.cs index fb99128e..df7367a5 100644 --- a/src/OpenIddict.Validation.SystemNetHttp/OpenIddictValidationSystemNetHttpHandlers.cs +++ b/src/OpenIddict.Validation.SystemNetHttp/OpenIddictValidationSystemNetHttpHandlers.cs @@ -40,8 +40,13 @@ public static partial class OpenIddictValidationSystemNetHttpHandlers /// [SuppressMessage("Reliability", "CA2000:Dispose objects before losing scope", Justification = "The HTTP request message is disposed later by a dedicated handler.")] - public ValueTask HandleAsync(TContext context!!) + public ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var request = new HttpRequestMessage(HttpMethod.Get, context.Address) { Headers = @@ -77,8 +82,13 @@ public static partial class OpenIddictValidationSystemNetHttpHandlers /// [SuppressMessage("Reliability", "CA2000:Dispose objects before losing scope", Justification = "The HTTP request message is disposed later by a dedicated handler.")] - public ValueTask HandleAsync(TContext context!!) + public ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var request = new HttpRequestMessage(HttpMethod.Post, context.Address) { Headers = @@ -112,8 +122,13 @@ public static partial class OpenIddictValidationSystemNetHttpHandlers .Build(); /// - public ValueTask HandleAsync(TContext context!!) + public ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.Transaction.Request is not null, SR.GetResourceString(SR.ID4008)); // This handler only applies to System.Net.Http requests. If the HTTP request cannot be resolved, @@ -170,8 +185,13 @@ public static partial class OpenIddictValidationSystemNetHttpHandlers .Build(); /// - public ValueTask HandleAsync(TContext context!!) + public ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.Transaction.Request is not null, SR.GetResourceString(SR.ID4008)); // This handler only applies to System.Net.Http requests. If the HTTP request cannot be resolved, @@ -199,7 +219,7 @@ public static partial class OpenIddictValidationSystemNetHttpHandlers private readonly IHttpClientFactory _factory; public SendHttpRequest(IHttpClientFactory factory) - => _factory = factory; + => _factory = factory ?? throw new ArgumentNullException(nameof(factory)); /// /// Gets the default descriptor definition assigned to this handler. @@ -213,8 +233,13 @@ public static partial class OpenIddictValidationSystemNetHttpHandlers .Build(); /// - public async ValueTask HandleAsync(TContext context!!) + public async ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // This handler only applies to System.Net.Http requests. If the HTTP request cannot be resolved, // this may indicate that the request was incorrectly processed by another client stack. var request = context.Transaction.GetHttpRequestMessage() ?? @@ -253,8 +278,13 @@ public static partial class OpenIddictValidationSystemNetHttpHandlers .Build(); /// - public ValueTask HandleAsync(TContext context!!) + public ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // This handler only applies to System.Net.Http requests. If the HTTP request cannot be resolved, // this may indicate that the request was incorrectly processed by another client stack. var request = context.Transaction.GetHttpRequestMessage() ?? @@ -286,8 +316,13 @@ public static partial class OpenIddictValidationSystemNetHttpHandlers .Build(); /// - public async ValueTask HandleAsync(TContext context!!) + public async ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // This handler only applies to System.Net.Http requests. If the HTTP response cannot be resolved, // this may indicate that the request was incorrectly processed by another client stack. var response = context.Transaction.GetHttpResponseMessage() ?? @@ -319,8 +354,13 @@ public static partial class OpenIddictValidationSystemNetHttpHandlers .Build(); /// - public ValueTask HandleAsync(TContext context!!) + public ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // This handler only applies to System.Net.Http requests. If the HTTP response cannot be resolved, // this may indicate that the request was incorrectly processed by another client stack. var response = context.Transaction.GetHttpResponseMessage() ?? diff --git a/src/OpenIddict.Validation/OpenIddictValidationBuilder.cs b/src/OpenIddict.Validation/OpenIddictValidationBuilder.cs index 4aa34ac0..6df14cc7 100644 --- a/src/OpenIddict.Validation/OpenIddictValidationBuilder.cs +++ b/src/OpenIddict.Validation/OpenIddictValidationBuilder.cs @@ -24,8 +24,8 @@ public class OpenIddictValidationBuilder /// Initializes a new instance of . /// /// The services collection. - public OpenIddictValidationBuilder(IServiceCollection services!!) - => Services = services; + public OpenIddictValidationBuilder(IServiceCollection services) + => Services = services ?? throw new ArgumentNullException(nameof(services)); /// /// Gets the services collection. @@ -41,9 +41,14 @@ public class OpenIddictValidationBuilder /// The . [EditorBrowsable(EditorBrowsableState.Advanced)] public OpenIddictValidationBuilder AddEventHandler( - Action> configuration!!) + Action> configuration) where TContext : OpenIddictValidationEvents.BaseContext { + if (configuration is null) + { + throw new ArgumentNullException(nameof(configuration)); + } + // Note: handlers registered using this API are assumed to be custom handlers by default. var builder = OpenIddictValidationHandlerDescriptor.CreateBuilder() .SetType(OpenIddictValidationHandlerType.Custom); @@ -59,8 +64,13 @@ public class OpenIddictValidationBuilder /// The handler descriptor. /// The . [EditorBrowsable(EditorBrowsableState.Advanced)] - public OpenIddictValidationBuilder AddEventHandler(OpenIddictValidationHandlerDescriptor descriptor!!) + public OpenIddictValidationBuilder AddEventHandler(OpenIddictValidationHandlerDescriptor descriptor) { + if (descriptor is null) + { + throw new ArgumentNullException(nameof(descriptor)); + } + // Register the handler in the services collection. Services.Add(descriptor.ServiceDescriptor); @@ -73,8 +83,13 @@ public class OpenIddictValidationBuilder /// The descriptor corresponding to the handler to remove. /// The . [EditorBrowsable(EditorBrowsableState.Advanced)] - public OpenIddictValidationBuilder RemoveEventHandler(OpenIddictValidationHandlerDescriptor descriptor!!) + public OpenIddictValidationBuilder RemoveEventHandler(OpenIddictValidationHandlerDescriptor descriptor) { + if (descriptor is null) + { + throw new ArgumentNullException(nameof(descriptor)); + } + Services.RemoveAll(descriptor.ServiceDescriptor.ServiceType); Services.PostConfigure(options => @@ -97,8 +112,13 @@ public class OpenIddictValidationBuilder /// The delegate used to configure the OpenIddict options. /// This extension can be safely called multiple times. /// The . - public OpenIddictValidationBuilder Configure(Action configuration!!) + public OpenIddictValidationBuilder Configure(Action configuration) { + if (configuration is null) + { + throw new ArgumentNullException(nameof(configuration)); + } + Services.Configure(configuration); return this; @@ -109,16 +129,28 @@ public class OpenIddictValidationBuilder /// /// The encrypting credentials. /// The . - public OpenIddictValidationBuilder AddEncryptionCredentials(EncryptingCredentials credentials!!) - => Configure(options => options.EncryptionCredentials.Add(credentials)); + public OpenIddictValidationBuilder AddEncryptionCredentials(EncryptingCredentials credentials) + { + if (credentials is null) + { + throw new ArgumentNullException(nameof(credentials)); + } + + return Configure(options => options.EncryptionCredentials.Add(credentials)); + } /// /// Registers an encryption key. /// /// The security key. /// The . - public OpenIddictValidationBuilder AddEncryptionKey(SecurityKey key!!) + public OpenIddictValidationBuilder AddEncryptionKey(SecurityKey key) { + if (key is null) + { + throw new ArgumentNullException(nameof(key)); + } + // If the encryption key is an asymmetric security key, ensure it has a private key. if (key is AsymmetricSecurityKey asymmetricSecurityKey && asymmetricSecurityKey.PrivateKeyStatus is PrivateKeyStatus.DoesNotExist) @@ -146,8 +178,13 @@ public class OpenIddictValidationBuilder /// /// The encryption certificate. /// The . - public OpenIddictValidationBuilder AddEncryptionCertificate(X509Certificate2 certificate!!) + public OpenIddictValidationBuilder AddEncryptionCertificate(X509Certificate2 certificate) { + if (certificate is null) + { + throw new ArgumentNullException(nameof(certificate)); + } + // If the certificate is a X.509v3 certificate that specifies at least one // key usage, ensure that the certificate key can be used for key encryption. if (certificate.Version >= 3) @@ -194,9 +231,14 @@ public class OpenIddictValidationBuilder /// An enumeration of flags indicating how and where to store the private key of the certificate. /// The . public OpenIddictValidationBuilder AddEncryptionCertificate( - Assembly assembly!!, string resource, + Assembly assembly, string resource, string? password, X509KeyStorageFlags flags) { + if (assembly is null) + { + throw new ArgumentNullException(nameof(assembly)); + } + if (string.IsNullOrEmpty(resource)) { throw new ArgumentException(SR.GetResourceString(SR.ID0062), nameof(resource)); @@ -237,8 +279,13 @@ public class OpenIddictValidationBuilder [SuppressMessage("Reliability", "CA2000:Dispose objects before losing scope", Justification = "The X.509 certificate is attached to the server options.")] public OpenIddictValidationBuilder AddEncryptionCertificate( - Stream stream!!, string? password, X509KeyStorageFlags flags) + Stream stream, string? password, X509KeyStorageFlags flags) { + if (stream is null) + { + throw new ArgumentNullException(nameof(stream)); + } + using var buffer = new MemoryStream(); stream.CopyTo(buffer); @@ -304,9 +351,14 @@ public class OpenIddictValidationBuilder /// /// The audiences valid for this resource server. /// The . - public OpenIddictValidationBuilder AddAudiences(params string[] audiences!!) + public OpenIddictValidationBuilder AddAudiences(params string[] audiences) { - if (audiences.Any(string.IsNullOrEmpty)) + if (audiences is null) + { + throw new ArgumentNullException(nameof(audiences)); + } + + if (audiences.Any(audience => string.IsNullOrEmpty(audience))) { throw new ArgumentException(SR.GetResourceString(SR.ID0123), nameof(audiences)); } @@ -340,8 +392,15 @@ public class OpenIddictValidationBuilder /// /// The server configuration. /// The . - public OpenIddictValidationBuilder SetConfiguration(OpenIddictConfiguration configuration!!) - => Configure(options => options.Configuration = configuration); + public OpenIddictValidationBuilder SetConfiguration(OpenIddictConfiguration configuration) + { + if (configuration is null) + { + throw new ArgumentNullException(nameof(configuration)); + } + + return Configure(options => options.Configuration = configuration); + } /// /// Sets the client identifier client_id used when communicating @@ -381,8 +440,15 @@ public class OpenIddictValidationBuilder /// /// The issuer address. /// The . - public OpenIddictValidationBuilder SetIssuer(Uri address!!) - => Configure(options => options.Issuer = address); + public OpenIddictValidationBuilder SetIssuer(Uri address) + { + if (address is null) + { + throw new ArgumentNullException(nameof(address)); + } + + return Configure(options => options.Issuer = address); + } /// /// Sets the issuer address, which is used to determine the actual location of the diff --git a/src/OpenIddict.Validation/OpenIddictValidationConfiguration.cs b/src/OpenIddict.Validation/OpenIddictValidationConfiguration.cs index a8b12b02..1c15fd27 100644 --- a/src/OpenIddict.Validation/OpenIddictValidationConfiguration.cs +++ b/src/OpenIddict.Validation/OpenIddictValidationConfiguration.cs @@ -18,7 +18,7 @@ public class OpenIddictValidationConfiguration : IPostConfigureOptions _service = service; + => _service = service ?? throw new ArgumentNullException(nameof(service)); /// /// Populates the default OpenIddict validation options and ensures @@ -26,8 +26,13 @@ public class OpenIddictValidationConfiguration : IPostConfigureOptions /// The name of the options instance to configure, if applicable. /// The options instance to initialize. - public void PostConfigure(string name, OpenIddictValidationOptions options!!) + public void PostConfigure(string name, OpenIddictValidationOptions options) { + if (options is null) + { + throw new ArgumentNullException(nameof(options)); + } + if (options.JsonWebTokenHandler is null) { throw new InvalidOperationException(SR.GetResourceString(SR.ID0075)); @@ -39,7 +44,7 @@ public class OpenIddictValidationConfiguration : IPostConfigureOptions descriptor.ContextType == typeof(ApplyIntrospectionRequestContext))) { diff --git a/src/OpenIddict.Validation/OpenIddictValidationDispatcher.cs b/src/OpenIddict.Validation/OpenIddictValidationDispatcher.cs index f344e3cd..15703c72 100644 --- a/src/OpenIddict.Validation/OpenIddictValidationDispatcher.cs +++ b/src/OpenIddict.Validation/OpenIddictValidationDispatcher.cs @@ -19,17 +19,22 @@ public class OpenIddictValidationDispatcher : IOpenIddictValidationDispatcher /// Creates a new instance of the class. /// public OpenIddictValidationDispatcher( - ILogger logger!!, - IOptionsMonitor options!!, - IServiceProvider provider!!) + ILogger logger, + IOptionsMonitor options, + IServiceProvider provider) { - _logger = logger; - _options = options; - _provider = provider; + _logger = logger ?? throw new ArgumentNullException(nameof(logger)); + _options = options ?? throw new ArgumentNullException(nameof(options)); + _provider = provider ?? throw new ArgumentNullException(nameof(provider)); } - public async ValueTask DispatchAsync(TContext context!!) where TContext : BaseContext + public async ValueTask DispatchAsync(TContext context) where TContext : BaseContext { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + await foreach (var handler in GetHandlersAsync()) { try diff --git a/src/OpenIddict.Validation/OpenIddictValidationEvents.cs b/src/OpenIddict.Validation/OpenIddictValidationEvents.cs index 866c4c17..81b4883f 100644 --- a/src/OpenIddict.Validation/OpenIddictValidationEvents.cs +++ b/src/OpenIddict.Validation/OpenIddictValidationEvents.cs @@ -21,8 +21,8 @@ public static partial class OpenIddictValidationEvents /// /// Creates a new instance of the class. /// - protected BaseContext(OpenIddictValidationTransaction transaction!!) - => Transaction = transaction; + protected BaseContext(OpenIddictValidationTransaction transaction) + => Transaction = transaction ?? throw new ArgumentNullException(nameof(transaction)); /// /// Gets the environment associated with the current request being processed. diff --git a/src/OpenIddict.Validation/OpenIddictValidationExtensions.cs b/src/OpenIddict.Validation/OpenIddictValidationExtensions.cs index dad8538a..769380fe 100644 --- a/src/OpenIddict.Validation/OpenIddictValidationExtensions.cs +++ b/src/OpenIddict.Validation/OpenIddictValidationExtensions.cs @@ -22,8 +22,13 @@ public static class OpenIddictValidationExtensions /// The services builder used by OpenIddict to register new services. /// This extension can be safely called multiple times. /// The . - public static OpenIddictValidationBuilder AddValidation(this OpenIddictBuilder builder!!) + public static OpenIddictValidationBuilder AddValidation(this OpenIddictBuilder builder) { + if (builder is null) + { + throw new ArgumentNullException(nameof(builder)); + } + builder.Services.AddLogging(); builder.Services.AddOptions(); @@ -58,9 +63,19 @@ public static class OpenIddictValidationExtensions /// This extension can be safely called multiple times. /// The . public static OpenIddictBuilder AddValidation( - this OpenIddictBuilder builder!!, - Action configuration!!) + this OpenIddictBuilder builder, + Action configuration) { + if (builder is null) + { + throw new ArgumentNullException(nameof(builder)); + } + + if (configuration is null) + { + throw new ArgumentNullException(nameof(configuration)); + } + configuration(builder.AddValidation()); return builder; diff --git a/src/OpenIddict.Validation/OpenIddictValidationFactory.cs b/src/OpenIddict.Validation/OpenIddictValidationFactory.cs index 68d6ccb9..773f7e5c 100644 --- a/src/OpenIddict.Validation/OpenIddictValidationFactory.cs +++ b/src/OpenIddict.Validation/OpenIddictValidationFactory.cs @@ -18,11 +18,11 @@ public class OpenIddictValidationFactory : IOpenIddictValidationFactory /// Creates a new instance of the class. /// public OpenIddictValidationFactory( - ILogger logger!!, - IOptionsMonitor options!!) + ILogger logger, + IOptionsMonitor options) { - _logger = logger; - _options = options; + _logger = logger ?? throw new ArgumentNullException(nameof(logger)); + _options = options ?? throw new ArgumentNullException(nameof(options)); } public ValueTask CreateTransactionAsync() diff --git a/src/OpenIddict.Validation/OpenIddictValidationHandler.cs b/src/OpenIddict.Validation/OpenIddictValidationHandler.cs index 356faa41..c193e1c5 100644 --- a/src/OpenIddict.Validation/OpenIddictValidationHandler.cs +++ b/src/OpenIddict.Validation/OpenIddictValidationHandler.cs @@ -18,8 +18,8 @@ public class OpenIddictValidationHandler : IOpenIddictValidationHandle /// Creates a new event using the specified handler delegate. /// /// The event handler delegate. - public OpenIddictValidationHandler(Func handler!!) - => _handler = handler; + public OpenIddictValidationHandler(Func handler) + => _handler = handler ?? throw new ArgumentNullException(nameof(handler)); /// /// Processes the event. @@ -28,5 +28,6 @@ public class OpenIddictValidationHandler : IOpenIddictValidationHandle /// /// A that can be used to monitor the asynchronous operation. /// - public ValueTask HandleAsync(TContext context!!) => _handler(context); + public ValueTask HandleAsync(TContext context) + => _handler(context ?? throw new ArgumentNullException(nameof(context))); } diff --git a/src/OpenIddict.Validation/OpenIddictValidationHandlerDescriptor.cs b/src/OpenIddict.Validation/OpenIddictValidationHandlerDescriptor.cs index 3a952f29..7436f7a6 100644 --- a/src/OpenIddict.Validation/OpenIddictValidationHandlerDescriptor.cs +++ b/src/OpenIddict.Validation/OpenIddictValidationHandlerDescriptor.cs @@ -72,8 +72,13 @@ public class OpenIddictValidationHandlerDescriptor /// /// The event handler filter type. /// The builder instance, so that calls can be easily chained. - public Builder AddFilter(Type type!!) + public Builder AddFilter(Type type) { + if (type is null) + { + throw new ArgumentNullException(nameof(type)); + } + if (!typeof(IOpenIddictValidationHandlerFilter<>).MakeGenericType(typeof(TContext)).IsAssignableFrom(type)) { throw new InvalidOperationException(SR.GetResourceString(SR.ID0104)); @@ -99,8 +104,13 @@ public class OpenIddictValidationHandlerDescriptor /// The existing descriptor properties are copied from. /// All the properties previously set on this instance are automatically replaced. /// The builder instance, so that calls can be easily chained. - public Builder Import(OpenIddictValidationHandlerDescriptor descriptor!!) + public Builder Import(OpenIddictValidationHandlerDescriptor descriptor) { + if (descriptor is null) + { + throw new ArgumentNullException(nameof(descriptor)); + } + if (descriptor.ContextType != typeof(TContext)) { throw new InvalidOperationException(SR.GetResourceString(SR.ID0284)); @@ -120,8 +130,13 @@ public class OpenIddictValidationHandlerDescriptor /// /// The service descriptor. /// The builder instance, so that calls can be easily chained. - public Builder SetServiceDescriptor(ServiceDescriptor descriptor!!) + public Builder SetServiceDescriptor(ServiceDescriptor descriptor) { + if (descriptor is null) + { + throw new ArgumentNullException(nameof(descriptor)); + } + var type = descriptor.ServiceType; if (!typeof(IOpenIddictValidationHandler<>).MakeGenericType(typeof(TContext)).IsAssignableFrom(type)) { @@ -167,8 +182,15 @@ public class OpenIddictValidationHandlerDescriptor /// /// The handler instance. /// The builder instance, so that calls can be easily chained. - public Builder UseInlineHandler(Func handler!!) - => UseSingletonHandler(new OpenIddictValidationHandler(handler)); + public Builder UseInlineHandler(Func handler) + { + if (handler is null) + { + throw new ArgumentNullException(nameof(handler)); + } + + return UseSingletonHandler(new OpenIddictValidationHandler(handler)); + } /// /// Configures the descriptor to use the specified scoped handler. @@ -186,10 +208,17 @@ public class OpenIddictValidationHandlerDescriptor /// The handler type. /// The factory used to create the handler. /// The builder instance, so that calls can be easily chained. - public Builder UseScopedHandler(Func factory!!) + public Builder UseScopedHandler(Func factory) where THandler : IOpenIddictValidationHandler - => SetServiceDescriptor(new ServiceDescriptor( + { + if (factory is null) + { + throw new ArgumentNullException(nameof(factory)); + } + + return SetServiceDescriptor(new ServiceDescriptor( typeof(THandler), factory, ServiceLifetime.Scoped)); + } /// /// Configures the descriptor to use the specified singleton handler. @@ -207,10 +236,17 @@ public class OpenIddictValidationHandlerDescriptor /// The handler type. /// The factory used to create the handler. /// The builder instance, so that calls can be easily chained. - public Builder UseSingletonHandler(Func factory!!) + public Builder UseSingletonHandler(Func factory) where THandler : IOpenIddictValidationHandler - => SetServiceDescriptor(new ServiceDescriptor( + { + if (factory is null) + { + throw new ArgumentNullException(nameof(factory)); + } + + return SetServiceDescriptor(new ServiceDescriptor( typeof(THandler), factory, ServiceLifetime.Singleton)); + } /// /// Configures the descriptor to use the specified singleton handler. @@ -218,9 +254,16 @@ public class OpenIddictValidationHandlerDescriptor /// The handler type. /// The handler instance. /// The builder instance, so that calls can be easily chained. - public Builder UseSingletonHandler(THandler handler!!) + public Builder UseSingletonHandler(THandler handler) where THandler : IOpenIddictValidationHandler - => SetServiceDescriptor(new ServiceDescriptor(typeof(THandler), handler)); + { + if (handler is null) + { + throw new ArgumentNullException(nameof(handler)); + } + + return SetServiceDescriptor(new ServiceDescriptor(typeof(THandler), handler)); + } /// /// Build a new descriptor instance, based on the parameters that were previously set. diff --git a/src/OpenIddict.Validation/OpenIddictValidationHandlerFilters.cs b/src/OpenIddict.Validation/OpenIddictValidationHandlerFilters.cs index 7de184f0..f1b07489 100644 --- a/src/OpenIddict.Validation/OpenIddictValidationHandlerFilters.cs +++ b/src/OpenIddict.Validation/OpenIddictValidationHandlerFilters.cs @@ -16,8 +16,15 @@ public static class OpenIddictValidationHandlerFilters /// public class RequireAccessTokenExtracted : IOpenIddictValidationHandlerFilter { - public ValueTask IsActiveAsync(ProcessAuthenticationContext context!!) - => new(context.ExtractAccessToken); + public ValueTask IsActiveAsync(ProcessAuthenticationContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(context.ExtractAccessToken); + } } /// @@ -25,8 +32,15 @@ public static class OpenIddictValidationHandlerFilters /// public class RequireAccessTokenValidated : IOpenIddictValidationHandlerFilter { - public ValueTask IsActiveAsync(ProcessAuthenticationContext context!!) - => new(context.ValidateAccessToken); + public ValueTask IsActiveAsync(ProcessAuthenticationContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(context.ValidateAccessToken); + } } /// @@ -34,8 +48,15 @@ public static class OpenIddictValidationHandlerFilters /// public class RequireAuthorizationEntryValidationEnabled : IOpenIddictValidationHandlerFilter { - public ValueTask IsActiveAsync(BaseContext context!!) - => new(context.Options.EnableAuthorizationEntryValidation); + public ValueTask IsActiveAsync(BaseContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(context.Options.EnableAuthorizationEntryValidation); + } } /// @@ -43,8 +64,15 @@ public static class OpenIddictValidationHandlerFilters /// public class RequireLocalValidation : IOpenIddictValidationHandlerFilter { - public ValueTask IsActiveAsync(BaseContext context!!) - => new(context.Options.ValidationType is OpenIddictValidationType.Direct); + public ValueTask IsActiveAsync(BaseContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(context.Options.ValidationType == OpenIddictValidationType.Direct); + } } /// @@ -52,8 +80,15 @@ public static class OpenIddictValidationHandlerFilters /// public class RequireIntrospectionValidation : IOpenIddictValidationHandlerFilter { - public ValueTask IsActiveAsync(BaseContext context!!) - => new(context.Options.ValidationType is OpenIddictValidationType.Introspection); + public ValueTask IsActiveAsync(BaseContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(context.Options.ValidationType == OpenIddictValidationType.Introspection); + } } /// @@ -61,7 +96,14 @@ public static class OpenIddictValidationHandlerFilters /// public class RequireTokenEntryValidationEnabled : IOpenIddictValidationHandlerFilter { - public ValueTask IsActiveAsync(BaseContext context!!) - => new(context.Options.EnableTokenEntryValidation); + public ValueTask IsActiveAsync(BaseContext context) + { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + + return new(context.Options.EnableTokenEntryValidation); + } } } diff --git a/src/OpenIddict.Validation/OpenIddictValidationHandlers.Discovery.cs b/src/OpenIddict.Validation/OpenIddictValidationHandlers.Discovery.cs index e291a0ec..e316d05a 100644 --- a/src/OpenIddict.Validation/OpenIddictValidationHandlers.Discovery.cs +++ b/src/OpenIddict.Validation/OpenIddictValidationHandlers.Discovery.cs @@ -48,8 +48,13 @@ public static partial class OpenIddictValidationHandlers .Build(); /// - public ValueTask HandleAsync(HandleConfigurationResponseContext context!!) + public ValueTask HandleAsync(HandleConfigurationResponseContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + foreach (var parameter in context.Response.GetParameters()) { if (!ValidateParameterType(parameter.Key, parameter.Value)) @@ -119,8 +124,13 @@ public static partial class OpenIddictValidationHandlers .Build(); /// - public ValueTask HandleAsync(HandleConfigurationResponseContext context!!) + public ValueTask HandleAsync(HandleConfigurationResponseContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // The issuer returned in the discovery document must exactly match the URL used to access it. // See https://openid.net/specs/openid-connect-discovery-1_0.html#ProviderConfigurationValidation. var issuer = (string?) context.Response[Metadata.Issuer]; @@ -166,8 +176,13 @@ public static partial class OpenIddictValidationHandlers .Build(); /// - public ValueTask HandleAsync(HandleConfigurationResponseContext context!!) + public ValueTask HandleAsync(HandleConfigurationResponseContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // Note: the jwks_uri node is required by the OpenID Connect discovery specification. // See https://openid.net/specs/openid-connect-discovery-1_0.html#ProviderConfigurationValidation. var address = (string?) context.Response[Metadata.JwksUri]; @@ -213,8 +228,13 @@ public static partial class OpenIddictValidationHandlers .Build(); /// - public ValueTask HandleAsync(HandleConfigurationResponseContext context!!) + public ValueTask HandleAsync(HandleConfigurationResponseContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var address = (string?) context.Response[Metadata.IntrospectionEndpoint]; if (!string.IsNullOrEmpty(address)) { @@ -252,8 +272,13 @@ public static partial class OpenIddictValidationHandlers .Build(); /// - public ValueTask HandleAsync(HandleConfigurationResponseContext context!!) + public ValueTask HandleAsync(HandleConfigurationResponseContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // Resolve the client authentication methods supported by the introspection endpoint, if available. var methods = context.Response[Metadata.IntrospectionEndpointAuthMethodsSupported]?.GetUnnamedParameters(); if (methods is { Count: > 0 }) @@ -289,8 +314,13 @@ public static partial class OpenIddictValidationHandlers .Build(); /// - public ValueTask HandleAsync(HandleCryptographyResponseContext context!!) + public ValueTask HandleAsync(HandleCryptographyResponseContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + foreach (var parameter in context.Response.GetParameters()) { if (!ValidateParameterType(parameter.Key, parameter.Value)) @@ -354,8 +384,13 @@ public static partial class OpenIddictValidationHandlers .Build(); /// - public ValueTask HandleAsync(HandleCryptographyResponseContext context!!) + public ValueTask HandleAsync(HandleCryptographyResponseContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var keys = context.Response[JsonWebKeySetParameterNames.Keys]?.GetUnnamedParameters(); if (keys is not { Count: > 0 }) { diff --git a/src/OpenIddict.Validation/OpenIddictValidationHandlers.Introspection.cs b/src/OpenIddict.Validation/OpenIddictValidationHandlers.Introspection.cs index e49de34e..92ee31f1 100644 --- a/src/OpenIddict.Validation/OpenIddictValidationHandlers.Introspection.cs +++ b/src/OpenIddict.Validation/OpenIddictValidationHandlers.Introspection.cs @@ -48,8 +48,13 @@ public static partial class OpenIddictValidationHandlers .Build(); /// - public ValueTask HandleAsync(PrepareIntrospectionRequestContext context!!) + public ValueTask HandleAsync(PrepareIntrospectionRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + context.Request.ClientId = context.Options.ClientId; context.Request.ClientSecret = context.Options.ClientSecret; @@ -73,8 +78,13 @@ public static partial class OpenIddictValidationHandlers .Build(); /// - public ValueTask HandleAsync(PrepareIntrospectionRequestContext context!!) + public ValueTask HandleAsync(PrepareIntrospectionRequestContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + context.Request.Token = context.Token; context.Request.TokenTypeHint = context.TokenTypeHint; @@ -98,8 +108,13 @@ public static partial class OpenIddictValidationHandlers .Build(); /// - public ValueTask HandleAsync(HandleIntrospectionResponseContext context!!) + public ValueTask HandleAsync(HandleIntrospectionResponseContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + foreach (var parameter in context.Response.GetParameters()) { if (!ValidateParameterType(parameter.Key, parameter.Value)) @@ -177,8 +192,13 @@ public static partial class OpenIddictValidationHandlers .Build(); /// - public ValueTask HandleAsync(HandleIntrospectionResponseContext context!!) + public ValueTask HandleAsync(HandleIntrospectionResponseContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // Note: the introspection specification requires that server return "active: false" instead of a proper // OAuth 2.0 error when the token is invalid, expired, revoked or invalid for any other reason. // While OpenIddict's server can be tweaked to return a proper error (by removing NormalizeErrorResponse) @@ -225,8 +245,13 @@ public static partial class OpenIddictValidationHandlers .Build(); /// - public ValueTask HandleAsync(HandleIntrospectionResponseContext context!!) + public ValueTask HandleAsync(HandleIntrospectionResponseContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // The issuer claim is optional. If it's not null or empty, validate it to // ensure it matches the issuer registered in the server configuration. var issuer = (string?) context.Response[Claims.Issuer]; @@ -273,8 +298,13 @@ public static partial class OpenIddictValidationHandlers .Build(); /// - public ValueTask HandleAsync(HandleIntrospectionResponseContext context!!) + public ValueTask HandleAsync(HandleIntrospectionResponseContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // OpenIddict-based authorization servers always return the actual token type using // the special "token_usage" claim, that helps resource servers determine whether the // introspected token is of the expected type and prevent token substitution attacks. @@ -327,8 +357,13 @@ public static partial class OpenIddictValidationHandlers .Build(); /// - public async ValueTask HandleAsync(HandleIntrospectionResponseContext context!!) + public async ValueTask HandleAsync(HandleIntrospectionResponseContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var configuration = await context.Options.ConfigurationManager.GetConfigurationAsync(default) ?? throw new InvalidOperationException(SR.GetResourceString(SR.ID0140)); diff --git a/src/OpenIddict.Validation/OpenIddictValidationHandlers.Protection.cs b/src/OpenIddict.Validation/OpenIddictValidationHandlers.Protection.cs index 56711cd3..483fcf10 100644 --- a/src/OpenIddict.Validation/OpenIddictValidationHandlers.Protection.cs +++ b/src/OpenIddict.Validation/OpenIddictValidationHandlers.Protection.cs @@ -51,8 +51,13 @@ public static partial class OpenIddictValidationHandlers .Build(); /// - public async ValueTask HandleAsync(ValidateTokenContext context!!) + public async ValueTask HandleAsync(ValidateTokenContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + var configuration = await context.Options.ConfigurationManager.GetConfigurationAsync(default) ?? throw new InvalidOperationException(SR.GetResourceString(SR.ID0140)); @@ -124,8 +129,8 @@ public static partial class OpenIddictValidationHandlers public ValidateReferenceTokenIdentifier() => throw new InvalidOperationException(SR.GetResourceString(SR.ID0139)); - public ValidateReferenceTokenIdentifier(IOpenIddictTokenManager tokenManager!!) - => _tokenManager = tokenManager; + public ValidateReferenceTokenIdentifier(IOpenIddictTokenManager tokenManager) + => _tokenManager = tokenManager ?? throw new ArgumentNullException(nameof(tokenManager)); /// /// Gets the default descriptor definition assigned to this handler. @@ -140,8 +145,13 @@ public static partial class OpenIddictValidationHandlers .Build(); /// - public async ValueTask HandleAsync(ValidateTokenContext context!!) + public async ValueTask HandleAsync(ValidateTokenContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // Reference tokens are base64url-encoded payloads of exactly 256 bits (generated using a // crypto-secure RNG). If the token length differs, the token cannot be a reference token. if (context.Token.Length != 43) @@ -203,8 +213,13 @@ public static partial class OpenIddictValidationHandlers .Build(); /// - public async ValueTask HandleAsync(ValidateTokenContext context!!) + public async ValueTask HandleAsync(ValidateTokenContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // If a principal was already attached, don't overwrite it. if (context.Principal is not null) { @@ -278,7 +293,7 @@ public static partial class OpenIddictValidationHandlers private readonly OpenIddictValidationService _service; public IntrospectToken(OpenIddictValidationService service) - => _service = service; + => _service = service ?? throw new ArgumentNullException(nameof(service)); /// /// Gets the default descriptor definition assigned to this handler. @@ -292,8 +307,13 @@ public static partial class OpenIddictValidationHandlers .Build(); /// - public async ValueTask HandleAsync(ValidateTokenContext context!!) + public async ValueTask HandleAsync(ValidateTokenContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // If a principal was already attached, don't overwrite it. if (context.Principal is not null) { @@ -390,8 +410,13 @@ public static partial class OpenIddictValidationHandlers .Build(); /// - public ValueTask HandleAsync(ValidateTokenContext context!!) + public ValueTask HandleAsync(ValidateTokenContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + if (context.Principal is null) { return default; @@ -430,8 +455,13 @@ public static partial class OpenIddictValidationHandlers .Build(); /// - public ValueTask HandleAsync(ValidateTokenContext context!!) + public ValueTask HandleAsync(ValidateTokenContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + if (context.Principal is null) { return default; @@ -522,8 +552,8 @@ public static partial class OpenIddictValidationHandlers public RestoreReferenceTokenProperties() => throw new InvalidOperationException(SR.GetResourceString(SR.ID0139)); - public RestoreReferenceTokenProperties(IOpenIddictTokenManager tokenManager!!) - => _tokenManager = tokenManager; + public RestoreReferenceTokenProperties(IOpenIddictTokenManager tokenManager) + => _tokenManager = tokenManager ?? throw new ArgumentNullException(nameof(tokenManager)); /// /// Gets the default descriptor definition assigned to this handler. @@ -538,8 +568,13 @@ public static partial class OpenIddictValidationHandlers .Build(); /// - public async ValueTask HandleAsync(ValidateTokenContext context!!) + public async ValueTask HandleAsync(ValidateTokenContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + if (context.Principal is null || string.IsNullOrEmpty(context.TokenId)) { return; @@ -573,8 +608,13 @@ public static partial class OpenIddictValidationHandlers .Build(); /// - public ValueTask HandleAsync(ValidateTokenContext context!!) + public ValueTask HandleAsync(ValidateTokenContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + if (context.Principal is null) { context.Reject( @@ -620,8 +660,13 @@ public static partial class OpenIddictValidationHandlers .Build(); /// - public ValueTask HandleAsync(ValidateTokenContext context!!) + public ValueTask HandleAsync(ValidateTokenContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.Principal is { Identity: ClaimsIdentity }, SR.GetResourceString(SR.ID4006)); var date = context.Principal.GetExpirationDate(); @@ -658,8 +703,13 @@ public static partial class OpenIddictValidationHandlers .Build(); /// - public ValueTask HandleAsync(ValidateTokenContext context!!) + public ValueTask HandleAsync(ValidateTokenContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.Principal is { Identity: ClaimsIdentity }, SR.GetResourceString(SR.ID4006)); // If no explicit audience has been configured, @@ -711,8 +761,8 @@ public static partial class OpenIddictValidationHandlers public ValidateTokenEntry() => throw new InvalidOperationException(SR.GetResourceString(SR.ID0139)); - public ValidateTokenEntry(IOpenIddictTokenManager tokenManager!!) - => _tokenManager = tokenManager; + public ValidateTokenEntry(IOpenIddictTokenManager tokenManager) + => _tokenManager = tokenManager ?? throw new ArgumentNullException(nameof(tokenManager)); /// /// Gets the default descriptor definition assigned to this handler. @@ -727,8 +777,13 @@ public static partial class OpenIddictValidationHandlers .Build(); /// - public async ValueTask HandleAsync(ValidateTokenContext context!!) + public async ValueTask HandleAsync(ValidateTokenContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.Principal is { Identity: ClaimsIdentity }, SR.GetResourceString(SR.ID4006)); var identifier = context.Principal.GetTokenId(); @@ -770,8 +825,8 @@ public static partial class OpenIddictValidationHandlers public ValidateAuthorizationEntry() => throw new InvalidOperationException(SR.GetResourceString(SR.ID0142)); - public ValidateAuthorizationEntry(IOpenIddictAuthorizationManager authorizationManager!!) - => _authorizationManager = authorizationManager; + public ValidateAuthorizationEntry(IOpenIddictAuthorizationManager authorizationManager) + => _authorizationManager = authorizationManager ?? throw new ArgumentNullException(nameof(authorizationManager)); /// /// Gets the default descriptor definition assigned to this handler. @@ -786,8 +841,13 @@ public static partial class OpenIddictValidationHandlers .Build(); /// - public async ValueTask HandleAsync(ValidateTokenContext context!!) + public async ValueTask HandleAsync(ValidateTokenContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + Debug.Assert(context.Principal is { Identity: ClaimsIdentity }, SR.GetResourceString(SR.ID4006)); var identifier = context.Principal.GetAuthorizationId(); diff --git a/src/OpenIddict.Validation/OpenIddictValidationHandlers.cs b/src/OpenIddict.Validation/OpenIddictValidationHandlers.cs index 53bdb4f2..8c56d3cb 100644 --- a/src/OpenIddict.Validation/OpenIddictValidationHandlers.cs +++ b/src/OpenIddict.Validation/OpenIddictValidationHandlers.cs @@ -45,8 +45,13 @@ public static partial class OpenIddictValidationHandlers .Build(); /// - public ValueTask HandleAsync(ProcessAuthenticationContext context!!) + public ValueTask HandleAsync(ProcessAuthenticationContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + (context.ExtractAccessToken, context.RequireAccessToken, context.ValidateAccessToken) = context.EndpointType switch { // The validation handler is responsible for validating access tokens for endpoints @@ -85,8 +90,13 @@ public static partial class OpenIddictValidationHandlers .Build(); /// - public ValueTask HandleAsync(ProcessAuthenticationContext context!!) + public ValueTask HandleAsync(ProcessAuthenticationContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + if (context.RequireAccessToken && string.IsNullOrEmpty(context.AccessToken)) { context.Reject( @@ -108,8 +118,8 @@ public static partial class OpenIddictValidationHandlers { private readonly IOpenIddictValidationDispatcher _dispatcher; - public ValidateAccessToken(IOpenIddictValidationDispatcher dispatcher!!) - => _dispatcher = dispatcher; + public ValidateAccessToken(IOpenIddictValidationDispatcher dispatcher) + => _dispatcher = dispatcher ?? throw new ArgumentNullException(nameof(dispatcher)); /// /// Gets the default descriptor definition assigned to this handler. @@ -123,8 +133,13 @@ public static partial class OpenIddictValidationHandlers .Build(); /// - public async ValueTask HandleAsync(ProcessAuthenticationContext context!!) + public async ValueTask HandleAsync(ProcessAuthenticationContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + if (context.AccessTokenPrincipal is not null || string.IsNullOrEmpty(context.AccessToken)) { return; @@ -179,8 +194,13 @@ public static partial class OpenIddictValidationHandlers .Build(); /// - public ValueTask HandleAsync(ProcessChallengeContext context!!) + public ValueTask HandleAsync(ProcessChallengeContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + // If an error was explicitly set by the application, don't override it. if (!string.IsNullOrEmpty(context.Response.Error) || !string.IsNullOrEmpty(context.Response.ErrorDescription) || @@ -233,8 +253,13 @@ public static partial class OpenIddictValidationHandlers .Build(); /// - public ValueTask HandleAsync(ProcessErrorContext context!!) + public ValueTask HandleAsync(ProcessErrorContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + context.Response.Error = context.Error; context.Response.ErrorDescription = context.ErrorDescription; context.Response.ErrorUri = context.ErrorUri; @@ -267,8 +292,13 @@ public static partial class OpenIddictValidationHandlers .Build(); /// - public ValueTask HandleAsync(TContext context!!) + public ValueTask HandleAsync(TContext context) { + if (context is null) + { + throw new ArgumentNullException(nameof(context)); + } + if (!string.IsNullOrEmpty(context.Transaction.Response?.Error)) { context.Reject( diff --git a/src/OpenIddict.Validation/OpenIddictValidationHelpers.cs b/src/OpenIddict.Validation/OpenIddictValidationHelpers.cs index 9ebc7297..6d869e9d 100644 --- a/src/OpenIddict.Validation/OpenIddictValidationHelpers.cs +++ b/src/OpenIddict.Validation/OpenIddictValidationHelpers.cs @@ -19,8 +19,13 @@ public static class OpenIddictValidationHelpers /// The property name. /// The property value or if it couldn't be found. public static TProperty? GetProperty( - this OpenIddictValidationTransaction transaction!!, string name) where TProperty : class + this OpenIddictValidationTransaction transaction, string name) where TProperty : class { + if (transaction is null) + { + throw new ArgumentNullException(nameof(transaction)); + } + if (string.IsNullOrEmpty(name)) { throw new ArgumentException(SR.GetResourceString(SR.ID0106), nameof(name)); @@ -43,9 +48,14 @@ public static class OpenIddictValidationHelpers /// The property value. /// The validation transaction, so that calls can be easily chained. public static OpenIddictValidationTransaction SetProperty( - this OpenIddictValidationTransaction transaction!!, + this OpenIddictValidationTransaction transaction, string name, TProperty? value) where TProperty : class { + if (transaction is null) + { + throw new ArgumentNullException(nameof(transaction)); + } + if (string.IsNullOrEmpty(name)) { throw new ArgumentException(SR.GetResourceString(SR.ID0106), nameof(name)); diff --git a/src/OpenIddict.Validation/OpenIddictValidationOptions.cs b/src/OpenIddict.Validation/OpenIddictValidationOptions.cs index 53bc6619..fdfa679c 100644 --- a/src/OpenIddict.Validation/OpenIddictValidationOptions.cs +++ b/src/OpenIddict.Validation/OpenIddictValidationOptions.cs @@ -44,7 +44,7 @@ public class OpenIddictValidationOptions /// Note: the list is automatically sorted based on the order assigned to each handler descriptor. /// As such, it MUST NOT be mutated after options initialization to preserve the exact order. /// - public List Handlers { get; } = new(DefaultHandlers); + public List Handlers { get; } = new(OpenIddictValidationHandlers.DefaultHandlers); /// /// Gets or sets the type of validation used by the OpenIddict validation services. diff --git a/src/OpenIddict.Validation/OpenIddictValidationRetriever.cs b/src/OpenIddict.Validation/OpenIddictValidationRetriever.cs index be390cb4..26d07900 100644 --- a/src/OpenIddict.Validation/OpenIddictValidationRetriever.cs +++ b/src/OpenIddict.Validation/OpenIddictValidationRetriever.cs @@ -16,8 +16,8 @@ public class OpenIddictValidationRetriever : IConfigurationRetriever class. /// /// The validation service. - public OpenIddictValidationRetriever(OpenIddictValidationService service!!) - => _service = service; + public OpenIddictValidationRetriever(OpenIddictValidationService service) + => _service = service ?? throw new ArgumentNullException(nameof(service)); /// /// Retrieves the OpenID Connect server configuration from the specified address. @@ -26,8 +26,7 @@ public class OpenIddictValidationRetriever : IConfigurationRetrieverThe retriever used by IdentityModel. /// The that can be used to abort the operation. /// The OpenID Connect server configuration retrieved from the remote server. - async Task IConfigurationRetriever.GetConfigurationAsync( - string address, IDocumentRetriever retriever, CancellationToken cancel) + async Task IConfigurationRetriever.GetConfigurationAsync(string address, IDocumentRetriever retriever, CancellationToken cancel) { if (string.IsNullOrEmpty(address)) { diff --git a/src/OpenIddict.Validation/OpenIddictValidationService.cs b/src/OpenIddict.Validation/OpenIddictValidationService.cs index 1117ef42..dd8f473d 100644 --- a/src/OpenIddict.Validation/OpenIddictValidationService.cs +++ b/src/OpenIddict.Validation/OpenIddictValidationService.cs @@ -19,8 +19,8 @@ public class OpenIddictValidationService /// Creates a new instance of the class. /// /// The service provider. - public OpenIddictValidationService(IServiceProvider provider!!) - => _provider = provider; + public OpenIddictValidationService(IServiceProvider provider) + => _provider = provider ?? throw new ArgumentNullException(nameof(provider)); /// /// Retrieves the OpenID Connect server configuration from the specified address. @@ -28,8 +28,13 @@ public class OpenIddictValidationService /// The address of the remote metadata endpoint. /// The that can be used to abort the operation. /// The OpenID Connect server configuration retrieved from the remote server. - public async ValueTask GetConfigurationAsync(Uri address!!, CancellationToken cancellationToken = default) + public async ValueTask GetConfigurationAsync(Uri address, CancellationToken cancellationToken = default) { + if (address is null) + { + throw new ArgumentNullException(nameof(address)); + } + if (!address.IsAbsoluteUri) { throw new ArgumentException(SR.GetResourceString(SR.ID0144), nameof(address)); @@ -162,8 +167,13 @@ public class OpenIddictValidationService /// The address of the remote metadata endpoint. /// The that can be used to abort the operation. /// The security keys retrieved from the remote server. - public async ValueTask GetSecurityKeysAsync(Uri address!!, CancellationToken cancellationToken = default) + public async ValueTask GetSecurityKeysAsync(Uri address, CancellationToken cancellationToken = default) { + if (address is null) + { + throw new ArgumentNullException(nameof(address)); + } + if (!address.IsAbsoluteUri) { throw new ArgumentException(SR.GetResourceString(SR.ID0144), nameof(address)); @@ -309,8 +319,13 @@ public class OpenIddictValidationService /// The that can be used to abort the operation. /// The claims principal created from the claim retrieved from the remote server. public async ValueTask IntrospectTokenAsync( - Uri address!!, string token, string? hint, CancellationToken cancellationToken = default) + Uri address, string token, string? hint, CancellationToken cancellationToken = default) { + if (address is null) + { + throw new ArgumentNullException(nameof(address)); + } + if (!address.IsAbsoluteUri || !address.IsWellFormedOriginalString()) { throw new ArgumentException(SR.GetResourceString(SR.ID0144), nameof(address)); diff --git a/test/OpenIddict.Server.IntegrationTests/OpenIddictServerIntegrationTestClient.cs b/test/OpenIddict.Server.IntegrationTests/OpenIddictServerIntegrationTestClient.cs index 25b447a8..ea22a65e 100644 --- a/test/OpenIddict.Server.IntegrationTests/OpenIddictServerIntegrationTestClient.cs +++ b/test/OpenIddict.Server.IntegrationTests/OpenIddictServerIntegrationTestClient.cs @@ -40,10 +40,10 @@ public class OpenIddictServerIntegrationTestClient : IAsyncDisposable /// /// The HTTP client used to communicate with the OpenID Connect server. /// The HTML parser used to parse the responses returned by the OpenID Connect server. - public OpenIddictServerIntegrationTestClient(HttpClient client!!, HtmlParser parser!!) + public OpenIddictServerIntegrationTestClient(HttpClient client, HtmlParser parser) { - HttpClient = client; - HtmlParser = parser; + HttpClient = client ?? throw new ArgumentNullException(nameof(client)); + HtmlParser = parser ?? throw new ArgumentNullException(nameof(parser)); } /// @@ -83,8 +83,13 @@ public class OpenIddictServerIntegrationTestClient : IAsyncDisposable /// The endpoint to which the request is sent. /// The OpenID Connect request to send. /// The OpenID Connect response returned by the server. - public Task GetAsync(string uri, OpenIddictRequest request!!) + public Task GetAsync(string uri, OpenIddictRequest request) { + if (request is null) + { + throw new ArgumentNullException(nameof(request)); + } + if (string.IsNullOrEmpty(uri)) { throw new ArgumentException("The URL cannot be null or empty.", nameof(uri)); @@ -110,8 +115,13 @@ public class OpenIddictServerIntegrationTestClient : IAsyncDisposable /// The endpoint to which the request is sent. /// The OpenID Connect request to send. /// The OpenID Connect response returned by the server. - public Task PostAsync(string uri, OpenIddictRequest request!!) + public Task PostAsync(string uri, OpenIddictRequest request) { + if (request is null) + { + throw new ArgumentNullException(nameof(request)); + } + if (string.IsNullOrEmpty(uri)) { throw new ArgumentException("The URL cannot be null or empty.", nameof(uri)); @@ -138,8 +148,13 @@ public class OpenIddictServerIntegrationTestClient : IAsyncDisposable /// The endpoint to which the request is sent. /// The OpenID Connect request to send. /// The OpenID Connect response returned by the server. - public Task SendAsync(string method, string uri, OpenIddictRequest request!!) + public Task SendAsync(string method, string uri, OpenIddictRequest request) { + if (request is null) + { + throw new ArgumentNullException(nameof(request)); + } + if (string.IsNullOrEmpty(method)) { throw new ArgumentException("The HTTP method cannot be null or empty.", nameof(method)); @@ -161,8 +176,18 @@ public class OpenIddictServerIntegrationTestClient : IAsyncDisposable /// The endpoint to which the request is sent. /// The OpenID Connect request to send. /// The OpenID Connect response returned by the server. - public Task SendAsync(HttpMethod method!!, string uri, OpenIddictRequest request!!) + public Task SendAsync(HttpMethod method, string uri, OpenIddictRequest request) { + if (method is null) + { + throw new ArgumentNullException(nameof(method)); + } + + if (request is null) + { + throw new ArgumentNullException(nameof(request)); + } + if (string.IsNullOrEmpty(uri)) { throw new ArgumentException("The URL cannot be null or empty.", nameof(uri)); @@ -179,8 +204,23 @@ public class OpenIddictServerIntegrationTestClient : IAsyncDisposable /// The endpoint to which the request is sent. /// The OpenID Connect request to send. /// The OpenID Connect response returned by the server. - public virtual async Task SendAsync(HttpMethod method!!, Uri uri!!, OpenIddictRequest request!!) + public virtual async Task SendAsync(HttpMethod method, Uri uri, OpenIddictRequest request) { + if (method is null) + { + throw new ArgumentNullException(nameof(method)); + } + + if (uri is null) + { + throw new ArgumentNullException(nameof(uri)); + } + + if (request is null) + { + throw new ArgumentNullException(nameof(request)); + } + if (HttpClient.BaseAddress is null && !uri.IsAbsoluteUri) { throw new ArgumentException("The address cannot be a relative URI when no base address " +