Table of Contents

Class OidcController

Namespace
SEBT.Portal.Api.Controllers.Auth
Assembly
SEBT.Portal.Api.dll

OIDC endpoints for external IdP login and step-up. Primary config uses flat Oidc keys (DiscoveryEndpoint, ClientId, CallbackRedirectUri); optional Oidc:StepUp:* selects a second client for elevated verification when stepUp=true on the config endpoint.

The controller owns PKCE generation, cookies, and HTTP mapping; the callback and complete-login business orchestration lives in UseCases handlers.

[ApiController]
[Route("api/auth/oidc")]
public class OidcController : ControllerBase
Inheritance
object
ControllerBase
OidcController

Constructors

OidcController(IOptionsSnapshot<OidcSettings>, IOptionsSnapshot<OidcStepUpSettings>, ILogger<OidcController>, IOidcCallbackFailureLogger, IOptions<JwtSettings>, IStateAllowlist, IPreAuthSessionStore, IWebHostEnvironment)

OIDC endpoints for external IdP login and step-up. Primary config uses flat Oidc keys (DiscoveryEndpoint, ClientId, CallbackRedirectUri); optional Oidc:StepUp:* selects a second client for elevated verification when stepUp=true on the config endpoint.

The controller owns PKCE generation, cookies, and HTTP mapping; the callback and complete-login business orchestration lives in UseCases handlers.

public OidcController(IOptionsSnapshot<OidcSettings> oidcSettings, IOptionsSnapshot<OidcStepUpSettings> oidcStepUpSettings, ILogger<OidcController> logger, IOidcCallbackFailureLogger callbackFailureLogger, IOptions<JwtSettings> jwtSettingsOptions, IStateAllowlist stateAllowlist, IPreAuthSessionStore sessionStore, IWebHostEnvironment environment)

Parameters

oidcSettings IOptionsSnapshot<OidcSettings>
oidcStepUpSettings IOptionsSnapshot<OidcStepUpSettings>
logger ILogger<OidcController>
callbackFailureLogger IOidcCallbackFailureLogger
jwtSettingsOptions IOptions<JwtSettings>
stateAllowlist IStateAllowlist
sessionStore IPreAuthSessionStore
environment IWebHostEnvironment

Methods

Authorize(string, bool, string?, string?, IOidcExchangeService, CancellationToken)

Server-side OIDC authorize redirect. Builds the full authorization URL on the server using the authorization_endpoint from the IdP discovery document and returns a 302 redirect.

[HttpGet("{code}/authorize")]
[ProducesResponseType(302)]
[ProducesResponseType(400)]
[ProducesResponseType(502)]
[ProducesResponseType(503)]
public Task<IActionResult> Authorize(string code, bool stepUp = false, string? returnUrl = null, string? language = null, IOidcExchangeService exchangeService = null, CancellationToken cancellationToken = default)

Parameters

code string
stepUp bool
returnUrl string
language string
exchangeService IOidcExchangeService
cancellationToken CancellationToken

Returns

Task<IActionResult>

Callback(OidcCallbackRequest?, ICommandHandler<OidcCallbackCommand, OidcCallbackResponse>, CancellationToken)

Server-side OIDC callback. Requires the oidc_session cookie to locate the pre-auth session; the orchestration (state validation, replay protection, code exchange, session advancement) is dispatched to OidcCallbackCommandHandler. The request body only needs code and state.

[HttpPost("callback")]
[ProducesResponseType(200)]
[ProducesResponseType(typeof(ErrorResponse), 400)]
[ProducesResponseType(typeof(ErrorResponse), 403)]
[ProducesResponseType(503)]
public Task<IActionResult> Callback(OidcCallbackRequest? body, ICommandHandler<OidcCallbackCommand, OidcCallbackResponse> handler, CancellationToken cancellationToken)

Parameters

body OidcCallbackRequest
handler ICommandHandler<OidcCallbackCommand, OidcCallbackResponse>
cancellationToken CancellationToken

Returns

Task<IActionResult>

CompleteLogin(CompleteLoginRequest, ICommandHandler<CompleteOidcLoginCommand, CompleteOidcLoginResponse>, CancellationToken)

Completes OIDC login. Requires the oidc_session cookie to locate the pre-auth session; the orchestration (callback-token verification, user resolution, portal JWT minting) is dispatched to CompleteOidcLoginCommandHandler. On success the portal JWT is written to the session cookie and the pre-auth cookie is cleared. The request body only needs callbackToken.

[HttpPost("complete-login")]
[ProducesResponseType(typeof(CompleteLoginResponse), 200)]
[ProducesResponseType(typeof(ErrorResponse), 400)]
[ProducesResponseType(typeof(ErrorResponse), 403)]
[ProducesResponseType(503)]
public Task<IActionResult> CompleteLogin(CompleteLoginRequest body, ICommandHandler<CompleteOidcLoginCommand, CompleteOidcLoginResponse> handler, CancellationToken cancellationToken)

Parameters

body CompleteLoginRequest
handler ICommandHandler<CompleteOidcLoginCommand, CompleteOidcLoginResponse>
cancellationToken CancellationToken

Returns

Task<IActionResult>

GetConfig(string, bool, CancellationToken)

OIDC config + pre-auth session creation. Generates PKCE server-side, stores state + code_verifier + stateCode in the session store, sets an oidc_session HttpOnly cookie, and returns only the code_challenge + state to the browser. The code_verifier never leaves the server.

[HttpGet("{code}/config")]
[ProducesResponseType(200)]
[ProducesResponseType(400)]
[ProducesResponseType(503)]
public Task<IActionResult> GetConfig(string code, bool stepUp = false, CancellationToken cancellationToken = default)

Parameters

code string
stepUp bool
cancellationToken CancellationToken

Returns

Task<IActionResult>

Remarks

The authorization endpoint is intentionally NOT returned in this response. Use the GET {code}/authorize endpoint for server-side redirect instead.

ReportCallbackFailure(OidcCallbackFailureReportRequest?, CancellationToken)

Records browser-only OIDC callback failures (IdP redirect ?error= or missing code/state) before redirect to off-boarding. Failures from POST callback / complete-login are logged server-side only.

[HttpPost("report-failure")]
[ProducesResponseType(204)]
[ProducesResponseType(typeof(ErrorResponse), 400)]
public Task<IActionResult> ReportCallbackFailure(OidcCallbackFailureReportRequest? body, CancellationToken cancellationToken)

Parameters

body OidcCallbackFailureReportRequest
cancellationToken CancellationToken

Returns

Task<IActionResult>