hubin 7 лет назад
Родитель
Сommit
70df0c14af

+ 20 - 0
mybatis-plus-boot-starter/src/main/java/com/baomidou/mybatisplus/autoconfigure/ConfigurationCustomizer.java

@@ -0,0 +1,20 @@
+package com.baomidou.mybatisplus.autoconfigure;
+
+import org.apache.ibatis.session.Configuration;
+
+/**
+ * Callback interface that can be customized a {@link Configuration} object generated on auto-configuration.
+ *
+ * @author Kazuki Shimizu
+ * @since 1.2.1
+ */
+@FunctionalInterface
+public interface ConfigurationCustomizer {
+
+    /**
+     * Customize the given a {@link Configuration} object.
+     * @param configuration the configuration object to customize
+     */
+    void customize(Configuration configuration);
+
+}

+ 273 - 0
mybatis-plus-boot-starter/src/main/java/com/baomidou/mybatisplus/autoconfigure/MybatisPlusAutoConfiguration.java

@@ -0,0 +1,273 @@
+package com.baomidou.mybatisplus.autoconfigure;
+
+
+import java.util.List;
+
+import javax.annotation.PostConstruct;
+import javax.sql.DataSource;
+
+import org.apache.ibatis.annotations.Mapper;
+import org.apache.ibatis.mapping.DatabaseIdProvider;
+import org.apache.ibatis.plugin.Interceptor;
+import org.apache.ibatis.session.ExecutorType;
+import org.apache.ibatis.session.SqlSessionFactory;
+import org.mybatis.spring.SqlSessionFactoryBean;
+import org.mybatis.spring.SqlSessionTemplate;
+import org.mybatis.spring.mapper.ClassPathMapperScanner;
+import org.mybatis.spring.mapper.MapperFactoryBean;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+import org.springframework.beans.BeansException;
+import org.springframework.beans.factory.BeanFactory;
+import org.springframework.beans.factory.BeanFactoryAware;
+import org.springframework.beans.factory.ObjectProvider;
+import org.springframework.beans.factory.support.BeanDefinitionRegistry;
+import org.springframework.boot.autoconfigure.AutoConfigurationPackages;
+import org.springframework.boot.autoconfigure.AutoConfigureAfter;
+import org.springframework.boot.autoconfigure.EnableAutoConfiguration;
+import org.springframework.boot.autoconfigure.condition.ConditionalOnClass;
+import org.springframework.boot.autoconfigure.condition.ConditionalOnMissingBean;
+import org.springframework.boot.autoconfigure.condition.ConditionalOnSingleCandidate;
+import org.springframework.boot.autoconfigure.jdbc.DataSourceAutoConfiguration;
+import org.springframework.boot.context.properties.EnableConfigurationProperties;
+import org.springframework.context.ApplicationContext;
+import org.springframework.context.ResourceLoaderAware;
+import org.springframework.context.annotation.Bean;
+import org.springframework.context.annotation.Import;
+import org.springframework.context.annotation.ImportBeanDefinitionRegistrar;
+import org.springframework.core.io.Resource;
+import org.springframework.core.io.ResourceLoader;
+import org.springframework.core.type.AnnotationMetadata;
+import org.springframework.util.Assert;
+import org.springframework.util.CollectionUtils;
+import org.springframework.util.ObjectUtils;
+import org.springframework.util.StringUtils;
+
+import com.baomidou.mybatisplus.core.MybatisConfiguration;
+import com.baomidou.mybatisplus.core.MybatisXMLLanguageDriver;
+import com.baomidou.mybatisplus.core.config.GlobalConfig;
+import com.baomidou.mybatisplus.core.handlers.MetaObjectHandler;
+import com.baomidou.mybatisplus.core.incrementer.IKeyGenerator;
+import com.baomidou.mybatisplus.core.injector.ISqlInjector;
+import com.baomidou.mybatisplus.extension.spring.MybatisSqlSessionFactoryBean;
+
+/**
+ * {@link EnableAutoConfiguration Auto-Configuration} for Mybatis. Contributes a
+ * {@link SqlSessionFactory} and a {@link SqlSessionTemplate}.
+ * <p>
+ * If {@link org.mybatis.spring.annotation.MapperScan} is used, or a
+ * configuration file is specified as a property, those will be considered,
+ * otherwise this auto-configuration will attempt to register mappers based on
+ * the interface definitions in or under the root auto-configuration package.
+ *
+ * @author Eddú Meléndez
+ * @author Josh Long
+ * @author Kazuki Shimizu
+ * @author Eduardo Macarrón
+ */
+@org.springframework.context.annotation.Configuration
+@ConditionalOnClass({SqlSessionFactory.class, SqlSessionFactoryBean.class})
+@ConditionalOnSingleCandidate(DataSource.class)
+@EnableConfigurationProperties(MybatisPlusProperties.class)
+@AutoConfigureAfter(DataSourceAutoConfiguration.class)
+public class MybatisPlusAutoConfiguration {
+
+    private static final Logger logger = LoggerFactory.getLogger(MybatisPlusAutoConfiguration.class);
+
+    private final MybatisPlusProperties properties;
+
+    private final Interceptor[] interceptors;
+
+    private final ResourceLoader resourceLoader;
+
+    private final DatabaseIdProvider databaseIdProvider;
+
+    private final List<ConfigurationCustomizer> configurationCustomizers;
+
+    private final ApplicationContext applicationContext;
+
+    public MybatisPlusAutoConfiguration(MybatisPlusProperties properties,
+                                        ObjectProvider<Interceptor[]> interceptorsProvider,
+                                        ResourceLoader resourceLoader,
+                                        ObjectProvider<DatabaseIdProvider> databaseIdProvider,
+                                        ObjectProvider<List<ConfigurationCustomizer>> configurationCustomizersProvider,
+                                        ApplicationContext applicationContext) {
+        this.properties = properties;
+        this.interceptors = interceptorsProvider.getIfAvailable();
+        this.resourceLoader = resourceLoader;
+        this.databaseIdProvider = databaseIdProvider.getIfAvailable();
+        this.configurationCustomizers = configurationCustomizersProvider.getIfAvailable();
+        this.applicationContext = applicationContext;
+    }
+
+    @PostConstruct
+    public void checkConfigFileExists() {
+        if (this.properties.isCheckConfigLocation() && StringUtils.hasText(this.properties.getConfigLocation())) {
+            Resource resource = this.resourceLoader.getResource(this.properties.getConfigLocation());
+            Assert.state(resource.exists(), "Cannot find config location: " + resource
+                + " (please add config file or check your Mybatis configuration)");
+        }
+    }
+
+    @Bean
+    @ConditionalOnMissingBean
+    public SqlSessionFactory sqlSessionFactory(DataSource dataSource) throws Exception {
+        MybatisSqlSessionFactoryBean factory = new MybatisSqlSessionFactoryBean();
+        factory.setDataSource(dataSource);
+        factory.setVfs(SpringBootVFS.class);
+        if (StringUtils.hasText(this.properties.getConfigLocation())) {
+            factory.setConfigLocation(this.resourceLoader.getResource(this.properties.getConfigLocation()));
+        }
+        applyConfiguration(factory);
+        if (this.properties.getConfigurationProperties() != null) {
+            factory.setConfigurationProperties(this.properties.getConfigurationProperties());
+        }
+        if (!ObjectUtils.isEmpty(this.interceptors)) {
+            factory.setPlugins(this.interceptors);
+        }
+        if (this.databaseIdProvider != null) {
+            factory.setDatabaseIdProvider(this.databaseIdProvider);
+        }
+        if (StringUtils.hasLength(this.properties.getTypeAliasesPackage())) {
+            factory.setTypeAliasesPackage(this.properties.getTypeAliasesPackage());
+        }
+        // TODO 自定义枚举包
+        if (StringUtils.hasLength(this.properties.getTypeEnumsPackage())) {
+            factory.setTypeEnumsPackage(this.properties.getTypeEnumsPackage());
+        }
+        if (this.properties.getTypeAliasesSuperType() != null) {
+            factory.setTypeAliasesSuperType(this.properties.getTypeAliasesSuperType());
+        }
+        if (StringUtils.hasLength(this.properties.getTypeHandlersPackage())) {
+            factory.setTypeHandlersPackage(this.properties.getTypeHandlersPackage());
+        }
+        if (!ObjectUtils.isEmpty(this.properties.resolveMapperLocations())) {
+            factory.setMapperLocations(this.properties.resolveMapperLocations());
+        }
+        GlobalConfig globalConfig;
+        if (!ObjectUtils.isEmpty(this.properties.getGlobalConfig())) {
+            globalConfig = this.properties.getGlobalConfig();
+        } else {
+            globalConfig = new GlobalConfig();
+        }
+        //注入填充器
+        if (this.applicationContext.getBeanNamesForType(MetaObjectHandler.class,
+            false, false).length > 0) {
+            MetaObjectHandler metaObjectHandler = this.applicationContext.getBean(MetaObjectHandler.class);
+            globalConfig.setMetaObjectHandler(metaObjectHandler);
+        }
+        //注入主键生成器
+        if (this.applicationContext.getBeanNamesForType(IKeyGenerator.class, false,
+            false).length > 0) {
+            IKeyGenerator keyGenerator = this.applicationContext.getBean(IKeyGenerator.class);
+            globalConfig.setKeyGenerator(keyGenerator);
+        }
+        //注入sql注入器
+        if (this.applicationContext.getBeanNamesForType(ISqlInjector.class, false,
+            false).length > 0) {
+            ISqlInjector iSqlInjector = this.applicationContext.getBean(ISqlInjector.class);
+            globalConfig.setSqlInjector(iSqlInjector);
+        }
+        factory.setGlobalConfig(globalConfig);
+        return factory.getObject();
+    }
+
+    private void applyConfiguration(MybatisSqlSessionFactoryBean factory) {
+        MybatisConfiguration configuration = this.properties.getConfiguration();
+        if (configuration == null && !StringUtils.hasText(this.properties.getConfigLocation())) {
+            configuration = new MybatisConfiguration();
+        }
+        if (configuration != null && !CollectionUtils.isEmpty(this.configurationCustomizers)) {
+            for (ConfigurationCustomizer customizer : this.configurationCustomizers) {
+                customizer.customize(configuration);
+            }
+        }
+        // TODO 自定义配置
+        if (null != configuration) {
+            configuration.setDefaultScriptingLanguage(MybatisXMLLanguageDriver.class);
+        }
+        factory.setConfiguration(configuration);
+    }
+
+    @Bean
+    @ConditionalOnMissingBean
+    public SqlSessionTemplate sqlSessionTemplate(SqlSessionFactory sqlSessionFactory) {
+        ExecutorType executorType = this.properties.getExecutorType();
+        if (executorType != null) {
+            return new SqlSessionTemplate(sqlSessionFactory, executorType);
+        } else {
+            return new SqlSessionTemplate(sqlSessionFactory);
+        }
+    }
+
+    /**
+     * This will just scan the same base package as Spring Boot does. If you want
+     * more power, you can explicitly use
+     * {@link org.mybatis.spring.annotation.MapperScan} but this will get typed
+     * mappers working correctly, out-of-the-box, similar to using Spring Data JPA
+     * repositories.
+     */
+    public static class AutoConfiguredMapperScannerRegistrar
+        implements BeanFactoryAware, ImportBeanDefinitionRegistrar, ResourceLoaderAware {
+
+        private BeanFactory beanFactory;
+
+        private ResourceLoader resourceLoader;
+
+        @Override
+        public void registerBeanDefinitions(AnnotationMetadata importingClassMetadata, BeanDefinitionRegistry registry) {
+
+            logger.debug("Searching for mappers annotated with @Mapper");
+
+            ClassPathMapperScanner scanner = new ClassPathMapperScanner(registry);
+
+            try {
+                if (this.resourceLoader != null) {
+                    scanner.setResourceLoader(this.resourceLoader);
+                }
+
+                List<String> packages = AutoConfigurationPackages.get(this.beanFactory);
+                if (logger.isDebugEnabled()) {
+                    packages.forEach(pkg -> logger.debug("Using auto-configuration base package '{}'", pkg));
+                }
+
+                scanner.setAnnotationClass(Mapper.class);
+                scanner.registerFilters();
+                scanner.doScan(StringUtils.toStringArray(packages));
+            } catch (IllegalStateException ex) {
+                logger.debug("Could not determine auto-configuration package, automatic mapper scanning disabled.", ex);
+            }
+        }
+
+        @Override
+        public void setBeanFactory(BeanFactory beanFactory) throws BeansException {
+            this.beanFactory = beanFactory;
+        }
+
+        @Override
+        public void setResourceLoader(ResourceLoader resourceLoader) {
+            this.resourceLoader = resourceLoader;
+        }
+    }
+
+    /**
+     * {@link org.mybatis.spring.annotation.MapperScan} ultimately ends up
+     * creating instances of {@link MapperFactoryBean}. If
+     * {@link org.mybatis.spring.annotation.MapperScan} is used then this
+     * auto-configuration is not needed. If it is _not_ used, however, then this
+     * will bring in a bean registrar and automatically register components based
+     * on the same component-scanning path as Spring Boot itself.
+     */
+    @org.springframework.context.annotation.Configuration
+    @Import({AutoConfiguredMapperScannerRegistrar.class})
+    @ConditionalOnMissingBean(MapperFactoryBean.class)
+    public static class MapperScannerRegistrarNotFoundConfiguration {
+
+        @PostConstruct
+        public void afterPropertiesSet() {
+            logger.debug("No {} found.", MapperFactoryBean.class.getName());
+        }
+    }
+
+}

