aboutsummaryrefslogtreecommitdiff
path: root/connector
diff options
context:
space:
mode:
authorThomas Lenz <thomas.lenz@egiz.gv.at>2020-02-21 16:22:31 +0100
committerThomas Lenz <thomas.lenz@egiz.gv.at>2020-02-21 16:22:31 +0100
commit7ba8da297b7be40255ba5efb40c69a21fb130b3b (patch)
tree14294d39790209235180d6a1de48539e163e7ebf /connector
parentd5f104bf22d204732897ef7127ad704d43d7a194 (diff)
downloadNational_eIDAS_Gateway-7ba8da297b7be40255ba5efb40c69a21fb130b3b.tar.gz
National_eIDAS_Gateway-7ba8da297b7be40255ba5efb40c69a21fb130b3b.tar.bz2
National_eIDAS_Gateway-7ba8da297b7be40255ba5efb40c69a21fb130b3b.zip
update to latest EAAF-components that uses OpenSAML3.x
Diffstat (limited to 'connector')
-rw-r--r--connector/src/main/java/at/asitplus/eidas/specific/connector/SpringInitializer.java4
-rw-r--r--connector/src/main/java/at/asitplus/eidas/specific/connector/config/PvpEndPointConfiguration.java11
-rw-r--r--connector/src/main/java/at/asitplus/eidas/specific/connector/config/PvpMetadataConfiguration.java32
-rw-r--r--connector/src/main/java/at/asitplus/eidas/specific/connector/controller/MonitoringController.java27
-rw-r--r--connector/src/main/java/at/asitplus/eidas/specific/connector/provider/PvpEndPointCredentialProvider.java59
-rw-r--r--connector/src/main/java/at/asitplus/eidas/specific/connector/provider/PvpMetadataConfigurationFactory.java6
-rw-r--r--connector/src/main/java/at/asitplus/eidas/specific/connector/provider/PvpMetadataProvider.java137
-rw-r--r--connector/src/main/java/at/asitplus/eidas/specific/connector/verification/AuthnRequestValidator.java18
-rw-r--r--connector/src/main/java/at/asitplus/eidas/specific/connector/verification/MetadataSignatureVerificationFilter.java175
-rw-r--r--connector/src/test/java/at/asitplus/eidas/specific/connector/test/AuthnRequestValidatorTest.java24
-rw-r--r--connector/src/test/resources/config/junit_config_1.properties12
-rw-r--r--connector/src/test/resources/config/keys/junit.jksbin0 -> 3980 bytes
12 files changed, 181 insertions, 324 deletions
diff --git a/connector/src/main/java/at/asitplus/eidas/specific/connector/SpringInitializer.java b/connector/src/main/java/at/asitplus/eidas/specific/connector/SpringInitializer.java
index 76802825..417828a6 100644
--- a/connector/src/main/java/at/asitplus/eidas/specific/connector/SpringInitializer.java
+++ b/connector/src/main/java/at/asitplus/eidas/specific/connector/SpringInitializer.java
@@ -48,7 +48,7 @@ import at.gv.egiz.components.spring.api.SpringLoader;
import at.gv.egiz.eaaf.core.api.IStatusMessenger;
import at.gv.egiz.eaaf.core.impl.logging.LogMessageProviderFactory;
import at.gv.egiz.eaaf.core.impl.utils.Random;
-import at.gv.egiz.eaaf.modules.pvp2.impl.opensaml.initialize.EaafDefaultSaml2Bootstrap;
+import at.gv.egiz.eaaf.modules.pvp2.impl.opensaml.initialize.EaafOpenSaml3xInitializer;
/**
* Web application initializer.
@@ -156,7 +156,7 @@ public class SpringInitializer implements WebApplicationInitializer {
LogMessageProviderFactory.setStatusMessager(rootContext.getBean(IStatusMessenger.class));
log.info("Bootstrap openSAML .... ");
- EaafDefaultSaml2Bootstrap.bootstrap();
+ EaafOpenSaml3xInitializer.eaafInitialize();
log.info("Seed random number generator ... ");
Random.seedRandom();
diff --git a/connector/src/main/java/at/asitplus/eidas/specific/connector/config/PvpEndPointConfiguration.java b/connector/src/main/java/at/asitplus/eidas/specific/connector/config/PvpEndPointConfiguration.java
index fb7cb625..82be730c 100644
--- a/connector/src/main/java/at/asitplus/eidas/specific/connector/config/PvpEndPointConfiguration.java
+++ b/connector/src/main/java/at/asitplus/eidas/specific/connector/config/PvpEndPointConfiguration.java
@@ -25,8 +25,8 @@ package at.asitplus.eidas.specific.connector.config;
import java.util.List;
-import org.opensaml.saml2.metadata.ContactPerson;
-import org.opensaml.saml2.metadata.Organization;
+import org.opensaml.saml.saml2.metadata.ContactPerson;
+import org.opensaml.saml.saml2.metadata.Organization;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
@@ -63,7 +63,7 @@ public class PvpEndPointConfiguration implements IPvp2BasicConfiguration {
}
@Override
- public Object getIdpSsoSoapService(String extractAuthUrlFromRequest) throws EaafException {
+ public String getIdpSsoSoapService(String extractAuthUrlFromRequest) throws EaafException {
log.warn("PVP S-Profile End-Point does NOT support SOAP Binding");
return null;
@@ -81,6 +81,11 @@ public class PvpEndPointConfiguration implements IPvp2BasicConfiguration {
return null;
}
+ @Override
+ public IConfiguration getBasicConfiguration() {
+ return basicConfiguration;
+ }
+
private String removePostFix(String url) {
if (url != null && url.endsWith("/")) {
return url.substring(0, url.length() - 1);
diff --git a/connector/src/main/java/at/asitplus/eidas/specific/connector/config/PvpMetadataConfiguration.java b/connector/src/main/java/at/asitplus/eidas/specific/connector/config/PvpMetadataConfiguration.java
index f1828f87..0fc061ff 100644
--- a/connector/src/main/java/at/asitplus/eidas/specific/connector/config/PvpMetadataConfiguration.java
+++ b/connector/src/main/java/at/asitplus/eidas/specific/connector/config/PvpMetadataConfiguration.java
@@ -26,12 +26,11 @@ package at.asitplus.eidas.specific.connector.config;
import java.util.Arrays;
import java.util.List;
-import org.opensaml.saml2.core.Attribute;
-import org.opensaml.saml2.core.NameIDType;
-import org.opensaml.saml2.metadata.ContactPerson;
-import org.opensaml.saml2.metadata.Organization;
-import org.opensaml.saml2.metadata.RequestedAttribute;
-import org.opensaml.xml.security.credential.Credential;
+import org.opensaml.saml.saml2.core.Attribute;
+import org.opensaml.saml.saml2.core.NameIDType;
+import org.opensaml.saml.saml2.metadata.ContactPerson;
+import org.opensaml.saml.saml2.metadata.Organization;
+import org.opensaml.saml.saml2.metadata.RequestedAttribute;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
@@ -39,17 +38,18 @@ import at.asitplus.eidas.specific.connector.MsEidasNodeConstants;
import at.gv.egiz.eaaf.core.api.idp.IConfiguration;
import at.gv.egiz.eaaf.core.exceptions.EaafException;
import at.gv.egiz.eaaf.modules.pvp2.api.IPvp2BasicConfiguration;
+import at.gv.egiz.eaaf.modules.pvp2.api.credential.EaafX509Credential;
import at.gv.egiz.eaaf.modules.pvp2.api.metadata.IPvpMetadataBuilderConfiguration;
+import at.gv.egiz.eaaf.modules.pvp2.api.utils.IPvp2CredentialProvider;
import at.gv.egiz.eaaf.modules.pvp2.exception.CredentialsNotAvailableException;
import at.gv.egiz.eaaf.modules.pvp2.impl.builder.PvpAttributeBuilder;
-import at.gv.egiz.eaaf.modules.pvp2.impl.utils.AbstractCredentialProvider;
public class PvpMetadataConfiguration implements IPvpMetadataBuilderConfiguration {
private static final Logger log = LoggerFactory.getLogger(PvpMetadataConfiguration.class);
private final IConfiguration basicConfig;
private final String authUrl;
- private final AbstractCredentialProvider pvpIdpCredentials;
+ private final IPvp2CredentialProvider pvpIdpCredentials;
private final IPvp2BasicConfiguration pvpBasicConfig;
/**
@@ -58,12 +58,12 @@ public class PvpMetadataConfiguration implements IPvpMetadataBuilderConfiguratio
* @param basicConfig Application configuration
* @param authUrl Public-URL Prefix of the application
* @param pvpBasicConfig PVP2 configuration object
- * @param pvpIdpCredentials PVP2 credentials
+ * @param pvpIdpCredentials2 PVP2 credentials
*/
public PvpMetadataConfiguration(IConfiguration basicConfig, String authUrl,
- IPvp2BasicConfiguration pvpBasicConfig, AbstractCredentialProvider pvpIdpCredentials) {
+ IPvp2BasicConfiguration pvpBasicConfig, IPvp2CredentialProvider pvpIdpCredentials2) {
this.authUrl = authUrl;
- this.pvpIdpCredentials = pvpIdpCredentials;
+ this.pvpIdpCredentials = pvpIdpCredentials2;
this.basicConfig = basicConfig;
this.pvpBasicConfig = pvpBasicConfig;
@@ -145,19 +145,19 @@ public class PvpMetadataConfiguration implements IPvpMetadataBuilderConfiguratio
}
@Override
- public Credential getMetadataSigningCredentials() throws CredentialsNotAvailableException {
- return pvpIdpCredentials.getIdpMetaDataSigningCredential();
+ public EaafX509Credential getMetadataSigningCredentials() throws CredentialsNotAvailableException {
+ return pvpIdpCredentials.getMetaDataSigningCredential();
}
@Override
- public Credential getRequestorResponseSigningCredentials() throws CredentialsNotAvailableException {
- return pvpIdpCredentials.getIdpAssertionSigningCredential();
+ public EaafX509Credential getRequestorResponseSigningCredentials() throws CredentialsNotAvailableException {
+ return pvpIdpCredentials.getMessageSigningCredential();
}
@Override
- public Credential getEncryptionCredentials() throws CredentialsNotAvailableException {
+ public EaafX509Credential getEncryptionCredentials() throws CredentialsNotAvailableException {
return null;
}
diff --git a/connector/src/main/java/at/asitplus/eidas/specific/connector/controller/MonitoringController.java b/connector/src/main/java/at/asitplus/eidas/specific/connector/controller/MonitoringController.java
index 2776ec53..633559de 100644
--- a/connector/src/main/java/at/asitplus/eidas/specific/connector/controller/MonitoringController.java
+++ b/connector/src/main/java/at/asitplus/eidas/specific/connector/controller/MonitoringController.java
@@ -29,12 +29,12 @@ import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.xml.transform.TransformerFactoryConfigurationError;
-import org.apache.commons.httpclient.HttpClient;
-import org.apache.commons.httpclient.HttpMethod;
-import org.apache.commons.httpclient.methods.GetMethod;
-import org.apache.commons.httpclient.params.HttpClientParams;
import org.apache.commons.lang3.StringUtils;
import org.apache.commons.text.StringEscapeUtils;
+import org.apache.http.client.methods.CloseableHttpResponse;
+import org.apache.http.client.methods.HttpGet;
+import org.apache.http.client.methods.HttpUriRequest;
+import org.apache.http.impl.client.CloseableHttpClient;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
@@ -49,6 +49,7 @@ import at.gv.egiz.eaaf.core.api.idp.IConfigurationWithSP;
import at.gv.egiz.eaaf.core.api.storage.ITransactionStorage;
import at.gv.egiz.eaaf.core.exceptions.EaafException;
import at.gv.egiz.eaaf.core.impl.utils.DomUtils;
+import at.gv.egiz.eaaf.core.impl.utils.IHttpClientFactory;
import at.gv.egiz.eaaf.core.impl.utils.Random;
import at.gv.egiz.eaaf.modules.pvp2.api.metadata.IPvpMetadataBuilderConfiguration;
import at.gv.egiz.eaaf.modules.pvp2.api.metadata.IPvpMetadataConfigurationFactory;
@@ -73,6 +74,8 @@ public class MonitoringController {
@Autowired
private IConfigurationWithSP config;
+ @Autowired private IHttpClientFactory httpClientFactory;
+
@Autowired
private PvpMetadataBuilder metadatabuilder;
@Autowired
@@ -248,17 +251,11 @@ public class MonitoringController {
// create HTTP client
// TODO: update if we switch to openSAML3
- final HttpClient httpClient = new HttpClient();
+ CloseableHttpClient httpClient = httpClientFactory.getHttpClient();
+ HttpUriRequest request = new HttpGet(urlString);
- // set parameters
- final HttpClientParams params = new HttpClientParams();
- params.setSoTimeout(5 * 1000);
- httpClient.setParams(params);
-
- // request URL
- final HttpMethod method = new GetMethod(urlString);
- final int respCode = httpClient.executeMethod(method);
- if (respCode != 200) {
+ final CloseableHttpResponse respCode = httpClient.execute(request);
+ if (respCode.getStatusLine().getStatusCode() != 200) {
log.warn("Monitoring: Has an error in '" + TEST_EIDASNODEMETADATA + "': " + " HTTP responsecode: "
+ respCode);
throw new Exception(TEST_EIDASNODEMETADATA + MESSAGE_ERROR);
@@ -266,7 +263,7 @@ public class MonitoringController {
}
// parse metadata
- DomUtils.parseXmlNonValidating(method.getResponseBodyAsStream());
+ DomUtils.parseXmlNonValidating(respCode.getEntity().getContent());
return TEST_EIDASNODEMETADATA + MESSAGE_OK;
diff --git a/connector/src/main/java/at/asitplus/eidas/specific/connector/provider/PvpEndPointCredentialProvider.java b/connector/src/main/java/at/asitplus/eidas/specific/connector/provider/PvpEndPointCredentialProvider.java
index 92373328..0ae5f76d 100644
--- a/connector/src/main/java/at/asitplus/eidas/specific/connector/provider/PvpEndPointCredentialProvider.java
+++ b/connector/src/main/java/at/asitplus/eidas/specific/connector/provider/PvpEndPointCredentialProvider.java
@@ -23,9 +23,6 @@
package at.asitplus.eidas.specific.connector.provider;
-import java.net.MalformedURLException;
-
-import org.apache.commons.lang3.StringUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
@@ -33,8 +30,8 @@ import org.springframework.beans.factory.annotation.Autowired;
import at.asitplus.eidas.specific.connector.MsEidasNodeConstants;
import at.gv.egiz.eaaf.core.api.idp.IConfiguration;
import at.gv.egiz.eaaf.core.exceptions.EaafConfigurationException;
-import at.gv.egiz.eaaf.core.exceptions.EaafException;
-import at.gv.egiz.eaaf.core.impl.utils.FileUtils;
+import at.gv.egiz.eaaf.core.impl.credential.KeyStoreConfiguration;
+import at.gv.egiz.eaaf.core.impl.credential.KeyStoreConfiguration.KeyStoreType;
import at.gv.egiz.eaaf.modules.pvp2.impl.utils.AbstractCredentialProvider;
public class PvpEndPointCredentialProvider extends AbstractCredentialProvider {
@@ -44,41 +41,25 @@ public class PvpEndPointCredentialProvider extends AbstractCredentialProvider {
IConfiguration basicConfiguration;
@Override
- public String getFriendlyName() {
- return "PVP2 S-Profile EndPoint";
- }
-
- @Override
- public String getKeyStoreFilePath() throws EaafException {
- try {
- final String path = basicConfiguration.getBasicConfiguration(
- MsEidasNodeConstants.PROP_CONFIG_PVP2_KEYSTORE_PATH);
- if (StringUtils.isEmpty(path)) {
- log.error(getFriendlyName() + " | Path to keyStore is NULL or EMPTY");
- throw new EaafConfigurationException("config.27",
- new Object[] { getFriendlyName() + " | Path to keyStore is NULL or EMPTY" });
-
- }
-
- return FileUtils.makeAbsoluteUrl(
- path,
- basicConfiguration.getConfigurationRootDirectory());
-
- } catch (final MalformedURLException e) {
- log.error(getFriendlyName() + " | Path to keyStore NOT valid.", e);
- throw new EaafConfigurationException("config.27",
- new Object[] { getFriendlyName() + " | Path to keyStore NOT valid." }, e);
-
- }
-
- }
-
- @Override
- public String getKeyStorePassword() {
- return basicConfiguration.getBasicConfiguration(MsEidasNodeConstants.PROP_CONFIG_PVP2_KEYSTORE_PASSWORD);
-
+ public KeyStoreConfiguration getBasicKeyStoreConfig() throws EaafConfigurationException {
+ final KeyStoreConfiguration keyStoreConfig = new KeyStoreConfiguration();
+ keyStoreConfig.setFriendlyName("PVP2 S-Profile EndPoint");
+ keyStoreConfig.setKeyStoreType(
+ basicConfiguration.getBasicConfiguration(MsEidasNodeConstants.CONFIG_PROPS_KEYSTORE_TYPE,
+ KeyStoreType.PKCS12.getKeyStoreType()));
+ keyStoreConfig.setKeyStoreName(
+ basicConfiguration.getBasicConfiguration(MsEidasNodeConstants.CONFIG_PROPS_KEYSTORE_NAME));
+ keyStoreConfig.setSoftKeyStoreFilePath(basicConfiguration.getBasicConfiguration(
+ MsEidasNodeConstants.PROP_CONFIG_PVP2_KEYSTORE_PATH));
+ keyStoreConfig.setSoftKeyStorePassword(
+ basicConfiguration.getBasicConfiguration(MsEidasNodeConstants.PROP_CONFIG_PVP2_KEYSTORE_PASSWORD));
+
+ keyStoreConfig.validate();
+
+ return keyStoreConfig;
}
-
+
+
@Override
public String getMetadataKeyAlias() {
return basicConfiguration.getBasicConfiguration(MsEidasNodeConstants.PROP_CONFIG_PVP2_KEY_METADATA_ALIAS);
diff --git a/connector/src/main/java/at/asitplus/eidas/specific/connector/provider/PvpMetadataConfigurationFactory.java b/connector/src/main/java/at/asitplus/eidas/specific/connector/provider/PvpMetadataConfigurationFactory.java
index 8b0419d0..e8bc4eb8 100644
--- a/connector/src/main/java/at/asitplus/eidas/specific/connector/provider/PvpMetadataConfigurationFactory.java
+++ b/connector/src/main/java/at/asitplus/eidas/specific/connector/provider/PvpMetadataConfigurationFactory.java
@@ -31,7 +31,7 @@ import at.gv.egiz.eaaf.core.api.idp.IConfiguration;
import at.gv.egiz.eaaf.modules.pvp2.api.IPvp2BasicConfiguration;
import at.gv.egiz.eaaf.modules.pvp2.api.metadata.IPvpMetadataBuilderConfiguration;
import at.gv.egiz.eaaf.modules.pvp2.api.metadata.IPvpMetadataConfigurationFactory;
-import at.gv.egiz.eaaf.modules.pvp2.impl.utils.AbstractCredentialProvider;
+import at.gv.egiz.eaaf.modules.pvp2.api.utils.IPvp2CredentialProvider;
@Service("PVPMetadataConfigurationFactory")
public class PvpMetadataConfigurationFactory implements IPvpMetadataConfigurationFactory {
@@ -43,9 +43,9 @@ public class PvpMetadataConfigurationFactory implements IPvpMetadataConfiguratio
@Override
public IPvpMetadataBuilderConfiguration generateMetadataBuilderConfiguration(String authUrl,
- AbstractCredentialProvider pvpIdpCredentials) {
+ IPvp2CredentialProvider pvpIdpCredentials) {
return new PvpMetadataConfiguration(basicConfig, authUrl, pvpBasicConfig, pvpIdpCredentials);
-
+
}
}
diff --git a/connector/src/main/java/at/asitplus/eidas/specific/connector/provider/PvpMetadataProvider.java b/connector/src/main/java/at/asitplus/eidas/specific/connector/provider/PvpMetadataProvider.java
index 6a223fd0..7738b0be 100644
--- a/connector/src/main/java/at/asitplus/eidas/specific/connector/provider/PvpMetadataProvider.java
+++ b/connector/src/main/java/at/asitplus/eidas/specific/connector/provider/PvpMetadataProvider.java
@@ -24,38 +24,60 @@
package at.asitplus.eidas.specific.connector.provider;
import java.io.IOException;
+import java.security.KeyStore;
+import java.security.KeyStoreException;
+import java.security.Provider;
import java.security.cert.CertificateException;
+import java.security.cert.X509Certificate;
+import java.text.MessageFormat;
+import java.util.ArrayList;
import java.util.List;
-import org.apache.commons.httpclient.HttpClient;
-import org.apache.commons.httpclient.params.HttpClientParams;
import org.apache.commons.lang3.StringUtils;
-import org.opensaml.saml2.metadata.provider.MetadataProvider;
-import org.opensaml.xml.parse.BasicParserPool;
+import org.opensaml.saml.metadata.resolver.MetadataResolver;
+import org.opensaml.saml.metadata.resolver.filter.MetadataFilter;
+import org.opensaml.saml.metadata.resolver.filter.MetadataFilterChain;
+import org.opensaml.security.x509.BasicX509Credential;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import at.asitplus.eidas.specific.connector.MsEidasNodeConstants;
-import at.asitplus.eidas.specific.connector.verification.MetadataSignatureVerificationFilter;
import at.gv.egiz.eaaf.core.api.idp.IConfigurationWithSP;
import at.gv.egiz.eaaf.core.api.idp.ISpConfiguration;
import at.gv.egiz.eaaf.core.exceptions.EaafConfigurationException;
-import at.gv.egiz.eaaf.core.impl.utils.FileUtils;
+import at.gv.egiz.eaaf.core.exceptions.EaafException;
+import at.gv.egiz.eaaf.core.impl.credential.EaafKeyStoreFactory;
+import at.gv.egiz.eaaf.core.impl.credential.EaafKeyStoreUtils;
+import at.gv.egiz.eaaf.core.impl.credential.KeyStoreConfiguration;
+import at.gv.egiz.eaaf.core.impl.credential.KeyStoreConfiguration.KeyStoreType;
+import at.gv.egiz.eaaf.core.impl.data.Pair;
+import at.gv.egiz.eaaf.core.impl.utils.IHttpClientFactory;
import at.gv.egiz.eaaf.modules.pvp2.exception.Pvp2MetadataException;
import at.gv.egiz.eaaf.modules.pvp2.impl.metadata.AbstractChainingMetadataProvider;
-import at.gv.egiz.eaaf.modules.pvp2.impl.metadata.MetadataFilterChain;
+import at.gv.egiz.eaaf.modules.pvp2.impl.metadata.PvpMetadataResolverFactory;
import at.gv.egiz.eaaf.modules.pvp2.impl.validation.metadata.PvpEntityCategoryFilter;
import at.gv.egiz.eaaf.modules.pvp2.impl.validation.metadata.SchemaValidationFilter;
+import at.gv.egiz.eaaf.modules.pvp2.impl.validation.metadata.SimpleMetadataSignatureVerificationFilter;
@Service("PVPMetadataProvider")
public class PvpMetadataProvider extends AbstractChainingMetadataProvider {
private static final Logger log = LoggerFactory.getLogger(PvpMetadataProvider.class);
+ private static final String PROVIDER_ID_PATTERN = "eIDAS resolver: {0}";
+
@Autowired(required = true)
IConfigurationWithSP basicConfig;
-
+ @Autowired
+ private PvpMetadataResolverFactory metadataProviderFactory;
+ @Autowired
+ private IHttpClientFactory httpClientFactory;
+
+ @Autowired
+ private EaafKeyStoreFactory keyStoreFactory;
+
+
@Override
protected String getMetadataUrl(String entityId) throws EaafConfigurationException {
final ISpConfiguration spConfig = basicConfig.getServiceProviderConfiguration(entityId);
@@ -80,7 +102,7 @@ public class PvpMetadataProvider extends AbstractChainingMetadataProvider {
}
@Override
- protected MetadataProvider createNewMetadataProvider(String entityId)
+ protected MetadataResolver createNewMetadataProvider(String entityId)
throws EaafConfigurationException, IOException, CertificateException {
final ISpConfiguration spConfig = basicConfig.getServiceProviderConfiguration(entityId);
if (spConfig != null) {
@@ -92,20 +114,44 @@ public class PvpMetadataProvider extends AbstractChainingMetadataProvider {
metadataUrl = entityId;
}
- final String trustStoreUrl = FileUtils.makeAbsoluteUrl(
- spConfig.getConfigurationValue(MsEidasNodeConstants.PROP_CONFIG_SP_PVP2_METADATA_TRUSTSTORE),
- authConfig.getConfigurationRootDirectory());
- final String trustStorePassword = spConfig.getConfigurationValue(
- MsEidasNodeConstants.PROP_CONFIG_SP_PVP2_METADATA_TRUSTSTORE_PASSWORD);
-
- return createNewSimpleMetadataProvider(metadataUrl,
- buildMetadataFilterChain(metadataUrl, trustStoreUrl, trustStorePassword),
- spConfig.getConfigurationValue(MsEidasNodeConstants.PROP_CONFIG_SP_UNIQUEIDENTIFIER),
- getTimer(),
- new BasicParserPool(),
- createHttpClient());
-
- } catch (final Pvp2MetadataException e) {
+
+ KeyStoreConfiguration keyStoreConfig = new KeyStoreConfiguration();
+ keyStoreConfig.setFriendlyName(MessageFormat.format(PROVIDER_ID_PATTERN, entityId));
+ keyStoreConfig.setKeyStoreType(KeyStoreType.JKS);
+ keyStoreConfig.setSoftKeyStoreFilePath(
+ spConfig.getConfigurationValue(MsEidasNodeConstants.PROP_CONFIG_SP_PVP2_METADATA_TRUSTSTORE));
+ keyStoreConfig.setSoftKeyStorePassword(spConfig.getConfigurationValue(
+ MsEidasNodeConstants.PROP_CONFIG_SP_PVP2_METADATA_TRUSTSTORE_PASSWORD));
+
+ keyStoreConfig.validate();
+
+ Pair<KeyStore, Provider> keyStore = keyStoreFactory.buildNewKeyStore(keyStoreConfig);
+
+ final List<MetadataFilter> filterList = new ArrayList<>();
+ filterList.add(new SchemaValidationFilter(true));
+ filterList.add(new SimpleMetadataSignatureVerificationFilter(
+ getTrustedCertificates(keyStore.getFirst()), entityId));
+ filterList.add(new PvpEntityCategoryFilter(
+ basicConfig.getBasicConfigurationBoolean(MsEidasNodeConstants.PROP_CONFIG_PVP_ENABLE_ENTITYCATEGORIES,
+ true)));
+
+ final MetadataFilterChain filter = new MetadataFilterChain();
+ filter.setFilters(filterList);
+
+ try {
+ return metadataProviderFactory.createMetadataProvider(getMetadataUrl(entityId),
+ filter,
+ MessageFormat.format(PROVIDER_ID_PATTERN, entityId),
+ httpClientFactory.getHttpClient());
+
+ } catch (final Pvp2MetadataException e) {
+ log.info("Can NOT build metadata provider for entityId: {}", entityId);
+ throw new EaafConfigurationException("module.eidasauth.04",
+ new Object[] { entityId, e.getMessage() }, e);
+
+ }
+
+ } catch (final EaafException e) {
log.info("Can NOT initialize Metadata signature-verification filter. Reason: " + e.getMessage());
throw new EaafConfigurationException("config.27",
new Object[] { "Can NOT initialize Metadata signature-verification filter. Reason: " + e
@@ -122,34 +168,37 @@ public class PvpMetadataProvider extends AbstractChainingMetadataProvider {
@Override
protected List<String> getAllMetadataUrlsFromConfiguration() throws EaafConfigurationException {
- // TODO Auto-generated method stub
return null;
}
- private HttpClient createHttpClient() {
- final HttpClient httpClient = new HttpClient();
- final HttpClientParams httpClientParams = new HttpClientParams();
- httpClientParams.setSoTimeout(MsEidasNodeConstants.METADATA_SOCKED_TIMEOUT);
- httpClient.setParams(httpClientParams);
- return httpClient;
-
+ @Override
+ protected String getMetadataProviderId() {
+ return "Service-provider chainging metadata provider";
+
}
+
+ private List<BasicX509Credential> getTrustedCertificates(KeyStore trustStore) throws EaafConfigurationException {
+ try {
+ final List<X509Certificate> certs =
+ EaafKeyStoreUtils.readCertsFromKeyStore(trustStore);
+ if (certs.isEmpty()) {
+ log.warn("No trusted metadata-signing certificates in configuration");
+ throw new EaafConfigurationException("module.eidasauth.02",
+ new Object[] { "No trusted metadata-signing certificates" });
- private MetadataFilterChain buildMetadataFilterChain(String metadataUrl,
- String trustStoreUrl, String trustStorePassword) throws CertificateException, Pvp2MetadataException {
- final MetadataFilterChain filterChain = new MetadataFilterChain();
- filterChain.getFilters().add(new SchemaValidationFilter(
- basicConfig.getBasicConfigurationBoolean(MsEidasNodeConstants.PROP_CONFIG_PVP_SCHEME_VALIDATION,
- true)));
+ }
- filterChain.getFilters().add(
- new MetadataSignatureVerificationFilter(
- trustStoreUrl, trustStorePassword, metadataUrl));
+ final List<BasicX509Credential> result = new ArrayList<>();
+ for (final X509Certificate cert : certs) {
+ result.add(new BasicX509Credential(cert));
- filterChain.getFilters().add(new PvpEntityCategoryFilter(
- basicConfig.getBasicConfigurationBoolean(MsEidasNodeConstants.PROP_CONFIG_PVP_ENABLE_ENTITYCATEGORIES,
- true)));
+ }
+ return result;
+
+ } catch (final KeyStoreException e) {
+ throw new EaafConfigurationException("module.eidasauth.01",
+ new Object[] { "Trusted metadata-signing certificates", e.getMessage() }, e);
- return filterChain;
+ }
}
}
diff --git a/connector/src/main/java/at/asitplus/eidas/specific/connector/verification/AuthnRequestValidator.java b/connector/src/main/java/at/asitplus/eidas/specific/connector/verification/AuthnRequestValidator.java
index 482e6761..26176c49 100644
--- a/connector/src/main/java/at/asitplus/eidas/specific/connector/verification/AuthnRequestValidator.java
+++ b/connector/src/main/java/at/asitplus/eidas/specific/connector/verification/AuthnRequestValidator.java
@@ -29,15 +29,15 @@ import java.util.List;
import javax.servlet.http.HttpServletRequest;
import org.apache.commons.lang3.StringUtils;
-import org.opensaml.saml2.core.AuthnContextClassRef;
-import org.opensaml.saml2.core.AuthnContextComparisonTypeEnumeration;
-import org.opensaml.saml2.core.AuthnRequest;
-import org.opensaml.saml2.core.NameIDPolicy;
-import org.opensaml.saml2.core.NameIDType;
-import org.opensaml.saml2.core.RequestedAuthnContext;
-import org.opensaml.saml2.core.Scoping;
-import org.opensaml.saml2.metadata.SPSSODescriptor;
-import org.opensaml.xml.XMLObject;
+import org.opensaml.core.xml.XMLObject;
+import org.opensaml.saml.saml2.core.AuthnContextClassRef;
+import org.opensaml.saml.saml2.core.AuthnContextComparisonTypeEnumeration;
+import org.opensaml.saml.saml2.core.AuthnRequest;
+import org.opensaml.saml.saml2.core.NameIDPolicy;
+import org.opensaml.saml.saml2.core.NameIDType;
+import org.opensaml.saml.saml2.core.RequestedAuthnContext;
+import org.opensaml.saml.saml2.core.Scoping;
+import org.opensaml.saml.saml2.metadata.SPSSODescriptor;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
diff --git a/connector/src/main/java/at/asitplus/eidas/specific/connector/verification/MetadataSignatureVerificationFilter.java b/connector/src/main/java/at/asitplus/eidas/specific/connector/verification/MetadataSignatureVerificationFilter.java
deleted file mode 100644
index b6dd249a..00000000
--- a/connector/src/main/java/at/asitplus/eidas/specific/connector/verification/MetadataSignatureVerificationFilter.java
+++ /dev/null
@@ -1,175 +0,0 @@
-/*
- * Copyright 2018 A-SIT Plus GmbH
- * AT-specific eIDAS Connector has been developed in a cooperation between EGIZ,
- * A-SIT Plus GmbH, A-SIT, and Graz University of Technology.
- *
- * Licensed under the EUPL, Version 1.2 or - as soon they will be approved by
- * the European Commission - subsequent versions of the EUPL (the "License");
- * You may not use this work except in compliance with the License.
- * You may obtain a copy of the License at:
- * https://joinup.ec.europa.eu/news/understanding-eupl-v12
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" basis,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- *
- * This product combines work with different licenses. See the "NOTICE" text
- * file for details on the various modules and licenses.
- * The "NOTICE" text file is part of the distribution. Any derivative works
- * that you distribute must include a readable copy of the "NOTICE" text file.
-*/
-
-package at.asitplus.eidas.specific.connector.verification;
-
-import java.io.IOException;
-import java.security.KeyStore;
-import java.security.KeyStoreException;
-import java.security.cert.Certificate;
-import java.security.cert.X509Certificate;
-import java.util.ArrayList;
-import java.util.Enumeration;
-import java.util.List;
-
-import org.opensaml.common.SignableSAMLObject;
-import org.opensaml.saml2.metadata.EntitiesDescriptor;
-import org.opensaml.saml2.metadata.EntityDescriptor;
-import org.opensaml.security.SAMLSignatureProfileValidator;
-import org.opensaml.xml.security.x509.BasicX509Credential;
-import org.opensaml.xml.signature.SignatureValidator;
-import org.opensaml.xml.validation.ValidationException;
-import org.slf4j.Logger;
-import org.slf4j.LoggerFactory;
-
-import at.gv.egiz.eaaf.core.exceptions.EaafException;
-import at.gv.egiz.eaaf.core.impl.utils.KeyStoreUtils;
-import at.gv.egiz.eaaf.modules.pvp2.exception.Pvp2MetadataException;
-import at.gv.egiz.eaaf.modules.pvp2.idp.exception.SamlRequestNotSignedException;
-import at.gv.egiz.eaaf.modules.pvp2.impl.validation.metadata.AbstractMetadataSignatureFilter;
-
-public class MetadataSignatureVerificationFilter extends AbstractMetadataSignatureFilter {
- private static final Logger log = LoggerFactory.getLogger(MetadataSignatureVerificationFilter.class);
-
- private final String metadataUrl;
- private final List<BasicX509Credential> trustedCredential = new ArrayList<>();
-
- /**
- * SAML2 Metadata signature verifier that checks signer certificates based on local TrustStores.
- *
- * @param trustStorePath Path to truststore
- * @param trustStorePassword TrustStore password
- * @param metadataUrl URL to PVP2 metadata
- * @throws Pvp2MetadataException In case of a verification error
- */
- public MetadataSignatureVerificationFilter(String trustStorePath, String trustStorePassword,
- String metadataUrl)
- throws Pvp2MetadataException {
- this.metadataUrl = metadataUrl;
-
- log.trace("Initialize metadata signature-verification filter with truststore: " + trustStorePath
- + " ... ");
- try {
- final KeyStore keyStore = KeyStoreUtils.loadKeyStore(trustStorePath, trustStorePassword);
- if (keyStore != null) {
- // load trusted certificates
- final Enumeration<String> aliases = keyStore.aliases();
- while (aliases.hasMoreElements()) {
- final String el = aliases.nextElement();
- log.trace("Process TrustStoreEntry: " + el);
- if (keyStore.isCertificateEntry(el)) {
- final Certificate cert = keyStore.getCertificate(el);
- if (cert != null && cert instanceof X509Certificate) {
- final BasicX509Credential trustedCert = new BasicX509Credential();
- trustedCert.setEntityCertificate((X509Certificate) cert);
- this.trustedCredential.add(trustedCert);
- log.debug("Add cert: " + ((X509Certificate) cert).getSubjectDN() + " as trusted for metadata: "
- + metadataUrl);
-
- } else {
- log.info("Can not process entry: " + el + ". Reason: is null");
- }
-
- }
- }
-
- } else {
- throw new Pvp2MetadataException("pvp2.26",
- new Object[] { "Can not open trustStore: " + trustStorePath + " for metadata: " + metadataUrl });
- }
-
- } catch (KeyStoreException | IOException e) {
- log.warn("Can not open trustStore: " + trustStorePath + " for metadata: " + metadataUrl + " Reason: "
- + e.getMessage(), e);
- throw new Pvp2MetadataException("pvp2.26",
- new Object[] { "Can not open trustStore: " + trustStorePath + " for metadata" }, e);
-
- }
-
- }
-
- @Override
- protected void verify(EntityDescriptor desc) throws Pvp2MetadataException {
- try {
- internalVerify(desc);
-
- } catch (final EaafException e) {
- log.info("Metadata verification FAILED for: " + metadataUrl + " Reason: " + e.getMessage());
- throw new Pvp2MetadataException("pvp2.26",
- new Object[] { "Metadata verification FAILED for: " + metadataUrl + " Reason: " + e.getMessage() },
- e);
-
- }
- }
-
- @Override
- protected void verify(EntitiesDescriptor desc) throws Pvp2MetadataException {
- throw new Pvp2MetadataException("pvp2.26",
- new Object[] { "EntitiesDescritors are NOT supported" });
-
- }
-
- @Override
- protected void verify(EntityDescriptor entity, EntitiesDescriptor desc) throws Pvp2MetadataException {
- throw new Pvp2MetadataException("pvp2.26",
- new Object[] { "EntitiesDescritors are NOT supported" });
-
- }
-
- private void internalVerify(SignableSAMLObject signedElement)
- throws EaafException {
- if (signedElement.getSignature() == null) {
- throw new SamlRequestNotSignedException();
- }
-
- try {
- final SAMLSignatureProfileValidator sigValidator = new SAMLSignatureProfileValidator();
- sigValidator.validate(signedElement.getSignature());
- } catch (final ValidationException e) {
- log.error("Failed to validate Signature", e);
- throw new SamlRequestNotSignedException(e);
- }
-
- boolean isTrusted = false;
- for (final BasicX509Credential cred : trustedCredential) {
- final SignatureValidator sigValidator = new SignatureValidator(cred);
- try {
- sigValidator.validate(signedElement.getSignature());
- isTrusted = true;
-
- } catch (final ValidationException e) {
- log.info("Failed to verfiy Signature with cert: " + cred.getEntityCertificate().getSubjectDN()
- + " Reason: " + e.getMessage());
-
- }
- }
-
- if (!isTrusted) {
- log.warn("PVP2 metadata: " + metadataUrl + " are NOT trusted!");
- throw new SamlRequestNotSignedException();
-
- }
-
- }
-
-}
diff --git a/connector/src/test/java/at/asitplus/eidas/specific/connector/test/AuthnRequestValidatorTest.java b/connector/src/test/java/at/asitplus/eidas/specific/connector/test/AuthnRequestValidatorTest.java
index db863815..e34c8036 100644
--- a/connector/src/test/java/at/asitplus/eidas/specific/connector/test/AuthnRequestValidatorTest.java
+++ b/connector/src/test/java/at/asitplus/eidas/specific/connector/test/AuthnRequestValidatorTest.java
@@ -12,11 +12,11 @@ import org.junit.Before;
import org.junit.BeforeClass;
import org.junit.Test;
import org.junit.runner.RunWith;
-import org.opensaml.saml2.core.AuthnRequest;
-import org.opensaml.xml.ConfigurationException;
-import org.opensaml.xml.io.Unmarshaller;
-import org.opensaml.xml.io.UnmarshallerFactory;
-import org.opensaml.xml.io.UnmarshallingException;
+import org.opensaml.core.config.InitializationException;
+import org.opensaml.core.xml.io.Unmarshaller;
+import org.opensaml.core.xml.io.UnmarshallingException;
+import org.opensaml.core.xml.util.XMLObjectSupport;
+import org.opensaml.saml.saml2.core.AuthnRequest;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.mock.web.MockHttpServletRequest;
import org.springframework.mock.web.MockHttpServletResponse;
@@ -38,7 +38,8 @@ import at.gv.egiz.eaaf.core.exceptions.AuthnRequestValidatorException;
import at.gv.egiz.eaaf.core.impl.idp.module.test.TestRequestImpl;
import at.gv.egiz.eaaf.core.impl.utils.DomUtils;
import at.gv.egiz.eaaf.modules.pvp2.api.validation.IAuthnRequestPostProcessor;
-import at.gv.egiz.eaaf.modules.pvp2.impl.opensaml.initialize.EaafDefaultSaml2Bootstrap;
+import at.gv.egiz.eaaf.modules.pvp2.impl.opensaml.initialize.EaafOpenSaml3xInitializer;
+import net.shibboleth.utilities.java.support.component.ComponentInitializationException;
@RunWith(SpringJUnit4ClassRunner.class)
@ContextConfiguration({
@@ -61,15 +62,16 @@ public class AuthnRequestValidatorTest {
/**
* jUnit class initializer.
- * @throws ConfigurationException In case of an error
+ * @throws ComponentInitializationException In case of an error
+ * @throws InitializationException In case of an error
*
*/
@BeforeClass
- public static void classInitializer() throws ConfigurationException {
+ public static void classInitializer() throws InitializationException, ComponentInitializationException {
final String current = new java.io.File(".").toURI().toString();
System.setProperty("eidas.ms.configuration", current + "src/test/resources/config/junit_config_1.properties");
- EaafDefaultSaml2Bootstrap.bootstrap();
+ EaafOpenSaml3xInitializer.eaafInitialize();
}
/**
@@ -286,9 +288,7 @@ public class AuthnRequestValidatorTest {
final Element authBlockDom =
DomUtils.parseXmlValidating(AuthnRequestValidatorTest.class.getResourceAsStream(resource));
- final UnmarshallerFactory unmarshallerFactory =
- org.opensaml.xml.Configuration.getUnmarshallerFactory();
- final Unmarshaller unmarshaller = unmarshallerFactory.getUnmarshaller(authBlockDom);
+ final Unmarshaller unmarshaller = XMLObjectSupport.getUnmarshaller(authBlockDom);
return (AuthnRequest) unmarshaller.unmarshall(authBlockDom);
}
diff --git a/connector/src/test/resources/config/junit_config_1.properties b/connector/src/test/resources/config/junit_config_1.properties
index 3f290948..982d3e24 100644
--- a/connector/src/test/resources/config/junit_config_1.properties
+++ b/connector/src/test/resources/config/junit_config_1.properties
@@ -39,8 +39,8 @@ eidas.ms.auth.eIDAS.node_v2.loa.requested.minimum=http://eidas.europa.eu/LoA/sub
eidas.ms.auth.eIDAS.szrclient.useTestService=true
eidas.ms.auth.eIDAS.szrclient.endpoint.prod=
eidas.ms.auth.eIDAS.szrclient.endpoint.test=http://localhost:1234/demoszr
-eidas.ms.auth.eIDAS.szrclient.ssl.keyStore.path=keys/.....
-eidas.ms.auth.eIDAS.szrclient.ssl.keyStore.password=
+eidas.ms.auth.eIDAS.szrclient.ssl.keyStore.path=keys/junit.jks
+eidas.ms.auth.eIDAS.szrclient.ssl.keyStore.password=password
eidas.ms.auth.eIDAS.szrclient.ssl.trustStore.path=
eidas.ms.auth.eIDAS.szrclient.ssl.trustStore.password=
eidas.ms.auth.eIDAS.szrclient.timeout.connection=15
@@ -80,8 +80,8 @@ eidas.ms.auth.eIDAS.node_v2.attributes.requested.representation.5=LegalName,true
## PVP2 S-Profile end-point configuration
-eidas.ms.pvp2.keystore.path=keys/.....
-eidas.ms.pvp2.keystore.password=
+eidas.ms.pvp2.keystore.path=keys/junit.jks
+eidas.ms.pvp2.keystore.password=password
eidas.ms.pvp2.key.metadata.alias=
eidas.ms.pvp2.key.metadata.password=
eidas.ms.pvp2.key.signing.alias=
@@ -90,8 +90,8 @@ eidas.ms.pvp2.metadata.validity=24
## Service Provider configuration
eidas.ms.sp.0.uniqueID=
-eidas.ms.sp.0.pvp2.metadata.truststore=
-eidas.ms.sp.0.pvp2.metadata.truststore.password=
+eidas.ms.sp.0.pvp2.metadata.truststore=keys/junit.jks
+eidas.ms.sp.0.pvp2.metadata.truststore.password=password
#eidas.ms.sp.0.friendlyName=
#eidas.ms.sp.0.pvp2.metadata.url=
diff --git a/connector/src/test/resources/config/keys/junit.jks b/connector/src/test/resources/config/keys/junit.jks
new file mode 100644
index 00000000..59e6ad13
--- /dev/null
+++ b/connector/src/test/resources/config/keys/junit.jks
Binary files differ