Search in sources :

Example 46 with org.opensaml.saml.saml2.metadata

use of org.opensaml.saml.saml2.metadata in project ddf by codice.

the class SimpleSignTest method testSignSamlObjectModifyAndResign.

@Test
public void testSignSamlObjectModifyAndResign() throws Exception {
    Document responseDoc = StaxUtils.read(new ByteArrayInputStream(cannedResponse.getBytes()));
    XMLObject responseXmlObject = OpenSAMLUtil.fromDom(responseDoc.getDocumentElement());
    org.opensaml.saml.saml2.core.Response response = (org.opensaml.saml.saml2.core.Response) responseXmlObject;
    simpleSign.signSamlObject(response);
    final SubjectConfirmationData scd = new SubjectConfirmationDataBuilder().buildObject();
    scd.setNotOnOrAfter(DateTime.now().plusMinutes(30));
    for (Assertion assertion : response.getAssertions()) {
        assertion.getSubject().getSubjectConfirmations().forEach(sc -> sc.setSubjectConfirmationData(scd));
    }
    Document doc = DOMUtils.createDocument();
    Element requestElement = OpenSAMLUtil.toDom(response, doc);
    String responseMessage = DOM2Writer.nodeToString(requestElement);
    responseDoc = StaxUtils.read(new ByteArrayInputStream(responseMessage.getBytes()));
    responseXmlObject = OpenSAMLUtil.fromDom(responseDoc.getDocumentElement());
    response = (org.opensaml.saml.saml2.core.Response) responseXmlObject;
    simpleSign.validateSignature(response.getSignature(), response.getDOM().getOwnerDocument());
}
Also used : Element(org.w3c.dom.Element) Assertion(org.opensaml.saml.saml2.core.Assertion) XMLObject(org.opensaml.core.xml.XMLObject) Document(org.w3c.dom.Document) SubjectConfirmationData(org.opensaml.saml.saml2.core.SubjectConfirmationData) SubjectConfirmationDataBuilder(org.opensaml.saml.saml2.core.impl.SubjectConfirmationDataBuilder) ByteArrayInputStream(java.io.ByteArrayInputStream) Test(org.junit.Test)

Example 47 with org.opensaml.saml.saml2.metadata

use of org.opensaml.saml.saml2.metadata in project ddf by codice.

the class MetadataConfigurationParser method privilegedParseEntityDescriptions.

private void privilegedParseEntityDescriptions(Path metadataFolder) throws IOException {
    try (DirectoryStream<Path> directoryStream = Files.newDirectoryStream(metadataFolder)) {
        for (Path path : directoryStream) {
            if (Files.isReadable(path)) {
                try (InputStream fileInputStream = Files.newInputStream(path)) {
                    List<EntityDescriptor> entityDescriptors = readEntityDescriptors(new InputStreamReader(fileInputStream, "UTF-8"));
                    entityDescriptors.forEach(this::processEntityDescriptor);
                }
            }
        }
    } catch (NoSuchFileException e) {
        LOGGER.debug("IDP metadata directory is not configured.", e);
    }
}
Also used : Path(java.nio.file.Path) EntityDescriptor(org.opensaml.saml.saml2.metadata.EntityDescriptor) InputStreamReader(java.io.InputStreamReader) InputStream(java.io.InputStream) NoSuchFileException(java.nio.file.NoSuchFileException)

Example 48 with org.opensaml.saml.saml2.metadata

use of org.opensaml.saml.saml2.metadata in project cas by apereo.

the class SamlIdPSaml2AttributeQueryProfileHandlerController method handlePostRequest.

/**
 * Handle post request.
 *
 * @param response the response
 * @param request  the request
 * @throws Exception the exception
 */
