3

I am getting 'Caused by: org.opensaml.xml.security.SecurityException: SAML message intended destination endpoint did not match recipient endpoint' exception while SSO between my app SP and client IdP.

Server log show the difference in schemas, see below:

Checking SAML message intended destination endpoint against receiver endpoint
2019-03-05 15:02:44.599 DEBUG [204 default task-41][BaseSAMLMessageDecoder] Intended message destination endpoint: https://my.app.com/app-gateway/saml/SSO
2019-03-05 15:02:44.599 DEBUG [204 default task-41][BaseSAMLMessageDecoder] Actual message receiver endpoint: http://my.app.com/app-gateway/saml/SSO
2019-03-05 15:02:44.600 ERROR [204 default task-41][BaseSAMLMessageDecoder] SAML message intended destination endpoint 'https://my.app.com/app-gateway/saml/SSO' did not match the recipient endpoint 'http://my.app.com/app-gateway/saml/SSO'

My application is running on STG on 2 instances with the LB in front, therefore I use SAMLContextProviderLB context provider instead of SAMLContextProviderImpl:

<bean id="contextProvider" class="org.springframework.security.saml.context.SAMLContextProviderLB">
        <property name="scheme" value="https"/>
        <property name="serverName" value="my.app.com"/>
        <property name="serverPort" value="443"/>
        <property name="includeServerPortInRequestURL" value="false"/>
        <property name="contextPath" value="/app-gateway"/>
    </bean>

<bean id="metadataGeneratorFilter" class="org.springframework.security.saml.metadata.MetadataGeneratorFilter">
        <constructor-arg>
            <bean class="org.springframework.security.saml.metadata.MetadataGenerator">
                <property name="entityBaseURL" value="https://my.app.com/app-gateway1"/>
                <property name="entityId" value="${cas.sso.entityId}"/>
                <property name="includeDiscoveryExtension" value="false"/>
                <property name="extendedMetadata" ref="extendedMetadata"/>
                <property name="keyManager" ref="keyManager"/>
            </bean>
        </constructor-arg>
    </bean>

In the source code of getActualReceiverEndpointURI the receiver endpoint URL is being taken from request httpRequest obj. Thus, I am trying to understand at which step that wrong URL http://my.app.com/app-gateway/saml/SSO was set to it. Can anyone explain me it?

protected String getActualReceiverEndpointURI(SAMLMessageContext messageContext) throws MessageDecodingException {
        InTransport inTransport = messageContext.getInboundMessageTransport();
        if (! (inTransport instanceof HttpServletRequestAdapter)) {
            log.error("Message context InTransport instance was an unsupported type: {}", 
                    inTransport.getClass().getName());
            throw new MessageDecodingException("Message context InTransport instance was an unsupported type");
        }
        HttpServletRequest httpRequest = ((HttpServletRequestAdapter)inTransport).getWrappedRequest();

        StringBuffer urlBuilder = httpRequest.getRequestURL();

        return urlBuilder.toString();
    }
Hutsul
  • 1,535
  • 4
  • 31
  • 51
  • How is done the communication between your application servers and your LB ? Http, https, ajp, anything else ? – Sébastien PRAT Mar 06 '19 at 09:38
  • @SébastienPRAT, thanks for you comment. The LB (barracuda) communicates with application via http. – Hutsul Mar 06 '19 at 14:23
  • 1
    The issue is TLS/SSL offloading. SAML library uses 'request.getScheme()' and this returns 'http' instead of 'https', so the recipient checking fails. Which deployment container is used? – Bernhard Thalmayr Mar 07 '19 at 13:45
  • @BernhardThalmayr. Thanks for your answer. The WildFly 10.1.0 Final is using as application server. Do you know, how I can change it and force it to use https? – Hutsul Mar 07 '19 at 14:42

2 Answers2

4

You might want to check the following page : https://developer.jboss.org/thread/240113

I had a similar issue, even with X-Forwarded-Proto properly set on the LB, the request was still interpreted in http only. The backend must be aware of the header.

add proxy-address-forwarding="true" on the http listener and two filter-ref

<http-listener name="default" socket-binding="http" proxy-address-forwarding="true"/>  
            <filter-ref name="server-header"/>  
            <filter-ref name="x-powered-by-header"/>  

Hope this help,

H. Tazi
  • 76
  • 5
1

For Apache Tomcat server, which is running behind AWS Application load balancer, need to enable the RemoteIPValue so that based on the x-forwarded-proto header, Tomcat will overwrite scheme(https) & port(443) accordingly.

In server.xml

<Valve className="org.apache.catalina.valves.RemoteIpValve" protocolHeader="X-Forwarded-Proto" internalProxies="10\.\d+\.\d+\.\d+|192\.168\.\d+\.\d+|169\.254\.\d+\.\d+|127\.\d+\.\d+\.\d+|172\.(1[6-9]|2[0-9]|3[0-1])\.\d+\.\d+" />
Velu
  • 1,681
  • 1
  • 22
  • 26