From ceb561e3e47816312c2c70040a2eebdc2b957321 Mon Sep 17 00:00:00 2001 From: Oliver Gierke Date: Tue, 12 Nov 2013 11:31:51 +0100 Subject: [PATCH] DATAMONGO-792 - Polishing of JavaConfig support for auditing. Original pull request: #94. --- .../mongodb/config/EnableMongoAuditing.java | 20 ++++++-- .../config/MongoAuditingRegistrar.java | 23 +++++---- ...uditingViaJavaConfigRepositoriesTests.java | 2 + .../MongoAuditingRegistrarUnitTests.java | 48 ++++++++++++++++++ src/docbkx/reference/mongodb.xml | 50 ++++++------------- 5 files changed, 95 insertions(+), 48 deletions(-) create mode 100644 spring-data-mongodb/src/test/java/org/springframework/data/mongodb/config/MongoAuditingRegistrarUnitTests.java diff --git a/spring-data-mongodb/src/main/java/org/springframework/data/mongodb/config/EnableMongoAuditing.java b/spring-data-mongodb/src/main/java/org/springframework/data/mongodb/config/EnableMongoAuditing.java index cce1cd9af..fff1b9f3d 100644 --- a/spring-data-mongodb/src/main/java/org/springframework/data/mongodb/config/EnableMongoAuditing.java +++ b/spring-data-mongodb/src/main/java/org/springframework/data/mongodb/config/EnableMongoAuditing.java @@ -24,11 +24,13 @@ import java.lang.annotation.Target; import org.springframework.context.annotation.Import; import org.springframework.data.auditing.DateTimeProvider; +import org.springframework.data.domain.AuditorAware; /** * Annotation to enable auditing in MongoDB via annotation configuration. * * @author Thomas Darimont + * @author Oliver Gierke */ @Inherited @Documented @@ -38,23 +40,31 @@ import org.springframework.data.auditing.DateTimeProvider; public @interface EnableMongoAuditing { /** - * @return References a bean of type AuditorAware to represent the current principal. + * Configures the {@link AuditorAware} bean to be used to lookup the current principal. + * + * @return */ String auditorAwareRef() default ""; /** - * @return Configures whether the creation and modification dates are set and defaults to {@literal true}. + * Configures whether the creation and modification dates are set. Defaults to {@literal true}. + * + * @return */ boolean setDates() default true; /** - * @return Configures whether the entity shall be marked as modified on creation and defaults to {@literal true}. + * Configures whether the entity shall be marked as modified on creation. Defaults to {@literal true}. + * + * @return */ boolean modifyOnCreate() default true; /** - * @return Configures a {@link DateTimeProvider} that allows customizing which DateTime shall be used for setting - * creation and modification dates. + * Configures a {@link DateTimeProvider} bean name that allows customizing the {@link org.joda.time.DateTime} to be + * used for setting creation and modification dates. + * + * @return */ String dateTimeProviderRef() default ""; } diff --git a/spring-data-mongodb/src/main/java/org/springframework/data/mongodb/config/MongoAuditingRegistrar.java b/spring-data-mongodb/src/main/java/org/springframework/data/mongodb/config/MongoAuditingRegistrar.java index 299a942dc..e3dac7934 100644 --- a/spring-data-mongodb/src/main/java/org/springframework/data/mongodb/config/MongoAuditingRegistrar.java +++ b/spring-data-mongodb/src/main/java/org/springframework/data/mongodb/config/MongoAuditingRegistrar.java @@ -34,10 +34,12 @@ import org.springframework.util.Assert; * {@link ImportBeanDefinitionRegistrar} to enable {@link EnableMongoAuditing} annotation. * * @author Thomas Darimont + * @author Oliver Gierke */ class MongoAuditingRegistrar extends AuditingBeanDefinitionRegistrarSupport { - /* (non-Javadoc) + /* + * (non-Javadoc) * @see org.springframework.data.auditing.config.AuditingBeanDefinitionRegistrarSupport#getAnnotation() */ @Override @@ -45,41 +47,44 @@ class MongoAuditingRegistrar extends AuditingBeanDefinitionRegistrarSupport { return EnableMongoAuditing.class; } - /* (non-Javadoc) + /* + * (non-Javadoc) * @see org.springframework.data.auditing.config.AuditingBeanDefinitionRegistrarSupport#registerBeanDefinitions(org.springframework.core.type.AnnotationMetadata, org.springframework.beans.factory.support.BeanDefinitionRegistry) */ @Override public void registerBeanDefinitions(AnnotationMetadata annotationMetadata, BeanDefinitionRegistry registry) { - Assert.notNull(annotationMetadata, "annotationMetadata must not be null!"); - Assert.notNull(annotationMetadata, "registry must not be null!"); + Assert.notNull(annotationMetadata, "AnnotationMetadata must not be null!"); + Assert.notNull(registry, "BeanDefinitionRegistry must not be null!"); registerIsNewStrategyFactoryIfNecessary(registry); super.registerBeanDefinitions(annotationMetadata, registry); } - /* (non-Javadoc) + /* + * (non-Javadoc) * @see org.springframework.data.auditing.config.AuditingBeanDefinitionRegistrarSupport#getAuditHandlerBeanDefinitionBuilder(org.springframework.data.auditing.config.AnnotationAuditingConfiguration) */ @Override protected BeanDefinitionBuilder getAuditHandlerBeanDefinitionBuilder(AnnotationAuditingConfiguration configuration) { - Assert.notNull(configuration, "configuration must not be null!"); + Assert.notNull(configuration, "AnnotationAuditingConfiguration must not be null!"); return configureDefaultAuditHandlerAttributes(configuration, BeanDefinitionBuilder.rootBeanDefinition(IsNewAwareAuditingHandler.class)).addConstructorArgReference( BeanNames.IS_NEW_STRATEGY_FACTORY); } - /* (non-Javadoc) + /* + * (non-Javadoc) * @see org.springframework.data.auditing.config.AuditingBeanDefinitionRegistrarSupport#registerAuditListener(org.springframework.beans.factory.config.BeanDefinition, org.springframework.beans.factory.support.BeanDefinitionRegistry) */ @Override protected void registerAuditListenerBeanDefinition(BeanDefinition auditingHandlerDefinition, BeanDefinitionRegistry registry) { - Assert.notNull(auditingHandlerDefinition, "auditingHandlerDefinition must not be null!"); - Assert.notNull(registry, "registry must not be null!"); + Assert.notNull(auditingHandlerDefinition, "BeanDefinition must not be null!"); + Assert.notNull(registry, "BeanDefinitionRegistry must not be null!"); registerInfrastructureBeanWithId(BeanDefinitionBuilder.rootBeanDefinition(AuditingEventListener.class) .addConstructorArgValue(auditingHandlerDefinition).getRawBeanDefinition(), diff --git a/spring-data-mongodb/src/test/java/org/springframework/data/mongodb/config/AuditingViaJavaConfigRepositoriesTests.java b/spring-data-mongodb/src/test/java/org/springframework/data/mongodb/config/AuditingViaJavaConfigRepositoriesTests.java index 493f7f2f0..df5d7a412 100644 --- a/spring-data-mongodb/src/test/java/org/springframework/data/mongodb/config/AuditingViaJavaConfigRepositoriesTests.java +++ b/spring-data-mongodb/src/test/java/org/springframework/data/mongodb/config/AuditingViaJavaConfigRepositoriesTests.java @@ -43,6 +43,7 @@ import com.mongodb.MongoClient; * Integration tests for auditing via Java config. * * @author Thomas Darimont + * @author Oliver Gierke */ @RunWith(SpringJUnit4ClassRunner.class) @ContextConfiguration @@ -68,6 +69,7 @@ public class AuditingViaJavaConfigRepositoriesTests { } @Bean + @SuppressWarnings("unchecked") public AuditorAware auditorProvider() { return mock(AuditorAware.class); } diff --git a/spring-data-mongodb/src/test/java/org/springframework/data/mongodb/config/MongoAuditingRegistrarUnitTests.java b/spring-data-mongodb/src/test/java/org/springframework/data/mongodb/config/MongoAuditingRegistrarUnitTests.java new file mode 100644 index 000000000..ad076c90d --- /dev/null +++ b/spring-data-mongodb/src/test/java/org/springframework/data/mongodb/config/MongoAuditingRegistrarUnitTests.java @@ -0,0 +1,48 @@ +/* + * Copyright 2013 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.data.mongodb.config; + +import org.junit.Test; +import org.junit.runner.RunWith; +import org.mockito.Mock; +import org.mockito.runners.MockitoJUnitRunner; +import org.springframework.beans.factory.support.BeanDefinitionRegistry; +import org.springframework.core.type.AnnotationMetadata; + +/** + * Unit tests for {@link JpaAuditingRegistrar}. + * + * @see DATAMONGO-792 + * @author Oliver Gierke + */ +@RunWith(MockitoJUnitRunner.class) +public class MongoAuditingRegistrarUnitTests { + + MongoAuditingRegistrar registrar = new MongoAuditingRegistrar(); + + @Mock AnnotationMetadata metadata; + @Mock BeanDefinitionRegistry registry; + + @Test(expected = IllegalArgumentException.class) + public void rejectsNullAnnotationMetadata() { + registrar.registerBeanDefinitions(null, registry); + } + + @Test(expected = IllegalArgumentException.class) + public void rejectsNullBeanDefinitionRegistry() { + registrar.registerBeanDefinitions(metadata, null); + } +} diff --git a/src/docbkx/reference/mongodb.xml b/src/docbkx/reference/mongodb.xml index 4f21b1e85..2705080db 100644 --- a/src/docbkx/reference/mongodb.xml +++ b/src/docbkx/reference/mongodb.xml @@ -579,21 +579,20 @@ public class MongoConfiguration { configuration: - Activating auditing in the Spring configuration + Activating auditing using XML configuration <mongo:auditing mapping-context-ref="customMappingContext" auditor-aware-ref="yourAuditorAwareImpl"/> - - Auditing via Java Config + Since Spring Data MongoDB 1.4 auditing can be enabled by annotating + a configuration class with the @EnableMongoAuditing + annotation. - Since Spring Data MongoDB 1.4 Auditing can be enabled by - annotating a configuration class with the - EnableMongoAuditing annotation. + + Activating auditing using JavaConfig @Configuration -@EnableMongoAuditing(auditorAwareRef="myAuditorProvider") -@EnableMongoRepositories +@EnableMongoAuditing class Config { @Bean @@ -601,34 +600,17 @@ class Config { return new AuditorAwareImpl(); } } - - Note that if you want to record information about the create-User - or modify-User, you can delcare a bean that implements the - AuditorAware interface. The bean name can also be - configured explicitly via the auditorAwareRef attribute of - the EnableMongoAuditing annotation, this can be - used to resolve an ambiguity. If no auditorAwareRef is - specified explicitly we try to discover and autowire an - AuditorAware implementation. - As you can see you have to provide a bean that implements the - AuditorAware interface which looks as - follows: - - - <interfacename>AuditorAware</interfacename> interface - - public interface AuditorAware<T, ID extends Serializable> { - - T getCurrentAuditor(); -} - - - Usually you will have some kind of authentication component in your - application that tracks the user currently working with the system. This - component should be AuditorAware and thus - allow seamless tracking of the auditor. + If you expose a bean of type + AuditorAware to the + ApplicationContext, the auditing + infrastructure will pick it up automatically and use it to determine the + current user to be set on domain types. If you have multiple + implementations registered in the + ApplicationContext, you can select the one + to be used by explicitly setting the auditorAwareRef + attribute of @EnableJpaAuditing.