@Document 注释中的 MongoDB 和 SpEL 表达式
我正在尝试使用 SpEL 根据我定义的一些规则将相同的文档加载到不同的集合中.
I am trying to use the SpEL to load the same Document into different collections based on some rules that i have defined.
所以从我所拥有的开始:
So to start with what i have:
-首先是文档:
@Document(collection = "#{@mySpecialProvider.getTargetCollectionName()}")
public class MongoDocument {
// some random fields go in
}
-第二个我有应该提供集合名称的提供程序 bean:
-second i have the provider bean that should provide the collection name:
@Component("mySpecialProvider")
public class MySpecialProvider {
public String getTargetCollectionName() {
// Thread local magic goes in bellow
String targetCollectionName = (String) RequestLocalContext.getFromLocalContext("targetCollectionName");
if (targetCollectionName == null) {
targetCollectionName = "defaultCollection";
}
return targetCollectionName;
}
}
问题是,当我尝试将文档插入应由提供程序生成的特定集合中时,我得到以下堆栈跟踪:
The problem is that when i try to insert a document into a specific collection that should be generated by the provider i get the following stacktrace:
org.springframework.expression.spel.SpelEvaluationException: EL1057E:(pos 1): 没有在上下文中注册 bean 解析器来解析对 bean 'mySpecialProvider' 的访问
我也尝试过制作spring组件ApplicationContextAware,但还是没有成功.
I also tried making the spring component ApplicationContextAware but still no luck.
推荐答案
正如我承诺的那样,我会带着我的问题的答案回来.要使其正常工作,您需要在应用程序上下文 XML 文件中对 mongoTemplate bean 进行以下设置:
As i promised i am returning with an answer to my question. To have it working you need to have the following settings for the mongoTemplate bean in the application context XML file:
<mongo:db-factory dbname="${myDatabaseName.from.properties.file}" mongo-ref="mongo"/>
<bean id="mongoMappingContext" class="org.springframework.data.mongodb.core.mapping.MongoMappingContext"/>
<bean id="mappingMongoConverter" class="org.springframework.data.mongodb.core.convert.MappingMongoConverter" c:mongoDbFactory-ref="mongoDbFactory"
c:mappingContext-ref="mongoMappingContext"/>
<bean id="mongoTemplate" class="org.springframework.data.mongodb.core.MongoTemplate"
c:mongoDbFactory-ref="mongoDbFactory" c:mongoConverter-ref="mappingMongoConverter"/>
通过上面的设置和我在我的问题中建议的解决方案有效.您可以使用相同的域对象并将其存储到基于您选择的设置的多个集合中.
And with the settings above and the solution i suggested in my question works. You can use the same domain object and store it into multiple collections based on settings of your choosing.
由于有人在相关问题中提出要求,我还将在此处更新 ThreadLocal 上下文的逻辑:
Since someone asked for it in a related question, i will also update here the logic for the ThreadLocal context:
创建一个封装以下实现的 RequestLocalContext 类:
Make a RequestLocalContext class that wraps over the following implementation:
private static final ThreadLocal<Map> CONTEXT = new ThreadLocal<Map>() {
protected Map initialValue() {
Map localMap = new HashMap();
localMap.put(LocalContextKeys.CONVERSATION_CONTEXT, new HashMap());
return localMap;
};
};
public static void putInLocalContext(Object key, Object value) {
Map localMap = CONTEXT.get();
localMap.put(key, value);
}
public static Object getFromLocalContext(Object key) {
Map localMap = CONTEXT.get();
return localMap.get(key);
}
其中 LocalContextKeys 是一个枚举,其中包含 ThreadLocal 上下文 Map 中允许的键.请注意,这些键是用户定义的,因此您可以随意放入任何您可能需要的键.
Where LocalContextKeys is an enum containing the keys allowed in the the ThreadLocal context Map. Note that the keys are user defined so feel free to put in there whatever you may need.
相关文章