@PostMapping(path = SamlIdPConstants.ENDPOINT_SAML2_SOAP_ATTRIBUTE_QUERY)
protected void handlePostRequest(final HttpServletResponse response, final HttpServletRequest request) throws Exception {
    val enabled = configurationContext.getCasProperties().getAuthn().getSamlIdp().getCore().isAttributeQueryProfileEnabled();
    if (!enabled) {
        LOGGER.warn("SAML2 attribute query profile is not enabled");
        response.setStatus(HttpStatus.SC_NOT_IMPLEMENTED);
        return;
    }
    val ctx = decodeSoapRequest(request);
    val query = (AttributeQuery) ctx.getMessage();
    try {
        val issuer = Objects.requireNonNull(query).getIssuer().getValue();
        val registeredService = verifySamlRegisteredService(issuer);
        val adaptor = getSamlMetadataFacadeFor(registeredService, query);
        val facade = adaptor.orElseThrow(() -> new UnauthorizedServiceException(UnauthorizedServiceException.CODE_UNAUTHZ_SERVICE, "Cannot find metadata linked to " + issuer));
        verifyAuthenticationContextSignature(ctx, request, query, facade, registeredService);
        val nameIdValue = determineNameIdForQuery(query, registeredService, facade);
        val factory = (SamlAttributeQueryTicketFactory) getConfigurationContext().getTicketFactory().get(SamlAttributeQueryTicket.class);
        val id = factory.createTicketIdFor(nameIdValue, facade.getEntityId());
        LOGGER.debug("Created ticket id for attribute query [{}]", id);
        val ticket = getConfigurationContext().getTicketRegistry().getTicket(id, SamlAttributeQueryTicket.class);
        if (ticket == null || ticket.isExpired()) {
            LOGGER.warn("Attribute query ticket [{}] has either expired, or it is linked to " + "a single sign-on session that is no longer valid and has now expired", id);
            throw new InvalidTicketException(id);
        }
        val authentication = ticket.getAuthentication();
        val principal = resolvePrincipalForAttributeQuery(authentication, registeredService);
        val releasePolicyContext = RegisteredServiceAttributeReleasePolicyContext.builder().registeredService(registeredService).service(ticket.getService()).principal(principal).build();
        val principalAttributes = registeredService.getAttributeReleasePolicy().getConsentableAttributes(releasePolicyContext);
        LOGGER.debug("Initial consentable principal attributes are [{}]", principalAttributes);
        val authenticationAttributes = getConfigurationContext().getAuthenticationAttributeReleasePolicy().getAuthenticationAttributesForRelease(authentication, null, Map.of(), registeredService);
        val finalAttributes = CollectionUtils.merge(principalAttributes, authenticationAttributes);
        val principalId = registeredService.getUsernameAttributeProvider().resolveUsername(authentication.getPrincipal(), ticket.getService(), registeredService);
        LOGGER.debug("Principal id used for attribute query response should be [{}]", principalId);
        LOGGER.debug("Final attributes to be processed for the SAML2 response are [{}]", finalAttributes);
        val casAssertion = buildCasAssertion(principalId, registeredService, finalAttributes);
        request.setAttribute(AttributeQuery.class.getSimpleName(), query);
        val buildContext = SamlProfileBuilderContext.builder().samlRequest(query).httpRequest(request).httpResponse(response).authenticatedAssertion(casAssertion).registeredService(registeredService).adaptor(facade).binding(SAMLConstants.SAML2_SOAP11_BINDING_URI).messageContext(ctx).build();
        getConfigurationContext().getResponseBuilder().build(buildContext);
    } catch (final Exception e) {
        LoggingUtils.error(LOGGER, e);
        request.setAttribute(SamlIdPConstants.REQUEST_ATTRIBUTE_ERROR, "Unable to build SOAP response: " + StringUtils.defaultString(e.getMessage()));
        val buildContext = SamlProfileBuilderContext.builder().samlRequest(query).httpRequest(request).httpResponse(response).binding(SAMLConstants.SAML2_SOAP11_BINDING_URI).messageContext(ctx).build();
        getConfigurationContext().getSamlFaultResponseBuilder().build(buildContext);
    }
}
Also used : lombok.val(lombok.val) SamlAttributeQueryTicketFactory(org.apereo.cas.ticket.query.SamlAttributeQueryTicketFactory) SamlAttributeQueryTicket(org.apereo.cas.ticket.query.SamlAttributeQueryTicket) AttributeQuery(org.opensaml.saml.saml2.core.AttributeQuery) InvalidTicketException(org.apereo.cas.ticket.InvalidTicketException) UnauthorizedServiceException(org.apereo.cas.services.UnauthorizedServiceException) UnauthorizedServiceException(org.apereo.cas.services.UnauthorizedServiceException) InvalidTicketException(org.apereo.cas.ticket.InvalidTicketException) PostMapping(org.springframework.web.bind.annotation.PostMapping)

