diff --git a/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-security/pom.xml b/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-security/pom.xml
index 05affc9d8f..92f4994bff 100644
--- a/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-security/pom.xml
+++ b/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-security/pom.xml
@@ -299,8 +299,14 @@
test
- com.squareup.okhttp3
- okhttp
+ org.apache.nifi
+ nifi-web-client-api
+ 2.0.0-SNAPSHOT
+
+
+ org.apache.nifi
+ nifi-web-client
+ 2.0.0-SNAPSHOT
org.glassfish.jaxb
diff --git a/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-security/src/main/java/org/apache/nifi/web/security/configuration/SamlAuthenticationSecurityConfiguration.java b/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-security/src/main/java/org/apache/nifi/web/security/configuration/SamlAuthenticationSecurityConfiguration.java
index d3b9c95bbb..27a8095480 100644
--- a/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-security/src/main/java/org/apache/nifi/web/security/configuration/SamlAuthenticationSecurityConfiguration.java
+++ b/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-security/src/main/java/org/apache/nifi/web/security/configuration/SamlAuthenticationSecurityConfiguration.java
@@ -73,7 +73,6 @@ import org.springframework.security.saml2.provider.service.web.authentication.lo
import org.springframework.security.web.authentication.session.NullAuthenticatedSessionStrategy;
import org.springframework.security.web.util.matcher.AntPathRequestMatcher;
-import javax.net.ssl.SSLContext;
import javax.net.ssl.X509ExtendedKeyManager;
import javax.net.ssl.X509ExtendedTrustManager;
import java.time.Duration;
@@ -95,8 +94,6 @@ public class SamlAuthenticationSecurityConfiguration {
private final LogoutRequestManager logoutRequestManager;
- private final SSLContext sslContext;
-
private final X509ExtendedKeyManager keyManager;
private final X509ExtendedTrustManager trustManager;
@@ -105,14 +102,12 @@ public class SamlAuthenticationSecurityConfiguration {
@Autowired final NiFiProperties properties,
@Autowired final BearerTokenProvider bearerTokenProvider,
@Autowired final LogoutRequestManager logoutRequestManager,
- @Autowired(required = false) final SSLContext sslContext,
@Autowired(required = false) final X509ExtendedKeyManager keyManager,
@Autowired(required = false) final X509ExtendedTrustManager trustManager
) {
this.properties = Objects.requireNonNull(properties, "Properties required");
this.bearerTokenProvider = Objects.requireNonNull(bearerTokenProvider, "Bearer Token Provider required");
this.logoutRequestManager = Objects.requireNonNull(logoutRequestManager, "Logout Request Manager required");
- this.sslContext = sslContext;
this.keyManager = keyManager;
this.trustManager = trustManager;
}
@@ -320,7 +315,7 @@ public class SamlAuthenticationSecurityConfiguration {
@Bean
public RelyingPartyRegistrationRepository relyingPartyRegistrationRepository() {
return properties.isSamlEnabled()
- ? new StandardRelyingPartyRegistrationRepository(properties, sslContext, keyManager, trustManager)
+ ? new StandardRelyingPartyRegistrationRepository(properties, keyManager, trustManager)
: getDisabledRelyingPartyRegistrationRepository();
}
diff --git a/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-security/src/main/java/org/apache/nifi/web/security/saml2/registration/StandardRegistrationBuilderProvider.java b/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-security/src/main/java/org/apache/nifi/web/security/saml2/registration/StandardRegistrationBuilderProvider.java
index b8717dfe70..bd3ba41530 100644
--- a/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-security/src/main/java/org/apache/nifi/web/security/saml2/registration/StandardRegistrationBuilderProvider.java
+++ b/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-security/src/main/java/org/apache/nifi/web/security/saml2/registration/StandardRegistrationBuilderProvider.java
@@ -16,26 +16,27 @@
*/
package org.apache.nifi.web.security.saml2.registration;
-import okhttp3.Call;
-import okhttp3.OkHttpClient;
-import okhttp3.Request;
-import okhttp3.Response;
-import okhttp3.ResponseBody;
import org.apache.nifi.util.FormatUtils;
import org.apache.nifi.util.NiFiProperties;
+import org.apache.nifi.web.client.StandardWebClientService;
+import org.apache.nifi.web.client.api.HttpResponseEntity;
+import org.apache.nifi.web.client.api.HttpResponseStatus;
+import org.apache.nifi.web.client.api.WebClientService;
+import org.apache.nifi.web.client.ssl.TlsContext;
import org.apache.nifi.web.security.saml2.SamlConfigurationException;
import org.springframework.core.io.DefaultResourceLoader;
import org.springframework.core.io.ResourceLoader;
import org.springframework.security.saml2.provider.service.registration.RelyingPartyRegistration;
import org.springframework.security.saml2.provider.service.registration.RelyingPartyRegistrations;
-import javax.net.ssl.SSLContext;
-import javax.net.ssl.SSLSocketFactory;
+import javax.net.ssl.X509KeyManager;
import javax.net.ssl.X509TrustManager;
import java.io.IOException;
import java.io.InputStream;
+import java.net.URI;
import java.time.Duration;
import java.util.Objects;
+import java.util.Optional;
import java.util.concurrent.TimeUnit;
/**
@@ -46,21 +47,23 @@ class StandardRegistrationBuilderProvider implements RegistrationBuilderProvider
private static final String HTTP_SCHEME_PREFIX = "http";
+ private static final String TLS_PROTOCOL = "TLS";
+
private static final ResourceLoader resourceLoader = new DefaultResourceLoader();
private final NiFiProperties properties;
- private final SSLContext sslContext;
+ private final X509KeyManager keyManager;
private final X509TrustManager trustManager;
public StandardRegistrationBuilderProvider(
final NiFiProperties properties,
- final SSLContext sslContext,
+ final X509KeyManager keyManager,
final X509TrustManager trustManager
) {
this.properties = Objects.requireNonNull(properties, "Properties required");
- this.sslContext = sslContext;
+ this.keyManager = keyManager;
this.trustManager = trustManager;
}
@@ -91,25 +94,26 @@ class StandardRegistrationBuilderProvider implements RegistrationBuilderProvider
}
private InputStream getRemoteInputStream(final String metadataUrl) {
- final OkHttpClient client = getHttpClient();
+ final WebClientService webClientService = getWebClientService();
+
+ final URI uri = URI.create(metadataUrl);
- final Request request = new Request.Builder().get().url(metadataUrl).build();
- final Call call = client.newCall(request);
try {
- final Response response = call.execute();
- if (response.isSuccessful()) {
- final ResponseBody body = Objects.requireNonNull(response.body(), "SAML Metadata response not found");
- return body.byteStream();
+ final HttpResponseEntity responseEntity = webClientService.get().uri(uri).retrieve();
+ final int statusCode = responseEntity.statusCode();
+
+ if (HttpResponseStatus.OK.getCode() == statusCode) {
+ return responseEntity.body();
} else {
- response.close();
- throw new SamlConfigurationException(String.format("SAML Metadata retrieval failed [%s] HTTP %d", metadataUrl, response.code()));
+ responseEntity.close();
+ throw new SamlConfigurationException(String.format("SAML Metadata retrieval failed [%s] HTTP %d", metadataUrl, statusCode));
}
} catch (final IOException e) {
throw new SamlConfigurationException(String.format("SAML Metadata retrieval failed [%s]", metadataUrl), e);
}
}
- private OkHttpClient getHttpClient() {
+ private WebClientService getWebClientService() {
final Duration connectTimeout = Duration.ofMillis(
(long) FormatUtils.getPreciseTimeDuration(properties.getSamlHttpClientConnectTimeout(), TimeUnit.MILLISECONDS)
);
@@ -117,15 +121,29 @@ class StandardRegistrationBuilderProvider implements RegistrationBuilderProvider
(long) FormatUtils.getPreciseTimeDuration(properties.getSamlHttpClientReadTimeout(), TimeUnit.MILLISECONDS)
);
- final OkHttpClient.Builder builder = new OkHttpClient.Builder()
- .connectTimeout(connectTimeout)
- .readTimeout(readTimeout);
+ final StandardWebClientService webClientService = new StandardWebClientService();
+ webClientService.setConnectTimeout(connectTimeout);
+ webClientService.setReadTimeout(readTimeout);
if (NIFI_TRUST_STORE_STRATEGY.equals(properties.getSamlHttpClientTruststoreStrategy())) {
- final SSLSocketFactory sslSocketFactory = sslContext.getSocketFactory();
- builder.sslSocketFactory(sslSocketFactory, trustManager);
+ webClientService.setTlsContext(new TlsContext() {
+ @Override
+ public String getProtocol() {
+ return TLS_PROTOCOL;
+ }
+
+ @Override
+ public X509TrustManager getTrustManager() {
+ return trustManager;
+ }
+
+ @Override
+ public Optional getKeyManager() {
+ return Optional.ofNullable(keyManager);
+ }
+ });
}
- return builder.build();
+ return webClientService;
}
}
diff --git a/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-security/src/main/java/org/apache/nifi/web/security/saml2/registration/StandardRelyingPartyRegistrationRepository.java b/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-security/src/main/java/org/apache/nifi/web/security/saml2/registration/StandardRelyingPartyRegistrationRepository.java
index 83c1fd435d..f5a62aea31 100644
--- a/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-security/src/main/java/org/apache/nifi/web/security/saml2/registration/StandardRelyingPartyRegistrationRepository.java
+++ b/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-security/src/main/java/org/apache/nifi/web/security/saml2/registration/StandardRelyingPartyRegistrationRepository.java
@@ -24,7 +24,6 @@ import org.springframework.security.saml2.core.Saml2X509Credential;
import org.springframework.security.saml2.provider.service.registration.RelyingPartyRegistration;
import org.springframework.security.saml2.provider.service.registration.RelyingPartyRegistrationRepository;
-import javax.net.ssl.SSLContext;
import javax.net.ssl.X509ExtendedKeyManager;
import javax.net.ssl.X509ExtendedTrustManager;
import java.security.Principal;
@@ -34,6 +33,7 @@ import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collection;
import java.util.List;
+
/**
* Standard implementation of Relying Party Registration Repository based on NiFi Properties
*/
@@ -52,8 +52,6 @@ public class StandardRelyingPartyRegistrationRepository implements RelyingPartyR
private final NiFiProperties properties;
- private final SSLContext sslContext;
-
private final X509ExtendedTrustManager trustManager;
private final X509ExtendedKeyManager keyManager;
@@ -63,19 +61,16 @@ public class StandardRelyingPartyRegistrationRepository implements RelyingPartyR
/**
* Standard implementation builds a Registration based on NiFi Properties and returns the same instance for all queries
*
- * @param sslContext SSL Context loaded from properties
* @param keyManager Key Manager loaded from properties
* @param trustManager Trust manager loaded from properties
* @param properties NiFi Application Properties
*/
public StandardRelyingPartyRegistrationRepository(
final NiFiProperties properties,
- final SSLContext sslContext,
final X509ExtendedKeyManager keyManager,
final X509ExtendedTrustManager trustManager
) {
this.properties = properties;
- this.sslContext = sslContext;
this.keyManager = keyManager;
this.trustManager = trustManager;
this.relyingPartyRegistration = getRelyingPartyRegistration();
@@ -87,7 +82,7 @@ public class StandardRelyingPartyRegistrationRepository implements RelyingPartyR
}
private RelyingPartyRegistration getRelyingPartyRegistration() {
- final RegistrationBuilderProvider registrationBuilderProvider = new StandardRegistrationBuilderProvider(properties, sslContext, trustManager);
+ final RegistrationBuilderProvider registrationBuilderProvider = new StandardRegistrationBuilderProvider(properties, keyManager, trustManager);
final RelyingPartyRegistration.Builder builder = registrationBuilderProvider.getRegistrationBuilder();
builder.registrationId(Saml2RegistrationProperty.REGISTRATION_ID.getProperty());
diff --git a/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-security/src/test/java/org/apache/nifi/web/security/saml2/registration/StandardRegistrationBuilderProviderTest.java b/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-security/src/test/java/org/apache/nifi/web/security/saml2/registration/StandardRegistrationBuilderProviderTest.java
index 6344413824..f3602e275d 100644
--- a/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-security/src/test/java/org/apache/nifi/web/security/saml2/registration/StandardRegistrationBuilderProviderTest.java
+++ b/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-security/src/test/java/org/apache/nifi/web/security/saml2/registration/StandardRegistrationBuilderProviderTest.java
@@ -20,10 +20,12 @@ import okhttp3.HttpUrl;
import okhttp3.mockwebserver.MockResponse;
import okhttp3.mockwebserver.MockWebServer;
import org.apache.commons.io.IOUtils;
-import org.apache.nifi.security.util.SslContextFactory;
+import org.apache.nifi.security.ssl.StandardKeyManagerBuilder;
+import org.apache.nifi.security.ssl.StandardKeyStoreBuilder;
+import org.apache.nifi.security.ssl.StandardSslContextBuilder;
+import org.apache.nifi.security.ssl.StandardTrustManagerBuilder;
import org.apache.nifi.security.util.TemporaryKeyStoreBuilder;
import org.apache.nifi.security.util.TlsConfiguration;
-import org.apache.nifi.security.util.TlsException;
import org.apache.nifi.util.NiFiProperties;
import org.apache.nifi.web.security.saml2.SamlConfigurationException;
import org.junit.jupiter.api.AfterEach;
@@ -34,11 +36,16 @@ import org.springframework.security.saml2.provider.service.registration.Saml2Mes
import javax.net.ssl.SSLContext;
import javax.net.ssl.SSLSocketFactory;
+import javax.net.ssl.X509ExtendedKeyManager;
+import javax.net.ssl.X509ExtendedTrustManager;
+import javax.net.ssl.X509KeyManager;
import javax.net.ssl.X509TrustManager;
+import java.io.FileInputStream;
import java.io.IOException;
import java.io.InputStream;
import java.net.URL;
import java.nio.charset.StandardCharsets;
+import java.security.KeyStore;
import java.util.Objects;
import java.util.Properties;
@@ -102,10 +109,15 @@ class StandardRegistrationBuilderProviderTest {
}
@Test
- void testGetRegistrationBuilderHttpsUrl() throws IOException, TlsException {
+ void testGetRegistrationBuilderHttpsUrl() throws IOException {
final TlsConfiguration tlsConfiguration = new TemporaryKeyStoreBuilder().build();
- final SSLContext sslContext = Objects.requireNonNull(SslContextFactory.createSslContext(tlsConfiguration));
- final X509TrustManager trustManager = SslContextFactory.getX509TrustManager(tlsConfiguration);
+ final X509KeyManager keyManager = getKeyManager(tlsConfiguration);
+ final X509TrustManager trustManager = getTrustManager(tlsConfiguration);
+ final SSLContext sslContext = new StandardSslContextBuilder()
+ .keyManager(keyManager)
+ .keyPassword(tlsConfiguration.getKeyPassword().toCharArray())
+ .trustManager(trustManager)
+ .build();
final SSLSocketFactory sslSocketFactory = Objects.requireNonNull(sslContext.getSocketFactory());
mockWebServer.useHttps(sslSocketFactory, PROXY_DISABLED);
@@ -117,7 +129,7 @@ class StandardRegistrationBuilderProviderTest {
final NiFiProperties properties = getProperties(metadataUrl, tlsConfiguration);
- assertRegistrationFound(properties, sslContext, trustManager);
+ assertRegistrationFound(properties, keyManager, trustManager);
}
private String getMetadataUrl() {
@@ -125,14 +137,41 @@ class StandardRegistrationBuilderProviderTest {
return url.toString();
}
- private void assertRegistrationFound(final NiFiProperties properties, final SSLContext sslContext, final X509TrustManager trustManager) {
- final StandardRegistrationBuilderProvider provider = new StandardRegistrationBuilderProvider(properties, sslContext, trustManager);
+ private void assertRegistrationFound(final NiFiProperties properties, final X509KeyManager keyManager, final X509TrustManager trustManager) {
+ final StandardRegistrationBuilderProvider provider = new StandardRegistrationBuilderProvider(properties, keyManager, trustManager);
final RelyingPartyRegistration.Builder builder = provider.getRegistrationBuilder();
final RelyingPartyRegistration registration = builder.build();
assertEquals(Saml2MessageBinding.POST, registration.getAssertionConsumerServiceBinding());
}
+ private X509ExtendedKeyManager getKeyManager(final TlsConfiguration tlsConfiguration) throws IOException {
+ try (InputStream inputStream = new FileInputStream(tlsConfiguration.getKeystorePath())) {
+ final KeyStore keyStore = new StandardKeyStoreBuilder()
+ .inputStream(inputStream)
+ .password(tlsConfiguration.getKeystorePassword().toCharArray())
+ .type(tlsConfiguration.getKeystoreType().getType())
+ .build();
+
+ return new StandardKeyManagerBuilder()
+ .keyStore(keyStore)
+ .keyPassword(tlsConfiguration.getFunctionalKeyPassword().toCharArray())
+ .build();
+ }
+ }
+
+ private X509ExtendedTrustManager getTrustManager(final TlsConfiguration tlsConfiguration) throws IOException {
+ try (InputStream inputStream = new FileInputStream(tlsConfiguration.getTruststorePath())) {
+ final KeyStore trustStore = new StandardKeyStoreBuilder()
+ .inputStream(inputStream)
+ .password(tlsConfiguration.getTruststorePassword().toCharArray())
+ .type(tlsConfiguration.getTruststoreType().getType())
+ .build();
+
+ return new StandardTrustManagerBuilder().trustStore(trustStore).build();
+ }
+ }
+
private NiFiProperties getProperties(final String metadataUrl) {
final Properties properties = new Properties();
properties.setProperty(NiFiProperties.SECURITY_USER_SAML_IDP_METADATA_URL, metadataUrl);
diff --git a/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-security/src/test/java/org/apache/nifi/web/security/saml2/registration/StandardRelyingPartyRegistrationRepositoryTest.java b/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-security/src/test/java/org/apache/nifi/web/security/saml2/registration/StandardRelyingPartyRegistrationRepositoryTest.java
index 47c603e4c0..3bc3cb8f1f 100644
--- a/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-security/src/test/java/org/apache/nifi/web/security/saml2/registration/StandardRelyingPartyRegistrationRepositoryTest.java
+++ b/nifi-framework-bundle/nifi-framework/nifi-web/nifi-web-security/src/test/java/org/apache/nifi/web/security/saml2/registration/StandardRelyingPartyRegistrationRepositoryTest.java
@@ -18,7 +18,6 @@ package org.apache.nifi.web.security.saml2.registration;
import org.apache.nifi.security.ssl.StandardKeyManagerBuilder;
import org.apache.nifi.security.ssl.StandardKeyStoreBuilder;
-import org.apache.nifi.security.ssl.StandardSslContextBuilder;
import org.apache.nifi.security.ssl.StandardTrustManagerBuilder;
import org.apache.nifi.security.util.TemporaryKeyStoreBuilder;
import org.apache.nifi.security.util.TlsConfiguration;
@@ -28,7 +27,6 @@ import org.opensaml.xmlsec.signature.support.SignatureConstants;
import org.springframework.security.saml2.core.Saml2X509Credential;
import org.springframework.security.saml2.provider.service.registration.RelyingPartyRegistration;
-import javax.net.ssl.SSLContext;
import javax.net.ssl.X509ExtendedKeyManager;
import javax.net.ssl.X509ExtendedTrustManager;
import javax.security.auth.x500.X500Principal;
@@ -59,7 +57,7 @@ class StandardRelyingPartyRegistrationRepositoryTest {
@Test
void testFindByRegistrationId() {
final NiFiProperties properties = getProperties();
- final StandardRelyingPartyRegistrationRepository repository = new StandardRelyingPartyRegistrationRepository(properties, null, null, null);
+ final StandardRelyingPartyRegistrationRepository repository = new StandardRelyingPartyRegistrationRepository(properties, null, null);
final RelyingPartyRegistration registration = repository.findByRegistrationId(Saml2RegistrationProperty.REGISTRATION_ID.getProperty());
@@ -81,10 +79,9 @@ class StandardRelyingPartyRegistrationRepositoryTest {
final TlsConfiguration tlsConfiguration = new TemporaryKeyStoreBuilder().build();
final X509ExtendedKeyManager keyManager = getKeyManager(tlsConfiguration);
final X509ExtendedTrustManager trustManager = getTrustManager(tlsConfiguration);
- final SSLContext sslContext = new StandardSslContextBuilder().keyManager(keyManager).trustManager(trustManager).build();
final NiFiProperties properties = getSingleLogoutProperties(tlsConfiguration);
- final StandardRelyingPartyRegistrationRepository repository = new StandardRelyingPartyRegistrationRepository(properties, sslContext, keyManager, trustManager);
+ final StandardRelyingPartyRegistrationRepository repository = new StandardRelyingPartyRegistrationRepository(properties, keyManager, trustManager);
final RelyingPartyRegistration registration = repository.findByRegistrationId(Saml2RegistrationProperty.REGISTRATION_ID.getProperty());