Skip to content

Commit

Permalink
Migrate the OpenID module to OpenIddict 6.0 (#16929)
Browse files Browse the repository at this point in the history
  • Loading branch information
kevinchalet authored Dec 17, 2024
1 parent 6aca8d1 commit 87d636a
Show file tree
Hide file tree
Showing 11 changed files with 374 additions and 104 deletions.
12 changes: 6 additions & 6 deletions Directory.Packages.props
Original file line number Diff line number Diff line change
Expand Up @@ -54,12 +54,12 @@
<PackageVersion Include="NJsonSchema" Version="11.1.0" />
<PackageVersion Include="NLog.Web.AspNetCore" Version="5.3.15" />
<PackageVersion Include="NodaTime" Version="3.2.0" />
<PackageVersion Include="OpenIddict.Core" Version="5.8.0" />
<PackageVersion Include="OpenIddict.Server.AspNetCore" Version="5.8.0" />
<PackageVersion Include="OpenIddict.Server.DataProtection" Version="5.8.0" />
<PackageVersion Include="OpenIddict.Validation.AspNetCore" Version="5.8.0" />
<PackageVersion Include="OpenIddict.Validation.DataProtection" Version="5.8.0" />
<PackageVersion Include="OpenIddict.Validation.SystemNetHttp" Version="5.8.0" />
<PackageVersion Include="OpenIddict.Core" Version="6.0.0" />
<PackageVersion Include="OpenIddict.Server.AspNetCore" Version="6.0.0" />
<PackageVersion Include="OpenIddict.Server.DataProtection" Version="6.0.0" />
<PackageVersion Include="OpenIddict.Validation.AspNetCore" Version="6.0.0" />
<PackageVersion Include="OpenIddict.Validation.DataProtection" Version="6.0.0" />
<PackageVersion Include="OpenIddict.Validation.SystemNetHttp" Version="6.0.0" />
<PackageVersion Include="OrchardCore.Translations.All" Version="2.1.0" />
<PackageVersion Include="PdfPig" Version="0.1.9" />
<PackageVersion Include="Shortcodes" Version="1.3.4" />
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -83,7 +83,7 @@ public void Configure(OpenIddictServerOptions options)

if (settings.LogoutEndpointPath.HasValue)
{
options.LogoutEndpointUris.Add(new Uri(
options.EndSessionEndpointUris.Add(new Uri(
settings.LogoutEndpointPath.ToUriComponent()[1..], UriKind.Relative));
}

Expand All @@ -95,7 +95,7 @@ public void Configure(OpenIddictServerOptions options)

if (settings.UserinfoEndpointPath.HasValue)
{
options.UserinfoEndpointUris.Add(new Uri(
options.UserInfoEndpointUris.Add(new Uri(
settings.UserinfoEndpointPath.ToUriComponent()[1..], UriKind.Relative));
}

Expand Down Expand Up @@ -195,18 +195,18 @@ public void Configure(OpenIddictServerDataProtectionOptions options)

public void Configure(string name, OpenIddictServerAspNetCoreOptions options)
{
// Note: the OpenID module handles the authorization, logout, token and userinfo requests
// Note: the OpenID module handles the authorization, end session, token and userinfo requests
// in its dedicated ASP.NET Core MVC controller, which requires enabling the pass-through mode.
options.EnableAuthorizationEndpointPassthrough = true;
options.EnableLogoutEndpointPassthrough = true;
options.EnableEndSessionEndpointPassthrough = true;
options.EnableTokenEndpointPassthrough = true;
options.EnableUserinfoEndpointPassthrough = true;
options.EnableUserInfoEndpointPassthrough = true;

// Note: caching is enabled for both authorization and logout requests to allow sending
// large POST authorization and logout requests, but can be programmatically disabled, as the
// authorization and logout views support flowing the entire payload and not just the request_id.
// Note: caching is enabled for both authorization and end session requests to allow sending
// large POST authorization and end session requests, but can be programmatically disabled, as the
// authorization and end session views support flowing the entire payload and not just the request_id.
options.EnableAuthorizationRequestCaching = true;
options.EnableLogoutRequestCaching = true;
options.EnableEndSessionRequestCaching = true;

// Note: error pass-through is enabled to allow the actions of the MVC authorization controller
// to handle the errors returned by the interactive endpoints without relying on the generic
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@
using Microsoft.AspNetCore.Http;
using Microsoft.AspNetCore.Mvc;
using Microsoft.Extensions.DependencyInjection;
using Microsoft.Extensions.Primitives;
using OpenIddict.Abstractions;
using OpenIddict.Server.AspNetCore;
using OrchardCore.Environment.Shell;
Expand Down Expand Up @@ -64,7 +65,7 @@ public async Task<IActionResult> Authorize()
// Retrieve the claims stored in the authentication cookie.
// If they can't be extracted, redirect the user to the login page.
var result = await HttpContext.AuthenticateAsync();
if (result == null || !result.Succeeded || request.HasPrompt(Prompts.Login))
if (result == null || !result.Succeeded || request.HasPromptValue(PromptValues.Login))
{
return RedirectToLoginPage(request);
}
Expand Down Expand Up @@ -99,7 +100,7 @@ public async Task<IActionResult> Authorize()

case ConsentTypes.Implicit:
case ConsentTypes.External when authorizations.Count > 0:
case ConsentTypes.Explicit when authorizations.Count > 0 && !request.HasPrompt(Prompts.Consent):
case ConsentTypes.Explicit when authorizations.Count > 0 && !request.HasPromptValue(PromptValues.Consent):
var identity = new ClaimsIdentity(result.Principal.Claims, OpenIddictServerAspNetCoreDefaults.AuthenticationScheme);
identity.AddClaim(new Claim(OpenIdConstants.Claims.EntityType, OpenIdConstants.EntityTypes.User));

Expand All @@ -123,7 +124,7 @@ public async Task<IActionResult> Authorize()

return SignIn(new ClaimsPrincipal(identity), OpenIddictServerAspNetCoreDefaults.AuthenticationScheme);

case ConsentTypes.Explicit when request.HasPrompt(Prompts.None):
case ConsentTypes.Explicit when request.HasPromptValue(PromptValues.None):
return Forbid(new AuthenticationProperties(new Dictionary<string, string>
{
[OpenIddictServerAspNetCoreConstants.Properties.Error] = Errors.ConsentRequired,
Expand All @@ -144,7 +145,7 @@ IActionResult RedirectToLoginPage(OpenIddictRequest request)
{
// If the client application requested promptless authentication,
// return an error indicating that the user is not logged in.
if (request.HasPrompt(Prompts.None))
if (request.HasPromptValue(PromptValues.None))
{
return Forbid(new AuthenticationProperties(new Dictionary<string, string>
{
Expand All @@ -155,9 +156,15 @@ IActionResult RedirectToLoginPage(OpenIddictRequest request)

string GetRedirectUrl()
{
// Override the prompt parameter to prevent infinite authentication/authorization loops.
var parameters = Request.Query.ToDictionary(kvp => kvp.Key, kvp => kvp.Value);
parameters[Parameters.Prompt] = "continue";
// To avoid endless login -> authorization redirects, the prompt=login flag
// is removed from the authorization request payload before redirecting the user.
var prompt = string.Join(" ", request.GetPromptValues().Remove(PromptValues.Login));

var parameters = Request.HasFormContentType ?
Request.Form.Where(parameter => parameter.Key != Parameters.Prompt).ToList() :
Request.Query.Where(parameter => parameter.Key != Parameters.Prompt).ToList();

parameters.Add(new(Parameters.Prompt, new StringValues(prompt)));

return Request.PathBase + Request.Path + QueryString.Create(parameters);
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -232,7 +232,8 @@ await HasPermissionAsync(OpenIddictConstants.Permissions.ResponseTypes.Token)),

AllowPasswordFlow = await HasPermissionAsync(OpenIddictConstants.Permissions.GrantTypes.Password),
AllowRefreshTokenFlow = await HasPermissionAsync(OpenIddictConstants.Permissions.GrantTypes.RefreshToken),
AllowLogoutEndpoint = await HasPermissionAsync(OpenIddictConstants.Permissions.Endpoints.Logout),
AllowLogoutEndpoint = await HasPermissionAsync("ept:logout") || // Still allowed for backcompat reasons.
await HasPermissionAsync(OpenIddictConstants.Permissions.Endpoints.EndSession),
AllowIntrospectionEndpoint = await HasPermissionAsync(OpenIddictConstants.Permissions.Endpoints.Introspection),
AllowRevocationEndpoint = await HasPermissionAsync(OpenIddictConstants.Permissions.Endpoints.Revocation),
ClientId = await _applicationManager.GetClientIdAsync(application),
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -57,11 +57,12 @@ public static async Task UpdateDescriptorFromSettings(this IOpenIdApplicationMan

if (model.AllowLogoutEndpoint)
{
descriptor.Permissions.Add(OpenIddictConstants.Permissions.Endpoints.Logout);
descriptor.Permissions.Add(OpenIddictConstants.Permissions.Endpoints.EndSession);
}
else
{
descriptor.Permissions.Remove(OpenIddictConstants.Permissions.Endpoints.Logout);
descriptor.Permissions.Remove("ept:logout"); // Still allowed for backcompat reasons.
descriptor.Permissions.Remove(OpenIddictConstants.Permissions.Endpoints.EndSession);
}

if (model.AllowAuthorizationCodeFlow || model.AllowHybridFlow)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -119,17 +119,17 @@
<div class="mb-3">
<div class="form-check">
<input type="checkbox" class="form-check-input" asp-for="AllowLogoutEndpoint" data-bs-toggle="collapse" data-bs-target="#postLogoutRedirectUris" checked="@Model.AllowLogoutEndpoint">
<label class="form-check-label" asp-for="AllowLogoutEndpoint">@T["Allow Logout Endpoint"]</label>
<label class="form-check-label" asp-for="AllowLogoutEndpoint">@T["Allow End Session Endpoint"]</label>
</div>
</div>
<div class="mb-3 collapse" id="postLogoutRedirectUris" name="postLogoutRedirectUris">
<div class="mb-3" asp-validation-class-for="PostLogoutRedirectUris">
<label asp-for="PostLogoutRedirectUris" class="form-label">@T["Logout Redirect Uris"]</label>
<label asp-for="PostLogoutRedirectUris" class="form-label">@T["Post-Logout Redirect Uris"]</label>
<input asp-for="PostLogoutRedirectUris" class="form-control" autofocus />
<span asp-validation-for="PostLogoutRedirectUris" class="text-danger"></span>
</div>
<div class="hint">
@T["Space delimited list of logout redirect URIs."]
@T["Space delimited list of post-logout redirect URIs."]
</div>
</div>
</div>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -131,17 +131,17 @@
<div class="mb-3">
<div class="form-check">
<input type="checkbox" class="form-check-input" asp-for="AllowLogoutEndpoint" data-bs-toggle="collapse" data-bs-target="#postLogoutRedirectUris" checked="@Model.AllowLogoutEndpoint">
<label class="form-check-label" asp-for="AllowLogoutEndpoint">@T["Allow Logout Endpoint"]</label>
<label class="form-check-label" asp-for="AllowLogoutEndpoint">@T["Allow End Session Endpoint"]</label>
</div>
</div>
<div class="mb-3 collapse" id="postLogoutRedirectUris" name="postLogoutRedirectUris">
<div class="mb-3" asp-validation-class-for="PostLogoutRedirectUris">
<label asp-for="PostLogoutRedirectUris">@T["Post Logout Redirect Uris"]</label>
<label asp-for="PostLogoutRedirectUris">@T["Post-Logout Redirect Uris"]</label>
<input asp-for="PostLogoutRedirectUris" class="form-control" autofocus />
<span asp-validation-for="PostLogoutRedirectUris" class="text-danger"></span>
</div>
<div class="hint">
@T["Space delimited list of logout redirect URIs."]
@T["Space delimited list of post-logout redirect URIs."]
</div>
</div>
</div>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -25,7 +25,7 @@
<div class="mb-3" asp-validation-class-for="EnableLogoutEndpoint">
<div class="form-check">
<input type="checkbox" class="form-check-input" asp-for="EnableLogoutEndpoint">
<label class="form-check-label" asp-for="EnableLogoutEndpoint">@T["Enable Logout Endpoint"]</label>
<label class="form-check-label" asp-for="EnableLogoutEndpoint">@T["Enable End Session Endpoint"]</label>
<span class="hint dashed">@T["Enables the endpoint:"]</span> <code>/connect/logout</code>
</div>
</div>
Expand Down
Loading

0 comments on commit 87d636a

Please sign in to comment.