Example 49 with org.opensaml.saml.saml2.metadata

use of org.opensaml.saml.saml2.metadata in project cas by apereo.

the class SamlIdPInitiatedProfileHandlerController method handleIdPInitiatedSsoRequest.

/**
 * Handle idp initiated sso requests.
 * The URL of the response location at the SP (called the "Assertion Consumer Service")
 * but can be omitted in favor of the IdP picking the default endpoint location from metadata.
 *
 * @param response the response
 * @param request  the request
 * @return the model and view
 * @throws Exception the exception
 */
@GetMapping(path = SamlIdPConstants.ENDPOINT_SAML2_IDP_INIT_PROFILE_SSO)
protected ModelAndView handleIdPInitiatedSsoRequest(final HttpServletResponse response, final HttpServletRequest request) throws Exception {
    val providerId = request.getParameter(SamlIdPConstants.PROVIDER_ID);
    if (StringUtils.isBlank(providerId)) {
        LOGGER.warn("No providerId parameter given in unsolicited SSO authentication request.");
        throw new MessageDecodingException("Missing providerId");
    }
    val registeredService = verifySamlRegisteredService(providerId);
    val adaptor = getSamlMetadataFacadeFor(registeredService, providerId);
    if (adaptor.isEmpty()) {
        throw new UnauthorizedServiceException(UnauthorizedServiceException.CODE_UNAUTHZ_SERVICE, "Cannot find metadata linked to " + providerId);
    }
    var shire = request.getParameter(SamlIdPConstants.SHIRE);
    val facade = adaptor.get();
    if (StringUtils.isBlank(shire)) {
        LOGGER.info("Resolving service provider assertion consumer service URL for [{}] and binding [{}]", providerId, SAMLConstants.SAML2_POST_BINDING_URI);
        val acs = facade.getAssertionConsumerService(SAMLConstants.SAML2_POST_BINDING_URI);
        shire = acs != null ? StringUtils.isBlank(acs.getResponseLocation()) ? acs.getLocation() : acs.getResponseLocation() : null;
    }
    if (StringUtils.isBlank(shire)) {
        LOGGER.warn("Unable to resolve service provider assertion consumer service URL for AuthnRequest construction for entityID: [{}]", providerId);
        throw new MessageDecodingException("Unable to resolve SP ACS URL for AuthnRequest construction");
    }
    val target = request.getParameter(SamlIdPConstants.TARGET);
    val time = request.getParameter(SamlIdPConstants.TIME);
    val builder = (SAMLObjectBuilder) getConfigurationContext().getOpenSamlConfigBean().getBuilderFactory().getBuilder(AuthnRequest.DEFAULT_ELEMENT_NAME);
    val authnRequest = (AuthnRequest) builder.buildObject();
    authnRequest.setAssertionConsumerServiceURL(shire);
    val isBuilder = (SAMLObjectBuilder) getConfigurationContext().getOpenSamlConfigBean().getBuilderFactory().getBuilder(Issuer.DEFAULT_ELEMENT_NAME);
    val issuer = (Issuer) isBuilder.buildObject();
    issuer.setValue(providerId);
    authnRequest.setIssuer(issuer);
    authnRequest.setProtocolBinding(SAMLConstants.SAML2_POST_BINDING_URI);
    val pBuilder = (SAMLObjectBuilder) getConfigurationContext().getOpenSamlConfigBean().getBuilderFactory().getBuilder(NameIDPolicy.DEFAULT_ELEMENT_NAME);
    val nameIDPolicy = (NameIDPolicy) pBuilder.buildObject();
    nameIDPolicy.setAllowCreate(Boolean.TRUE);
    authnRequest.setNameIDPolicy(nameIDPolicy);
    if (NumberUtils.isCreatable(time)) {
        authnRequest.setIssueInstant(Instant.ofEpochMilli(Long.parseLong(time)));
    } else {
        authnRequest.setIssueInstant(ZonedDateTime.now(ZoneOffset.UTC).toInstant());
    }
    authnRequest.setForceAuthn(Boolean.FALSE);
    if (StringUtils.isNotBlank(target)) {
        request.setAttribute(SamlProtocolConstants.PARAMETER_SAML_RELAY_STATE, target);
    }
    val ctx = new MessageContext();
    if (facade.isAuthnRequestsSigned() || registeredService.isSignUnsolicitedAuthnRequest()) {
        getConfigurationContext().getSamlObjectSigner().encode(authnRequest, registeredService, facade, response, request, SAMLConstants.SAML2_POST_BINDING_URI, authnRequest, ctx);
    }
    ctx.setMessage(authnRequest);
    val bindingContext = ctx.getSubcontext(SAMLBindingContext.class, true);
    Objects.requireNonNull(bindingContext).setHasBindingSignature(false);
    SAMLBindingSupport.setRelayState(ctx, target);
    val pair = Pair.<RequestAbstractType, MessageContext>of(authnRequest, ctx);
    val modelAndView = initiateAuthenticationRequest(pair, response, request);
    if (modelAndView != null) {
        val view = (RedirectView) modelAndView.getView();
        val urlBuilder = new URIBuilder(Objects.requireNonNull(view).getUrl());
        val paramNames = request.getParameterNames();
        while (paramNames.hasMoreElements()) {
            val parameterName = paramNames.nextElement();
            if (!parameterName.equalsIgnoreCase(SamlIdPConstants.TARGET) && !parameterName.equalsIgnoreCase(SamlIdPConstants.TIME) && !parameterName.equalsIgnoreCase(SamlIdPConstants.SHIRE) && !parameterName.equalsIgnoreCase(SamlIdPConstants.PROVIDER_ID)) {
                urlBuilder.addParameter(parameterName, request.getParameter(parameterName));
            }
        }
        view.setUrl(urlBuilder.build().toString());
    }
    return modelAndView;
}
Also used : lombok.val(lombok.val) MessageDecodingException(org.opensaml.messaging.decoder.MessageDecodingException) AuthnRequest(org.opensaml.saml.saml2.core.AuthnRequest) SAMLObjectBuilder(org.opensaml.saml.common.SAMLObjectBuilder) Issuer(org.opensaml.saml.saml2.core.Issuer) NameIDPolicy(org.opensaml.saml.saml2.core.NameIDPolicy) RequestAbstractType(org.opensaml.saml.saml2.core.RequestAbstractType) RedirectView(org.springframework.web.servlet.view.RedirectView) UnauthorizedServiceException(org.apereo.cas.services.UnauthorizedServiceException) MessageContext(org.opensaml.messaging.context.MessageContext) URIBuilder(org.apache.http.client.utils.URIBuilder) GetMapping(org.springframework.web.bind.annotation.GetMapping)

