Reputation: 815
I have a spring boot 3 resource server secured as per spring-addons-starter-oidc
https://github.com/ch4mpy/spring-addons/tree/master/samples/webmvc-jwt-default with
origins: https://localhost:8444
keycloak-issuer: http://localhost:8080/realms/services
com:
c4-soft:
springaddons:
oidc:
cors:
- path: /**
allowed-origin-patterns: ${origins}
ops:
- iss: ${keycloak-issuer}
authorities:
- path: $.realm_access.roles
- path: $.resource_access.*.roles
resourceserver:
permit-all:
- /greet/public
- /actuator/health/readiness
- /actuator/health/liveness
- /v3/api-docs/**
I have a keycloak server running locally and can create a bearer token.
curl "http://localhost:8080/realms/services/protocol/openid-connect/token" -d "client_id=service1" -d "client_secret=xxxxxxx" -d "grant_type=client_credentials"
However, when I make a GET request with the bearer token in the header as
curl -H 'Accept: application/json' -H "Authorization: Bearer <access_token>" https://localhost:8444/service1/hello
I get a 404 response:
{
"timestamp": "2025-01-27T23:18:05.319+00:00",
"status": 404,
"error": "Not Found",
"path": "/service1/hello"
}
I have a standard application / RestController as per the repo, and no Security @Configuration (using repo default):
new SpringApplicationBuilder(Service1.class).web(WebApplicationType.SERVLET).run(args);
@RestController
@RequestMapping("/service1")
public class SimpleRestService {
@GetMapping("/hello")
public String hello() {
LOGGER.debug("just saying hello...");
return "Hello World!";
}
}
My keycloak client configuration looks like this:
"id" : "services",
"realm" : "services",
"displayName" : "Services API",
"displayNameHtml" : "<div class=\"logo-text\"><span>Services API</span></div>",
"enabled" : true,
"registrationAllowed" : true,
"rememberMe" : true,
"resetPasswordAllowed" : true,
"revokeRefreshToken" : false,
"refreshTokenMaxReuse" : 0,
"clients" : [ {
"clientId" : "service1",
"name": "Service1 Application",
"rootUrl": "https://localhost:8444",
"baseUrl": "https://localhost:8444",
"surrogateAuthRequired" : false,
"enabled" : true,
"alwaysDisplayInConsole" : false,
"clientAuthenticatorType" : "client-secret",
"secret" : "xxxxxxxxx",
"redirectUris": [ "/" ],
"webOrigins": [ "+" ],
"notBefore" : 0,
"bearerOnly" : false,
"consentRequired" : false,
"standardFlowEnabled" : true,
"implicitFlowEnabled" : false,
"directAccessGrantsEnabled" : true,
"serviceAccountsEnabled" : true,
"publicClient" : false,
"frontchannelLogout" : false,
"protocol" : "openid-connect",
"attributes" : {
"post.logout.redirect.uris" : "+",
"use.refresh.tokens" : "true",
"pkce.code.challenge.method" : "S256"
},
"fullScopeAllowed" : true,
"defaultClientScopes" : [ "web-origins", "acr", "profile", "roles", "email", "basic", "test-scope" ],
"optionalClientScopes" : [ "address", "phone", "offline_access", "microprofile-jwt" ]
}
Can anyone explain why I am getting a 404? I'm at a loss.
Debug logs (as trace didn't seem to show anything untoward) for application startup:
[DEBUG] 2025-01-27 17:20:33.312 [main] o.s.s.c.a.a.c.AuthenticationConfiguration$DefaultPasswordEncoderAuthenticationManagerBuilder [-] No authenticationProviders and no parentAuthenticationManager defined. Returning null.
[INFO ] 2025-01-27 17:20:33.779 [main] o.s.s.w.a.c.ChannelProcessingFilter [-] Validated configuration attributes
[DEBUG] 2025-01-27 17:20:33.782 [main] o.s.s.w.DefaultSecurityFilterChain [-] Will secure any request with filters: DisableEncodeUrlFilter, ChannelProcessingFilter, WebAsyncManagerIntegrationFilter, SecurityContextHolderFilter, HeaderWriterFilter, LogoutFilter, BearerTokenAuthenticationFilter, RequestCacheAwareFilter, SecurityContextHolderAwareRequestFilter, AnonymousAuthenticationFilter, SessionManagementFilter, ExceptionTranslationFilter, AuthorizationFilter
[INFO ] 2025-01-27 17:20:35.104 [main] o.e.s.Service1 [-] Started Service1 in 6.884 seconds (process running for 8.113)
And for the actual request:
[DEBUG] 2025-01-27 17:21:11.824 [https-jsse-nio-8444-exec-6] o.s.s.w.FilterChainProxy [6ccb14c1c4c733e973f82e8ce9ab9eb4-a221bc7f2646003e] Securing GET /service1/hello
[DEBUG] 2025-01-27 17:21:11.833 [https-jsse-nio-8444-exec-6] o.s.s.w.a.c.ChannelProcessingFilter [6ccb14c1c4c733e973f82e8ce9ab9eb4-785f093b40ca0bdf] Request: filter invocation [GET /service1/hello]; ConfigAttributes: [REQUIRES_SECURE_CHANNEL]
[DEBUG] 2025-01-27 17:21:12.148 [https-jsse-nio-8444-exec-6] o.s.s.o.s.r.a.JwtAuthenticationProvider [6ccb14c1c4c733e973f82e8ce9ab9eb4-785f093b40ca0bdf] Authenticated token
[DEBUG] 2025-01-27 17:21:12.149 [https-jsse-nio-8444-exec-6] o.s.s.o.s.r.w.a.BearerTokenAuthenticationFilter [6ccb14c1c4c733e973f82e8ce9ab9eb4-785f093b40ca0bdf] Set SecurityContextHolder to JwtAuthenticationToken [Principal=org.springframework.security.oauth2.jwt.Jwt@b37aa3bc, Credentials=[PROTECTED], Authenticated=true, Details=WebAuthenticationDetails [RemoteIpAddress=0:0:0:0:0:0:0:1, SessionId=null], Granted Authorities=[]]
[DEBUG] 2025-01-27 17:21:12.161 [https-jsse-nio-8444-exec-6] o.s.s.w.FilterChainProxy [6ccb14c1c4c733e973f82e8ce9ab9eb4-51efe1fc48535bb0] Secured GET /service1/hello
[DEBUG] 2025-01-27 17:21:12.181 [https-jsse-nio-8444-exec-6] o.s.s.w.FilterChainProxy [-] Securing GET /error
[DEBUG] 2025-01-27 17:21:12.182 [https-jsse-nio-8444-exec-6] o.s.s.w.a.c.ChannelProcessingFilter [53d2696c8c0e07f1aacb1234ed263a34-e5d411eb631fb220] Request: filter invocation [GET /error]; ConfigAttributes: [REQUIRES_SECURE_CHANNEL]
[DEBUG] 2025-01-27 17:21:12.184 [https-jsse-nio-8444-exec-6] o.s.s.w.FilterChainProxy [53d2696c8c0e07f1aacb1234ed263a34-8ab5f71e1943d243] Secured GET /error
Upvotes: 0
Views: 41