How to configure {baseUrl} for endpoint /saml2/authenticate/{registrationId} spring-security-saml2?

I'm trying to implement saml2 SSO.
My project uses a gateway (port 8090). The authentication logic is located in the second service (port 8080), but I want all requests to go through the gateway.

I tried to implement this but I ended up in a redirect to the second service localhost:8080/saml2/authenticate/{registrationId}. I assume that the problem is that the service(second) calling the identity provider must also accept requests, and not delegate them to the gateway.
Maybe there is some workaround to make this request go through the gateway?

Also, I cannot transfer this logic to the gateway, because there is currently no support for reactive SAML.

I have almost no working experience with security (especially SAML). So I will be grateful for any help!

Dependencies:
- Gateway

<dependency>
    <groupId>org.springframework.cloud</groupId>
    <artifactId>spring-cloud-starter-gateway</artifactId>
    <version>3.0.4</version>
</dependency>

- SAML dependencies in the second service

<dependency>
    <groupId>org.springframework.security</groupId>
    <artifactId>spring-security-saml2-service-provider</artifactId>
    <version>5.5.2</version>
</dependency>
<dependency>
    <groupId>org.opensaml</groupId>
    <artifactId>opensaml-core</artifactId>
    <version>4.1.1</version>
</dependency>
<dependency>
    <groupId>org.opensaml</groupId>
    <artifactId>opensaml-saml-api</artifactId>
    <version>4.1.1</version>
</dependency>
<dependency>
    <groupId>org.opensaml</groupId>
    <artifactId>opensaml-saml-impl</artifactId>
    <version>4.1.1</version>
</dependency>

Upvotes: 2

Views: 1698

Answers (1)

Eventually I found out that this can be done with 6 version of Spring security config.

https://github.com/spring-projects/spring-security/issues/8873

http.saml2Login(saml2 -> {                
    saml2.authenticationRequestUri("yourUrl")
};

Also you can try override RelyingPartyRegistration:

    @Bean
    public RelyingPartyRegistration relyingPartyRegistration() {
        return RelyingPartyRegistrations
                .fromMetadataLocation(assertingPartyMetadataLocation)
                .entityId("%s/saml2/service-provider-metadata/adfs".formatted(gatewayUrl))
                .assertionConsumerServiceLocation("%s/login/saml2/sso/adfs".formatted(gatewayUrl))
                .singleLogoutServiceLocation("%s/logout".formatted(gatewayUrl))
                .registrationId("adfs")
                .build();
    }

Login url changed via custom AuthenticationEntryPoint:

    public AuthenticationEntryPoint entryPoint() {
        return (request, response, exception) ->
                response.sendRedirect("%s/saml2/authenticate/adfs".formatted(gatewayUrl));
    }

And use it with:

http
    .exceptionHandling(customizer -> customizer.authenticationEntryPoint(entryPoint()))

Upvotes: 1

Related Questions