+ 208 - 0
mybatis-plus-boot-starter/src/main/java/com/baomidou/mybatisplus/autoconfigure/MybatisPlusProperties.java

@@ -0,0 +1,208 @@
+package com.baomidou.mybatisplus.autoconfigure;
+
+import java.io.IOException;
+import java.util.Optional;
+import java.util.Properties;
+import java.util.stream.Stream;
+
+import org.apache.ibatis.session.ExecutorType;
+import org.springframework.boot.context.properties.ConfigurationProperties;
+import org.springframework.boot.context.properties.NestedConfigurationProperty;
+import org.springframework.core.io.Resource;
+import org.springframework.core.io.support.PathMatchingResourcePatternResolver;
+import org.springframework.core.io.support.ResourcePatternResolver;
+
+import com.baomidou.mybatisplus.core.MybatisConfiguration;
+import com.baomidou.mybatisplus.core.config.GlobalConfig;
+
+/**
+ * Configuration properties for MyBatis.
+ *
+ * @author Eddú Meléndez
+ * @author Kazuki Shimizu
+ */
+@ConfigurationProperties(prefix = "mybatis-plus")
+public class MybatisPlusProperties {
+
+    private static final ResourcePatternResolver resourceResolver = new PathMatchingResourcePatternResolver();
+
+    /**
+     * Location of MyBatis xml config file.
+     */
+    private String configLocation;
+
+    /**
+     * Locations of MyBatis mapper files.
+     */
+    private String[] mapperLocations;
+
+    /**
+     * Packages to search type aliases. (Package delimiters are ",; \t\n")
+     */
+    private String typeAliasesPackage;
+
+    /**
+     * The super class for filtering type alias.
+     * If this not specifies, the MyBatis deal as type alias all classes that searched from typeAliasesPackage.
+     */
+    private Class<?> typeAliasesSuperType;
+
+    /**
+     * Packages to search for type handlers. (Package delimiters are ",; \t\n")
+     */
+    private String typeHandlersPackage;
+
+    /**
+     * TODO 枚举包
+     */
+    private String typeEnumsPackage;
+
+    /**
+     * Indicates whether perform presence check of the MyBatis xml config file.
+     */
+    private boolean checkConfigLocation = false;
+
+    /**
+     * Execution mode for {@link org.mybatis.spring.SqlSessionTemplate}.
+     */
+    private ExecutorType executorType;
+
+    /**
+     * Externalized properties for MyBatis configuration.
+     */
+    private Properties configurationProperties;
+
+    /**
+     * A Configuration object for customize default settings. If {@link #configLocation}
+     * is specified, this property is not used.
+     */
+    @NestedConfigurationProperty
+    private MybatisConfiguration configuration;
+
+    /**
+     * TODO 全局枚举
+     */
+    @NestedConfigurationProperty
+    private GlobalConfig globalConfig;
+
+    /**
+     * @since 1.1.0
+     */
+    public String getConfigLocation() {
+        return this.configLocation;
+    }
+
+    /**
+     * @since 1.1.0
+     */
+    public void setConfigLocation(String configLocation) {
+        this.configLocation = configLocation;
+    }
+
+    public String[] getMapperLocations() {
+        return this.mapperLocations;
+    }
+
+    public void setMapperLocations(String[] mapperLocations) {
+        this.mapperLocations = mapperLocations;
+    }
+
+    public String getTypeHandlersPackage() {
+        return this.typeHandlersPackage;
+    }
+
+    public void setTypeHandlersPackage(String typeHandlersPackage) {
+        this.typeHandlersPackage = typeHandlersPackage;
+    }
+
+    public String getTypeEnumsPackage() {
+        return typeEnumsPackage;
+    }
+
+    public void setTypeEnumsPackage(String typeEnumsPackage) {
+        this.typeEnumsPackage = typeEnumsPackage;
+    }
+
+    public String getTypeAliasesPackage() {
+        return this.typeAliasesPackage;
+    }
+
+    public void setTypeAliasesPackage(String typeAliasesPackage) {
+        this.typeAliasesPackage = typeAliasesPackage;
+    }
+
+    /**
+     * @since 1.3.3
+     */
+    public Class<?> getTypeAliasesSuperType() {
+        return typeAliasesSuperType;
+    }
+
+    /**
+     * @since 1.3.3
+     */
+    public void setTypeAliasesSuperType(Class<?> typeAliasesSuperType) {
+        this.typeAliasesSuperType = typeAliasesSuperType;
+    }
+
+    public boolean isCheckConfigLocation() {
+        return this.checkConfigLocation;
+    }
+
+    public void setCheckConfigLocation(boolean checkConfigLocation) {
+        this.checkConfigLocation = checkConfigLocation;
+    }
+
+    public ExecutorType getExecutorType() {
+        return this.executorType;
+    }
+
+    public void setExecutorType(ExecutorType executorType) {
+        this.executorType = executorType;
+    }
+
+    /**
+     * @since 1.2.0
+     */
+    public Properties getConfigurationProperties() {
+        return configurationProperties;
+    }
+
+    /**
+     * @since 1.2.0
+     */
+    public void setConfigurationProperties(Properties configurationProperties) {
+        this.configurationProperties = configurationProperties;
+    }
+
+    public MybatisConfiguration getConfiguration() {
+        return configuration;
+    }
+
+    public void setConfiguration(MybatisConfiguration configuration) {
+        this.configuration = configuration;
+    }
+
+    public GlobalConfig getGlobalConfig() {
+        return globalConfig;
+    }
+
+    public void setGlobalConfig(GlobalConfig globalConfig) {
+        this.globalConfig = globalConfig;
+    }
+
+    public Resource[] resolveMapperLocations() {
+        return Stream.of(Optional.ofNullable(this.mapperLocations).orElse(new String[0]))
+            .flatMap(location -> Stream.of(getResources(location)))
+            .toArray(Resource[]::new);
+    }
+
+    private Resource[] getResources(String location) {
+        try {
+            return resourceResolver.getResources(location);
+        } catch (IOException e) {
+            return new Resource[0];
+        }
+    }
+
+}

