diff --git a/spring-boot-autoconfigure/src/main/java/org/springframework/boot/autoconfigure/mongo/MongoDataAutoConfiguration.java b/spring-boot-autoconfigure/src/main/java/org/springframework/boot/autoconfigure/mongo/MongoDataAutoConfiguration.java index 2300cd6f639..1ee5a50df74 100644 --- a/spring-boot-autoconfigure/src/main/java/org/springframework/boot/autoconfigure/mongo/MongoDataAutoConfiguration.java +++ b/spring-boot-autoconfigure/src/main/java/org/springframework/boot/autoconfigure/mongo/MongoDataAutoConfiguration.java @@ -22,6 +22,10 @@ import java.util.Collections; import java.util.HashSet; import java.util.Set; +import com.mongodb.DB; +import com.mongodb.Mongo; +import com.mongodb.MongoClient; + import org.springframework.beans.factory.BeanClassLoaderAware; import org.springframework.beans.factory.BeanFactory; import org.springframework.beans.factory.NoSuchBeanDefinitionException; @@ -42,6 +46,7 @@ import org.springframework.core.type.filter.AnnotationTypeFilter; import org.springframework.dao.DataAccessException; import org.springframework.dao.support.PersistenceExceptionTranslator; import org.springframework.data.annotation.Persistent; +import org.springframework.data.mapping.model.FieldNamingStrategy; import org.springframework.data.mongodb.MongoDbFactory; import org.springframework.data.mongodb.core.MongoTemplate; import org.springframework.data.mongodb.core.SimpleMongoDbFactory; @@ -57,10 +62,6 @@ import org.springframework.util.Assert; import org.springframework.util.ClassUtils; import org.springframework.util.StringUtils; -import com.mongodb.DB; -import com.mongodb.Mongo; -import com.mongodb.MongoClient; - /** * {@link EnableAutoConfiguration Auto-configuration} for Spring Data's mongo support. *
@@ -136,6 +137,21 @@ public class MongoDataAutoConfiguration implements BeanClassLoaderAware { throws ClassNotFoundException { MongoMappingContext context = new MongoMappingContext(); context.setInitialEntitySet(getInitialEntitySet(beanFactory)); + Class extends FieldNamingStrategy> fieldNamingStrategyClass = this.properties. + getFieldNamingStrategy(); + if (fieldNamingStrategyClass != null) { + try { + context.setFieldNamingStrategy(fieldNamingStrategyClass.newInstance()); + } + catch (InstantiationException e) { + throw new IllegalArgumentException("Invalid custom FieldNamingStrategy " + + "(is it abstract?) '" + fieldNamingStrategyClass.getName() + "'", e); + } + catch (IllegalAccessException e) { + throw new IllegalArgumentException("Invalid custom FieldNamingStrategy " + + "(is the constructor accessible?)'" + fieldNamingStrategyClass.getName() + "'", e); + } + } return context; } diff --git a/spring-boot-autoconfigure/src/main/java/org/springframework/boot/autoconfigure/mongo/MongoProperties.java b/spring-boot-autoconfigure/src/main/java/org/springframework/boot/autoconfigure/mongo/MongoProperties.java index fb63094b0b7..1c48e23899a 100644 --- a/spring-boot-autoconfigure/src/main/java/org/springframework/boot/autoconfigure/mongo/MongoProperties.java +++ b/spring-boot-autoconfigure/src/main/java/org/springframework/boot/autoconfigure/mongo/MongoProperties.java @@ -21,6 +21,7 @@ import java.util.Arrays; import java.util.List; import org.springframework.boot.context.properties.ConfigurationProperties; +import org.springframework.data.mapping.model.FieldNamingStrategy; import com.mongodb.MongoClient; import com.mongodb.MongoClientOptions; @@ -36,6 +37,7 @@ import com.mongodb.ServerAddress; * @author Phillip Webb * @author Josh Long * @author Andy Wilkinson + * @author EddĂș MelĂ©ndez */ @ConfigurationProperties(prefix = "spring.data.mongodb") public class MongoProperties { @@ -82,6 +84,11 @@ public class MongoProperties { */ private char[] password; + /** + * Fully qualified name of the FieldNamingStrategy to use. + */ + private Class extends FieldNamingStrategy> fieldNamingStrategy; + public String getHost() { return this.host; } @@ -122,6 +129,14 @@ public class MongoProperties { this.password = password; } + public Class extends FieldNamingStrategy> getFieldNamingStrategy() { + return this.fieldNamingStrategy; + } + + public void setFieldNamingStrategy(Class extends FieldNamingStrategy> fieldNamingStrategy) { + this.fieldNamingStrategy = fieldNamingStrategy; + } + public void clearPassword() { if (this.password == null) { return; diff --git a/spring-boot-autoconfigure/src/test/java/org/springframework/boot/autoconfigure/mongo/MongoDataAutoConfigurationTests.java b/spring-boot-autoconfigure/src/test/java/org/springframework/boot/autoconfigure/mongo/MongoDataAutoConfigurationTests.java index 6e30429c465..49804780cfd 100644 --- a/spring-boot-autoconfigure/src/test/java/org/springframework/boot/autoconfigure/mongo/MongoDataAutoConfigurationTests.java +++ b/spring-boot-autoconfigure/src/test/java/org/springframework/boot/autoconfigure/mongo/MongoDataAutoConfigurationTests.java @@ -1,5 +1,5 @@ /* - * Copyright 2012-2014 the original author or authors. + * Copyright 2012-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. @@ -21,6 +21,7 @@ import java.util.Set; import org.hamcrest.Matchers; import org.junit.After; +import org.junit.Rule; import org.junit.Test; import org.springframework.boot.autoconfigure.AutoConfigurationPackages; import org.springframework.boot.autoconfigure.PropertyPlaceholderAutoConfiguration; @@ -30,6 +31,9 @@ import org.springframework.context.annotation.AnnotationConfigApplicationContext import org.springframework.context.annotation.Bean; import org.springframework.context.annotation.Configuration; import org.springframework.core.convert.converter.Converter; +import org.springframework.data.mapping.model.CamelCaseAbbreviatingFieldNamingStrategy; +import org.springframework.data.mapping.model.FieldNamingStrategy; +import org.springframework.data.mapping.model.PropertyNameFieldNamingStrategy; import org.springframework.data.mongodb.core.MongoTemplate; import org.springframework.data.mongodb.core.convert.CustomConversions; import org.springframework.data.mongodb.core.mapping.MongoMappingContext; @@ -37,6 +41,7 @@ import org.springframework.data.mongodb.gridfs.GridFsTemplate; import org.springframework.test.util.ReflectionTestUtils; import com.mongodb.Mongo; +import org.junit.rules.ExpectedException; import static org.hamcrest.Matchers.hasSize; import static org.junit.Assert.assertEquals; @@ -51,6 +56,9 @@ import static org.junit.Assert.assertTrue; */ public class MongoDataAutoConfigurationTests { + @Rule + public final ExpectedException thrown = ExpectedException.none(); + private AnnotationConfigApplicationContext context; @After @@ -103,6 +111,38 @@ public class MongoDataAutoConfigurationTests { City.class); } + @Test + public void defaultFieldNamingStrategy() { + testFieldNamingStrategy(null, PropertyNameFieldNamingStrategy.class); + } + + @Test + public void customFieldNamingStrategy() { + testFieldNamingStrategy(CamelCaseAbbreviatingFieldNamingStrategy.class.getName(), + CamelCaseAbbreviatingFieldNamingStrategy.class); + } + + @Test + public void interfaceFieldNamingStrategy() { + thrown.expectMessage("Invalid custom FieldNamingStrategy"); + testFieldNamingStrategy(FieldNamingStrategy.class.getName(), null); + } + + public void testFieldNamingStrategy(String strategy, Class extends FieldNamingStrategy> expectedType) { + this.context = new AnnotationConfigApplicationContext(); + if (strategy != null) { + EnvironmentTestUtils.addEnvironment(this.context, + "spring.data.mongodb.field-naming-strategy:" + strategy); + } + this.context.register(PropertyPlaceholderAutoConfiguration.class, + MongoAutoConfiguration.class, MongoDataAutoConfiguration.class); + this.context.refresh(); + MongoMappingContext mappingContext = this.context.getBean(MongoMappingContext.class); + FieldNamingStrategy fieldNamingStrategy = + (FieldNamingStrategy) ReflectionTestUtils.getField(mappingContext, "fieldNamingStrategy"); + assertEquals(expectedType, fieldNamingStrategy.getClass()); + } + @SuppressWarnings({ "unchecked", "rawtypes" }) private static void assertDomainTypesDiscovered(MongoMappingContext mappingContext, Class>... types) { diff --git a/spring-boot-docs/src/main/asciidoc/appendix-application-properties.adoc b/spring-boot-docs/src/main/asciidoc/appendix-application-properties.adoc index be57aea4b7e..48a4b413c76 100644 --- a/spring-boot-docs/src/main/asciidoc/appendix-application-properties.adoc +++ b/spring-boot-docs/src/main/asciidoc/appendix-application-properties.adoc @@ -322,6 +322,7 @@ content into your application; rather pick only the properties that you need. spring.data.mongodb.username= spring.data.mongodb.password= spring.data.mongodb.repositories.enabled=true # if spring data repository support is enabled + spring.data.mongodb.field-naming-strategy= # fully qualified name of the FieldNamingStrategy to use # JPA ({sc-spring-boot-autoconfigure}/orm/jpa/JpaBaseConfiguration.{sc-ext}[JpaBaseConfiguration], {sc-spring-boot-autoconfigure}/orm/jpa/HibernateJpaAutoConfiguration.{sc-ext}[HibernateJpaAutoConfiguration]) spring.jpa.properties.*= # properties to set on the JPA connection