javascript
在运行时交换出Spring Bean配置
最近,我遇到了一個(gè)我從未遇到過(guò)的問(wèn)題:引入了基于運(yùn)行時(shí)引入的配置來(lái)重新連接Bean內(nèi)部的功能。 這對(duì)于簡(jiǎn)單的配置更改或交換掉諸如Strategy或Factory類之類的東西非常有價(jià)值,而不是重建應(yīng)用程序上下文的復(fù)雜部分。
我能夠找到一些有關(guān)如何執(zhí)行此操作的注釋,但是我認(rèn)為有些人可能會(huì)發(fā)現(xiàn)我的注釋和代碼示例很有用,特別是因?yàn)槲铱梢源_認(rèn)該技術(shù)在Spring 1.2.6之前的版本中可以使用。 不幸的是,并不是我們所有人都有幸成為每個(gè)圖書館中最新最好的圖書館。
問(wèn)題范圍
我將概述的方法主要是針對(duì)單個(gè)bean的更改,盡管可以輕松擴(kuò)展此代碼以更改多個(gè)bean。 可以通過(guò)JMX或向管理員公開的其他UI調(diào)用它。
它沒(méi)有涉及的一件事是在整個(gè)應(yīng)用程序中重新布線單例–可以想到,這可以通過(guò)對(duì)當(dāng)前應(yīng)用程序上下文的某種反射和檢查來(lái)完成,但是在大多數(shù)應(yīng)用程序中,除非它們具有某種臨時(shí)關(guān)閉或關(guān)閉的方式,否則可能不安全。在整個(gè)應(yīng)用程序中進(jìn)行更改時(shí),將一段時(shí)間內(nèi)的所有處理都阻塞。
編碼
這是示例代碼。 它將獲取一個(gè)包含bean定義的字符串列表,并將它們連接到新的臨時(shí)Spring上下文中。 您將看到可以提供父上下文,這在您的新bean定義需要引用應(yīng)用程序中已經(jīng)配置的bean時(shí)很有用。
public static <T> Map<String, T> extractBeans(Class<T> beanType,List<String> contextXmls, ApplicationContext parentContext) throws Exception {List<String> paths = new ArrayList<String>();try {for (String xml : contextXmls) {File file = File.createTempFile("spring", "xml");// ... write the file using a utility methodFileUtils.writeStringToFile(file, xml, "UTF-8");paths.add(file.getAbsolutePath());}String[] pathArray = paths.toArray(new String[0]);return buildContextAndGetBeans(beanType, pathArray, parentContext);} finally {// ... clean up temp files immediately if desired} }private static <T> Map<String, T> buildContextAndGetBeans(Class<T> beanType,String[] paths, ApplicationContext parentContext) throws Exception {FileSystemXmlApplicationContext context =new FileSystemXmlApplicationContext(paths, false, parentContext) {@Override // suppress refresh events bubbling to parent contextpublic void publishEvent(ApplicationEvent event) { }};try {// avoid classloader errors in some environmentscontext.setClassLoader(beanType.getClassLoader());context.refresh(); // parse and load contextMap<String, T> beanMap = context.getBeansOfType(beanType);return beanMap;} finally {try {context.close();} catch (Exception e) {// ... log this}} }如果查看buildContextAndGetBeans() ,您將看到它通過(guò)使用提供的XML bean定義文件構(gòu)建Spring上下文來(lái)完成大部分工作。 然后,它返回所請(qǐng)求類型的構(gòu)造bean的映射。
注意:由于臨時(shí)Spring上下文已被破壞,因此請(qǐng)確保您的bean沒(méi)有生命周期方法,該方法會(huì)導(dǎo)致它們?cè)谕V够蚱茐臅r(shí)處于無(wú)效狀態(tài)。
這是一個(gè)Spring上下文的示例,可用于重新連接組件。 想象一下,我們有一個(gè)電子商務(wù)系統(tǒng),可以進(jìn)行欺詐檢查,但是可以使用多種策略來(lái)檢查欺詐。 我們可能希望從服務(wù)類中交換這些內(nèi)??容,而不必停止并重新配置應(yīng)用程序,因?yàn)檫@樣做會(huì)造成業(yè)務(wù)損失。 也許我們正在發(fā)現(xiàn)對(duì)該系統(tǒng)的特定濫用,可以通過(guò)更改用于定位欺詐性訂單的策略來(lái)更好地解決。
這是一個(gè)示例XML定義,可用于重新連接我們的FraudService 。
<?xml version="1.0" encoding="UTF-8"?> <!DOCTYPE beans PUBLIC "-//SPRING//DTD BEAN//EN" "http://www.springframework.org/dtd/spring-beans.dtd"> <beans><bean id="fraudStrategy" class="com.example.SomeFraudStategory"><!-- example of a bean defined in the parent application context that we can reference --><property name="fraudRuleFactory" ref="fraudRuleFactory"/></bean> </beans>這是您可以使用對(duì)定義的欺詐策略的引用來(lái)重新連接Bean的代碼,假設(shè)您已將其包含在名為SpringUtils的實(shí)用工具類中:
public class FraudService implements ApplicationContextAware {private ApplicationContext context;// volatile for thread safety (in Java 1.5 and up only)private volatile FraudStrategy fraudStrategy;@Override // get a handle on the the parent contextpublic void setApplicationContext(ApplicationContext context) {this.context = context;}public void swapFraudStategy(String xmlDefinition) throws Exception {List<Sting> definitions = Arrays.asList(xmlDefinition);Map<String, FraudStrategy> beans =SpringUtils.extractBeans(FraudStrategy.class, definitions, context);if (beans.size() != 1) {throw new RuntimeException("Invalid number of beans: " + beans .size());}this.fraudStrategy = beans.values().iterator().next();}}在那里,您擁有了! 可以適當(dāng)?shù)財(cái)U(kuò)展此示例以滿足您的需求,但是我認(rèn)為它展示了如何動(dòng)態(tài)創(chuàng)建Spring上下文并使用其bean重新配置應(yīng)用程序而無(wú)需停機(jī)的基礎(chǔ)知識(shí)。
參考:在Carfey Software博客上 ,我們的JCG合作伙伴提供了在運(yùn)行時(shí)交換Spring Bean配置的信息 。
相關(guān)文章 :- 零XML的Spring配置
- Spring依賴注入技術(shù)的發(fā)展
- Spring MVC3 Hibernate CRUD示例應(yīng)用程序
- 使用Spring AOP進(jìn)行面向方面的編程
- Spring MVC開發(fā)–快速教程
翻譯自: https://www.javacodegeeks.com/2011/09/swapping-out-spring-bean-configuration.html
總結(jié)
以上是生活随笔為你收集整理的在运行时交换出Spring Bean配置的全部?jī)?nèi)容,希望文章能夠幫你解決所遇到的問(wèn)題。
- 上一篇: 盗版电脑系统有哪些软件(电脑盗版软件下载
- 下一篇: 使用Spring配置LogBack日志记