Example 50 with org.opensaml.saml.saml2.metadata

use of org.opensaml.saml.saml2.metadata in project cas by apereo.

the class SamlRegisteredServiceCachedMetadataEndpoint method getCachedMetadataObject.

/**
 * Gets cached metadata object.
 *
 * @param serviceId the service id
 * @param entityId  the entity id
 * @return the cached metadata object
 */
@ReadOperation
@Operation(summary = "Get SAML2 cached metadata", parameters = { @Parameter(name = "serviceId", required = true), @Parameter(name = "entityId") })
public Map<String, Object> getCachedMetadataObject(final String serviceId, @Nullable final String entityId) {
    try {
        val registeredService = findRegisteredService(serviceId);
        val issuer = StringUtils.defaultIfBlank(entityId, registeredService.getServiceId());
        val criteriaSet = new CriteriaSet();
        criteriaSet.add(new EntityIdCriterion(issuer));
        criteriaSet.add(new EntityRoleCriterion(SPSSODescriptor.DEFAULT_ELEMENT_NAME));
        val metadataResolver = cachingMetadataResolver.resolve(registeredService, criteriaSet);
        val iteration = metadataResolver.resolve(criteriaSet).spliterator();
        return StreamSupport.stream(iteration, false).map(entity -> Pair.of(entity.getEntityID(), SamlUtils.transformSamlObject(openSamlConfigBean, entity).toString())).collect(Collectors.toMap(Pair::getLeft, Pair::getRight));
    } catch (final Exception e) {
        LoggingUtils.error(LOGGER, e);
        return CollectionUtils.wrap("error", e.getMessage());
    }
}
Also used : lombok.val(lombok.val) CasConfigurationProperties(org.apereo.cas.configuration.CasConfigurationProperties) ReadOperation(org.springframework.boot.actuate.endpoint.annotation.ReadOperation) SamlRegisteredServiceCachingMetadataResolver(org.apereo.cas.support.saml.services.idp.metadata.cache.SamlRegisteredServiceCachingMetadataResolver) StringUtils(org.apache.commons.lang3.StringUtils) DeleteOperation(org.springframework.boot.actuate.endpoint.annotation.DeleteOperation) SamlUtils(org.apereo.cas.support.saml.SamlUtils) LoggingUtils(org.apereo.cas.util.LoggingUtils) Operation(io.swagger.v3.oas.annotations.Operation) SamlRegisteredService(org.apereo.cas.support.saml.services.SamlRegisteredService) Pair(org.apache.commons.lang3.tuple.Pair) Map(java.util.Map) CollectionUtils(org.apereo.cas.util.CollectionUtils) Nullable(org.springframework.lang.Nullable) StreamSupport(java.util.stream.StreamSupport) ServicesManager(org.apereo.cas.services.ServicesManager) AuditableContext(org.apereo.cas.audit.AuditableContext) Endpoint(org.springframework.boot.actuate.endpoint.annotation.Endpoint) Collection(java.util.Collection) lombok.val(lombok.val) Collectors(java.util.stream.Collectors) RegisteredService(org.apereo.cas.services.RegisteredService) BaseCasActuatorEndpoint(org.apereo.cas.web.BaseCasActuatorEndpoint) SPSSODescriptor(org.opensaml.saml.saml2.metadata.SPSSODescriptor) OpenSamlConfigBean(org.apereo.cas.support.saml.OpenSamlConfigBean) Parameter(io.swagger.v3.oas.annotations.Parameter) Slf4j(lombok.extern.slf4j.Slf4j) AuditableExecution(org.apereo.cas.audit.AuditableExecution) EntityRoleCriterion(org.opensaml.saml.criterion.EntityRoleCriterion) NumberUtils(org.apache.commons.lang3.math.NumberUtils) EntityIdCriterion(org.opensaml.core.criterion.EntityIdCriterion) CriteriaSet(net.shibboleth.utilities.java.support.resolver.CriteriaSet) CriteriaSet(net.shibboleth.utilities.java.support.resolver.CriteriaSet) EntityIdCriterion(org.opensaml.core.criterion.EntityIdCriterion) EntityRoleCriterion(org.opensaml.saml.criterion.EntityRoleCriterion) ReadOperation(org.springframework.boot.actuate.endpoint.annotation.ReadOperation) ReadOperation(org.springframework.boot.actuate.endpoint.annotation.ReadOperation) DeleteOperation(org.springframework.boot.actuate.endpoint.annotation.DeleteOperation) Operation(io.swagger.v3.oas.annotations.Operation)

