mirror of https://github.com/elunez/eladmin
enable spring context holder
parent
4792b06312
commit
fcae3766d3
|
@ -16,6 +16,7 @@
|
||||||
package me.zhengjie.utils;
|
package me.zhengjie.utils;
|
||||||
|
|
||||||
import lombok.extern.slf4j.Slf4j;
|
import lombok.extern.slf4j.Slf4j;
|
||||||
|
import org.apache.commons.lang3.BooleanUtils;
|
||||||
import org.springframework.beans.BeansException;
|
import org.springframework.beans.BeansException;
|
||||||
import org.springframework.beans.factory.DisposableBean;
|
import org.springframework.beans.factory.DisposableBean;
|
||||||
import org.springframework.context.ApplicationContext;
|
import org.springframework.context.ApplicationContext;
|
||||||
|
@ -24,7 +25,10 @@ import org.springframework.core.env.Environment;
|
||||||
import org.springframework.stereotype.Service;
|
import org.springframework.stereotype.Service;
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
import java.util.Arrays;
|
import java.util.Arrays;
|
||||||
|
import java.util.HashMap;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
import java.util.Map;
|
||||||
|
import java.util.concurrent.ConcurrentHashMap;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @author Jie
|
* @author Jie
|
||||||
|
@ -33,9 +37,9 @@ import java.util.List;
|
||||||
@Slf4j
|
@Slf4j
|
||||||
public class SpringContextHolder implements ApplicationContextAware, DisposableBean {
|
public class SpringContextHolder implements ApplicationContextAware, DisposableBean {
|
||||||
|
|
||||||
private static ApplicationContext applicationContext = null;
|
private static Map<ClassLoader, ApplicationContext> applicationContextMap = new ConcurrentHashMap<>();
|
||||||
private static final List<CallBack> CALL_BACKS = new ArrayList<>();
|
private static final Map<ClassLoader, List<CallBack>> CALL_BACKS_MAP = new HashMap<>();
|
||||||
private static boolean addCallback = true;
|
private static Map<ClassLoader, Boolean> addCallbackMap = new HashMap<>();
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* 针对 某些初始化方法,在SpringContextHolder 未初始化时 提交回调方法。
|
* 针对 某些初始化方法,在SpringContextHolder 未初始化时 提交回调方法。
|
||||||
|
@ -44,8 +48,12 @@ public class SpringContextHolder implements ApplicationContextAware, DisposableB
|
||||||
* @param callBack 回调函数
|
* @param callBack 回调函数
|
||||||
*/
|
*/
|
||||||
public synchronized static void addCallBacks(CallBack callBack) {
|
public synchronized static void addCallBacks(CallBack callBack) {
|
||||||
if (addCallback) {
|
ClassLoader classLoader = Thread.currentThread().getContextClassLoader();
|
||||||
SpringContextHolder.CALL_BACKS.add(callBack);
|
|
||||||
|
Boolean addCallback = addCallbackMap.get(classLoader);
|
||||||
|
if (addCallback == null || BooleanUtils.isNotTrue(addCallback)) {
|
||||||
|
CALL_BACKS_MAP.putIfAbsent(classLoader, new ArrayList<>());
|
||||||
|
CALL_BACKS_MAP.get(classLoader).add(callBack);
|
||||||
} else {
|
} else {
|
||||||
log.warn("CallBack:{} 已无法添加!立即执行", callBack.getCallBackName());
|
log.warn("CallBack:{} 已无法添加!立即执行", callBack.getCallBackName());
|
||||||
callBack.executor();
|
callBack.executor();
|
||||||
|
@ -58,7 +66,8 @@ public class SpringContextHolder implements ApplicationContextAware, DisposableB
|
||||||
@SuppressWarnings("unchecked")
|
@SuppressWarnings("unchecked")
|
||||||
public static <T> T getBean(String name) {
|
public static <T> T getBean(String name) {
|
||||||
assertContextInjected();
|
assertContextInjected();
|
||||||
return (T) applicationContext.getBean(name);
|
ClassLoader classLoader = Thread.currentThread().getContextClassLoader();
|
||||||
|
return (T) applicationContextMap.get(classLoader).getBean(name);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -66,7 +75,8 @@ public class SpringContextHolder implements ApplicationContextAware, DisposableB
|
||||||
*/
|
*/
|
||||||
public static <T> T getBean(Class<T> requiredType) {
|
public static <T> T getBean(Class<T> requiredType) {
|
||||||
assertContextInjected();
|
assertContextInjected();
|
||||||
return applicationContext.getBean(requiredType);
|
ClassLoader classLoader = Thread.currentThread().getContextClassLoader();
|
||||||
|
return (T) applicationContextMap.get(classLoader).getBean(requiredType);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -110,6 +120,8 @@ public class SpringContextHolder implements ApplicationContextAware, DisposableB
|
||||||
* 检查ApplicationContext不为空.
|
* 检查ApplicationContext不为空.
|
||||||
*/
|
*/
|
||||||
private static void assertContextInjected() {
|
private static void assertContextInjected() {
|
||||||
|
ClassLoader classLoader = Thread.currentThread().getContextClassLoader();
|
||||||
|
ApplicationContext applicationContext = applicationContextMap.get(classLoader);
|
||||||
if (applicationContext == null) {
|
if (applicationContext == null) {
|
||||||
throw new IllegalStateException("applicaitonContext属性未注入, 请在applicationContext" +
|
throw new IllegalStateException("applicaitonContext属性未注入, 请在applicationContext" +
|
||||||
".xml中定义SpringContextHolder或在SpringBoot启动类中注册SpringContextHolder.");
|
".xml中定义SpringContextHolder或在SpringBoot启动类中注册SpringContextHolder.");
|
||||||
|
@ -120,9 +132,10 @@ public class SpringContextHolder implements ApplicationContextAware, DisposableB
|
||||||
* 清除SpringContextHolder中的ApplicationContext为Null.
|
* 清除SpringContextHolder中的ApplicationContext为Null.
|
||||||
*/
|
*/
|
||||||
private static void clearHolder() {
|
private static void clearHolder() {
|
||||||
|
ClassLoader classLoader = Thread.currentThread().getContextClassLoader();
|
||||||
log.debug("清除SpringContextHolder中的ApplicationContext:"
|
log.debug("清除SpringContextHolder中的ApplicationContext:"
|
||||||
+ applicationContext);
|
+ applicationContextMap.get(classLoader));
|
||||||
applicationContext = null;
|
applicationContextMap.remove(classLoader);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
@ -132,17 +145,23 @@ public class SpringContextHolder implements ApplicationContextAware, DisposableB
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void setApplicationContext(ApplicationContext applicationContext) throws BeansException {
|
public void setApplicationContext(ApplicationContext applicationContext) throws BeansException {
|
||||||
if (SpringContextHolder.applicationContext != null) {
|
// if (SpringContextHolder.applicationContext != null) {
|
||||||
log.warn("SpringContextHolder中的ApplicationContext被覆盖, 原有ApplicationContext为:" + SpringContextHolder.applicationContext);
|
// log.warn("SpringContextHolder中的ApplicationContext被覆盖, 原有ApplicationContext为:" + SpringContextHolder.applicationContext);
|
||||||
}
|
// }
|
||||||
SpringContextHolder.applicationContext = applicationContext;
|
ClassLoader classLoader = Thread.currentThread().getContextClassLoader();
|
||||||
if (addCallback) {
|
applicationContextMap.putIfAbsent(classLoader, applicationContext);
|
||||||
for (CallBack callBack : SpringContextHolder.CALL_BACKS) {
|
|
||||||
callBack.executor();
|
Boolean addCallback = addCallbackMap.get(classLoader);
|
||||||
|
if (BooleanUtils.isNotTrue(addCallback)) {
|
||||||
|
List<CallBack> callBacks = CALL_BACKS_MAP.get(classLoader);
|
||||||
|
if (callBacks != null) {
|
||||||
|
for (CallBack callBack : callBacks) {
|
||||||
|
callBack.executor();
|
||||||
|
}
|
||||||
|
callBacks.clear();
|
||||||
}
|
}
|
||||||
CALL_BACKS.clear();
|
|
||||||
}
|
}
|
||||||
SpringContextHolder.addCallback = false;
|
addCallbackMap.put(classLoader, true);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -150,6 +169,7 @@ public class SpringContextHolder implements ApplicationContextAware, DisposableB
|
||||||
* @return /
|
* @return /
|
||||||
*/
|
*/
|
||||||
public static List<String> getAllServiceBeanName() {
|
public static List<String> getAllServiceBeanName() {
|
||||||
|
ApplicationContext applicationContext = applicationContextMap.get(Thread.currentThread().getContextClassLoader());
|
||||||
return new ArrayList<>(Arrays.asList(applicationContext
|
return new ArrayList<>(Arrays.asList(applicationContext
|
||||||
.getBeanNamesForAnnotation(Service.class)));
|
.getBeanNamesForAnnotation(Service.class)));
|
||||||
}
|
}
|
||||||
|
|
|
@ -15,7 +15,6 @@
|
||||||
*/
|
*/
|
||||||
package me.zhengjie;
|
package me.zhengjie;
|
||||||
|
|
||||||
import com.alibaba.druid.spring.boot.autoconfigure.DruidDataSourceAutoConfigure;
|
|
||||||
import io.swagger.annotations.Api;
|
import io.swagger.annotations.Api;
|
||||||
import me.zhengjie.annotation.rest.AnonymousGetMapping;
|
import me.zhengjie.annotation.rest.AnonymousGetMapping;
|
||||||
import me.zhengjie.utils.SpringContextHolder;
|
import me.zhengjie.utils.SpringContextHolder;
|
||||||
|
@ -55,7 +54,7 @@ import java.util.List;
|
||||||
@EnableAsync
|
@EnableAsync
|
||||||
@RestController
|
@RestController
|
||||||
@Api(hidden = true)
|
@Api(hidden = true)
|
||||||
@SpringBootApplication(exclude = DruidDataSourceAutoConfigure.class)
|
@SpringBootApplication
|
||||||
@EnableTransactionManagement
|
@EnableTransactionManagement
|
||||||
@EnableJpaAuditing(auditorAwareRef = "auditorAware")
|
@EnableJpaAuditing(auditorAwareRef = "auditorAware")
|
||||||
public class AppRun {
|
public class AppRun {
|
||||||
|
|
|
@ -32,7 +32,6 @@ import org.springframework.boot.actuate.endpoint.web.annotation.ControllerEndpoi
|
||||||
import org.springframework.boot.actuate.endpoint.web.annotation.ServletEndpointsSupplier;
|
import org.springframework.boot.actuate.endpoint.web.annotation.ServletEndpointsSupplier;
|
||||||
import org.springframework.boot.actuate.endpoint.web.servlet.WebMvcEndpointHandlerMapping;
|
import org.springframework.boot.actuate.endpoint.web.servlet.WebMvcEndpointHandlerMapping;
|
||||||
import org.springframework.boot.autoconfigure.SpringBootApplication;
|
import org.springframework.boot.autoconfigure.SpringBootApplication;
|
||||||
import org.springframework.boot.autoconfigure.jdbc.DataSourceAutoConfiguration;
|
|
||||||
import org.springframework.boot.context.ApplicationPidFileWriter;
|
import org.springframework.boot.context.ApplicationPidFileWriter;
|
||||||
import org.springframework.context.annotation.Bean;
|
import org.springframework.context.annotation.Bean;
|
||||||
import org.springframework.core.env.Environment;
|
import org.springframework.core.env.Environment;
|
||||||
|
@ -55,7 +54,7 @@ import java.util.List;
|
||||||
@EnableAsync
|
@EnableAsync
|
||||||
@RestController
|
@RestController
|
||||||
@Api(hidden = true)
|
@Api(hidden = true)
|
||||||
@SpringBootApplication(exclude = DataSourceAutoConfiguration.class)
|
@SpringBootApplication
|
||||||
@EnableTransactionManagement
|
@EnableTransactionManagement
|
||||||
@EnableJpaAuditing(auditorAwareRef = "auditorAware")
|
@EnableJpaAuditing(auditorAwareRef = "auditorAware")
|
||||||
public class AppRun {
|
public class AppRun {
|
||||||
|
|
|
@ -32,7 +32,6 @@ import org.springframework.boot.actuate.endpoint.web.annotation.ControllerEndpoi
|
||||||
import org.springframework.boot.actuate.endpoint.web.annotation.ServletEndpointsSupplier;
|
import org.springframework.boot.actuate.endpoint.web.annotation.ServletEndpointsSupplier;
|
||||||
import org.springframework.boot.actuate.endpoint.web.servlet.WebMvcEndpointHandlerMapping;
|
import org.springframework.boot.actuate.endpoint.web.servlet.WebMvcEndpointHandlerMapping;
|
||||||
import org.springframework.boot.autoconfigure.SpringBootApplication;
|
import org.springframework.boot.autoconfigure.SpringBootApplication;
|
||||||
import org.springframework.boot.autoconfigure.jdbc.DataSourceAutoConfiguration;
|
|
||||||
import org.springframework.boot.context.ApplicationPidFileWriter;
|
import org.springframework.boot.context.ApplicationPidFileWriter;
|
||||||
import org.springframework.context.annotation.Bean;
|
import org.springframework.context.annotation.Bean;
|
||||||
import org.springframework.core.env.Environment;
|
import org.springframework.core.env.Environment;
|
||||||
|
@ -55,7 +54,7 @@ import java.util.List;
|
||||||
@EnableAsync
|
@EnableAsync
|
||||||
@RestController
|
@RestController
|
||||||
@Api(hidden = true)
|
@Api(hidden = true)
|
||||||
@SpringBootApplication(exclude = DataSourceAutoConfiguration.class)
|
@SpringBootApplication
|
||||||
@EnableTransactionManagement
|
@EnableTransactionManagement
|
||||||
@EnableJpaAuditing(auditorAwareRef = "auditorAware")
|
@EnableJpaAuditing(auditorAwareRef = "auditorAware")
|
||||||
public class AppRun {
|
public class AppRun {
|
||||||
|
|
Loading…
Reference in New Issue