diff options
author | Thomas Lenz <thomas.lenz@egiz.gv.at> | 2020-11-07 18:21:49 +0100 |
---|---|---|
committer | Thomas Lenz <thomas.lenz@egiz.gv.at> | 2020-11-07 18:21:49 +0100 |
commit | 57d813b9cfbbd231a2e6f9d47169b31435d1d6c0 (patch) | |
tree | 7ce36328e4250bc798840daa73ff0f42f8f41a85 | |
parent | f358f3ba6a24d5e9575b3fd63e3fbfe8848b63c4 (diff) | |
download | National_eIDAS_Gateway-57d813b9cfbbd231a2e6f9d47169b31435d1d6c0.tar.gz National_eIDAS_Gateway-57d813b9cfbbd231a2e6f9d47169b31435d1d6c0.tar.bz2 National_eIDAS_Gateway-57d813b9cfbbd231a2e6f9d47169b31435d1d6c0.zip |
code clean-up and first jUnit test modifications for CreateIdentityLink task
14 files changed, 595 insertions, 332 deletions
diff --git a/basicConfig/default_config.properties b/basicConfig/default_config.properties index dda5144e..2e0aebcc 100644 --- a/basicConfig/default_config.properties +++ b/basicConfig/default_config.properties @@ -50,6 +50,15 @@ eidas.ms.auth.eIDAS.szrclient.params.vkz= eidas.ms.auth.eIDAS.szrclient.params.useSZRForbPKCalculation=false +## E-AuthBlock configuration +eidas.ms.auth.eIDAS.authblock.keystore.type=jks +eidas.ms.auth.eIDAS.authblock.keystore.path=keys/teststore.jks +eidas.ms.auth.eIDAS.authblock.keystore.password=f/+saJBc3a}*/T^s +eidas.ms.auth.eIDAS.authblock.keystore.name= +eidas.ms.auth.eIDAS.authblock.key.alias=connectorkeypair +eidas.ms.auth.eIDAS.authblock.key.password=f/+saJBc3a}*/T^s + + #Raw eIDAS Id data storage eidas.ms.auth.eIDAS.szrclient.workarounds.eidmapping.revisionlog.active=true diff --git a/basicConfig/keys/teststore.jks b/basicConfig/keys/teststore.jks Binary files differnew file mode 100644 index 00000000..fcc6400c --- /dev/null +++ b/basicConfig/keys/teststore.jks 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 651b7b78..8dbb74c7 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 @@ -173,4 +173,11 @@ public class PvpMetadataProvider extends AbstractChainingMetadataProvider { return "Service-provider chainging metadata provider"; } + + @Override + public void doDestroy() { + this.fullyDestroy(); + + } + } diff --git a/connector_lib/src/main/java/at/asitplus/eidas/specific/connector/MsEidasNodeConstants.java b/connector_lib/src/main/java/at/asitplus/eidas/specific/connector/MsEidasNodeConstants.java index 10ec9791..b1ef799f 100644 --- a/connector_lib/src/main/java/at/asitplus/eidas/specific/connector/MsEidasNodeConstants.java +++ b/connector_lib/src/main/java/at/asitplus/eidas/specific/connector/MsEidasNodeConstants.java @@ -86,15 +86,22 @@ public class MsEidasNodeConstants { public static final String PROP_EIDAS_REQUEST_LOA_MINIMUM_LEVEL = "auth.eIDAS.node_v2.loa.requested.minimum"; - public static final String PROP_CONFIG_SP_AUTHBLOCK_KEYSTORE_PASSWORD = - "auth.eIDAS.authblock.keystore.password"; - public static final String PROP_CONFIG_SP_AUTHBLOCK_KEYSTSTORE_FRIENDLYNAME = - "auth.eIDAS.authblock.keystore.friendlyName"; - public static final String PROP_CONFIG_SP_AUTHBLOCK_KEYSTORE_PATH = - "auth.eIDAS.authblock.keystore.path"; - public static final String PROP_CONFIG_SP_AUTHBLOCK_KEYSTORE_TYPE = - "auth.eIDAS.authblock.keystore.type"; + public static final String PROP_CONFIG_AUTHBLOCK_KEYSTORE_TYPE = + "auth.eIDAS.authblock.keystore.type"; + public static final String PROP_CONFIG_AUTHBLOCK_KEYSTORE_PATH = + "auth.eIDAS.authblock.keystore.path"; + public static final String PROP_CONFIG_AUTHBLOCK_KEYSTORE_PASSWORD = + "auth.eIDAS.authblock.keystore.password"; + public static final String PROP_CONFIG_AUTHBLOCK_KEYSTORE_NAME = + "auth.eIDAS.authblock.keystore.name"; + public static final String PROP_CONFIG_AUTHBLOCK_KEY_ALIAS = + "auth.eIDAS.authblock.key.alias"; + public static final String PROP_CONFIG_AUTHBLOCK_KEY_PASSWORD = + "auth.eIDAS.authblock.key.password"; + + + public static final String PROP_CONFIG_SP_LIST_PREFIX = "sp."; public static final String PROP_CONFIG_SP_UNIQUEIDENTIFIER = EaafConfigConstants.SERVICE_UNIQUEIDENTIFIER; diff --git a/eidas_modules/authmodule-eIDAS-v2/src/main/java/at/asitplus/eidas/specific/modules/auth/eidas/v2/service/AuthBlockSigningService.java b/eidas_modules/authmodule-eIDAS-v2/src/main/java/at/asitplus/eidas/specific/modules/auth/eidas/v2/service/AuthBlockSigningService.java new file mode 100644 index 00000000..30d255b9 --- /dev/null +++ b/eidas_modules/authmodule-eIDAS-v2/src/main/java/at/asitplus/eidas/specific/modules/auth/eidas/v2/service/AuthBlockSigningService.java @@ -0,0 +1,147 @@ +package at.asitplus.eidas.specific.modules.auth.eidas.v2.service; + +import java.security.Key; +import java.security.KeyStore; +import java.security.KeyStoreException; +import java.security.Provider; +import java.security.cert.X509Certificate; +import java.util.Base64; + +import javax.annotation.PostConstruct; + +import org.apache.commons.lang3.StringUtils; +import org.jose4j.lang.JoseException; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Service; + +import com.fasterxml.jackson.core.JsonProcessingException; +import com.fasterxml.jackson.databind.ObjectMapper; + +import at.asitplus.eidas.specific.connector.MsEidasNodeConstants; +import at.asitplus.eidas.specific.modules.auth.eidas.v2.utils.JoseUtils; +import at.gv.egiz.eaaf.core.api.idp.IConfiguration; +import at.gv.egiz.eaaf.core.exception.EaafKeyAccessException; +import at.gv.egiz.eaaf.core.exceptions.EaafConfigurationException; +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.data.Pair; +import lombok.extern.slf4j.Slf4j; + +/** + * Service to build and sign AuthBlock's for E-ID system. + * + * @author tlenz + * + */ +@Slf4j +@Service("authBlockSigningService") +public class AuthBlockSigningService { + + private static final String KEYSTORE_FRIENDLYNAME = "AuthBlock_Signing"; + + private static ObjectMapper mapper = new ObjectMapper(); + + @Autowired + IConfiguration basicConfig; + + @Autowired + EaafKeyStoreFactory keyStoreFactory; + + + private Pair<KeyStore, Provider> keyStore; + + /** + * Build and sign an AuthBlock for E-ID system. + * + * @param dataToSign data that should be added into AuthBlock + * @return serialized JWS + * @throws JsonProcessingException In case of a AuthBlock generation error + * @throws JoseException In case of a JWS signing error + * @throws EaafException In case of a KeyStore or Key error + */ + public String buildSignedAuthBlock(String dataToSign) + throws JsonProcessingException, EaafException, JoseException { + log.debug("Building and sign authBlock with data: {}", dataToSign); + + // build AuthBlock + String jwsPayload = mapper.writeValueAsString(dataToSign); + + //sign JWS + return JoseUtils + .createSignature(keyStore, getKeyAlias(), getKeyPassword(), jwsPayload, false, + KEYSTORE_FRIENDLYNAME); + } + + + /** + * Get the Base64 encoded PublicKey that is used to sign the AuthBlock. + * + * @return Base64 encoded PublicKey + * @throws EaafKeyAccessException In case of an unknown or invalid key + */ + public String getBase64EncodedPublicKey() throws EaafKeyAccessException { + Pair<Key, X509Certificate[]> keyPair = EaafKeyStoreUtils.getPrivateKeyAndCertificates( + keyStore.getFirst(), getKeyAlias(), getKeyPassword(), true, KEYSTORE_FRIENDLYNAME); + return Base64.getEncoder().encodeToString(keyPair.getSecond()[0].getPublicKey().getEncoded()); + + } + + @PostConstruct + private void initialize() throws KeyStoreException, EaafException { + log.debug("Initializing AuthBlock signing service ... "); + // read Connector wide config data TODO connector wide! + String keyStoreName = basicConfig + .getBasicConfiguration(MsEidasNodeConstants.PROP_CONFIG_AUTHBLOCK_KEYSTORE_NAME); + String keyStorePw = basicConfig + .getBasicConfiguration(MsEidasNodeConstants.PROP_CONFIG_AUTHBLOCK_KEYSTORE_PASSWORD); + String keyStorePath = basicConfig + .getBasicConfiguration(MsEidasNodeConstants.PROP_CONFIG_AUTHBLOCK_KEYSTORE_PATH); + String keyStoreType = basicConfig + .getBasicConfiguration(MsEidasNodeConstants.PROP_CONFIG_AUTHBLOCK_KEYSTORE_TYPE); + + + //build new KeyStore configuration + KeyStoreConfiguration keyStoreConfiguration = new KeyStoreConfiguration(); + keyStoreConfiguration.setFriendlyName(KEYSTORE_FRIENDLYNAME); + + keyStoreConfiguration.setSoftKeyStoreFilePath(keyStorePath); + keyStoreConfiguration.setSoftKeyStorePassword(keyStorePw); + keyStoreConfiguration.setKeyStoreType(KeyStoreConfiguration.KeyStoreType.fromString(keyStoreType)); + keyStoreConfiguration.setKeyStoreName(keyStoreName); + + //validate KeyStore configuration + keyStoreConfiguration.validate(); + + //validate key alias + if (StringUtils.isEmpty(getKeyAlias())) { + throw new EaafConfigurationException("config.08", + new Object[] {MsEidasNodeConstants.PROP_CONFIG_AUTHBLOCK_KEY_ALIAS}); + + } + + //build new KeyStore based on configuration + keyStore = keyStoreFactory.buildNewKeyStore(keyStoreConfiguration); + + log.info("AuthBlock signing-service successful initialized"); + + } + + private char[] getKeyPassword() { + final String value = basicConfig.getBasicConfiguration(MsEidasNodeConstants.PROP_CONFIG_AUTHBLOCK_KEY_PASSWORD); + if (value != null) { + return value.trim().toCharArray(); + } + + return null; + + } + + + private String getKeyAlias() { + return basicConfig + .getBasicConfiguration(MsEidasNodeConstants.PROP_CONFIG_AUTHBLOCK_KEY_ALIAS); + + } +} diff --git a/eidas_modules/authmodule-eIDAS-v2/src/main/java/at/asitplus/eidas/specific/modules/auth/eidas/v2/tasks/CreateIdentityLinkTask.java b/eidas_modules/authmodule-eIDAS-v2/src/main/java/at/asitplus/eidas/specific/modules/auth/eidas/v2/tasks/CreateIdentityLinkTask.java index 8626c709..1ffd56e4 100644 --- a/eidas_modules/authmodule-eIDAS-v2/src/main/java/at/asitplus/eidas/specific/modules/auth/eidas/v2/tasks/CreateIdentityLinkTask.java +++ b/eidas_modules/authmodule-eIDAS-v2/src/main/java/at/asitplus/eidas/specific/modules/auth/eidas/v2/tasks/CreateIdentityLinkTask.java @@ -23,16 +23,37 @@ package at.asitplus.eidas.specific.modules.auth.eidas.v2.tasks; +import java.io.IOException; +import java.io.InputStream; +import java.util.HashMap; +import java.util.List; +import java.util.Map; + +import javax.servlet.http.HttpServletRequest; +import javax.servlet.http.HttpServletResponse; +import javax.xml.parsers.ParserConfigurationException; + +import org.apache.commons.lang3.StringUtils; +import org.joda.time.DateTime; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Component; +import org.w3c.dom.Element; +import org.w3c.dom.Node; +import org.xml.sax.SAXException; + +import com.google.common.collect.ImmutableMap; +import com.google.common.collect.ImmutableSet; + import at.asitplus.eidas.specific.connector.MsConnectorEventCodes; import at.asitplus.eidas.specific.connector.MsEidasNodeConstants; import at.asitplus.eidas.specific.modules.auth.eidas.v2.Constants; import at.asitplus.eidas.specific.modules.auth.eidas.v2.dao.ErnbEidData; import at.asitplus.eidas.specific.modules.auth.eidas.v2.exception.EidasAttributeException; import at.asitplus.eidas.specific.modules.auth.eidas.v2.exception.SzrCommunicationException; +import at.asitplus.eidas.specific.modules.auth.eidas.v2.service.AuthBlockSigningService; import at.asitplus.eidas.specific.modules.auth.eidas.v2.service.ICcSpecificEidProcessingService; import at.asitplus.eidas.specific.modules.auth.eidas.v2.szr.SzrClient; import at.asitplus.eidas.specific.modules.auth.eidas.v2.utils.EidasResponseUtils; -import at.asitplus.eidas.specific.modules.auth.eidas.v2.utils.JoseUtils; import at.gv.e_government.reference.namespace.persondata._20020228.AlternativeNameType; import at.gv.e_government.reference.namespace.persondata._20020228.PersonNameType; import at.gv.e_government.reference.namespace.persondata._20020228.PhysicalPersonType; @@ -43,8 +64,6 @@ import at.gv.egiz.eaaf.core.api.idp.auth.data.IIdentityLink; import at.gv.egiz.eaaf.core.api.idp.process.ExecutionContext; import at.gv.egiz.eaaf.core.exceptions.EaafException; import at.gv.egiz.eaaf.core.exceptions.TaskExecutionException; -import at.gv.egiz.eaaf.core.impl.credential.EaafKeyStoreFactory; -import at.gv.egiz.eaaf.core.impl.credential.KeyStoreConfiguration; import at.gv.egiz.eaaf.core.impl.data.Pair; import at.gv.egiz.eaaf.core.impl.idp.auth.builder.BpkBuilder; import at.gv.egiz.eaaf.core.impl.idp.auth.data.AuthProcessDataWrapper; @@ -52,36 +71,16 @@ import at.gv.egiz.eaaf.core.impl.idp.auth.data.SimpleIdentityLinkAssertionParser import at.gv.egiz.eaaf.core.impl.idp.auth.modules.AbstractAuthServletTask; import at.gv.egiz.eaaf.core.impl.utils.DomUtils; import at.gv.egiz.eaaf.core.impl.utils.XPathUtils; -import com.fasterxml.jackson.databind.ObjectMapper; -import com.google.common.collect.ImmutableMap; -import com.google.common.collect.ImmutableSet; import eu.eidas.auth.commons.attribute.AttributeDefinition; import eu.eidas.auth.commons.attribute.AttributeValue; import eu.eidas.auth.commons.light.ILightResponse; import eu.eidas.auth.commons.protocol.eidas.impl.PostalAddress; +import lombok.Data; import lombok.extern.slf4j.Slf4j; -import org.apache.commons.lang3.StringUtils; -import org.joda.time.DateTime; -import org.springframework.beans.factory.annotation.Autowired; -import org.springframework.stereotype.Component; -import org.w3c.dom.Element; -import org.w3c.dom.Node; import szrservices.IdentityLinkType; import szrservices.PersonInfoType; import szrservices.TravelDocumentType; -import javax.servlet.http.HttpServletRequest; -import javax.servlet.http.HttpServletResponse; -import java.io.InputStream; -import java.security.KeyStore; -import java.security.KeyStoreException; -import java.security.Provider; -import java.security.PublicKey; -import java.util.Base64; -import java.util.HashMap; -import java.util.List; -import java.util.Map; - /** * Task that creates the IdentityLink for an eIDAS authenticated person. * @@ -97,12 +96,12 @@ public class CreateIdentityLinkTask extends AbstractAuthServletTask { private SzrClient szrClient; @Autowired private ICcSpecificEidProcessingService eidPostProcessor; - + @Autowired - EaafKeyStoreFactory keyStoreFactory; + private AuthBlockSigningService authBlockSigner; private static final String EID_STATUS = "urn:eidgvat:eid.status.eidas"; - + /* * (non-Javadoc) * @@ -118,164 +117,57 @@ public class CreateIdentityLinkTask extends AbstractAuthServletTask { final AuthProcessDataWrapper authProcessData = pendingReq.getSessionData(AuthProcessDataWrapper.class); final ILightResponse eidasResponse = authProcessData .getGenericDataFromSession(Constants.DATA_FULL_EIDAS_RESPONSE, ILightResponse.class); - boolean isNewEidMode = pendingReq.getServiceProviderConfiguration() - .isConfigurationValue(MsEidasNodeConstants.PROP_CONFIG_SP_NEW_EID_MODE, false); - final Map<String, Object> simpleAttrMap = convertEidasAttrToSimpleMap( eidasResponse.getAttributes().getAttributeMap()); - IIdentityLink identityLink = null; - String bpk = null; - // post-process eIDAS attributes final ErnbEidData eidData = eidPostProcessor.postProcess(simpleAttrMap); // write MDS into technical log and revision log writeMdsLogInformation(eidData); - // connect SZR-Gateway + //build IdentityLink or VSZ and eidasBind if (basicConfig.getBasicConfigurationBoolean(Constants.CONIG_PROPS_EIDAS_SZRCLIENT_DEBUG_USEDUMMY, false)) { - log.warn("SZR-Dummy IS ACTIVE! IdentityLink is NOT VALID!!!!"); - // create fake IdL - // - fetch IdL template from resources - final InputStream s = CreateIdentityLinkTask.class - .getResourceAsStream("/resources/xmldata/fakeIdL_IdL_template.xml"); - final Element idlTemplate = DomUtils.parseXmlValidating(s); - - identityLink = new SimpleIdentityLinkAssertionParser(idlTemplate).parseIdentityLink(); - - // replace data - final Element idlassertion = identityLink.getSamlAssertion(); - - // - set fake baseID; - final Node prIdentification = XPathUtils - .selectSingleNode(idlassertion, SimpleIdentityLinkAssertionParser.PERSON_IDENT_VALUE_XPATH); - prIdentification.getFirstChild().setNodeValue(eidData.getPseudonym()); - - // - set last name - final Node prFamilyName = XPathUtils - .selectSingleNode(idlassertion, SimpleIdentityLinkAssertionParser.PERSON_FAMILY_NAME_XPATH); - prFamilyName.getFirstChild().setNodeValue(eidData.getFamilyName()); - - // - set first name - final Node prGivenName = XPathUtils - .selectSingleNode(idlassertion, SimpleIdentityLinkAssertionParser.PERSON_GIVEN_NAME_XPATH); - prGivenName.getFirstChild().setNodeValue(eidData.getGivenName()); - - // - set date of birth - final Node prDateOfBirth = XPathUtils - .selectSingleNode(idlassertion, SimpleIdentityLinkAssertionParser.PERSON_DATE_OF_BIRTH_XPATH); - - prDateOfBirth.getFirstChild().setNodeValue(eidData.getFormatedDateOfBirth()); - - identityLink = new SimpleIdentityLinkAssertionParser(idlassertion).parseIdentityLink(); - - new BpkBuilder(); - final Pair<String, String> bpkCalc = BpkBuilder - .generateAreaSpecificPersonIdentifier(identityLink.getIdentificationValue(), - identityLink.getIdentificationType(), - pendingReq.getServiceProviderConfiguration() - .getAreaSpecificTargetIdentifier()); - bpk = bpkCalc.getFirst(); - + SzrResultHolder idlResult = createDummyIdentityLinkForTestDeployment(eidData); + //inject personal-data into session + authProcessData.setIdentityLink(idlResult.getIdentityLink()); + + // set bPK and bPKType into auth session + authProcessData.setGenericDataToSession(PvpAttributeDefinitions.BPK_NAME, extendBpkByPrefix( + idlResult.getBpK(), pendingReq.getServiceProviderConfiguration().getAreaSpecificTargetIdentifier())); + authProcessData.setGenericDataToSession(PvpAttributeDefinitions.EID_SECTOR_FOR_IDENTIFIER_NAME, + pendingReq.getServiceProviderConfiguration() + .getAreaSpecificTargetIdentifier()); + } else { - // contact SZR Gateway - log.debug("Starting connecting SZR Gateway"); - final PersonInfoType personInfo = new PersonInfoType(); - final PersonNameType personName = new PersonNameType(); - final PhysicalPersonType naturalPerson = new PhysicalPersonType(); - final TravelDocumentType eDocument = new TravelDocumentType(); - - naturalPerson.setName(personName); - personInfo.setPerson(naturalPerson); - personInfo.setTravelDocument(eDocument); - - // person information - personName.setFamilyName(eidData.getFamilyName()); - personName.setGivenName(eidData.getGivenName()); - naturalPerson.setDateOfBirth(eidData.getFormatedDateOfBirth()); - eDocument.setIssuingCountry(eidData.getCitizenCountryCode()); - eDocument.setDocumentNumber(eidData.getPseudonym()); - - // eID document information - eDocument.setDocumentType(basicConfig - .getBasicConfiguration(Constants.CONIG_PROPS_EIDAS_SZRCLIENT_PARAMS_EDOCUMENTTYPE, - Constants.SZR_CONSTANTS_DEFAULT_DOCUMENT_TYPE)); - - // set PlaceOfBirth if available - if (eidData.getPlaceOfBirth() != null) { - log.trace("Find 'PlaceOfBirth' attribute: " + eidData.getPlaceOfBirth()); - if (basicConfig - .getBasicConfigurationBoolean(Constants.CONIG_PROPS_EIDAS_SZRCLIENT_PARAMS_SETPLACEOFBIRTHIFAVAILABLE, - true)) { - naturalPerson.setPlaceOfBirth(eidData.getPlaceOfBirth()); - log.trace("Adding 'PlaceOfBirth' to ERnB request ... "); - - } - } - - // set BirthName if available - if (eidData.getBirthName() != null) { - log.trace("Find 'BirthName' attribute: " + eidData.getBirthName()); - if (basicConfig - .getBasicConfigurationBoolean(Constants.CONIG_PROPS_EIDAS_SZRCLIENT_PARAMS_SETBIRTHNAMEIFAVAILABLE, - true)) { - final AlternativeNameType alternativeName = new AlternativeNameType(); - naturalPerson.setAlternativeName(alternativeName); - alternativeName.setFamilyName(eidData.getBirthName()); - log.trace("Adding 'BirthName' to ERnB request ... "); - - } - } - - if (isNewEidMode) { - - // read Connector wide config data TODO connector wide! - String keyStoreAlias = basicConfig - .getBasicConfiguration(MsEidasNodeConstants.PROP_CONFIG_SP_AUTHBLOCK_KEYSTSTORE_FRIENDLYNAME); - String keyStorePw = basicConfig - .getBasicConfiguration(MsEidasNodeConstants.PROP_CONFIG_SP_AUTHBLOCK_KEYSTORE_PASSWORD); - String keyStorePath = basicConfig - .getBasicConfiguration(MsEidasNodeConstants.PROP_CONFIG_SP_AUTHBLOCK_KEYSTORE_PATH); - String keyStoreType = basicConfig - .getBasicConfiguration(MsEidasNodeConstants.PROP_CONFIG_SP_AUTHBLOCK_KEYSTORE_TYPE); - - - // get verschlüsselte Stammzahl + //build SZR request from eIDAS data + final PersonInfoType personInfo = generateSzrRequest(eidData); + + //request SZR based on IDL or E-ID mode + if (pendingReq.getServiceProviderConfiguration() + .isConfigurationValue(MsEidasNodeConstants.PROP_CONFIG_SP_NEW_EID_MODE, false)) { + + // get encrypted baseId String vsz = szrClient.getEncryptedStammzahl(personInfo); - - // build Keystore - Pair<KeyStore, Provider> keystoreProvider = initKeystore(keyStoreAlias, keyStorePw, keyStorePath, - keyStoreType); - - // get pubKey - PublicKey publicKey = keystoreProvider.getFirst().getCertificate(keyStoreAlias).getPublicKey(); - - // encode pubKey base64 - String pk64 = Base64.getEncoder().encodeToString(publicKey.getEncoded()); - + // get eIDAS bind - String signedEidasBind = szrClient.getBcBind(vsz, pk64, EID_STATUS); - - // build AuthBlock (JWS) - ObjectMapper mapper = new ObjectMapper(); - String jwsPayload = mapper.writeValueAsString(pendingReq.getUniqueTransactionIdentifier()); - - String jwsSignature = JoseUtils - .createSignature(keystoreProvider, keyStoreAlias, keyStorePw.toCharArray(), jwsPayload, false, - keyStoreAlias); - + String signedEidasBind = szrClient.getBcBind(vsz, + authBlockSigner.getBase64EncodedPublicKey(), + EID_STATUS); + + //get signed AuthBlock + String jwsSignature = authBlockSigner.buildSignedAuthBlock(pendingReq.getUniqueTransactionIdentifier()); + + //inject personal-data into session authProcessData.setGenericDataToSession(Constants.SZR_AUTHBLOCK, jwsSignature); authProcessData.setGenericDataToSession(Constants.EIDAS_BIND, signedEidasBind); + } else { - - final IdentityLinkType result = szrClient.getIdentityLinkInRawMode(personInfo); - - final Element idlFromSzr = (Element) result.getAssertion(); - identityLink = new SimpleIdentityLinkAssertionParser(idlFromSzr).parseIdentityLink(); - - // write ERnB inputdata into revisionlog + //request SZR + SzrResultHolder idlResult = requestSzrForIdentityLink(personInfo); + + // write ERnB input-data into revision-log if (basicConfig.getBasicConfigurationBoolean( Constants.CONIG_PROPS_EIDAS_SZRCLIENT_WORKAROUND_REVISIONLOGDATASTORE_ACTIVE, false)) { revisionsLogger.logEvent(pendingReq, MsConnectorEventCodes.SZR_ERNB_EIDAS_RAW_ID, @@ -283,100 +175,158 @@ public class CreateIdentityLinkTask extends AbstractAuthServletTask { revisionsLogger.logEvent(pendingReq, MsConnectorEventCodes.SZR_ERNB_EIDAS_ERNB_ID, eidData.getPseudonym()); } - - // get bPK from SZR - if (basicConfig - .getBasicConfigurationBoolean(Constants.CONIG_PROPS_EIDAS_SZRCLIENT_DEBUG_USESRZFORBPKGENERATION, true)) { - bpk = szrClient - .getBpk(personInfo, pendingReq.getServiceProviderConfiguration().getAreaSpecificTargetIdentifier(), - basicConfig - .getBasicConfiguration(Constants.CONIG_PROPS_EIDAS_SZRCLIENT_PARAMS_VKZ, "no VKZ defined")) - .get(0); - - } else { - log.debug("Calculating bPK from baseId ... "); - new BpkBuilder(); - final Pair<String, String> bpkCalc = BpkBuilder - .generateAreaSpecificPersonIdentifier(identityLink.getIdentificationValue(), - identityLink.getIdentificationType(), - pendingReq.getServiceProviderConfiguration() - .getAreaSpecificTargetIdentifier()); - bpk = bpkCalc.getFirst(); - - } + + //check result-data and write revision-log based on current state + checkStateAndWriteRevisionLog(idlResult); + + + //inject personal-data into session + authProcessData.setIdentityLink(idlResult.getIdentityLink()); + + // set bPK and bPKType into auth session + authProcessData.setGenericDataToSession(PvpAttributeDefinitions.BPK_NAME, extendBpkByPrefix( + idlResult.getBpK(), pendingReq.getServiceProviderConfiguration().getAreaSpecificTargetIdentifier())); + authProcessData.setGenericDataToSession(PvpAttributeDefinitions.EID_SECTOR_FOR_IDENTIFIER_NAME, + pendingReq.getServiceProviderConfiguration() + .getAreaSpecificTargetIdentifier()); + } } + + //add generic info's into session + authProcessData.setForeigner(true); + authProcessData.setGenericDataToSession(PvpAttributeDefinitions.EID_ISSUING_NATION_NAME, EidasResponseUtils + .parseEidasPersonalIdentifier((String) simpleAttrMap.get(Constants.eIDAS_ATTR_PERSONALIDENTIFIER)) + .getFirst()); + authProcessData.setQaaLevel(eidasResponse.getLevelOfAssurance()); + + // store pending-request + requestStoreage.storePendingRequest(pendingReq); + + + } catch (final EidasAttributeException e) { + throw new TaskExecutionException(pendingReq, "Minimum required eIDAS attributeset not found.", e); - if (isNewEidMode) { - authProcessData.setForeigner(true); - authProcessData.setGenericDataToSession(PvpAttributeDefinitions.EID_ISSUING_NATION_NAME, EidasResponseUtils - .parseEidasPersonalIdentifier((String) simpleAttrMap.get(Constants.eIDAS_ATTR_PERSONALIDENTIFIER)) - .getFirst()); - authProcessData.setQaaLevel(eidasResponse.getLevelOfAssurance()); + } catch (final EaafException e) { + throw new TaskExecutionException(pendingReq, "IdentityLink generation for foreign person FAILED.", e); - } else { - if (identityLink == null) { - log.error("ERnB did not return an identity link."); - throw new SzrCommunicationException("ernb.00", null); + } catch (final Exception e) { + log.error("IdentityLink generation for foreign person FAILED.", e); + throw new TaskExecutionException(pendingReq, "IdentityLink generation for foreign person FAILED.", e); - } - revisionsLogger.logEvent(pendingReq, - MsConnectorEventCodes.SZR_IDL_RECEIVED, - identityLink.getSamlAssertion() - .getAttribute(SimpleIdentityLinkAssertionParser.ASSERTIONID)); + } + } - if (bpk == null) { - log.error("ERnB did not return a bPK for target: " + pendingReq.getServiceProviderConfiguration() - .getAreaSpecificTargetIdentifier()); - throw new SzrCommunicationException("ernb.01", null); + private PersonInfoType generateSzrRequest(ErnbEidData eidData) { + log.debug("Starting connecting SZR Gateway"); + final PersonInfoType personInfo = new PersonInfoType(); + final PersonNameType personName = new PersonNameType(); + final PhysicalPersonType naturalPerson = new PhysicalPersonType(); + final TravelDocumentType eDocument = new TravelDocumentType(); + + naturalPerson.setName(personName); + personInfo.setPerson(naturalPerson); + personInfo.setTravelDocument(eDocument); + + // person information + personName.setFamilyName(eidData.getFamilyName()); + personName.setGivenName(eidData.getGivenName()); + naturalPerson.setDateOfBirth(eidData.getFormatedDateOfBirth()); + eDocument.setIssuingCountry(eidData.getCitizenCountryCode()); + eDocument.setDocumentNumber(eidData.getPseudonym()); + + // eID document information + eDocument.setDocumentType(basicConfig + .getBasicConfiguration(Constants.CONIG_PROPS_EIDAS_SZRCLIENT_PARAMS_EDOCUMENTTYPE, + Constants.SZR_CONSTANTS_DEFAULT_DOCUMENT_TYPE)); + + // set PlaceOfBirth if available + if (eidData.getPlaceOfBirth() != null) { + log.trace("Find 'PlaceOfBirth' attribute: " + eidData.getPlaceOfBirth()); + if (basicConfig + .getBasicConfigurationBoolean(Constants.CONIG_PROPS_EIDAS_SZRCLIENT_PARAMS_SETPLACEOFBIRTHIFAVAILABLE, + true)) { + naturalPerson.setPlaceOfBirth(eidData.getPlaceOfBirth()); + log.trace("Adding 'PlaceOfBirth' to ERnB request ... "); - } - revisionsLogger.logEvent(pendingReq, MsConnectorEventCodes.SZR_BPK_RECEIVED); + } + } - log.debug("ERnB communication was successfull"); + // set BirthName if available + if (eidData.getBirthName() != null) { + log.trace("Find 'BirthName' attribute: " + eidData.getBirthName()); + if (basicConfig + .getBasicConfigurationBoolean(Constants.CONIG_PROPS_EIDAS_SZRCLIENT_PARAMS_SETBIRTHNAMEIFAVAILABLE, + true)) { + final AlternativeNameType alternativeName = new AlternativeNameType(); + naturalPerson.setAlternativeName(alternativeName); + alternativeName.setFamilyName(eidData.getBirthName()); + log.trace("Adding 'BirthName' to ERnB request ... "); - authProcessData.setForeigner(true); - authProcessData.setIdentityLink(identityLink); - authProcessData.setGenericDataToSession(PvpAttributeDefinitions.EID_ISSUING_NATION_NAME, EidasResponseUtils - .parseEidasPersonalIdentifier((String) simpleAttrMap.get(Constants.eIDAS_ATTR_PERSONALIDENTIFIER)) - .getFirst()); + } + } + + return personInfo; + + } - // set bPK and bPKType into auth session - authProcessData.setGenericDataToSession(PvpAttributeDefinitions.BPK_NAME, extendBpkByPrefix(bpk, pendingReq - .getServiceProviderConfiguration().getAreaSpecificTargetIdentifier())); - authProcessData.setGenericDataToSession(PvpAttributeDefinitions.EID_SECTOR_FOR_IDENTIFIER_NAME, + private SzrResultHolder requestSzrForIdentityLink(PersonInfoType personInfo) + throws SzrCommunicationException, EaafException { + //request IdentityLink from SZR + final IdentityLinkType result = szrClient.getIdentityLinkInRawMode(personInfo); + + final Element idlFromSzr = (Element) result.getAssertion(); + IIdentityLink identityLink = new SimpleIdentityLinkAssertionParser(idlFromSzr).parseIdentityLink(); + + // get bPK from SZR + String bpk; + if (basicConfig + .getBasicConfigurationBoolean(Constants.CONIG_PROPS_EIDAS_SZRCLIENT_DEBUG_USESRZFORBPKGENERATION, true)) { + bpk = szrClient + .getBpk(personInfo, pendingReq.getServiceProviderConfiguration().getAreaSpecificTargetIdentifier(), + basicConfig + .getBasicConfiguration(Constants.CONIG_PROPS_EIDAS_SZRCLIENT_PARAMS_VKZ, "no VKZ defined")) + .get(0); + + } else { + log.debug("Calculating bPK from baseId ... "); + new BpkBuilder(); + final Pair<String, String> bpkCalc = BpkBuilder + .generateAreaSpecificPersonIdentifier(identityLink.getIdentificationValue(), + identityLink.getIdentificationType(), pendingReq.getServiceProviderConfiguration() .getAreaSpecificTargetIdentifier()); + bpk = bpkCalc.getFirst(); - // store pending-request - requestStoreage.storePendingRequest(pendingReq); - } - } catch (final EidasAttributeException e) { - throw new TaskExecutionException(pendingReq, "Minimum required eIDAS attributeset not found.", e); + } + + return new SzrResultHolder(identityLink, bpk); + + } + + private void checkStateAndWriteRevisionLog(SzrResultHolder idlResult) throws SzrCommunicationException { + // write some infos into revision log + if (idlResult.getIdentityLink() == null) { + log.error("ERnB did not return an identity link."); + throw new SzrCommunicationException("ernb.00", null); - } catch (final EaafException e) { - throw new TaskExecutionException(pendingReq, "IdentityLink generation for foreign person FAILED.", e); + } + revisionsLogger.logEvent(pendingReq, + MsConnectorEventCodes.SZR_IDL_RECEIVED, + idlResult.getIdentityLink().getSamlAssertion() + .getAttribute(SimpleIdentityLinkAssertionParser.ASSERTIONID)); - } catch (final Exception e) { - log.error("IdentityLink generation for foreign person FAILED.", e); - throw new TaskExecutionException(pendingReq, "IdentityLink generation for foreign person FAILED.", e); + if (idlResult.getBpK() == null) { + log.error("ERnB did not return a bPK for target: " + pendingReq.getServiceProviderConfiguration() + .getAreaSpecificTargetIdentifier()); + throw new SzrCommunicationException("ernb.01", null); } + revisionsLogger.logEvent(pendingReq, MsConnectorEventCodes.SZR_BPK_RECEIVED); + log.debug("ERnB communication was successfull"); + } - - private Pair<KeyStore, Provider> initKeystore(String keyAlias, String keyPw, String path, String type) - throws EaafException, KeyStoreException { - KeyStoreConfiguration keyStoreConfiguration = new KeyStoreConfiguration(); - - final String current = new java.io.File(".").toURI().toString(); - keyStoreConfiguration.setSoftKeyStoreFilePath(current + path); - keyStoreConfiguration.setSoftKeyStorePassword(keyPw); - keyStoreConfiguration.setKeyStoreType(KeyStoreConfiguration.KeyStoreType.fromString(type)); - keyStoreConfiguration.setFriendlyName(keyAlias); - keyStoreConfiguration.setKeyStoreName(keyAlias); - return keyStoreFactory.buildNewKeyStore(keyStoreConfiguration); - } - + private String extendBpkByPrefix(String bpk, String type) { String bpkType = null; @@ -406,7 +356,7 @@ public class CreateIdentityLinkTask extends AbstractAuthServletTask { for (final AttributeDefinition<?> el : attributeMap.keySet()) { - final Class parameterizedType = el.getParameterizedType(); + final Class<?> parameterizedType = el.getParameterizedType(); if (DateTime.class.equals(parameterizedType)) { final DateTime attribute = EidasResponseUtils.translateDateAttribute(el, attributeMap.get(el).asList()); if (attribute != null) { @@ -466,5 +416,72 @@ public class CreateIdentityLinkTask extends AbstractAuthServletTask { } } + + @Data + private static class SzrResultHolder { + final IIdentityLink identityLink; + final String bpK; + + } + + /** + * Build a dummy IdentityLink and a dummy bPK based on eIDAS information. + * + * <br><br> + * <b>FOR LOCAL TESTING ONLY!!!</b> + * + * @param eidData Information from eIDAS response + * @return IdentityLink and bPK + * @throws ParserConfigurationException In case of an IDL processing error + * @throws SAXException In case of an IDL processing error + * @throws IOException In case of an IDL processing error + * @throws EaafException In case of a bPK generation error + */ + private SzrResultHolder createDummyIdentityLinkForTestDeployment(ErnbEidData eidData) + throws ParserConfigurationException, SAXException, IOException, EaafException { + log.warn("SZR-Dummy IS ACTIVE! IdentityLink is NOT VALID!!!!"); + // create fake IdL + // - fetch IdL template from resources + final InputStream s = CreateIdentityLinkTask.class + .getResourceAsStream("/resources/xmldata/fakeIdL_IdL_template.xml"); + final Element idlTemplate = DomUtils.parseXmlValidating(s); + + IIdentityLink identityLink = new SimpleIdentityLinkAssertionParser(idlTemplate).parseIdentityLink(); + + // replace data + final Element idlassertion = identityLink.getSamlAssertion(); + + // - set fake baseID; + final Node prIdentification = XPathUtils + .selectSingleNode(idlassertion, SimpleIdentityLinkAssertionParser.PERSON_IDENT_VALUE_XPATH); + prIdentification.getFirstChild().setNodeValue(eidData.getPseudonym()); + + // - set last name + final Node prFamilyName = XPathUtils + .selectSingleNode(idlassertion, SimpleIdentityLinkAssertionParser.PERSON_FAMILY_NAME_XPATH); + prFamilyName.getFirstChild().setNodeValue(eidData.getFamilyName()); + + // - set first name + final Node prGivenName = XPathUtils + .selectSingleNode(idlassertion, SimpleIdentityLinkAssertionParser.PERSON_GIVEN_NAME_XPATH); + prGivenName.getFirstChild().setNodeValue(eidData.getGivenName()); + + // - set date of birth + final Node prDateOfBirth = XPathUtils + .selectSingleNode(idlassertion, SimpleIdentityLinkAssertionParser.PERSON_DATE_OF_BIRTH_XPATH); + + prDateOfBirth.getFirstChild().setNodeValue(eidData.getFormatedDateOfBirth()); + + identityLink = new SimpleIdentityLinkAssertionParser(idlassertion).parseIdentityLink(); + + new BpkBuilder(); + final Pair<String, String> bpkCalc = BpkBuilder + .generateAreaSpecificPersonIdentifier(identityLink.getIdentificationValue(), + identityLink.getIdentificationType(), + pendingReq.getServiceProviderConfiguration() + .getAreaSpecificTargetIdentifier()); + return new SzrResultHolder(identityLink, bpkCalc.getFirst()); + + } } diff --git a/eidas_modules/authmodule-eIDAS-v2/src/main/resources/eidas_v2_auth.beans.xml b/eidas_modules/authmodule-eIDAS-v2/src/main/resources/eidas_v2_auth.beans.xml index fbb48229..6cc704ab 100644 --- a/eidas_modules/authmodule-eIDAS-v2/src/main/resources/eidas_v2_auth.beans.xml +++ b/eidas_modules/authmodule-eIDAS-v2/src/main/resources/eidas_v2_auth.beans.xml @@ -58,6 +58,9 @@ <!-- <bean id="eIDASDataStore" class="at.asitplus.eidas.specific.modules.auth.eidas.v2.service.eIDASDataStore" /> --> + <bean id="authBlockSigningService" + class="at.asitplus.eidas.specific.modules.auth.eidas.v2.service.AuthBlockSigningService" /> + <bean id="EIDPostProcessingService" class="at.asitplus.eidas.specific.modules.auth.eidas.v2.service.CcSpecificEidProcessingService" /> diff --git a/eidas_modules/authmodule-eIDAS-v2/src/test/java/at/asitplus/eidas/specific/modules/auth/eidas/v2/test/SzrClientTestProduction.java b/eidas_modules/authmodule-eIDAS-v2/src/test/java/at/asitplus/eidas/specific/modules/auth/eidas/v2/test/SzrClientTestProduction.java index a30ea2a0..2f573f53 100644 --- a/eidas_modules/authmodule-eIDAS-v2/src/test/java/at/asitplus/eidas/specific/modules/auth/eidas/v2/test/SzrClientTestProduction.java +++ b/eidas_modules/authmodule-eIDAS-v2/src/test/java/at/asitplus/eidas/specific/modules/auth/eidas/v2/test/SzrClientTestProduction.java @@ -59,7 +59,7 @@ import szrservices.PersonInfoType; import szrservices.SZRException_Exception; import szrservices.TravelDocumentType; -//@Ignore +@Ignore @RunWith(SpringJUnit4ClassRunner.class) @ContextConfiguration("/SpringTest-context_basic_test.xml") public class SzrClientTestProduction { diff --git a/eidas_modules/authmodule-eIDAS-v2/src/test/java/at/asitplus/eidas/specific/modules/auth/eidas/v2/test/tasks/CreateIdentityLinkTaskEidNewTest.java b/eidas_modules/authmodule-eIDAS-v2/src/test/java/at/asitplus/eidas/specific/modules/auth/eidas/v2/test/tasks/CreateIdentityLinkTaskEidNewTest.java index 888b7631..f67b4d93 100644 --- a/eidas_modules/authmodule-eIDAS-v2/src/test/java/at/asitplus/eidas/specific/modules/auth/eidas/v2/test/tasks/CreateIdentityLinkTaskEidNewTest.java +++ b/eidas_modules/authmodule-eIDAS-v2/src/test/java/at/asitplus/eidas/specific/modules/auth/eidas/v2/test/tasks/CreateIdentityLinkTaskEidNewTest.java @@ -1,7 +1,5 @@ package at.asitplus.eidas.specific.modules.auth.eidas.v2.test.tasks; -import static at.asitplus.eidas.specific.connector.MsEidasNodeConstants.PROP_CONFIG_SP_AUTHBLOCK_KEYSTSTORE_FRIENDLYNAME; -import static at.asitplus.eidas.specific.connector.MsEidasNodeConstants.PROP_CONFIG_SP_AUTHBLOCK_KEYSTORE_PASSWORD; import static at.asitplus.eidas.specific.connector.MsEidasNodeConstants.PROP_CONFIG_SP_NEW_EID_MODE; import static org.mockito.ArgumentMatchers.any; import static org.powermock.api.mockito.PowerMockito.when; @@ -9,13 +7,22 @@ import static org.powermock.api.mockito.PowerMockito.when; import java.io.IOException; import java.net.URI; import java.net.URISyntaxException; +import java.security.KeyStore; +import java.security.Provider; +import java.security.cert.X509Certificate; +import java.util.Arrays; +import java.util.Collections; import java.util.HashMap; +import java.util.List; import java.util.Map; import javax.xml.namespace.QName; import org.apache.commons.lang3.RandomStringUtils; import org.jetbrains.annotations.NotNull; +import org.jose4j.jwa.AlgorithmConstraints; +import org.jose4j.jwa.AlgorithmConstraints.ConstraintType; +import org.jose4j.jws.AlgorithmIdentifiers; import org.junit.Assert; import org.junit.Before; import org.junit.BeforeClass; @@ -38,12 +45,18 @@ import at.asitplus.eidas.specific.connector.MsEidasNodeConstants; import at.asitplus.eidas.specific.modules.auth.eidas.v2.Constants; import at.asitplus.eidas.specific.modules.auth.eidas.v2.service.EidasAttributeRegistry; import at.asitplus.eidas.specific.modules.auth.eidas.v2.tasks.CreateIdentityLinkTask; -import at.asitplus.eidas.specific.modules.auth.eidas.v2.test.dummy.DummySpecificCommunicationService; +import at.asitplus.eidas.specific.modules.auth.eidas.v2.utils.JoseUtils; +import at.asitplus.eidas.specific.modules.auth.eidas.v2.utils.JoseUtils.JwsResult; import at.gv.egiz.eaaf.core.api.data.EaafConfigConstants; import at.gv.egiz.eaaf.core.api.data.EaafConstants; import at.gv.egiz.eaaf.core.api.idp.IConfiguration; import at.gv.egiz.eaaf.core.api.idp.process.ExecutionContext; +import at.gv.egiz.eaaf.core.exceptions.EaafException; import at.gv.egiz.eaaf.core.exceptions.EaafStorageException; +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.data.Pair; import at.gv.egiz.eaaf.core.impl.idp.auth.data.AuthProcessDataWrapper; import at.gv.egiz.eaaf.core.impl.idp.module.test.DummySpConfiguration; import at.gv.egiz.eaaf.core.impl.idp.module.test.TestRequestImpl; @@ -53,7 +66,6 @@ import eu.eidas.auth.commons.attribute.ImmutableAttributeMap; import eu.eidas.auth.commons.attribute.PersonType; import eu.eidas.auth.commons.protocol.impl.AuthenticationResponse; import lombok.val; -import szrservices.PersonInfoType; import szrservices.SZR; import szrservices.SignContentEntry; import szrservices.SignContentResponseType; @@ -66,17 +78,16 @@ import szrservices.SignContentResponseType; @ContextConfiguration("/SpringTest-context_tasks_test.xml") public class CreateIdentityLinkTaskEidNewTest { - @Autowired(required = true) private CreateIdentityLinkTask task; - // @Autowired(required = true) - // private FinalizeAuthenticationTask authTask; - @Autowired(required = true) - private DummySpecificCommunicationService commService; + @Autowired(required = true) private IConfiguration basicConfig; @Autowired protected EidasAttributeRegistry attrRegistry; + + @Autowired + EaafKeyStoreFactory keyStoreFactory; final ExecutionContext executionContext = new ExecutionContextImpl(); private MockHttpServletRequest httpReq; @@ -88,6 +99,13 @@ public class CreateIdentityLinkTaskEidNewTest { private static final String PW = "f/+saJBc3a}*/T^s"; private static final String ALIAS = "connectorkeypair"; + private static final List<String> BINDING_AUTH_ALGORITHM_WHITELIST_SIGNING = Collections.unmodifiableList( + Arrays.asList( + AlgorithmIdentifiers.ECDSA_USING_P256_CURVE_AND_SHA256, + AlgorithmIdentifiers.ECDSA_USING_P521_CURVE_AND_SHA512, + AlgorithmIdentifiers.RSA_PSS_USING_SHA256, + AlgorithmIdentifiers.RSA_PSS_USING_SHA512)); + @Rule public final SoapServiceRule soap = SoapServiceRule.newInstance(); @@ -99,7 +117,8 @@ public class CreateIdentityLinkTaskEidNewTest { @BeforeClass public static void classInitializer() throws IOException { final String current = new java.io.File(".").toURI().toString(); - System.setProperty("eidas.ms.configuration", current + "src/test/resources/config/junit_config_3.properties"); + System.setProperty("eidas.ms.configuration", current + + "src/test/resources/config/junit_config_3.properties"); } @@ -118,16 +137,13 @@ public class CreateIdentityLinkTaskEidNewTest { spConfig.put(EaafConfigConstants.SERVICE_UNIQUEIDENTIFIER, "testSp"); spConfig.put("target", "urn:publicid:gv.at:cdid+XX"); spConfig.put(PROP_CONFIG_SP_NEW_EID_MODE, "true"); - spConfig.put(PROP_CONFIG_SP_AUTHBLOCK_KEYSTORE_PASSWORD, PW); - spConfig.put(PROP_CONFIG_SP_AUTHBLOCK_KEYSTSTORE_FRIENDLYNAME, ALIAS); oaParam = new DummySpConfiguration(spConfig, basicConfig); pendingReq = new TestRequestImpl(); - AuthenticationResponse response = buildDummyAuthResponse(); - + final AuthenticationResponse response = buildDummyAuthResponse(); pendingReq.getSessionData(AuthProcessDataWrapper.class) - .setGenericDataToSession(Constants.DATA_FULL_EIDAS_RESPONSE, response); + .setGenericDataToSession(Constants.DATA_FULL_EIDAS_RESPONSE, response); pendingReq.setSpConfig(oaParam); pendingReq.setPendingReqId(at.gv.egiz.eaaf.core.impl.utils.Random.nextProcessReferenceValue()); pendingReq.setAuthUrl("http://test.com/"); @@ -141,73 +157,109 @@ public class CreateIdentityLinkTaskEidNewTest { @NotNull private AuthenticationResponse buildDummyAuthResponse() throws URISyntaxException { - AttributeDefinition attributeDef = AttributeDefinition.builder() - .friendlyName(Constants.eIDAS_ATTR_PERSONALIDENTIFIER) - .nameUri(new URI("ad", "sd", "ff")) - .personType(PersonType.LEGAL_PERSON) - .xmlType(new QName("http://saf", "as", "af")) - .attributeValueMarshaller( - "eu.eidas.auth.commons.attribute.impl.LiteralStringAttributeValueMarshaller") - .build(); - AttributeDefinition attributeDef2 = AttributeDefinition.builder() - .friendlyName(Constants.eIDAS_ATTR_CURRENTFAMILYNAME) - .nameUri(new URI("ad", "sd", "fff")) - .personType(PersonType.LEGAL_PERSON) - .xmlType(new QName("http://saf", "as", "aff")) - .attributeValueMarshaller( - "eu.eidas.auth.commons.attribute.impl.LiteralStringAttributeValueMarshaller") - .build(); - AttributeDefinition attributeDef3 = AttributeDefinition.builder() - .friendlyName(Constants.eIDAS_ATTR_CURRENTGIVENNAME) - .nameUri(new URI("ad", "sd", "ffff")) - .personType(PersonType.LEGAL_PERSON) - .xmlType(new QName("http://saf", "as", "afff")) - .attributeValueMarshaller( - "eu.eidas.auth.commons.attribute.impl.LiteralStringAttributeValueMarshaller") - .build(); - AttributeDefinition attributeDef4 = AttributeDefinition.builder().friendlyName(Constants.eIDAS_ATTR_DATEOFBIRTH) - .nameUri(new URI("ad", "sd", "fffff")) - .personType(PersonType.LEGAL_PERSON) - .xmlType(new QName("http://saf", "as", "affff")) - .attributeValueMarshaller( - "eu.eidas.auth.commons.attribute.impl.DateTimeAttributeValueMarshaller") - .build(); - - ImmutableAttributeMap attributeMap = ImmutableAttributeMap.builder().put(attributeDef, "de/st/" + RandomStringUtils - .randomNumeric(64)).put(attributeDef2, RandomStringUtils.randomAlphabetic(10)).put(attributeDef3, - RandomStringUtils - .randomAlphabetic(10)) - .put(attributeDef4, "2001-01-01").build(); - + final AttributeDefinition attributeDef = AttributeDefinition.builder() + .friendlyName(Constants.eIDAS_ATTR_PERSONALIDENTIFIER) + .nameUri(new URI("ad", "sd", "ff")) + .personType(PersonType.LEGAL_PERSON) + .xmlType(new QName("http://saf", "as", "af")) + .attributeValueMarshaller( + "eu.eidas.auth.commons.attribute.impl.LiteralStringAttributeValueMarshaller") + .build(); + final AttributeDefinition attributeDef2 = AttributeDefinition.builder() + .friendlyName(Constants.eIDAS_ATTR_CURRENTFAMILYNAME) + .nameUri(new URI("ad", "sd", "fff")) + .personType(PersonType.LEGAL_PERSON) + .xmlType(new QName("http://saf", "as", "aff")) + .attributeValueMarshaller( + "eu.eidas.auth.commons.attribute.impl.LiteralStringAttributeValueMarshaller") + .build(); + final AttributeDefinition attributeDef3 = AttributeDefinition.builder() + .friendlyName(Constants.eIDAS_ATTR_CURRENTGIVENNAME) + .nameUri(new URI("ad", "sd", "ffff")) + .personType(PersonType.LEGAL_PERSON) + .xmlType(new QName("http://saf", "as", "afff")) + .attributeValueMarshaller( + "eu.eidas.auth.commons.attribute.impl.LiteralStringAttributeValueMarshaller") + .build(); + final AttributeDefinition attributeDef4 = AttributeDefinition.builder().friendlyName( + Constants.eIDAS_ATTR_DATEOFBIRTH) + .nameUri(new URI("ad", "sd", "fffff")) + .personType(PersonType.LEGAL_PERSON) + .xmlType(new QName("http://saf", "as", "affff")) + .attributeValueMarshaller( + "eu.eidas.auth.commons.attribute.impl.DateTimeAttributeValueMarshaller") + .build(); + + final ImmutableAttributeMap attributeMap = ImmutableAttributeMap.builder().put(attributeDef, "de/st/" + + RandomStringUtils + .randomNumeric(64)).put(attributeDef2, RandomStringUtils.randomAlphabetic(10)).put(attributeDef3, + RandomStringUtils + .randomAlphabetic(10)) + .put(attributeDef4, "2001-01-01").build(); val b = new AuthenticationResponse.Builder(); - return b.id("aasdf").issuer("asd").subject("asf").statusCode("200").inResponseTo("asdf").subjectNameIdFormat("afaf") - .attributes(attributeMap).build(); + return b.id("aasdf").issuer("asd").subject("asf").statusCode("200").inResponseTo("asdf") + .subjectNameIdFormat("afaf") + .attributes(attributeMap).build(); } @Test - public void fullTest() { - // keystore password f/+saJBc3a}*/T^s - try { - - String test = szrMock.getStammzahlEncrypted(new PersonInfoType(), false); - - when(szrMock, "getStammzahlEncrypted", any(), any()).thenReturn(RandomStringUtils.randomNumeric(10)); - val signContentResp = new SignContentResponseType(); - SignContentEntry signContentEntry = new SignContentEntry(); - signContentEntry.setValue(RandomStringUtils.randomAlphanumeric(10)); - signContentResp.getOut().add(signContentEntry); - when(szrMock, "signContent", any(), any(), any()).thenReturn(signContentResp); - task.execute(pendingReq, executionContext); - - } catch (Exception e) { - e.printStackTrace(); - Assert.fail(); - } - + public void successfulProcess() throws Exception { + //initialize test + when(szrMock, "getStammzahlEncrypted", any(), any()).thenReturn(RandomStringUtils.randomNumeric(10)); + val signContentResp = new SignContentResponseType(); + final SignContentEntry signContentEntry = new SignContentEntry(); + signContentEntry.setValue(RandomStringUtils.randomAlphanumeric(10)); + signContentResp.getOut().add(signContentEntry); + when(szrMock, "signContent", any(), any(), any()).thenReturn(signContentResp); + + //perform test + task.execute(pendingReq, executionContext); + + //validate state + final AuthProcessDataWrapper authProcessData = pendingReq.getSessionData(AuthProcessDataWrapper.class); + Assert.assertNotNull("AuthProcessData", authProcessData); + Assert.assertNotNull("eidasBind", authProcessData.getGenericDataFromSession(Constants.EIDAS_BIND, String.class)); + + String authBlock = authProcessData.getGenericDataFromSession(Constants.SZR_AUTHBLOCK, String.class); + Assert.assertNotNull("AuthBlock", authBlock); + + //check authblock signature + final AlgorithmConstraints constraints = new AlgorithmConstraints(ConstraintType.PERMIT, + BINDING_AUTH_ALGORITHM_WHITELIST_SIGNING + .toArray(new String[BINDING_AUTH_ALGORITHM_WHITELIST_SIGNING.size()])); + Pair<KeyStore, Provider> keyStore = getKeyStore(); + X509Certificate[] trustedCerts = EaafKeyStoreUtils.getPrivateKeyAndCertificates( + keyStore.getFirst(), ALIAS, PW.toCharArray(), true, "junit").getSecond(); + JwsResult result = JoseUtils.validateSignature(authBlock, Arrays.asList(trustedCerts) , constraints); + Assert.assertTrue("AuthBlock not valid", result.isValid()); + + } + private Pair<KeyStore, Provider> getKeyStore() throws EaafException { + // read Connector wide config data TODO connector wide! + String keyStoreName = basicConfig + .getBasicConfiguration(MsEidasNodeConstants.PROP_CONFIG_AUTHBLOCK_KEYSTORE_NAME); + String keyStorePw = basicConfig + .getBasicConfiguration(MsEidasNodeConstants.PROP_CONFIG_AUTHBLOCK_KEYSTORE_PASSWORD); + String keyStorePath = basicConfig + .getBasicConfiguration(MsEidasNodeConstants.PROP_CONFIG_AUTHBLOCK_KEYSTORE_PATH); + String keyStoreType = basicConfig + .getBasicConfiguration(MsEidasNodeConstants.PROP_CONFIG_AUTHBLOCK_KEYSTORE_TYPE); + + + //build new KeyStore configuration + KeyStoreConfiguration keyStoreConfiguration = new KeyStoreConfiguration(); + keyStoreConfiguration.setFriendlyName("jUnit test"); + + keyStoreConfiguration.setSoftKeyStoreFilePath(keyStorePath); + keyStoreConfiguration.setSoftKeyStorePassword(keyStorePw); + keyStoreConfiguration.setKeyStoreType(KeyStoreConfiguration.KeyStoreType.fromString(keyStoreType)); + keyStoreConfiguration.setKeyStoreName(keyStoreName); + + //build new KeyStore based on configuration + return keyStoreFactory.buildNewKeyStore(keyStoreConfiguration); + } } - - diff --git a/eidas_modules/authmodule-eIDAS-v2/src/test/resources/SpringTest-context_tasks_test.xml b/eidas_modules/authmodule-eIDAS-v2/src/test/resources/SpringTest-context_tasks_test.xml index dd116bd3..7d5a4c53 100644 --- a/eidas_modules/authmodule-eIDAS-v2/src/test/resources/SpringTest-context_tasks_test.xml +++ b/eidas_modules/authmodule-eIDAS-v2/src/test/resources/SpringTest-context_tasks_test.xml @@ -45,6 +45,9 @@ ref="specificConnectorAdditionalAttributesFileWithPath" /> </bean> + <bean id="authBlockSigningService" + class="at.asitplus.eidas.specific.modules.auth.eidas.v2.service.AuthBlockSigningService" /> + <!-- Authentication Process Tasks --> <bean id="ConnecteIDASNodeTask" class="at.asitplus.eidas.specific.modules.auth.eidas.v2.tasks.GenerateAuthnRequestTask" diff --git a/eidas_modules/authmodule-eIDAS-v2/src/test/resources/config/junit_config_1.properties b/eidas_modules/authmodule-eIDAS-v2/src/test/resources/config/junit_config_1.properties index 35867187..21ed51e7 100644 --- a/eidas_modules/authmodule-eIDAS-v2/src/test/resources/config/junit_config_1.properties +++ b/eidas_modules/authmodule-eIDAS-v2/src/test/resources/config/junit_config_1.properties @@ -50,6 +50,14 @@ eidas.ms.auth.eIDAS.szrclient.params.vkz= eidas.ms.auth.eIDAS.szrclient.params.useSZRForbPKCalculation=false +eidas.ms.auth.eIDAS.authblock.keystore.password=f/+saJBc3a}*/T^s +eidas.ms.auth.eIDAS.authblock.keystore.friendlyName=connectorkeypair +eidas.ms.auth.eIDAS.authblock.keystore.path=./../keystore/teststore.jks +eidas.ms.auth.eIDAS.authblock.keystore.type=jks +eidas.ms.auth.eIDAS.authblock.key.alias=connectorkeypair +eidas.ms.auth.eIDAS.authblock.key.password=f/+saJBc3a}*/T^s + + #Raw eIDAS Id data storage eidas.ms.auth.eIDAS.szrclient.workarounds.eidmapping.revisionlog.active=true diff --git a/eidas_modules/authmodule-eIDAS-v2/src/test/resources/config/junit_config_2.properties b/eidas_modules/authmodule-eIDAS-v2/src/test/resources/config/junit_config_2.properties index 95ac8ec5..dcdadce5 100644 --- a/eidas_modules/authmodule-eIDAS-v2/src/test/resources/config/junit_config_2.properties +++ b/eidas_modules/authmodule-eIDAS-v2/src/test/resources/config/junit_config_2.properties @@ -49,6 +49,14 @@ eidas.ms.auth.eIDAS.szrclient.params.vkz= eidas.ms.auth.eIDAS.szrclient.params.useSZRForbPKCalculation=false +eidas.ms.auth.eIDAS.authblock.keystore.password=f/+saJBc3a}*/T^s +eidas.ms.auth.eIDAS.authblock.keystore.friendlyName=connectorkeypair +eidas.ms.auth.eIDAS.authblock.keystore.path=./../keystore/teststore.jks +eidas.ms.auth.eIDAS.authblock.keystore.type=jks +eidas.ms.auth.eIDAS.authblock.key.alias=connectorkeypair +eidas.ms.auth.eIDAS.authblock.key.password=f/+saJBc3a}*/T^s + + #Raw eIDAS Id data storage eidas.ms.auth.eIDAS.szrclient.workarounds.eidmapping.revisionlog.active=true diff --git a/eidas_modules/authmodule-eIDAS-v2/src/test/resources/config/junit_config_3.properties b/eidas_modules/authmodule-eIDAS-v2/src/test/resources/config/junit_config_3.properties index 79352734..c830d447 100644 --- a/eidas_modules/authmodule-eIDAS-v2/src/test/resources/config/junit_config_3.properties +++ b/eidas_modules/authmodule-eIDAS-v2/src/test/resources/config/junit_config_3.properties @@ -49,8 +49,10 @@ eidas.ms.auth.eIDAS.szrclient.params.vkz= eidas.ms.auth.eIDAS.authblock.keystore.password=f/+saJBc3a}*/T^s eidas.ms.auth.eIDAS.authblock.keystore.friendlyName=connectorkeypair -eidas.ms.auth.eIDAS.authblock.keystore.path=src/test/resources/keystore/teststore.jks +eidas.ms.auth.eIDAS.authblock.keystore.path=./../keystore/teststore.jks eidas.ms.auth.eIDAS.authblock.keystore.type=jks +eidas.ms.auth.eIDAS.authblock.key.alias=connectorkeypair +eidas.ms.auth.eIDAS.authblock.key.password=f/+saJBc3a}*/T^s eidas.ms.auth.eIDAS.szrclient.params.useSZRForbPKCalculation=false @@ -19,7 +19,7 @@ <!-- ===================================================================== --> <egiz-spring-api>0.3</egiz-spring-api> <egiz-eventlog-slf4jBackend>0.4</egiz-eventlog-slf4jBackend> - <eaaf-core.version>1.1.8</eaaf-core.version> + <eaaf-core.version>1.1.10-SNAPSHOT</eaaf-core.version> <org.springframework.version>5.2.9.RELEASE</org.springframework.version> <org.thymeleaf-spring5.version>3.0.11.RELEASE</org.thymeleaf-spring5.version> <cxf.version>3.4.0</cxf.version> |