Sfoglia il codice sorgente

调整Spring容器上下文初始化方式.

聂秋荣 1 settimana fa
parent
commit
f99a894452

+ 6 - 8
mybatis-plus-spring/src/main/java/com/baomidou/mybatisplus/extension/spi/SpringCompatibleSet.java

@@ -17,7 +17,6 @@ package com.baomidou.mybatisplus.extension.spi;
 
 import com.baomidou.mybatisplus.core.toolkit.AopUtils;
 import com.baomidou.mybatisplus.core.toolkit.ExceptionUtils;
-import com.baomidou.mybatisplus.extension.spring.MybatisPlusApplicationContextAware;
 import lombok.SneakyThrows;
 import org.apache.ibatis.exceptions.PersistenceException;
 import org.apache.ibatis.logging.Log;
@@ -45,7 +44,7 @@ public class SpringCompatibleSet implements CompatibleSet {
 
     private static final Log LOG = LogFactory.getLog(SpringCompatibleSet.class);
 
-    private static volatile ApplicationContext applicationContext;
+    public static volatile ApplicationContext applicationContext;
 
     @Override
     public SqlSession getSqlSession(SqlSessionFactory sessionFactory) {
@@ -101,13 +100,12 @@ public class SpringCompatibleSet implements CompatibleSet {
 
     @Override
     public <T> T getBean(Class<T> clz) {
-        if (applicationContext == null && !MybatisPlusApplicationContextAware.hasApplicationContext()) {
-            LOG.warn("MybatisPlusApplicationContextAware is not initialized. Please ensure that MybatisPlusApplicationContextAware is properly registered as a Spring Bean in the application context.");
-            return null;
+        if (applicationContext != null) {
+            ObjectProvider<T> provider = applicationContext.getBeanProvider(clz);
+            return provider.getIfAvailable();
         }
-        ApplicationContext context = applicationContext !=null  ? applicationContext : MybatisPlusApplicationContextAware.getApplicationContext();
-        ObjectProvider<T> provider = context.getBeanProvider(clz);
-        return provider.getIfAvailable();
+        LOG.warn("The applicationContext property is empty. Please initialize it via the static field of applicationContext in SpringContextHolder or by calling the setApplicationContext method of MybatisSqlSessionFactoryBean.");
+        return null;
     }
 
     @Override

+ 6 - 0
mybatis-plus-spring/src/main/java/com/baomidou/mybatisplus/extension/spring/MybatisPlusApplicationContextAware.java

@@ -15,6 +15,7 @@
  */
 package com.baomidou.mybatisplus.extension.spring;
 
+import com.baomidou.mybatisplus.core.spi.CompatibleHelper;
 import com.baomidou.mybatisplus.core.toolkit.Assert;
 import org.jetbrains.annotations.NotNull;
 import org.slf4j.Logger;
@@ -28,7 +29,9 @@ import org.springframework.context.ApplicationContextAware;
  *
  * @author nieqiurong
  * @since 3.5.12
+ * @deprecated 3.5.13 初始化顺序不太好兼容Bean初始化方法执行逻辑,使用{@link MybatisSqlSessionFactoryBean#setApplicationContext(ApplicationContext)}替代.
  */
+@Deprecated
 public class MybatisPlusApplicationContextAware implements ApplicationContextAware {
 
     private static final Logger LOGGER = LoggerFactory.getLogger(MybatisPlusApplicationContextAware.class);
@@ -39,6 +42,9 @@ public class MybatisPlusApplicationContextAware implements ApplicationContextAwa
     public void setApplicationContext(@NotNull ApplicationContext applicationContext) throws BeansException {
         LOGGER.info("Register ApplicationContext instances {}", applicationContext.getDisplayName());
         MybatisPlusApplicationContextAware.applicationContext = applicationContext;
+        if (CompatibleHelper.hasCompatibleSet()) {
+            CompatibleHelper.getCompatibleSet().setContext(applicationContext);
+        }
     }
 
     public static boolean hasApplicationContext() {

+ 25 - 2
mybatis-plus-spring/src/main/java/com/baomidou/mybatisplus/extension/spring/MybatisSqlSessionFactoryBean.java

@@ -17,8 +17,10 @@ package com.baomidou.mybatisplus.extension.spring;
 
 import com.baomidou.mybatisplus.core.*;
 import com.baomidou.mybatisplus.core.config.GlobalConfig;
+import com.baomidou.mybatisplus.core.spi.CompatibleHelper;
 import com.baomidou.mybatisplus.core.toolkit.GlobalConfigUtils;
 import com.baomidou.mybatisplus.extension.toolkit.SqlHelper;
+import lombok.Getter;
 import lombok.Setter;
 import org.apache.ibatis.cache.Cache;
 import org.apache.ibatis.executor.ErrorContext;
@@ -41,6 +43,8 @@ import org.mybatis.spring.SqlSessionFactoryBean;
 import org.mybatis.spring.transaction.SpringManagedTransactionFactory;
 import org.springframework.beans.factory.FactoryBean;
 import org.springframework.beans.factory.InitializingBean;
+import org.springframework.context.ApplicationContext;
+import org.springframework.context.ApplicationContextAware;
 import org.springframework.context.ApplicationListener;
 import org.springframework.context.ConfigurableApplicationContext;
 import org.springframework.context.event.ContextRefreshedEvent;
@@ -76,7 +80,7 @@ import static org.springframework.util.StringUtils.tokenizeToStringArray;
  * @author hubin
  * @since 2017-01-04
  */
-public class MybatisSqlSessionFactoryBean implements FactoryBean<SqlSessionFactory>, InitializingBean, ApplicationListener<ContextRefreshedEvent> {
+public class MybatisSqlSessionFactoryBean implements FactoryBean<SqlSessionFactory>, InitializingBean, ApplicationListener<ContextRefreshedEvent>, ApplicationContextAware {
 
     private static final Logger LOGGER = LoggerFactory.getLogger(MybatisSqlSessionFactoryBean.class);
 
@@ -101,7 +105,6 @@ public class MybatisSqlSessionFactoryBean implements FactoryBean<SqlSessionFacto
 
     private String environment = SqlSessionFactoryBean.class.getSimpleName();
 
-
     private boolean failFast;
 
     private Interceptor[] plugins;
@@ -134,6 +137,12 @@ public class MybatisSqlSessionFactoryBean implements FactoryBean<SqlSessionFacto
 
     private ObjectWrapperFactory objectWrapperFactory;
 
+    /**
+     * @since 3.5.13
+     */
+    @Getter
+    private ApplicationContext applicationContext;
+
     @Setter
     private GlobalConfig globalConfig;
 
@@ -523,6 +532,20 @@ public class MybatisSqlSessionFactoryBean implements FactoryBean<SqlSessionFacto
         }
     }
 
+    /**
+     * 设置上下文对象
+     * <p>注意: 手动构建的bean对象需要手动赋值,通过xml属性初始化的会自动赋值</p>
+     * @since 3.5.13
+     * @param applicationContext ApplicationContext
+     */
+    @Override
+    public void setApplicationContext(ApplicationContext applicationContext) {
+        this.applicationContext = applicationContext;
+        if (CompatibleHelper.hasCompatibleSet()) {
+            CompatibleHelper.getCompatibleSet().setContext(applicationContext);
+        }
+    }
+
     /**
      * {@inheritDoc}
      */

+ 7 - 4
spring-boot-starter/mybatis-plus-spring-boot-autoconfigure/src/main/java/com/baomidou/mybatisplus/autoconfigure/MybatisPlusAutoConfiguration.java

@@ -24,7 +24,6 @@ import com.baomidou.mybatisplus.core.handlers.PostInitTableInfoHandler;
 import com.baomidou.mybatisplus.core.incrementer.IKeyGenerator;
 import com.baomidou.mybatisplus.core.incrementer.IdentifierGenerator;
 import com.baomidou.mybatisplus.core.injector.ISqlInjector;
-import com.baomidou.mybatisplus.core.spi.CompatibleHelper;
 import com.baomidou.mybatisplus.extension.spring.MybatisPlusApplicationContextAware;
 import com.baomidou.mybatisplus.extension.spring.MybatisSqlSessionFactoryBean;
 import org.apache.ibatis.annotations.Mapper;
@@ -149,9 +148,6 @@ public class MybatisPlusAutoConfiguration implements InitializingBean {
         if (!CollectionUtils.isEmpty(mybatisPlusPropertiesCustomizers)) {
             mybatisPlusPropertiesCustomizers.forEach(i -> i.customize(properties));
         }
-        if (CompatibleHelper.hasCompatibleSet()) {
-            CompatibleHelper.getCompatibleSet().setContext(applicationContext);
-        }
         checkConfigFileExists();
     }
 
@@ -169,6 +165,7 @@ public class MybatisPlusAutoConfiguration implements InitializingBean {
         MybatisSqlSessionFactoryBean factory = new MybatisSqlSessionFactoryBean();
         factory.setDataSource(dataSource);
         factory.setVfs(SpringBootVFS.class);
+        factory.setApplicationContext(this.applicationContext);
         if (StringUtils.hasText(this.properties.getConfigLocation())) {
             factory.setConfigLocation(this.resourceLoader.getResource(this.properties.getConfigLocation()));
         }
@@ -380,7 +377,13 @@ public class MybatisPlusAutoConfiguration implements InitializingBean {
         }
     }
 
+    /**
+     * @deprecated 3.5.13
+     * @see MybatisSqlSessionFactoryBean#setApplicationContext(ApplicationContext)
+     * @return MybatisPlusApplicationContextAware
+     */
     @Bean
+    @Deprecated
     @ConditionalOnMissingBean(MybatisPlusApplicationContextAware.class)
     public MybatisPlusApplicationContextAware mybatisPlusSpringApplicationContextAware() {
         return new MybatisPlusApplicationContextAware();