diff --git a/sandbox/OpenIddict.Sandbox.AspNet.Client/Controllers/AuthenticationController.cs b/sandbox/OpenIddict.Sandbox.AspNet.Client/Controllers/AuthenticationController.cs index a27103b30..01b3f3f6e 100644 --- a/sandbox/OpenIddict.Sandbox.AspNet.Client/Controllers/AuthenticationController.cs +++ b/sandbox/OpenIddict.Sandbox.AspNet.Client/Controllers/AuthenticationController.cs @@ -31,7 +31,7 @@ public async Task LogIn(string provider, string returnUrl) // the user is directly redirected to GitHub (in this case, no login page is shown). if (string.Equals(provider, "Local+GitHub", StringComparison.Ordinal)) { - var properties = new AuthenticationProperties(new Dictionary + var properties = new AuthenticationProperties(new Dictionary { // Note: when only one client is registered in the client options, // specifying the issuer URI or the provider name is not required. @@ -61,7 +61,7 @@ public async Task LogIn(string provider, string returnUrl) return new HttpStatusCodeResult(400); } - var properties = new AuthenticationProperties(new Dictionary + var properties = new AuthenticationProperties(new Dictionary { // Note: when only one client is registered in the client options, // specifying the issuer URI or the provider name is not required. @@ -86,7 +86,7 @@ public async Task LogOut(string returnUrl) // Retrieve the identity stored in the local authentication cookie. If it's not available, // this indicate that the user is already logged out locally (or has not logged in yet). var result = await context.Authentication.AuthenticateAsync(CookieAuthenticationDefaults.AuthenticationType); - if (result is not { Identity: ClaimsIdentity identity }) + if (result is not { Identity: ClaimsIdentity { IsAuthenticated: true } identity }) { // Only allow local return URLs to prevent open redirect attacks. return Redirect(Url.IsLocalUrl(returnUrl) ? returnUrl : "/"); @@ -100,7 +100,7 @@ public async Task LogOut(string returnUrl) if (identity.FindFirst(Claims.Private.RegistrationId)?.Value is string identifier && await _service.GetServerConfigurationByRegistrationIdAsync(identifier) is { EndSessionEndpoint: Uri }) { - var properties = new AuthenticationProperties(new Dictionary + var properties = new AuthenticationProperties(new Dictionary { [OpenIddictClientOwinConstants.Properties.RegistrationId] = identifier, @@ -161,7 +161,7 @@ public async Task LogInCallback() // Such identities cannot be used as-is to build an authentication cookie in ASP.NET (as the // antiforgery stack requires at least a name claim to bind CSRF cookies to the user's identity) but // the access/refresh tokens can be retrieved using result.Properties.GetTokens() to make API calls. - if (result.Identity is not ClaimsIdentity { IsAuthenticated: true }) + if (result is not { Identity.IsAuthenticated: true }) { throw new InvalidOperationException("The external authorization data cannot be used for authentication."); } @@ -234,6 +234,6 @@ public async Task LogOutCallback() // to the authorization server. Applications that prefer delaying the removal of the local cookie can // remove the corresponding code from the logout action and remove the authentication cookie in this action. - return Redirect(result.Properties.RedirectUri ?? "/"); + return Redirect(result?.Properties?.RedirectUri ?? "/"); } } diff --git a/sandbox/OpenIddict.Sandbox.AspNet.Server/Controllers/AuthenticationController.cs b/sandbox/OpenIddict.Sandbox.AspNet.Server/Controllers/AuthenticationController.cs index f40c1fd83..c512e6744 100644 --- a/sandbox/OpenIddict.Sandbox.AspNet.Server/Controllers/AuthenticationController.cs +++ b/sandbox/OpenIddict.Sandbox.AspNet.Server/Controllers/AuthenticationController.cs @@ -51,7 +51,7 @@ public async Task LogInCallback() // Such identities cannot be used as-is to build an authentication cookie in ASP.NET (as the // antiforgery stack requires at least a name claim to bind CSRF cookies to the user's identity) but // the access/refresh tokens can be retrieved using result.Properties.GetTokens() to make API calls. - if (result.Identity is not ClaimsIdentity { IsAuthenticated: true }) + if (result is not { Identity.IsAuthenticated: true }) { throw new InvalidOperationException("The external authorization data cannot be used for authentication."); } diff --git a/sandbox/OpenIddict.Sandbox.AspNet.Server/Controllers/AuthorizationController.cs b/sandbox/OpenIddict.Sandbox.AspNet.Server/Controllers/AuthorizationController.cs index 9b76c5ffd..e3117b32b 100644 --- a/sandbox/OpenIddict.Sandbox.AspNet.Server/Controllers/AuthorizationController.cs +++ b/sandbox/OpenIddict.Sandbox.AspNet.Server/Controllers/AuthorizationController.cs @@ -89,7 +89,7 @@ public async Task Authorize() { context.Authentication.Challenge( authenticationTypes: OpenIddictServerOwinDefaults.AuthenticationType, - properties: new AuthenticationProperties(new Dictionary + properties: new AuthenticationProperties(new Dictionary { [OpenIddictServerOwinConstants.Properties.Error] = Errors.InvalidRequest, [OpenIddictServerOwinConstants.Properties.ErrorDescription] = @@ -99,7 +99,7 @@ public async Task Authorize() return new EmptyResult(); } - var properties = new AuthenticationProperties(new Dictionary + var properties = new AuthenticationProperties(new Dictionary { // Note: when only one client is registered in the client options, // specifying the issuer URI or the provider name is not required. @@ -146,7 +146,7 @@ public async Task Authorize() case ConsentTypes.External when authorizations.Count is 0: context.Authentication.Challenge( authenticationTypes: OpenIddictServerOwinDefaults.AuthenticationType, - properties: new AuthenticationProperties(new Dictionary + properties: new AuthenticationProperties(new Dictionary { [OpenIddictServerOwinConstants.Properties.Error] = Errors.ConsentRequired, [OpenIddictServerOwinConstants.Properties.ErrorDescription] = @@ -202,7 +202,7 @@ public async Task Authorize() case ConsentTypes.Systematic when request.HasPromptValue(PromptValues.None): context.Authentication.Challenge( authenticationTypes: OpenIddictServerOwinDefaults.AuthenticationType, - properties: new AuthenticationProperties(new Dictionary + properties: new AuthenticationProperties(new Dictionary { [OpenIddictServerOwinConstants.Properties.Error] = Errors.ConsentRequired, [OpenIddictServerOwinConstants.Properties.ErrorDescription] = @@ -215,16 +215,7 @@ public async Task Authorize() default: return View(new AuthorizeViewModel { ApplicationName = await _applicationManager.GetDisplayNameAsync(application), - Scope = request.Scope, - - // Flow the request parameters so they can be received by the Accept/Reject actions. - Parameters = string.Equals(Request.HttpMethod, "POST", StringComparison.OrdinalIgnoreCase) ? - from name in Request.Form.AllKeys - from value in Request.Form.GetValues(name) - select new KeyValuePair(name, value) : - from name in Request.QueryString.AllKeys - from value in Request.QueryString.GetValues(name) - select new KeyValuePair(name, value) + Scope = request.Scope }); } } @@ -274,7 +265,7 @@ public async Task Accept() { context.Authentication.Challenge( authenticationTypes: OpenIddictServerOwinDefaults.AuthenticationType, - properties: new AuthenticationProperties(new Dictionary + properties: new AuthenticationProperties(new Dictionary { [OpenIddictServerOwinConstants.Properties.Error] = Errors.ConsentRequired, [OpenIddictServerOwinConstants.Properties.ErrorDescription] = @@ -335,17 +326,7 @@ public ActionResult Deny() } [HttpGet, Route("~/connect/endsession")] - public ActionResult EndSession() => View(new AuthorizeViewModel - { - // Flow the request parameters so they can be received by the Accept/Reject actions. - Parameters = string.Equals(Request.HttpMethod, "POST", StringComparison.OrdinalIgnoreCase) ? - from name in Request.Form.AllKeys - from value in Request.Form.GetValues(name) - select new KeyValuePair(name, value) : - from name in Request.QueryString.AllKeys - from value in Request.QueryString.GetValues(name) - select new KeyValuePair(name, value) - }); + public ActionResult EndSession() => View(); [ActionName(nameof(EndSession)), HttpPost, Route("~/connect/endsession"), ValidateAntiForgeryToken] public ActionResult EndSessionPost() @@ -381,7 +362,7 @@ public async Task Exchange() { context.Authentication.Challenge( authenticationTypes: OpenIddictServerOwinDefaults.AuthenticationType, - properties: new AuthenticationProperties(new Dictionary + properties: new AuthenticationProperties(new Dictionary { [OpenIddictServerOwinConstants.Properties.Error] = Errors.InvalidGrant, [OpenIddictServerOwinConstants.Properties.ErrorDescription] = "The token is no longer valid." @@ -395,7 +376,7 @@ public async Task Exchange() { context.Authentication.Challenge( authenticationTypes: OpenIddictServerOwinDefaults.AuthenticationType, - properties: new AuthenticationProperties(new Dictionary + properties: new AuthenticationProperties(new Dictionary { [OpenIddictServerOwinConstants.Properties.Error] = Errors.InvalidGrant, [OpenIddictServerOwinConstants.Properties.ErrorDescription] = "The user is no longer allowed to sign in." diff --git a/sandbox/OpenIddict.Sandbox.AspNet.Server/Controllers/ResourceController.cs b/sandbox/OpenIddict.Sandbox.AspNet.Server/Controllers/ResourceController.cs index 80318ef78..98968c5bd 100644 --- a/sandbox/OpenIddict.Sandbox.AspNet.Server/Controllers/ResourceController.cs +++ b/sandbox/OpenIddict.Sandbox.AspNet.Server/Controllers/ResourceController.cs @@ -27,7 +27,7 @@ public async Task GetMessage() { context.Authentication.Challenge( authenticationTypes: OpenIddictValidationOwinDefaults.AuthenticationType, - properties: new AuthenticationProperties(new Dictionary + properties: new AuthenticationProperties(new Dictionary { [OpenIddictValidationOwinConstants.Properties.Scope] = "demo_api", [OpenIddictValidationOwinConstants.Properties.Error] = Errors.InsufficientScope, @@ -43,7 +43,7 @@ public async Task GetMessage() { context.Authentication.Challenge( authenticationTypes: OpenIddictValidationOwinDefaults.AuthenticationType, - properties: new AuthenticationProperties(new Dictionary + properties: new AuthenticationProperties(new Dictionary { [OpenIddictValidationOwinConstants.Properties.Error] = Errors.InvalidToken, [OpenIddictValidationOwinConstants.Properties.ErrorDescription] = diff --git a/sandbox/OpenIddict.Sandbox.AspNet.Server/ViewModels/Authorization/AuthorizeViewModel.cs b/sandbox/OpenIddict.Sandbox.AspNet.Server/ViewModels/Authorization/AuthorizeViewModel.cs index d7c03180a..8b01f7d61 100644 --- a/sandbox/OpenIddict.Sandbox.AspNet.Server/ViewModels/Authorization/AuthorizeViewModel.cs +++ b/sandbox/OpenIddict.Sandbox.AspNet.Server/ViewModels/Authorization/AuthorizeViewModel.cs @@ -1,10 +1,12 @@ -using System.Collections.Generic; -using System.Web.Mvc; +using System.ComponentModel.DataAnnotations; namespace OpenIddict.Sandbox.AspNet.Server.ViewModels.Authorization; -[Bind(Exclude = nameof(Parameters))] -public class LogoutViewModel +public class AuthorizeViewModel { - public IEnumerable> Parameters { get; internal set; } + [Display(Name = "Application")] + public string ApplicationName { get; set; } + + [Display(Name = "Scope")] + public string Scope { get; set; } } diff --git a/sandbox/OpenIddict.Sandbox.AspNet.Server/ViewModels/Authorization/LogoutViewModel.cs b/sandbox/OpenIddict.Sandbox.AspNet.Server/ViewModels/Authorization/LogoutViewModel.cs deleted file mode 100644 index c1d47f1a8..000000000 --- a/sandbox/OpenIddict.Sandbox.AspNet.Server/ViewModels/Authorization/LogoutViewModel.cs +++ /dev/null @@ -1,17 +0,0 @@ -using System.Collections.Generic; -using System.ComponentModel.DataAnnotations; -using System.Web.Mvc; - -namespace OpenIddict.Sandbox.AspNet.Server.ViewModels.Authorization; - -[Bind(Exclude = nameof(Parameters))] -public class AuthorizeViewModel -{ - [Display(Name = "Application")] - public string ApplicationName { get; set; } - - [Display(Name = "Scope")] - public string Scope { get; set; } - - public IEnumerable> Parameters { get; internal set; } -} diff --git a/sandbox/OpenIddict.Sandbox.AspNet.Server/Views/Authorization/Authorize.cshtml b/sandbox/OpenIddict.Sandbox.AspNet.Server/Views/Authorization/Authorize.cshtml index f41150a26..c2241406a 100644 --- a/sandbox/OpenIddict.Sandbox.AspNet.Server/Views/Authorization/Authorize.cshtml +++ b/sandbox/OpenIddict.Sandbox.AspNet.Server/Views/Authorization/Authorize.cshtml @@ -11,7 +11,13 @@ @Html.AntiForgeryToken() @* Flow the request parameters so they can be received by the Accept/Reject actions: *@ - foreach (var parameter in Model.Parameters) + foreach (var parameter in string.Equals(Request.HttpMethod, "POST", StringComparison.OrdinalIgnoreCase) ? + from name in Request.Form.AllKeys + from value in Request.Form.GetValues(name) + select new KeyValuePair(name, value) : + from name in Request.QueryString.AllKeys + from value in Request.QueryString.GetValues(name) + select new KeyValuePair(name, value)) { } diff --git a/sandbox/OpenIddict.Sandbox.AspNet.Server/Views/Authorization/EndSession.cshtml b/sandbox/OpenIddict.Sandbox.AspNet.Server/Views/Authorization/EndSession.cshtml index 2c8e1058a..4d270f904 100644 --- a/sandbox/OpenIddict.Sandbox.AspNet.Server/Views/Authorization/EndSession.cshtml +++ b/sandbox/OpenIddict.Sandbox.AspNet.Server/Views/Authorization/EndSession.cshtml @@ -9,7 +9,13 @@ @Html.AntiForgeryToken() @* Flow the request parameters so they can be received by the EndSessionPost action: *@ - foreach (var parameter in Model.Parameters) + foreach (var parameter in string.Equals(Request.HttpMethod, "POST", StringComparison.OrdinalIgnoreCase) ? + from name in Request.Form.AllKeys + from value in Request.Form.GetValues(name) + select new KeyValuePair(name, value) : + from name in Request.QueryString.AllKeys + from value in Request.QueryString.GetValues(name) + select new KeyValuePair(name, value)) { } diff --git a/sandbox/OpenIddict.Sandbox.AspNetCore.Client/Controllers/AuthenticationController.cs b/sandbox/OpenIddict.Sandbox.AspNetCore.Client/Controllers/AuthenticationController.cs index 65a66739a..70b170aef 100644 --- a/sandbox/OpenIddict.Sandbox.AspNetCore.Client/Controllers/AuthenticationController.cs +++ b/sandbox/OpenIddict.Sandbox.AspNetCore.Client/Controllers/AuthenticationController.cs @@ -154,7 +154,7 @@ public async Task LogInCallback() // Such identities cannot be used as-is to build an authentication cookie in ASP.NET Core (as the // antiforgery stack requires at least a name claim to bind CSRF cookies to the user's identity) but // the access/refresh tokens can be retrieved using result.Properties.GetTokens() to make API calls. - if (result is not { Succeeded: true, Principal: ClaimsPrincipal { Identity.IsAuthenticated: true } }) + if (result is not { Succeeded: true, Principal.Identity.IsAuthenticated: true }) { throw new InvalidOperationException("The external authorization data cannot be used for authentication."); } diff --git a/sandbox/OpenIddict.Sandbox.AspNetCore.Server/Controllers/AuthenticationController.cs b/sandbox/OpenIddict.Sandbox.AspNetCore.Server/Controllers/AuthenticationController.cs index 42ab36e77..c9f36220c 100644 --- a/sandbox/OpenIddict.Sandbox.AspNetCore.Server/Controllers/AuthenticationController.cs +++ b/sandbox/OpenIddict.Sandbox.AspNetCore.Server/Controllers/AuthenticationController.cs @@ -45,7 +45,7 @@ public async Task LogInCallback() // Such identities cannot be used as-is to build an authentication cookie in ASP.NET Core (as the // antiforgery stack requires at least a name claim to bind CSRF cookies to the user's identity) but // the access/refresh tokens can be retrieved using result.Properties.GetTokens() to make API calls. - if (result is not { Succeeded: true, Principal: ClaimsPrincipal { Identity.IsAuthenticated: true } }) + if (result is not { Succeeded: true, Principal.Identity.IsAuthenticated: true }) { throw new InvalidOperationException("The external authorization data cannot be used for authentication."); } diff --git a/sandbox/OpenIddict.Sandbox.AspNetCore.Server/Controllers/AuthorizationController.cs b/sandbox/OpenIddict.Sandbox.AspNetCore.Server/Controllers/AuthorizationController.cs index 06bd1f2bd..94bc58058 100644 --- a/sandbox/OpenIddict.Sandbox.AspNetCore.Server/Controllers/AuthorizationController.cs +++ b/sandbox/OpenIddict.Sandbox.AspNetCore.Server/Controllers/AuthorizationController.cs @@ -331,7 +331,7 @@ public async Task Verify() { // Retrieve the claims principal associated with the user code. var result = await HttpContext.AuthenticateAsync(OpenIddictServerAspNetCoreDefaults.AuthenticationScheme); - if (result.Succeeded && !string.IsNullOrEmpty(result.Principal.GetClaim(Claims.ClientId))) + if (result is { Succeeded: true } && !string.IsNullOrEmpty(result.Principal.GetClaim(Claims.ClientId))) { // Retrieve the application details from the database using the client_id stored in the principal. var application = await _applicationManager.FindByClientIdAsync(result.Principal.GetClaim(Claims.ClientId)!) ?? @@ -371,7 +371,7 @@ public async Task VerifyAccept() // Retrieve the claims principal associated with the user code. var result = await HttpContext.AuthenticateAsync(OpenIddictServerAspNetCoreDefaults.AuthenticationScheme); - if (result.Succeeded && !string.IsNullOrEmpty(result.Principal.GetClaim(Claims.ClientId))) + if (result is { Succeeded: true } && !string.IsNullOrEmpty(result.Principal.GetClaim(Claims.ClientId))) { // Create the claims-based identity that will be used by OpenIddict to generate tokens. var identity = new ClaimsIdentity( diff --git a/sandbox/OpenIddict.Sandbox.Maui.Client/Platforms/MacCatalyst/Program.cs b/sandbox/OpenIddict.Sandbox.Maui.Client/Platforms/MacCatalyst/Program.cs index f6d30888c..c8034c22e 100644 --- a/sandbox/OpenIddict.Sandbox.Maui.Client/Platforms/MacCatalyst/Program.cs +++ b/sandbox/OpenIddict.Sandbox.Maui.Client/Platforms/MacCatalyst/Program.cs @@ -1,5 +1,4 @@ #if MACCATALYST -using ObjCRuntime; using UIKit; namespace OpenIddict.Sandbox.Maui.Client; diff --git a/sandbox/OpenIddict.Sandbox.Maui.Client/Platforms/iOS/Program.cs b/sandbox/OpenIddict.Sandbox.Maui.Client/Platforms/iOS/Program.cs index 25b9ce72c..0eaccdb46 100644 --- a/sandbox/OpenIddict.Sandbox.Maui.Client/Platforms/iOS/Program.cs +++ b/sandbox/OpenIddict.Sandbox.Maui.Client/Platforms/iOS/Program.cs @@ -1,5 +1,4 @@ #if IOS -using ObjCRuntime; using UIKit; namespace OpenIddict.Sandbox.Maui.Client; diff --git a/test/OpenIddict.Server.Owin.IntegrationTests/OpenIddictServerOwinIntegrationTests.cs b/test/OpenIddict.Server.Owin.IntegrationTests/OpenIddictServerOwinIntegrationTests.cs index 7b06248d5..95305be8a 100644 --- a/test/OpenIddict.Server.Owin.IntegrationTests/OpenIddictServerOwinIntegrationTests.cs +++ b/test/OpenIddict.Server.Owin.IntegrationTests/OpenIddictServerOwinIntegrationTests.cs @@ -749,7 +749,7 @@ protected override ValueTask CreateServer else if (context.Request.Path == new PathString("/challenge/custom")) { - var properties = new AuthenticationProperties(new Dictionary + var properties = new AuthenticationProperties(new Dictionary { [OpenIddictServerOwinConstants.Properties.Error] = "custom_error", [OpenIddictServerOwinConstants.Properties.ErrorDescription] = "custom_error_description",