+ 53 - 0
mybatis-plus-boot-starter/src/main/java/com/baomidou/mybatisplus/autoconfigure/SpringBootVFS.java

@@ -0,0 +1,53 @@
+package com.baomidou.mybatisplus.autoconfigure;
+
+
+import java.io.IOException;
+import java.io.UncheckedIOException;
+import java.net.URL;
+import java.util.List;
+import java.util.stream.Collectors;
+import java.util.stream.Stream;
+
+import org.apache.ibatis.io.VFS;
+
+import org.springframework.core.io.Resource;
+import org.springframework.core.io.support.PathMatchingResourcePatternResolver;
+import org.springframework.core.io.support.ResourcePatternResolver;
+
+/**
+ * @author Hans Westerbeek
+ * @author Eddú Meléndez
+ * @author Kazuki Shimizu
+ */
+public class SpringBootVFS extends VFS {
+
+    private final ResourcePatternResolver resourceResolver;
+
+    public SpringBootVFS() {
+        this.resourceResolver = new PathMatchingResourcePatternResolver(getClass().getClassLoader());
+    }
+
+    @Override
+    public boolean isValid() {
+        return true;
+    }
+
+    @Override
+    protected List<String> list(URL url, String path) throws IOException {
+        Resource[] resources = resourceResolver.getResources("classpath*:" + path + "/**/*.class");
+        return Stream.of(resources)
+            .map(resource -> preserveSubpackageName(resource, path))
+            .collect(Collectors.toList());
+    }
+
+    private static String preserveSubpackageName(final Resource resource, final String rootPath) {
+        try {
+            final String uriStr = resource.getURI().toString();
+            final int start = uriStr.indexOf(rootPath);
+            return uriStr.substring(start);
+        } catch (IOException e) {
+            throw new UncheckedIOException(e);
+        }
+    }
+
+}

