mybatis源码分析
2020-04-23 16:17:42 106 举报
AI智能生成
mybatis源码分析
作者其他创作
大纲/内容
获取SqlSessionFactory对象
new SqlSessionFactoryBuilder()
执行build方法,<br>返回SqlSessionFactory对象<br>
XMLConfigBuilder parser = <br>new XMLConfigBuilder(inputStream, environment, properties);<br>创建XMLConfigBuilder对象,并初始化字段<br>
this.configuration = configuration;
this.typeAliasRegistry = this.configuration.getTypeAliasRegistry();
this.typeHandlerRegistry = this.configuration.getTypeHandlerRegistry();
this.environment = environment;<br>
this.parser =<br> new XPathParser(inputStream, true, props, new XMLMapperEntityResolver()<br>创建XPathParser解析器
parser.parse()<br>解析全局配置文件
parseConfiguration<br>
propertiesElement<br>解析<properties>元素
Properties defaults = context.getChildrenAsProperties();<br>添加子元素内容至defaults
defaults =Resources.getResourceAsProperties(resource)<br>读取外部properties文件内容至defaults
parser.setVariables(defaults);<br>XPathParser添加变量信息<br>
configuration.setVariables(defaults)
settingsAsProperties<br>解析<settings>元素<br>mybatis全局设置
Properties props = context.getChildrenAsProperties();<br>获取子元素内容
metaConfig.hasSetter(String.valueOf(key)<br>校验子元素是否合法
typeAliasesElement<br>解析<typeAliases>元素<br>类型别名<br>
pluginElement<br>解析<plugIns>元素<br>插件
获取拦截器<br>child.getStringAttribute("interceptor");<br>
获取属性<br>child.getChildrenAsProperties()<br>
创建拦截器实例<br>Interceptor interceptorInstance = <br>(Interceptor) resolveClass(interceptor).getDeclaredConstructor().newInstance(); <br>
添加拦截器至configuration全局变量中<br> configuration.addInterceptor(interceptorInstance)<br>
objectFactoryElement<br>解析<objectFactory>元素
objectWrapperFactoryElement<br>解析<objectWrapperFactory>元素
reflectorFactoryElement<br>解析<reflectorFactory>元素
settingsElement<br>将<settings>元素内容填充至configuration对象中
将<settings>元素配置的全局属性添加至configuration中
configuration.setCacheEnabled(booleanValueOf(props.getProperty("cacheEnabled"), true)); <br>
configuration.setMapUnderscoreToCamelCase(booleanValueOf(props.getProperty("mapUnderscoreToCamelCase"), false)); <br>
....
databaseIdProviderElement<br>解析<databaseIdProvider>元素<br>数据库厂商标识<br>
typeHandlerElement<br>解析<typeHandlers>元素<br>
mapperElement<br>解析<mappers>元素<br>
package
configuration.addMappers(mapperPackage)
MapperRegistry-><br>addMappers(packageName);<br>
resolverUtil.find(new ResolverUtil.IsA(superType), packageName);<br>解析指定包中Class
addMapper(mapperClass);
knownMappers.put(type, new MapperProxyFactory<>(type));<br>添加MapperProxy代理对象
MapperAnnotationBuilder->parse()<br>解析Mapper接口中定义的注解
MapperAnnotationBuilder-><br>loadXmlResource();<br>加载xml映射文件<br>
InputStream inputStream = type.getResourceAsStream("/" + xmlResource);
inputStream = Resources.getResourceAsStream(type.getClassLoader(), xmlResource);
XMLMapperBuilder xmlParser = new XMLMapperBuilder(inputStream, assistant.getConfiguration(), xmlResource, configuration.getSqlFragments(), type.getName());<br> xmlParser.parse();
MapperAnnotationBuilder-><br>parseStatement(method);<br>
MapperBuilderAssistant-><br>addMappedStatement<br>
mapper
resource<br>url<br>
Resources.getResourceAsStream(resource)<br>加载资源文件为流
XMLMapperBuilder-><br>parse()<br>解析<mapper>元素
configurationElement
namespace
cacheRefElement<br>解析cache-ref属性<br>
cacheElement<br>解析cache属性<br>
parameterMapElement<br>/mapper/parameterMap<br>
builderAssistant.addParameterMap
resultMapElements<br>/mapper/resultMap<br>
sqlElement<br>/mapper/sql<br>
buildStatementFromContext<br>select|insert|update|delete<br>
XMLStatementBuilder-><br>parseStatementNode();<br>
解析xml元素
MapperBuilderAssistant-><br>addMappedStatement<br>
MappedStatement statement = statementBuilder.build();
configuration.addMappedStatement(statement);
bindMapperForNamespace
builderAssistant.getCurrentNamespace()
configuration.addLoadedResource("namespace:" + namespace); <br>
configuration.addMapper(boundType);
parsePendingResultMaps
parsePendingCacheRefs
parsePendingStatements
class
Resources.classForName(mapperClass);
configuration.addMapper(boundType);
获取SqlSession对象
DefaultSqlSessionFactory-><br>openSession()<br>
DefaultSqlSessionFactory-><br>openSessionFromDataSource<br>
configuration.getEnvironment()<br>获取环境变量
tx = transactionFactory.newTransaction();<br>创建事务
Executor executor = configuration.newExecutor(tx, execType)<br>创建执行器
BatchExecutor<br>执行器不仅重用语句还会执行批量更新<br>
ReuseExecutor<br>执行器会重用预处理语句(PreparedStatement)<br>
SimpleExecutor<br>普通的执行器<br>
CachingExecutor<br>setting中开启二级缓存(cacheEnabled=true)
executor = (Executor) interceptorChain.pluginAll(executor);<br>拦截器处理,插件对执行器进行二次包装
new DefaultSqlSession(configuration, executor, autoCommit);<br>返回DefaultSqlSession对象
获取接口代理对象 MapperProxy
DefaultSqlSession-><br>getMapper(Class<T> type)<br>
Configuration-><br>getMapper<br>
MapperRegistry-><br>getMapper<br>
(MapperProxyFactory<T>) knownMappers.get(type)
mapperProxyFactory.newInstance(sqlSession)
MapperProxy<T> mapperProxy = new MapperProxy<>(sqlSession, mapperInterface, methodCache);
(T) Proxy.newProxyInstance(mapperInterface.getClassLoader(), new Class[] { mapperInterface }, mapperProxy);
执行增删改查方法
MapperProxy-><br>invoke()<br>进入代理对象invoke方法
Object上定义的方法直接执行
MapperMethod-><br>execute<br>
command.getType()<br>INSERT|UPDATE|DELETE|SELECT<br>
executeForMany
method.convertArgsToSqlCommandParam
paramNameResolver.getNamedParams(args)
sqlSession.selectList(command.getName(), param)
DefaultSqlSession-><br>configuration.getMappedStatement(statement)<br>
wrapCollection()<br>参数统一封装为map
executor.query<br>执行器查询
MappedStatement-><br>ms.getBoundSql(parameterObject)<br>
query
先查询缓存
delegate.query<br>
BaseExecutor-><br>queryFromDatabase<br>
doQuery<br>
ms.getConfiguration();
StatementHandler handler = <br>configuration.newStatementHandler();<br>
StatementHandler statementHandler =<br> new RoutingStatementHandler<br>
STATEMENT:SimpleStatementHandler
PREPARED:PreparedStatementHandler
CALLABLE:CallableStatementHandler
BaseStatementHandler->
this.parameterHandler = configuration.newParameterHandler<br>创建参数处理器
(ParameterHandler) interceptorChain.pluginAll(parameterHandler);
this.resultSetHandler = configuration.newResultSetHandler<br>创建结果处理器
resultSetHandler = (ResultSetHandler) interceptorChain.pluginAll(resultSetHandler); <br>
(StatementHandler) interceptorChain.pluginAll(statementHandler);<br>
stmt = prepareStatement(handler, ms.getStatementLog()); <br>
Connection connection = getConnection(statementLog); <br>
JdbcTransaction-><br>transaction.getConnection();<br>获取数据库连接
dataSource.getConnection()<br>从连接池获取connection
connection.setAutoCommit(desiredAutoCommit);<br>设置事务
stmt = handler.prepare(connection, transaction.getTimeout());
RoutingStatementHandler-><br>delegate.prepare(connection, transactionTimeout);<br>
BaseStatementHandler-><br>prepare<br>
instantiateStatement
PreparedStatementHandler-><br>String sql = boundSql.getSql()<br>connection.prepareStatement(sql)<br>
setStatementTimeout
setFetchSize
return statement
handler.parameterize(stmt);
RoutingStatementHandler-><br>delegate.parameterize(statement);<br>
PreparedStatementHandler-><br>parameterHandler.setParameters((PreparedStatement) statement);<br>
DefaultParameterHandler-><br>TypeHandler typeHandler = parameterMapping.getTypeHandler();<br> JdbcType jdbcType = parameterMapping.getJdbcType();<br>typeHandler.setParameter(ps, i + 1, value, jdbcType);<br>
handler.query(stmt, resultHandler);
RoutingStatementHandler-><br>delegate.query(statement, resultHandler);<br>
PreparedStatementHandler-><br>PreparedStatement ps = (PreparedStatement) statement;<br> ps.execute();<br>
resultSetHandler.handleResultSets(ps);<br> 处理参数
0 条评论
下一页