Movatterモバイル変換


[0]ホーム

URL:


Skip to content

Navigation Menu

Sign in
Appearance settings

Search code, repositories, users, issues, pull requests...

Provide feedback

We read every piece of feedback, and take your input very seriously.

Saved searches

Use saved searches to filter your results more quickly

Sign up
Appearance settings

MyBatisNativeConfiguration.java

Kazuki Shimizu edited this pageJun 6, 2023 ·3 revisions

This class is a configuration class for building a native image with MyBatis. If you want to use the MyBatis on Native image, please this class copy to your application.

NOTE:

This configuration will move tomybatis-spring-native.

packagecom.example.mybatisnativesample;importorg.apache.commons.logging.LogFactory;importorg.apache.ibatis.annotations.DeleteProvider;importorg.apache.ibatis.annotations.InsertProvider;importorg.apache.ibatis.annotations.SelectProvider;importorg.apache.ibatis.annotations.UpdateProvider;importorg.apache.ibatis.cache.decorators.FifoCache;importorg.apache.ibatis.cache.decorators.LruCache;importorg.apache.ibatis.cache.decorators.SoftCache;importorg.apache.ibatis.cache.decorators.WeakCache;importorg.apache.ibatis.cache.impl.PerpetualCache;importorg.apache.ibatis.javassist.util.proxy.ProxyFactory;importorg.apache.ibatis.javassist.util.proxy.RuntimeSupport;importorg.apache.ibatis.logging.Log;importorg.apache.ibatis.logging.commons.JakartaCommonsLoggingImpl;importorg.apache.ibatis.logging.jdk14.Jdk14LoggingImpl;importorg.apache.ibatis.logging.log4j2.Log4j2Impl;importorg.apache.ibatis.logging.nologging.NoLoggingImpl;importorg.apache.ibatis.logging.slf4j.Slf4jImpl;importorg.apache.ibatis.logging.stdout.StdOutImpl;importorg.apache.ibatis.reflection.TypeParameterResolver;importorg.apache.ibatis.scripting.defaults.RawLanguageDriver;importorg.apache.ibatis.scripting.xmltags.XMLLanguageDriver;importorg.apache.ibatis.session.SqlSessionFactory;importorg.mybatis.spring.SqlSessionFactoryBean;importorg.mybatis.spring.mapper.MapperFactoryBean;importorg.mybatis.spring.mapper.MapperScannerConfigurer;importorg.springframework.aot.hint.MemberCategory;importorg.springframework.aot.hint.RuntimeHints;importorg.springframework.aot.hint.RuntimeHintsRegistrar;importorg.springframework.beans.PropertyValue;importorg.springframework.beans.factory.BeanFactory;importorg.springframework.beans.factory.BeanFactoryAware;importorg.springframework.beans.factory.aot.BeanFactoryInitializationAotContribution;importorg.springframework.beans.factory.aot.BeanFactoryInitializationAotProcessor;importorg.springframework.beans.factory.aot.BeanRegistrationExcludeFilter;importorg.springframework.beans.factory.config.BeanDefinition;importorg.springframework.beans.factory.config.ConfigurableBeanFactory;importorg.springframework.beans.factory.config.ConfigurableListableBeanFactory;importorg.springframework.beans.factory.support.MergedBeanDefinitionPostProcessor;importorg.springframework.beans.factory.support.RegisteredBean;importorg.springframework.beans.factory.support.RootBeanDefinition;importorg.springframework.context.annotation.Bean;importorg.springframework.context.annotation.Configuration;importorg.springframework.context.annotation.ImportRuntimeHints;importorg.springframework.core.ResolvableType;importorg.springframework.util.ClassUtils;importorg.springframework.util.ReflectionUtils;importjava.lang.annotation.Annotation;importjava.lang.reflect.Method;importjava.lang.reflect.ParameterizedType;importjava.lang.reflect.Type;importjava.util.ArrayList;importjava.util.HashMap;importjava.util.HashSet;importjava.util.Map;importjava.util.Set;importjava.util.TreeSet;importjava.util.function.Function;importjava.util.stream.Collectors;importjava.util.stream.Stream;@Configuration(proxyBeanMethods =false)@ImportRuntimeHints(MyBatisNativeConfiguration.MyBaitsRuntimeHintsRegistrar.class)publicclassMyBatisNativeConfiguration {@BeanMyBatisBeanFactoryInitializationAotProcessormyBatisBeanFactoryInitializationAotProcessor() {returnnewMyBatisBeanFactoryInitializationAotProcessor();  }@BeanstaticMyBatisMapperFactoryBeanPostProcessormyBatisMapperFactoryBeanPostProcessor() {returnnewMyBatisMapperFactoryBeanPostProcessor();  }staticclassMyBaitsRuntimeHintsRegistrarimplementsRuntimeHintsRegistrar {@OverridepublicvoidregisterHints(RuntimeHintshints,ClassLoaderclassLoader) {Stream.of(RawLanguageDriver.class,XMLLanguageDriver.class,RuntimeSupport.class,ProxyFactory.class,Slf4jImpl.class,Log.class,JakartaCommonsLoggingImpl.class,Log4j2Impl.class,Jdk14LoggingImpl.class,StdOutImpl.class,NoLoggingImpl.class,SqlSessionFactory.class,PerpetualCache.class,FifoCache.class,LruCache.class,SoftCache.class,WeakCache.class,SqlSessionFactoryBean.class,ArrayList.class,HashMap.class,TreeSet.class,HashSet.class      ).forEach(x ->hints.reflection().registerType(x,MemberCategory.values()));Stream.of("org/apache/ibatis/builder/xml/*.dtd","org/apache/ibatis/builder/xml/*.xsd"      ).forEach(hints.resources()::registerPattern);    }  }staticclassMyBatisBeanFactoryInitializationAotProcessorimplementsBeanFactoryInitializationAotProcessor,BeanRegistrationExcludeFilter {privatefinalSet<Class<?>>excludeClasses =newHashSet<>();MyBatisBeanFactoryInitializationAotProcessor() {excludeClasses.add(MapperScannerConfigurer.class);    }@OverridepublicbooleanisExcludedFromAotProcessing(RegisteredBeanregisteredBean) {returnexcludeClasses.contains(registeredBean.getBeanClass());    }@OverridepublicBeanFactoryInitializationAotContributionprocessAheadOfTime(ConfigurableListableBeanFactorybeanFactory) {String[]beanNames =beanFactory.getBeanNamesForType(MapperFactoryBean.class);if (beanNames.length ==0) {returnnull;      }return (context,code) -> {RuntimeHintshints =context.getRuntimeHints();for (StringbeanName :beanNames) {BeanDefinitionbeanDefinition =beanFactory.getBeanDefinition(beanName.substring(1));PropertyValuemapperInterface =beanDefinition.getPropertyValues().getPropertyValue("mapperInterface");if (mapperInterface !=null &&mapperInterface.getValue() !=null) {Class<?>mapperInterfaceType = (Class<?>)mapperInterface.getValue();if (mapperInterfaceType !=null) {registerReflectionTypeIfNecessary(mapperInterfaceType,hints);hints.proxies().registerJdkProxy(mapperInterfaceType);hints.resources()                  .registerPattern(mapperInterfaceType.getName().replace('.','/').concat(".xml"));registerMapperRelationships(mapperInterfaceType,hints);            }          }        }      };    }privatevoidregisterMapperRelationships(Class<?>mapperInterfaceType,RuntimeHintshints) {Method[]methods =ReflectionUtils.getAllDeclaredMethods(mapperInterfaceType);for (Methodmethod :methods) {if (method.getDeclaringClass() !=Object.class) {ReflectionUtils.makeAccessible(method);registerSqlProviderTypes(method,hints,SelectProvider.class,SelectProvider::value,SelectProvider::type);registerSqlProviderTypes(method,hints,InsertProvider.class,InsertProvider::value,InsertProvider::type);registerSqlProviderTypes(method,hints,UpdateProvider.class,UpdateProvider::value,UpdateProvider::type);registerSqlProviderTypes(method,hints,DeleteProvider.class,DeleteProvider::value,DeleteProvider::type);Class<?>returnType =MyBatisMapperTypeUtils.resolveReturnClass(mapperInterfaceType,method);registerReflectionTypeIfNecessary(returnType,hints);MyBatisMapperTypeUtils.resolveParameterClasses(mapperInterfaceType,method)              .forEach(x ->registerReflectionTypeIfNecessary(x,hints));        }      }    }@SafeVarargsprivate <TextendsAnnotation>voidregisterSqlProviderTypes(Methodmethod,RuntimeHintshints,Class<T>annotationType,Function<T,Class<?>>...providerTypeResolvers) {for (Tannotation :method.getAnnotationsByType(annotationType)) {for (Function<T,Class<?>>providerTypeResolver :providerTypeResolvers) {registerReflectionTypeIfNecessary(providerTypeResolver.apply(annotation),hints);        }      }    }privatevoidregisterReflectionTypeIfNecessary(Class<?>type,RuntimeHintshints) {if (!type.isPrimitive() && !type.getName().startsWith("java")) {hints.reflection().registerType(type,MemberCategory.values());      }    }  }staticclassMyBatisMapperTypeUtils {privateMyBatisMapperTypeUtils() {// NOP    }staticClass<?>resolveReturnClass(Class<?>mapperInterface,Methodmethod) {TyperesolvedReturnType =TypeParameterResolver.resolveReturnType(method,mapperInterface);returntypeToClass(resolvedReturnType,method.getReturnType());    }staticSet<Class<?>>resolveParameterClasses(Class<?>mapperInterface,Methodmethod) {returnStream.of(TypeParameterResolver.resolveParamTypes(method,mapperInterface))          .map(x ->typeToClass(x,xinstanceofClass ? (Class<?>)x :Object.class)).collect(Collectors.toSet());    }privatestaticClass<?>typeToClass(Typesrc,Class<?>fallback) {Class<?>result =null;if (srcinstanceofClass<?>) {if (((Class<?>)src).isArray()) {result = ((Class<?>)src).getComponentType();        }else {result = (Class<?>)src;        }      }elseif (srcinstanceofParameterizedType) {ParameterizedTypeparameterizedType = (ParameterizedType)src;intindex = (parameterizedType.getRawType()instanceofClass            &&Map.class.isAssignableFrom((Class<?>)parameterizedType.getRawType())            &&parameterizedType.getActualTypeArguments().length >1) ?1 :0;TypeactualType =parameterizedType.getActualTypeArguments()[index];result =typeToClass(actualType,fallback);      }if (result ==null) {result =fallback;      }returnresult;    }  }staticclassMyBatisMapperFactoryBeanPostProcessorimplementsMergedBeanDefinitionPostProcessor,BeanFactoryAware {privatestaticfinalorg.apache.commons.logging.LogLOG =LogFactory.getLog(MyBatisMapperFactoryBeanPostProcessor.class);privatestaticfinalStringMAPPER_FACTORY_BEAN ="org.mybatis.spring.mapper.MapperFactoryBean";privateConfigurableBeanFactorybeanFactory;@OverridepublicvoidsetBeanFactory(BeanFactorybeanFactory) {this.beanFactory = (ConfigurableBeanFactory)beanFactory;    }@OverridepublicvoidpostProcessMergedBeanDefinition(RootBeanDefinitionbeanDefinition,Class<?>beanType,StringbeanName) {if (ClassUtils.isPresent(MAPPER_FACTORY_BEAN,this.beanFactory.getBeanClassLoader())) {resolveMapperFactoryBeanTypeIfNecessary(beanDefinition);      }    }privatevoidresolveMapperFactoryBeanTypeIfNecessary(RootBeanDefinitionbeanDefinition) {if (!beanDefinition.hasBeanClass() || !MapperFactoryBean.class.isAssignableFrom(beanDefinition.getBeanClass())) {return;      }if (beanDefinition.getResolvableType().hasUnresolvableGenerics()) {Class<?>mapperInterface =getMapperInterface(beanDefinition);if (mapperInterface !=null) {// Exposes a generic type information to context for prevent early initializingbeanDefinition              .setTargetType(ResolvableType.forClassWithGenerics(beanDefinition.getBeanClass(),mapperInterface));        }      }    }privateClass<?>getMapperInterface(RootBeanDefinitionbeanDefinition) {try {return (Class<?>)beanDefinition.getPropertyValues().get("mapperInterface");      }catch (Exceptione) {LOG.debug("Fail getting mapper interface type.",e);returnnull;      }    }  }}
Clone this wiki locally

[8]ページ先頭

©2009-2025 Movatter.jp