From 2b4e36c67f76b889d0e53318fda1a086cf60a040 Mon Sep 17 00:00:00 2001 From: Rob Winch <362503+rwinch@users.noreply.github.com> Date: Thu, 9 Oct 2025 08:37:46 -0500 Subject: [PATCH] Add RequiredFactor.Builder.Authority() Closes gh-18033 --- .../authorization/RequiredFactor.java | 72 +++++++++++++++++++ .../authorization/RequiredFactorTests.java | 53 ++++++++++++++ 2 files changed, 125 insertions(+) diff --git a/core/src/main/java/org/springframework/security/authorization/RequiredFactor.java b/core/src/main/java/org/springframework/security/authorization/RequiredFactor.java index a579325966..b6ff187c78 100644 --- a/core/src/main/java/org/springframework/security/authorization/RequiredFactor.java +++ b/core/src/main/java/org/springframework/security/authorization/RequiredFactor.java @@ -127,6 +127,78 @@ public final class RequiredFactor { return this; } + /** + * A convenience method for invoking {@link #authority(String)} with + * {@link FactorGrantedAuthority#AUTHORIZATION_CODE_AUTHORITY}. + * @return the builder. + */ + public Builder authorizationCodeAuthority() { + return authority(FactorGrantedAuthority.AUTHORIZATION_CODE_AUTHORITY); + } + + /** + * A convenience method for invoking {@link #authority(String)} with + * {@link FactorGrantedAuthority#BEARER_AUTHORITY}. + * @return the builder. + */ + public Builder bearerTokenAuthority() { + return authority(FactorGrantedAuthority.BEARER_AUTHORITY); + } + + /** + * A convenience method for invoking {@link #authority(String)} with + * {@link FactorGrantedAuthority#CAS_AUTHORITY}. + * @return the builder. + */ + public Builder casAuthority() { + return authority(FactorGrantedAuthority.CAS_AUTHORITY); + } + + /** + * A convenience method for invoking {@link #authority(String)} with + * {@link FactorGrantedAuthority#PASSWORD_AUTHORITY}. + * @return the builder. + */ + public Builder passwordAuthority() { + return authority(FactorGrantedAuthority.PASSWORD_AUTHORITY); + } + + /** + * A convenience method for invoking {@link #authority(String)} with + * {@link FactorGrantedAuthority#OTT_AUTHORITY}. + * @return the builder. + */ + public Builder ottAuthority() { + return authority(FactorGrantedAuthority.OTT_AUTHORITY); + } + + /** + * A convenience method for invoking {@link #authority(String)} with + * {@link FactorGrantedAuthority#SAML_RESPONSE_AUTHORITY}. + * @return the builder. + */ + public Builder samlAuthority() { + return authority(FactorGrantedAuthority.SAML_RESPONSE_AUTHORITY); + } + + /** + * A convenience method for invoking {@link #authority(String)} with + * {@link FactorGrantedAuthority#WEBAUTHN_AUTHORITY}. + * @return the builder. + */ + public Builder webauthnAuthority() { + return authority(FactorGrantedAuthority.WEBAUTHN_AUTHORITY); + } + + /** + * A convenience method for invoking {@link #authority(String)} with + * {@link FactorGrantedAuthority#X509_AUTHORITY}. + * @return the builder. + */ + public Builder x509Authority() { + return authority(FactorGrantedAuthority.X509_AUTHORITY); + } + /** * Sets the optional {@link Duration} of time that the {@link RequiredFactor} is * valid for. diff --git a/core/src/test/java/org/springframework/security/authorization/RequiredFactorTests.java b/core/src/test/java/org/springframework/security/authorization/RequiredFactorTests.java index 137fdbe209..8efd51188f 100644 --- a/core/src/test/java/org/springframework/security/authorization/RequiredFactorTests.java +++ b/core/src/test/java/org/springframework/security/authorization/RequiredFactorTests.java @@ -17,6 +17,7 @@ package org.springframework.security.authorization; import java.time.Duration; +import java.util.function.Consumer; import org.junit.jupiter.api.Test; @@ -57,4 +58,56 @@ class RequiredFactorTests { assertThat(requiredPassword.getValidDuration()).isEqualTo(validDuration); } + @Test + void builderAuthorizationCodeAuthority() { + assertBuilderSetsAuthority(RequiredFactor.Builder::authorizationCodeAuthority, + FactorGrantedAuthority.AUTHORIZATION_CODE_AUTHORITY); + } + + @Test + void builderBearerTokenAuthority() { + assertBuilderSetsAuthority(RequiredFactor.Builder::bearerTokenAuthority, + FactorGrantedAuthority.BEARER_AUTHORITY); + } + + @Test + void builderCasAuthority() { + assertBuilderSetsAuthority(RequiredFactor.Builder::casAuthority, FactorGrantedAuthority.CAS_AUTHORITY); + } + + @Test + void builderPasswordAuthority() { + assertBuilderSetsAuthority(RequiredFactor.Builder::passwordAuthority, + FactorGrantedAuthority.PASSWORD_AUTHORITY); + } + + @Test + void builderOttAuthority() { + assertBuilderSetsAuthority(RequiredFactor.Builder::ottAuthority, FactorGrantedAuthority.OTT_AUTHORITY); + } + + @Test + void builderSamlAuthority() { + assertBuilderSetsAuthority(RequiredFactor.Builder::samlAuthority, + FactorGrantedAuthority.SAML_RESPONSE_AUTHORITY); + } + + @Test + void builderWebauthnAuthority() { + assertBuilderSetsAuthority(RequiredFactor.Builder::webauthnAuthority, + FactorGrantedAuthority.WEBAUTHN_AUTHORITY); + } + + @Test + void builderX509Authority() { + assertBuilderSetsAuthority(RequiredFactor.Builder::x509Authority, FactorGrantedAuthority.X509_AUTHORITY); + } + + private static void assertBuilderSetsAuthority(Consumer configure, String expected) { + RequiredFactor.Builder builder = RequiredFactor.builder(); + configure.accept(builder); + RequiredFactor requiredFactor = builder.build(); + assertThat(requiredFactor.getAuthority()).isEqualTo(expected); + } + }