diff --git a/src/main/java/org/springframework/cloud/bindings/boot/SpringSecurityOAuth2BindingsPropertiesProcessor.java b/src/main/java/org/springframework/cloud/bindings/boot/SpringSecurityOAuth2BindingsPropertiesProcessor.java index 3577d68..bc28f59 100644 --- a/src/main/java/org/springframework/cloud/bindings/boot/SpringSecurityOAuth2BindingsPropertiesProcessor.java +++ b/src/main/java/org/springframework/cloud/bindings/boot/SpringSecurityOAuth2BindingsPropertiesProcessor.java @@ -16,8 +16,11 @@ package org.springframework.cloud.bindings.boot; +import org.springframework.boot.context.event.ApplicationPreparedEvent; +import org.springframework.boot.logging.DeferredLog; import org.springframework.cloud.bindings.Binding; import org.springframework.cloud.bindings.Bindings; +import org.springframework.context.ApplicationListener; import org.springframework.core.env.Environment; import java.util.*; @@ -27,13 +30,15 @@ import static org.springframework.cloud.bindings.boot.Guards.isKindEnabled; /** * An implementation of {@link BindingsPropertiesProcessor} that detects {@link Binding}s of kind: {@value KIND}. */ -public final class SpringSecurityOAuth2BindingsPropertiesProcessor implements BindingsPropertiesProcessor { +public final class SpringSecurityOAuth2BindingsPropertiesProcessor implements BindingsPropertiesProcessor, ApplicationListener { /** * The {@link Binding} kind that this processor is interested in: {@value}. **/ public static final String KIND = "OAuth2"; + private static final DeferredLog LOG = new DeferredLog(); + @Override public void process(Environment environment, Bindings bindings, Map properties) { if (!isKindEnabled(environment, KIND)) { @@ -43,6 +48,10 @@ public final class SpringSecurityOAuth2BindingsPropertiesProcessor implements Bi bindings.filterBindings(KIND).forEach(binding -> { MapMapper map = new MapMapper(binding.getSecret(), properties); String provider = binding.getProvider(); + if (provider == null) { + LOG.warn(String.format("Binding '%s' is missing required 'provider' and will not be processed.", binding.getName())); + return; + } String clientName = binding.getName(); properties.put(String.format("spring.security.oauth2.client.registration.%s.provider", clientName), provider); map.from("client-id").to(String.format("spring.security.oauth2.client.registration.%s.client-id", clientName)); @@ -57,4 +66,8 @@ public final class SpringSecurityOAuth2BindingsPropertiesProcessor implements Bi }); } + @Override + public void onApplicationEvent(ApplicationPreparedEvent event) { + LOG.switchTo(getClass()); + } } diff --git a/src/main/resources/META-INF/spring.factories b/src/main/resources/META-INF/spring.factories index e1aa3cb..5a0b912 100644 --- a/src/main/resources/META-INF/spring.factories +++ b/src/main/resources/META-INF/spring.factories @@ -1,6 +1,7 @@ org.springframework.context.ApplicationListener=\ org.springframework.cloud.bindings.boot.BindingFlattenedEnvironmentPostProcessor, \ org.springframework.cloud.bindings.boot.BindingSpecificEnvironmentPostProcessor, \ + org.springframework.cloud.bindings.boot.SpringSecurityOAuth2BindingsPropertiesProcessor, \ org.springframework.cloud.bindings.boot.VaultBindingsPropertiesProcessor org.springframework.boot.env.EnvironmentPostProcessor=\ org.springframework.cloud.bindings.boot.BindingFlattenedEnvironmentPostProcessor, \ diff --git a/src/test/java/org/springframework/cloud/bindings/boot/SpringSecurityOAuth2BindingsPropertiesProcessorTest.java b/src/test/java/org/springframework/cloud/bindings/boot/SpringSecurityOAuth2BindingsPropertiesProcessorTest.java index 957470b..2a2589d 100644 --- a/src/test/java/org/springframework/cloud/bindings/boot/SpringSecurityOAuth2BindingsPropertiesProcessorTest.java +++ b/src/test/java/org/springframework/cloud/bindings/boot/SpringSecurityOAuth2BindingsPropertiesProcessorTest.java @@ -63,6 +63,13 @@ final class SpringSecurityOAuth2BindingsPropertiesProcessorTest { .withEntry("user-info-authentication-method", "my-provider-user-info-authentication-method") .withEntry("jwk-set-uri", "my-provider-jwk-set-uri") .withEntry("user-name-attribute", "my-provider-user-name-attribute") + ), + // Don't crash when provider is missing + new Binding("test-missing-provider", Paths.get("test-path"), + new FluentMap() + .withEntry("kind", KIND), + new FluentMap() + .withEntry("client-id", "my-provider-client-id") ) ); @@ -81,8 +88,9 @@ final class SpringSecurityOAuth2BindingsPropertiesProcessorTest { ; } + @Test @DisplayName("contributes client properties for OIDC providers") - void testOIDCProvider() { + void testOidcProvider() { new SpringSecurityOAuth2BindingsPropertiesProcessor().process(environment, bindings, properties); assertThat(properties) .containsEntry("spring.security.oauth2.client.registration.test-name-2.client-id", "okta-client-id") @@ -92,6 +100,7 @@ final class SpringSecurityOAuth2BindingsPropertiesProcessorTest { ; } + @Test @DisplayName("contributes client properties for non-OIDC providers") void testProvider() { new SpringSecurityOAuth2BindingsPropertiesProcessor().process(environment, bindings, properties);