Aggregations

EntityDescriptor (org.opensaml.saml.saml2.metadata.EntityDescriptor)24 SamlRegisteredServiceServiceProviderMetadataFacade (org.apereo.cas.support.saml.services.idp.metadata.SamlRegisteredServiceServiceProviderMetadataFacade)12 lombok.val (lombok.val)11 AuthnRequest (org.opensaml.saml.saml2.core.AuthnRequest)11 InputStream (java.io.InputStream)10 ArrayList (java.util.ArrayList)10 IOException (java.io.IOException)9 UnauthorizedServiceException (org.apereo.cas.services.UnauthorizedServiceException)9 Document (org.w3c.dom.Document)9 Element (org.w3c.dom.Element)9 List (java.util.List)8 CriteriaSet (net.shibboleth.utilities.java.support.resolver.CriteriaSet)8 SamlRegisteredServiceCachingMetadataResolver (org.apereo.cas.support.saml.services.idp.metadata.cache.SamlRegisteredServiceCachingMetadataResolver)8 Map (java.util.Map)7 SamlRegisteredService (org.apereo.cas.support.saml.services.SamlRegisteredService)7 XMLObject (org.opensaml.core.xml.XMLObject)7 X509Certificate (java.security.cert.X509Certificate)6 HashMap (java.util.HashMap)6 Slf4j (lombok.extern.slf4j.Slf4j)6 EntityIdCriterion (org.opensaml.core.criterion.EntityIdCriterion)6