+ 4 - 0
mybatis-plus-boot-starter/src/main/java/com/baomidou/mybatisplus/autoconfigure/package-info.java

@@ -0,0 +1,4 @@
+/**
+ * Spring Boot Stater
+ */
+package com.baomidou.mybatisplus.autoconfigure;

+ 120 - 0
mybatis-plus-boot-starter/src/main/resources/META-INF/additional-spring-configuration-metadata.json

@@ -0,0 +1,120 @@
+{
+  "hints": [{
+    "sourceType": "com.baomidou.mybatisplus.spring.boot.starter.GlobalConfig",
+    "name": "mybatis-plus.global-config.id-type",
+    "type": "java.lang.Integer",
+    "description": "主键类型",
+    "values": [
+      {
+        "value": "0",
+        "description": "数据库ID自增"
+      }, {
+        "value": "1",
+        "description": "用户输入ID"
+      }, {
+        "value": "2",
+        "description": "分布式全局唯一ID"
+      }, {
+        "value": "3",
+        "description": "全局唯一ID-UUID"
+      }
+    ]
+  },{
+      "sourceType": "com.baomidou.mybatisplus.spring.boot.starter.GlobalConfig",
+      "name": "mybatis-plus.global-config.field-strategy",
+      "type": "java.lang.Integer",
+      "description": "字段验证策略",
+      "values": [
+        {
+          "value": "0",
+          "description": "忽略判断"
+        }, {
+          "value": "1",
+          "description": "非 NULL 判断"
+        }, {
+          "value": "2",
+          "description": "非空判断"
+        }
+    ]
+  }],
+  "groups": [
+    {
+      "sourceType": "com.baomidou.mybatisplus.spring.boot.starter.MybatisPlusProperties",
+      "name": "mybatis-plus",
+      "type": "com.baomidou.mybatisplus.spring.boot.starter.MybatisPlusProperties"
+    },
+    {
+      "sourceType": "com.baomidou.mybatisplus.spring.boot.starter.MybatisPlusProperties",
+      "name": "mybatis-plus.configuration",
+      "sourceMethod": "getConfiguration()",
+      "type": "com.baomidou.mybatisplus.MybatisConfiguration"
+    },
+    {
+      "sourceType": "com.baomidou.mybatisplus.spring.boot.starter.MybatisPlusProperties",
+      "name": "mybatis-plus.global-config",
+      "sourceMethod": "getGlobalConfig()",
+      "type": "com.baomidou.mybatisplus.spring.boot.starter.GlobalConfig"
+    }
+  ],
+  "properties": [
+    {
+      "sourceType": "com.baomidou.mybatisplus.spring.boot.starter.GlobalConfig",
+      "name": "mybatis-plus.global-config.capital-mode",
+      "type": "java.lang.Boolean",
+      "description": "是否大写命名"
+    },
+    {
+      "sourceType": "com.baomidou.mybatisplus.spring.boot.starter.GlobalConfig",
+      "name": "mybatis-plus.global-config.db-column-underline",
+      "type": "java.lang.Boolean",
+      "description": "是否使用下划线命名"
+    },
+    {
+      "sourceType": "com.baomidou.mybatisplus.spring.boot.starter.GlobalConfig",
+      "name": "mybatis-plus.global-config.identifier-quote",
+      "type": "java.lang.String",
+      "description": "标识符"
+    },
+    {
+      "sourceType": "com.baomidou.mybatisplus.spring.boot.starter.GlobalConfig",
+      "name": "mybatis-plus.global-config.key-generator",
+      "type": "java.lang.String",
+      "description": "表关键词key生成器"
+    },
+    {
+      "sourceType": "com.baomidou.mybatisplus.spring.boot.starter.GlobalConfig",
+      "name": "mybatis-plus.global-config.logic-delete-value",
+      "type": "java.lang.String",
+      "description": "逻辑删除全局值"
+    },
+    {
+      "sourceType": "com.baomidou.mybatisplus.spring.boot.starter.GlobalConfig",
+      "name": "mybatis-plus.global-config.logic-not-delete-value",
+      "type": "java.lang.String",
+      "description": "逻辑未删除全局值"
+    },
+    {
+      "sourceType": "com.baomidou.mybatisplus.spring.boot.starter.GlobalConfig",
+      "name": "mybatis-plus.global-config.meta-object-handler",
+      "type": "java.lang.String",
+      "description": "元对象字段填充控制器"
+    },
+    {
+      "sourceType": "com.baomidou.mybatisplus.spring.boot.starter.GlobalConfig",
+      "name": "mybatis-plus.global-config.refresh-mapper",
+      "type": "java.lang.Boolean",
+      "description": "是否动态刷新mapper"
+    },
+    {
+      "sourceType": "com.baomidou.mybatisplus.spring.boot.starter.GlobalConfig",
+      "name": "mybatis-plus.global-config.sql-injector",
+      "type": "java.lang.String",
+      "description": "SQL注入器"
+    },{
+      "sourceType": "com.baomidou.mybatisplus.spring.boot.starter.MybatisPlusProperties",
+      "name": "mybatis-plus.type-enums-package",
+      "type": "java.lang.String",
+      "description": "自定义枚举包"
+    }
+  ]
+}

