diff --git a/spring-data-commons-core/src/main/java/org/springframework/data/mapping/context/AbstractMappingContext.java b/spring-data-commons-core/src/main/java/org/springframework/data/mapping/context/AbstractMappingContext.java
index 027917954..52b6edb99 100644
--- a/spring-data-commons-core/src/main/java/org/springframework/data/mapping/context/AbstractMappingContext.java
+++ b/spring-data-commons-core/src/main/java/org/springframework/data/mapping/context/AbstractMappingContext.java
@@ -32,6 +32,8 @@ import java.util.Map;
import java.util.Set;
import java.util.concurrent.ConcurrentHashMap;
import java.util.concurrent.ConcurrentMap;
+import java.util.concurrent.locks.Lock;
+import java.util.concurrent.locks.ReentrantReadWriteLock;
import org.springframework.beans.factory.InitializingBean;
import org.springframework.context.ApplicationEventPublisher;
@@ -51,6 +53,9 @@ import org.springframework.validation.Validator;
/**
* Base class to build mapping metadata and thus create instances of {@link PersistentEntity} and
* {@link PersistentProperty}.
+ *
+ * The implementation uses a {@link ReentrantReadWriteLock} to make sure {@link PersistentEntity} are completely
+ * populated before accessing them from outside.
*
* @param E the concrete {@link PersistentEntity} type the {@link MappingContext} implementation creates
* @param P the concrete {@link PersistentProperty} type the {@link MappingContext} implementation creates
@@ -70,6 +75,10 @@ public abstract class AbstractMappingContext getPersistentEntities() {
- return persistentEntities.values();
+ try {
+ read.lock();
+ return persistentEntities.values();
+ } finally {
+ read.unlock();
+ }
}
/*
@@ -132,10 +146,16 @@ public abstract class AbstractMappingContext type) {
- E entity = persistentEntities.get(type);
+ try {
+ read.lock();
+ E entity = persistentEntities.get(type);
- if (entity != null) {
- return entity;
+ if (entity != null) {
+ return entity;
+ }
+
+ } finally {
+ read.unlock();
}
if (strict) {
@@ -144,7 +164,7 @@ public abstract class AbstractMappingContext type = typeInformation.getType();
try {
+
+ write.lock();
+
final E entity = createPersistentEntity(typeInformation);
// Eagerly cache the entity as we might have to find it during recursive lookups.
@@ -260,8 +283,11 @@ public abstract class AbstractMappingContext> {
+
+ @Test
+ public void foo() throws InterruptedException {
+
+ final DummyMappingContext context = new DummyMappingContext();
+
+ Thread a = new Thread(new Runnable() {
+ public void run() {
+ context.getPersistentEntity(Person.class);
+ }
+ });
+
+ Thread b = new Thread(new Runnable() {
+
+ public void run() {
+
+ PersistentEntity