From 8df2051fefb505c65c8ae69effd87c6d27f9cf28 Mon Sep 17 00:00:00 2001 From: Dave Syer Date: Tue, 27 Jun 2017 13:08:02 +0100 Subject: [PATCH] Fix encryptor configuration to prevent infinite loop --- .../ConfigServerBootstrapConfiguration.java | 41 ++++------------ .../config/EncryptionAutoConfiguration.java | 47 ++++++++++++++----- .../SingleEncryptorAutoConfiguration.java | 41 ---------------- .../encryption/LocatorTextEncryptor.java | 10 +--- .../main/resources/META-INF/spring.factories | 6 +-- 5 files changed, 47 insertions(+), 98 deletions(-) delete mode 100644 spring-cloud-config-server/src/main/java/org/springframework/cloud/config/server/config/SingleEncryptorAutoConfiguration.java diff --git a/spring-cloud-config-server/src/main/java/org/springframework/cloud/config/server/bootstrap/ConfigServerBootstrapConfiguration.java b/spring-cloud-config-server/src/main/java/org/springframework/cloud/config/server/bootstrap/ConfigServerBootstrapConfiguration.java index 3845f31c..dc8b611a 100644 --- a/spring-cloud-config-server/src/main/java/org/springframework/cloud/config/server/bootstrap/ConfigServerBootstrapConfiguration.java +++ b/spring-cloud-config-server/src/main/java/org/springframework/cloud/config/server/bootstrap/ConfigServerBootstrapConfiguration.java @@ -15,29 +15,25 @@ */ package org.springframework.cloud.config.server.bootstrap; -import org.springframework.beans.BeansException; -import org.springframework.beans.factory.BeanFactory; import org.springframework.beans.factory.annotation.Autowired; -import org.springframework.beans.factory.config.BeanPostProcessor; import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty; import org.springframework.boot.context.properties.EnableConfigurationProperties; import org.springframework.cloud.config.client.ConfigClientProperties; import org.springframework.cloud.config.server.config.ConfigServerProperties; import org.springframework.cloud.config.server.config.EnvironmentRepositoryConfiguration; -import org.springframework.cloud.config.server.encryption.LocatorTextEncryptor; import org.springframework.cloud.config.server.environment.EnvironmentRepository; import org.springframework.cloud.config.server.environment.EnvironmentRepositoryPropertySourceLocator; import org.springframework.context.annotation.Bean; import org.springframework.context.annotation.Configuration; import org.springframework.context.annotation.Import; -import org.springframework.security.crypto.encrypt.TextEncryptor; import org.springframework.util.StringUtils; /** - * Bootstrap configuration to fetch external configuration from a (possibly remote) - * {@link EnvironmentRepository}. Off by default because it can delay startup, but can be - * enabled with spring.cloud.config.server.bootstrap=true. This would be - * useful, for example, if the config server were embedded in another app that wanted to + * Bootstrap configuration to fetch external configuration from a (possibly + * remote) {@link EnvironmentRepository}. Off by default because it can delay + * startup, but can be enabled with + * spring.cloud.config.server.bootstrap=true. This would be useful, + * for example, if the config server were embedded in another app that wanted to * be configured from the same repository as all the other clients. * * @author Dave Syer @@ -45,25 +41,7 @@ import org.springframework.util.StringUtils; */ @Configuration @ConditionalOnProperty("spring.cloud.config.server.bootstrap") -public class ConfigServerBootstrapConfiguration implements BeanPostProcessor { - - @Autowired - private BeanFactory beanFactory; - - @Override - public Object postProcessBeforeInitialization(Object bean, String beanName) - throws BeansException { - return bean; - } - - @Override - public Object postProcessAfterInitialization(Object bean, String beanName) - throws BeansException { - if (bean instanceof TextEncryptor && !(bean instanceof LocatorTextEncryptor)) { - return new LocatorTextEncryptor(beanFactory); - } - return bean; - } +public class ConfigServerBootstrapConfiguration { @EnableConfigurationProperties(ConfigServerProperties.class) @Import(EnvironmentRepositoryConfiguration.class) @@ -80,15 +58,14 @@ public class ConfigServerBootstrapConfiguration implements BeanPostProcessor { @Bean public EnvironmentRepositoryPropertySourceLocator environmentRepositoryPropertySourceLocator() { - return new EnvironmentRepositoryPropertySourceLocator(this.repository, - this.client.getName(), this.client.getProfile(), getDefaultLabel()); + return new EnvironmentRepositoryPropertySourceLocator(this.repository, this.client.getName(), + this.client.getProfile(), getDefaultLabel()); } private String getDefaultLabel() { if (StringUtils.hasText(this.client.getLabel())) { return this.client.getLabel(); - } - else if (StringUtils.hasText(this.server.getDefaultLabel())) { + } else if (StringUtils.hasText(this.server.getDefaultLabel())) { return this.server.getDefaultLabel(); } return null; diff --git a/spring-cloud-config-server/src/main/java/org/springframework/cloud/config/server/config/EncryptionAutoConfiguration.java b/spring-cloud-config-server/src/main/java/org/springframework/cloud/config/server/config/EncryptionAutoConfiguration.java index 07d27f68..7fbec57f 100644 --- a/spring-cloud-config-server/src/main/java/org/springframework/cloud/config/server/config/EncryptionAutoConfiguration.java +++ b/spring-cloud-config-server/src/main/java/org/springframework/cloud/config/server/config/EncryptionAutoConfiguration.java @@ -26,6 +26,8 @@ import org.springframework.cloud.bootstrap.encrypt.KeyProperties.KeyStore; import org.springframework.cloud.config.server.encryption.CipherEnvironmentEncryptor; import org.springframework.cloud.config.server.encryption.EnvironmentEncryptor; import org.springframework.cloud.config.server.encryption.KeyStoreTextEncryptorLocator; +import org.springframework.cloud.config.server.encryption.LocatorTextEncryptor; +import org.springframework.cloud.config.server.encryption.SingleTextEncryptorLocator; import org.springframework.cloud.config.server.encryption.TextEncryptorLocator; import org.springframework.cloud.context.encrypt.EncryptorFactory; import org.springframework.context.annotation.Bean; @@ -37,9 +39,9 @@ import org.springframework.security.rsa.crypto.RsaSecretEncryptor; import org.springframework.util.StringUtils; /** - * Auto configuration for text encryptors and environment encryptors (non-web stuff). - * Users can provide beans of the same type as any or all of the beans defined here in - * application code to override the default behaviour. + * Auto configuration for text encryptors and environment encryptors (non-web + * stuff). Users can provide beans of the same type as any or all of the beans + * defined here in application code to override the default behaviour. * * @author Bartosz Wojtkiewicz * @author Rafal Zukowski @@ -56,8 +58,14 @@ public class EncryptionAutoConfiguration { @Autowired private KeyProperties key; + @Autowired(required = false) + private TextEncryptorLocator locator; + @Bean - public TextEncryptor nullTextEncryptor() { + public TextEncryptor defaultTextEncryptor() { + if (locator != null) { + return new LocatorTextEncryptor(locator); + } if (StringUtils.hasText(this.key.getKey())) { return new EncryptorFactory().create(this.key.getKey()); } @@ -66,18 +74,31 @@ public class EncryptionAutoConfiguration { } - @Bean - @ConditionalOnMissingBean + @Configuration @ConditionalOnProperty(value = "spring.cloud.config.server.encrypt.enabled", matchIfMissing = true) - public EnvironmentEncryptor environmentEncryptor( - TextEncryptorLocator textEncryptorLocator) { - return new CipherEnvironmentEncryptor(textEncryptorLocator); + protected static class EncryptorConfiguration { + + @Autowired(required = false) + private TextEncryptorLocator locator; + + @Autowired + private TextEncryptor encryptor; + + @Bean + @ConditionalOnMissingBean + public EnvironmentEncryptor environmentEncryptor() { + TextEncryptorLocator locator = this.locator; + if (locator == null) { + locator = new SingleTextEncryptorLocator(encryptor); + } + return new CipherEnvironmentEncryptor(locator); + } + } @Configuration @ConditionalOnClass(RsaSecretEncryptor.class) - @ConditionalOnProperty(value = "encrypt.keyStore.location", matchIfMissing = false) - @EnableConfigurationProperties(KeyProperties.class) + @ConditionalOnProperty(value = "encrypt.key-store.location", matchIfMissing = false) protected static class KeyStoreConfiguration { @Autowired @@ -87,8 +108,8 @@ public class EncryptionAutoConfiguration { @ConditionalOnMissingBean public TextEncryptorLocator textEncryptorLocator() { KeyStore keyStore = this.key.getKeyStore(); - KeyStoreTextEncryptorLocator locator = new KeyStoreTextEncryptorLocator(new KeyStoreKeyFactory( - keyStore.getLocation(), keyStore.getPassword().toCharArray()), + KeyStoreTextEncryptorLocator locator = new KeyStoreTextEncryptorLocator( + new KeyStoreKeyFactory(keyStore.getLocation(), keyStore.getPassword().toCharArray()), keyStore.getSecret(), keyStore.getAlias()); locator.setRsaAlgorithm(this.key.getRsa().getAlgorithm()); locator.setSalt(this.key.getRsa().getSalt()); diff --git a/spring-cloud-config-server/src/main/java/org/springframework/cloud/config/server/config/SingleEncryptorAutoConfiguration.java b/spring-cloud-config-server/src/main/java/org/springframework/cloud/config/server/config/SingleEncryptorAutoConfiguration.java deleted file mode 100644 index 0ad0c64d..00000000 --- a/spring-cloud-config-server/src/main/java/org/springframework/cloud/config/server/config/SingleEncryptorAutoConfiguration.java +++ /dev/null @@ -1,41 +0,0 @@ -/* - * Copyright 2015 the original author or authors. - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -package org.springframework.cloud.config.server.config; - -import org.springframework.beans.factory.annotation.Autowired; -import org.springframework.boot.autoconfigure.AutoConfigureAfter; -import org.springframework.boot.autoconfigure.condition.ConditionalOnMissingBean; -import org.springframework.cloud.config.server.encryption.SingleTextEncryptorLocator; -import org.springframework.cloud.config.server.encryption.TextEncryptorLocator; -import org.springframework.context.annotation.Bean; -import org.springframework.context.annotation.Configuration; -import org.springframework.security.crypto.encrypt.TextEncryptor; - -@Configuration -@AutoConfigureAfter(EncryptionAutoConfiguration.class) -public class SingleEncryptorAutoConfiguration { - - @Autowired(required = false) - private TextEncryptor encryptor; - - @Bean - @ConditionalOnMissingBean - public TextEncryptorLocator textEncryptorLocator() { - return new SingleTextEncryptorLocator(this.encryptor); - } - -} \ No newline at end of file diff --git a/spring-cloud-config-server/src/main/java/org/springframework/cloud/config/server/encryption/LocatorTextEncryptor.java b/spring-cloud-config-server/src/main/java/org/springframework/cloud/config/server/encryption/LocatorTextEncryptor.java index 6c4b5497..053c0b4d 100644 --- a/spring-cloud-config-server/src/main/java/org/springframework/cloud/config/server/encryption/LocatorTextEncryptor.java +++ b/spring-cloud-config-server/src/main/java/org/springframework/cloud/config/server/encryption/LocatorTextEncryptor.java @@ -18,7 +18,6 @@ package org.springframework.cloud.config.server.encryption; import java.util.Map; -import org.springframework.beans.factory.BeanFactory; import org.springframework.security.crypto.encrypt.TextEncryptor; /** @@ -31,10 +30,8 @@ public class LocatorTextEncryptor implements TextEncryptor { private TextEncryptorLocator locator; - private BeanFactory beanFactory; - - public LocatorTextEncryptor(BeanFactory beanFactory) { - this.beanFactory = beanFactory; + public LocatorTextEncryptor(TextEncryptorLocator locator) { + this.locator = locator; } @Override @@ -45,9 +42,6 @@ public class LocatorTextEncryptor implements TextEncryptor { } private TextEncryptorLocator getLocator() { - if (locator == null) { - locator = beanFactory.getBean(TextEncryptorLocator.class); - } return locator; } diff --git a/spring-cloud-config-server/src/main/resources/META-INF/spring.factories b/spring-cloud-config-server/src/main/resources/META-INF/spring.factories index 7b893f04..f145f03c 100644 --- a/spring-cloud-config-server/src/main/resources/META-INF/spring.factories +++ b/spring-cloud-config-server/src/main/resources/META-INF/spring.factories @@ -1,8 +1,7 @@ # Bootstrap components org.springframework.cloud.bootstrap.BootstrapConfiguration=\ org.springframework.cloud.config.server.bootstrap.ConfigServerBootstrapConfiguration,\ -org.springframework.cloud.config.server.config.EncryptionAutoConfiguration,\ -org.springframework.cloud.config.server.config.SingleEncryptorAutoConfiguration +org.springframework.cloud.config.server.config.EncryptionAutoConfiguration # Application listeners org.springframework.context.ApplicationListener=\ @@ -11,5 +10,4 @@ org.springframework.cloud.config.server.bootstrap.ConfigServerBootstrapApplicati # Autoconfiguration org.springframework.boot.autoconfigure.EnableAutoConfiguration=\ org.springframework.cloud.config.server.config.ConfigServerAutoConfiguration,\ -org.springframework.cloud.config.server.config.EncryptionAutoConfiguration,\ -org.springframework.cloud.config.server.config.SingleEncryptorAutoConfiguration +org.springframework.cloud.config.server.config.EncryptionAutoConfiguration