您的位置:首页 > 编程语言 > Java开发

Mybatis3源码分析(07)-加载Configuration-总结

2015-12-19 08:50 591 查看

Configuration中的配置信息

下图是官方文档中对Configuration的介绍



这里xml配置是由两个对象加载Configuration对象中

XMLConfigBuilder。这个对象负责加载除mappers映射器之外的所有配置。
XMLMapperBuilder。这个对象只负责加载mappers映射器中的配置。其中他还有个助手:MapperBuilderAssisant。XMLMapperBuilder与MapperBuilderAssisant有明确的分工。

XMLConfigBuilder加载配置

这个加载过程比较简单,主要是读取配置,再创建对象,最后把对象加入Configruation中。而创建对象主要有两方式:

通过类名加载对象。
从配置中加载类名或类的别名
通过类名实例化对象
设置对象属性
将对象加入Configuration中

如下例:
//解析对象工厂
private void objectFactoryElement(XNode context) throws Exception {
if (context != null) {
//从配置中读取类名
String type = context.getStringAttribute("type");
//从配置中读取改造
Properties properties = context.getChildrenAsProperties();
//根据类名创建对象
ObjectFactory factory = (ObjectFactory) resolveClass(type).newInstance();
//设置对象属性
factory.setProperties(properties);
//加入到Configuration中
configuration.setObjectFactory(factory);
}
}


通过配置的内容(字符串)加载对象。这种对象一般都结构简单的,如枚举类型,Boolean类型等.
读取配置的字符串内容
调用valueOf方法得一个对象

如下例:
configuration.setAutoMappingBehavior(AutoMappingBehavior.valueOf(props.getProperty("autoMappingBehavior", "PARTIAL")));


XMLMapperBuilder加载配置

XMLMapperBuilder主要加载如下三个配置,其他的比较少用。

cache
resultMap
select/update/insert/delete

XMLMapperBuillder的助手XMLMapperAssiant

一个XMLMapperBuilder就会有一个助手。两个对象有明确的分工。XMLMapperBuilder对象负责从XML读取配置,而他的助手负责创建对象并加载到Configuration中。例如:
private ResultMapping buildResultMappingFromContext(XNode context, Class<?> resultType, ArrayList<ResultFlag> flags) throws Exception {
//XMLapperBuilder负责从xml读取配置
String property = context.getStringAttribute("property");
String column = context.getStringAttribute("column");
String javaType = context.getStringAttribute("javaType");
String jdbcType = context.getStringAttribute("jdbcType");
String nestedSelect = context.getStringAttribute("select");
String nestedResultMap = context.getStringAttribute("resultMap",
processNestedResultMappings(context, Collections.<ResultMapping> emptyList()));
String notNullColumn = context.getStringAttribute("notNullColumn");
String columnPrefix = context.getStringAttribute("columnPrefix");
String typeHandler = context.getStringAttribute("typeHandler");
String resulSet = context.getStringAttribute("resultSet");
String foreignColumn = context.getStringAttribute("foreignColumn");
boolean lazy = "lazy".equals(context.getStringAttribute("fetchType", configuration.isLazyLoadingEnabled() ? "lazy" : "eager"));
Class<?> javaTypeClass = resolveClass(javaType);
@SuppressWarnings("unchecked")
Class<? extends TypeHandler<?>> typeHandlerClass = (Class<? extends TypeHandler<?>>) resolveClass(typeHandler);
JdbcType jdbcTypeEnum = resolveJdbcType(jdbcType);
//助手负责创建对象并加入Configuration
return builderAssistant.buildResultMapping(resultType, property, column, javaTypeClass, jdbcTypeEnum, nestedSelect, nestedResultMap, notNullColumn, columnPrefix, typeHandlerClass, flags, resulSet, foreignColumn, lazy);
}
这个助手创建对象时,利用对象提供的build()方法,这是构建者模式,这种模式负责构建复杂的对象
public ParameterMapping buildParameterMapping(
Class<?> parameterType,
String property,
Class<?> javaType,
JdbcType jdbcType,
String resultMap,
ParameterMode parameterMode,
Class<? extends TypeHandler<?>> typeHandler,
Integer numericScale) {
resultMap = applyCurrentNamespace(resultMap, true);

// Class parameterType = parameterMapBuilder.type();
Class<?> javaTypeClass = resolveParameterJavaType(parameterType, property, javaType, jdbcType);
TypeHandler<?> typeHandlerInstance = resolveTypeHandler(javaTypeClass, typeHandler);
//利用Builder来创建对象
ParameterMapping.Builder builder = new ParameterMapping.Builder(configuration, property, javaTypeClass);
builder.jdbcType(jdbcType);
builder.resultMapId(resultMap);
builder.mode(parameterMode);
builder.numericScale(numericScale);
builder.typeHandler(typeHandlerInstance);
return builder.build();
}

Configuration中默认的Cache对象

Cache对象采用装饰模式实现,对PerpetualCache层层装饰,实现最终需要实现的功能



Configuration中的resultMaps属性



一个resultMap元素对应一个ResultMap对象
resultMap元素中的idArg/id/result/association/collection元素对应一个ResultMapping对象,所有resultMap会有多个ResultMapping对象
association/collection元素对应一个内映射的ResultMap

不管是ResultMap对应还是内映射的ResultMap对象都会被加入到Configuration.resultMaps属性

Configuration.mappedStatements属性

select/update/insert/detele元素会被解析成一个MappedStatement对象,这个对象有一个SqlSource属性,这个属性代表了sql具体的定义。SqlSource又由多个SqlNode组成,这个SqlNode是用组合模式实现的。BoundSql和SqlNode对象在以后分析sql执行时再讨论。
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签:  java jdbc mybatis sql 源码