+ 1 - 0
mybatis-plus-boot-starter/src/main/resources/META-INF/spring-devtools.properties

@@ -0,0 +1 @@
+restart.include.mybatis-plus=/mybatis-plus-[\\w-]+\.jar

+ 3 - 0
mybatis-plus-boot-starter/src/main/resources/META-INF/spring.factories

@@ -0,0 +1,3 @@
+# Auto Configure
+org.springframework.boot.autoconfigure.EnableAutoConfiguration=\
+com.baomidou.mybatisplus.autoconfigure.MybatisPlusAutoConfiguration

+ 5 - 0
mybatis-plus-core/src/main/java/com/baomidou/mybatisplus/core/config/GlobalConfig.java

@@ -16,6 +16,7 @@
 package com.baomidou.mybatisplus.core.config;
 
 import com.baomidou.mybatisplus.core.handlers.MetaObjectHandler;
+import com.baomidou.mybatisplus.core.incrementer.IKeyGenerator;
 import com.baomidou.mybatisplus.core.injector.ISqlInjector;
 import com.baomidou.mybatisplus.core.toolkit.GlobalConfigUtils;
 import lombok.Data;
@@ -53,6 +54,10 @@ public class GlobalConfig implements Serializable {
      * SQL注入器
      */
     private ISqlInjector sqlInjector;
+    /**
+     * 表关键词 key 生成器
+     */
+    private IKeyGenerator keyGenerator;
     /**
      * 单例重用SqlSession
      */