This is an automated email from the ASF dual-hosted git repository.
exceptionfactory pushed a commit to branch support/nifi-1.x
in repository https://gitbox.apache.org/repos/asf/nifi.git
The following commit(s) were added to refs/heads/support/nifi-1.x by this push:
new cbfc47d460 NIFI-12695 Enabled PKCE Support for OIDC Integration
cbfc47d460 is described below
commit cbfc47d46021eb46c6d4c387096af8777bd0ea4a
Author: exceptionfactory <[email protected]>
AuthorDate: Tue Jan 30 21:59:42 2024 -0600
NIFI-12695 Enabled PKCE Support for OIDC Integration
- Added Spring Security PKCE OAuth2 Request Customizer to standard Resolver
Signed-off-by: Pierre Villard <[email protected]>
This closes #8324.
(cherry picked from commit 547f338147f4c48d9612ce4e7a6d52e0d8714f7f)
---
nifi-docs/src/main/asciidoc/administration-guide.adoc | 3 +++
.../web/StandardOAuth2AuthorizationRequestResolver.java | 9 +++++++--
.../StandardOAuth2AuthorizationRequestResolverTest.java | 14 ++++++++++++++
3 files changed, 24 insertions(+), 2 deletions(-)
diff --git a/nifi-docs/src/main/asciidoc/administration-guide.adoc
b/nifi-docs/src/main/asciidoc/administration-guide.adoc
index c50eea6c03..dc9819aab1 100644
--- a/nifi-docs/src/main/asciidoc/administration-guide.adoc
+++ b/nifi-docs/src/main/asciidoc/administration-guide.adoc
@@ -497,6 +497,9 @@ The implementation supports the Authorization Code Grant
Type as described in
link:https://www.rfc-editor.org/rfc/rfc6749#section-4.1[RFC 6749 Section 4.1^]
and
link:https://openid.net/specs/openid-connect-core-1_0.html#CodeFlowSteps[OpenID
Connect Core Section 3.1.1^].
+The Authorization Code Grant Type implementation supports
link:https://www.rfc-editor.org/rfc/rfc7636[RFC 7636] Proof
+Key for Code Exchange as part of the authentication process. PKCE support uses
the `S256` code challenge method.
+
After successful authentication with the Authorization Server, NiFi generates
an application Bearer Token with an
expiration based on the OAuth2 Access Token expiration. NiFi stores authorized
tokens using the local State
Provider and encrypts serialized information using the application Sensitive
Properties Key.
diff --git
a/nifi-nar-bundles/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-security/src/main/java/org/apache/nifi/web/security/oidc/client/web/StandardOAuth2AuthorizationRequestResolver.java
b/nifi-nar-bundles/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-security/src/main/java/org/apache/nifi/web/security/oidc/client/web/StandardOAuth2AuthorizationRequestResolver.java
index dd8ca86ee3..3cdd3cc74e 100644
---
a/nifi-nar-bundles/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-security/src/main/java/org/apache/nifi/web/security/oidc/client/web/StandardOAuth2AuthorizationRequestResolver.java
+++
b/nifi-nar-bundles/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-security/src/main/java/org/apache/nifi/web/security/oidc/client/web/StandardOAuth2AuthorizationRequestResolver.java
@@ -19,7 +19,7 @@ package org.apache.nifi.web.security.oidc.client.web;
import org.apache.nifi.web.util.RequestUriBuilder;
import
org.springframework.security.oauth2.client.registration.ClientRegistrationRepository;
import
org.springframework.security.oauth2.client.web.DefaultOAuth2AuthorizationRequestResolver;
-import
org.springframework.security.oauth2.client.web.OAuth2AuthorizationRequestRedirectFilter;
+import
org.springframework.security.oauth2.client.web.OAuth2AuthorizationRequestCustomizers;
import
org.springframework.security.oauth2.client.web.OAuth2AuthorizationRequestResolver;
import
org.springframework.security.oauth2.core.endpoint.OAuth2AuthorizationRequest;
import org.springframework.web.util.UriComponentsBuilder;
@@ -28,6 +28,8 @@ import javax.servlet.http.HttpServletRequest;
import java.net.URI;
import java.util.Objects;
+import static
org.springframework.security.oauth2.client.web.OAuth2AuthorizationRequestRedirectFilter.DEFAULT_AUTHORIZATION_REQUEST_BASE_URI;
+
/**
* Authorization Request Resolver supports handling of headers from reverse
proxy servers
*/
@@ -41,7 +43,10 @@ public class StandardOAuth2AuthorizationRequestResolver
implements OAuth2Authori
*/
public StandardOAuth2AuthorizationRequestResolver(final
ClientRegistrationRepository clientRegistrationRepository) {
Objects.requireNonNull(clientRegistrationRepository, "Repository
required");
- resolver = new
DefaultOAuth2AuthorizationRequestResolver(clientRegistrationRepository,
OAuth2AuthorizationRequestRedirectFilter.DEFAULT_AUTHORIZATION_REQUEST_BASE_URI);
+ final DefaultOAuth2AuthorizationRequestResolver requestResolver = new
DefaultOAuth2AuthorizationRequestResolver(clientRegistrationRepository,
DEFAULT_AUTHORIZATION_REQUEST_BASE_URI);
+ // Enable RFC 7636 Proof Key for Code Exchange on Requests
+
requestResolver.setAuthorizationRequestCustomizer(OAuth2AuthorizationRequestCustomizers.withPkce());
+ resolver = requestResolver;
}
/**
diff --git
a/nifi-nar-bundles/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-security/src/test/java/org/apache/nifi/web/security/oidc/client/web/StandardOAuth2AuthorizationRequestResolverTest.java
b/nifi-nar-bundles/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-security/src/test/java/org/apache/nifi/web/security/oidc/client/web/StandardOAuth2AuthorizationRequestResolverTest.java
index 5644c68f66..a862d099c9 100644
---
a/nifi-nar-bundles/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-security/src/test/java/org/apache/nifi/web/security/oidc/client/web/StandardOAuth2AuthorizationRequestResolverTest.java
+++
b/nifi-nar-bundles/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-security/src/test/java/org/apache/nifi/web/security/oidc/client/web/StandardOAuth2AuthorizationRequestResolverTest.java
@@ -30,11 +30,15 @@ import
org.springframework.security.oauth2.core.AuthorizationGrantType;
import
org.springframework.security.oauth2.core.endpoint.OAuth2AuthorizationRequest;
import javax.servlet.ServletContext;
+import org.springframework.security.oauth2.core.endpoint.PkceParameterNames;
+
import java.net.URI;
+import java.util.Map;
import static org.junit.jupiter.api.Assertions.assertEquals;
import static org.junit.jupiter.api.Assertions.assertNotNull;
import static org.junit.jupiter.api.Assertions.assertNull;
+import static org.junit.jupiter.api.Assertions.assertTrue;
import static org.mockito.ArgumentMatchers.eq;
import static org.mockito.Mockito.when;
@@ -99,6 +103,7 @@ class StandardOAuth2AuthorizationRequestResolverTest {
assertNotNull(authorizationRequest);
assertEquals(REDIRECT_URI, authorizationRequest.getRedirectUri());
+ assertPkceParametersFound(authorizationRequest);
}
@Test
@@ -119,6 +124,15 @@ class StandardOAuth2AuthorizationRequestResolverTest {
assertNotNull(authorizationRequest);
assertEquals(FORWARDED_REDIRECT_URI,
authorizationRequest.getRedirectUri());
+ assertPkceParametersFound(authorizationRequest);
+ }
+
+ private void assertPkceParametersFound(final OAuth2AuthorizationRequest
authorizationRequest) {
+
assertNotNull(authorizationRequest.getAttribute(PkceParameterNames.CODE_VERIFIER));
+
+ final Map<String, Object> additionalParameters =
authorizationRequest.getAdditionalParameters();
+
assertTrue(additionalParameters.containsKey(PkceParameterNames.CODE_CHALLENGE));
+
assertTrue(additionalParameters.containsKey(PkceParameterNames.CODE_CHALLENGE_METHOD));
}
ClientRegistration getClientRegistration() {