SqlSource
首先看下SqlSource整体的解析过程,最后产生的可以直接传给sql执行的sql以及ParameterMapping就包含在BoundSql中
首先看下接口定义
/**
* Represents the content of a mapped statement read from an XML file or an annotation.
* It creates the SQL that will be passed to the database out of the input parameter received from the user.
*
* @author Clinton Begin
*/
public interface SqlSource {
BoundSql getBoundSql(Object parameterObject);
}
从注释可以看出,SqlSource代表MappedStatement的内容,可以通过SqlSource来产生数据库可以执行的sql
SqlSource主要有两个实现类
如果sql语句中包含${},那么会被被识别为动态sql,即DynamicSqlSource
下面看下是如何创建的
创建
在初始化的源码分析中,我们知道是通过LanguageDriver来创建SqlSource的,默认使用的是LanguageDriver的实现类XMLLanguageDriver
@Override
public SqlSource createSqlSource(Configuration configuration, XNode script, Class<?> parameterType) {
XMLScriptBuilder builder = new XMLScriptBuilder(configuration, script, parameterType);
return builder.parseScriptNode();
}
主要是交给XMLScriptBuilder来进行解析,接着看
public SqlSource parseScriptNode() {
// 根据解析的标签内容解析成sqlNode,并且判断是否是动态sql
MixedSqlNode rootSqlNode = parseDynamicTags(context);
SqlSource sqlSource;
// 根据是否是动态sql,来决定创建哪种类型的SqlSource
if (isDynamic) {
sqlSource = new DynamicSqlSource(configuration, rootSqlNode);
} else {
sqlSource = new RawSqlSource(configuration, rootSqlNode, parameterType);
}
return sqlSource;
}
protected MixedSqlNode parseDynamicTags(XNode node) {
List<SqlNode> contents = new ArrayList<>();
NodeList children = node.getNode().getChildNodes();
for (int i = 0; i < children.getLength(); i++) {
XNode child = node.newXNode(children.item(i));
// 如果是sql文本,会判断文本中是否出现了${},如果出现了,代表是动态sql,会创建一个TextSqlNode节点
// 否则是普通的静态sql文本,此时会创建一个StaticTextSqlNode
if (child.getNode().getNodeType() == Node.CDATA_SECTION_NODE || child.getNode().getNodeType() == Node.<