`
Donald_Draper
  • 浏览: 971714 次
社区版块
存档分类
最新评论

DefaultSqlSession第一讲query解析

阅读更多
上一篇文章:我们说过DefaultSqlSession,DefaultSqlSessionFactory根据执行器类型,事务级别,是否提交等信息,来构建执行器Executor,然后根据执行器和configuration构建SqlSession,默认为DefaultSqlSession,从DefaultSqlSession的类信息方法来看,DefaultSqlSession的查询则委托给executor的query,插入,更新,删除,则委托给executor的update,提交,回滚,清除缓存,刷新Statement,关闭SqlSession,都是委托给Executor的相应方法。这一节节我们来Executor
//执行器的构建
//根据数据源,事务级别,是否自动提交,创建执行器
org.apache.ibatis.executor.Executor executor = configuration.newExecutor(tx, execType, autoCommit);

//Configuration
public Executor newExecutor(Transaction transaction, ExecutorType executorType, boolean autoCommit)
    {
        executorType = executorType != null ? executorType : defaultExecutorType;
        executorType = executorType != null ? executorType : ExecutorType.SIMPLE;
        Executor executor;
        if(ExecutorType.BATCH == executorType)
            executor = new BatchExecutor(this, transaction);
        else
        if(ExecutorType.REUSE == executorType)
            executor = new ReuseExecutor(this, transaction);
        else
            executor = new SimpleExecutor(this, transaction);
        if(cacheEnabled)
            executor = new CachingExecutor(executor, autoCommit);
	//将执行器插入到拦截器链中
        executor = (Executor)interceptorChain.pluginAll(executor);
        return executor;
}

从上面configuration的创建执行器方法,可以看出执行器有BatchExecutor,ReuseExecutor,SimpleExecutor
根据执行器类型,创建执行器,如果缓存启用,则包装executor为CachingExecutor;
//BatchExecutor
public class BatchExecutor extends BaseExecutor
{
    public static final int BATCH_UPDATE_RETURN_VALUE = -2147482646;
    private final List statementList = new ArrayList();
    private final List batchResultList = new ArrayList();
    private String currentSql;
    private MappedStatement currentStatement;
    public BatchExecutor(Configuration configuration, Transaction transaction)
    {
        super(configuration, transaction);
    }
}

//SimpleExecutor
public class SimpleExecutor extends BaseExecutor
{
    public SimpleExecutor(Configuration configuration, Transaction transaction)
    {
        super(configuration, transaction);
    }
}


//CachingExecutor
public class CachingExecutor
    implements Executor
{
    private Executor _flddelegate;
    private boolean autoCommit;
    private TransactionalCacheManager tcm;
    private boolean dirty;
    public CachingExecutor(Executor delegate)
    {
        this(delegate, false);
    }
    public CachingExecutor(Executor delegate, boolean autoCommit)
    {
        tcm = new TransactionalCacheManager();
        _flddelegate = delegate;
        this.autoCommit = autoCommit;
    }
    public Transaction getTransaction()
    {
        return _flddelegate.getTransaction();
    }
    //更新
    public int update(MappedStatement ms, Object parameterObject)
        throws SQLException
    {
        //刷新刷新
        flushCacheIfRequired(ms);
	//调用代理更新
        return _flddelegate.update(ms, parameterObject);
    }
    //查询
    public List query(MappedStatement ms, Object parameterObject, RowBounds rowBounds, ResultHandler resultHandler)
        throws SQLException
    {
        BoundSql boundSql = ms.getBoundSql(parameterObject);
        CacheKey key = createCacheKey(ms, parameterObject, rowBounds, boundSql);
        return query(ms, parameterObject, rowBounds, resultHandler, key, boundSql);
    }
    //查询
    public List query(MappedStatement ms, Object parameterObject, RowBounds rowBounds, ResultHandler resultHandler, CacheKey key, BoundSql boundSql)
        throws SQLException
    {
        Cache cache;
        cache = ms.getCache();
        if(cache == null)
            break MISSING_BLOCK_LABEL_183;
        flushCacheIfRequired(ms);
        if(!ms.isUseCache() || resultHandler != null)
            break MISSING_BLOCK_LABEL_183;
        ensureNoOutParams(ms, key, parameterObject, boundSql);
        if(dirty)
            break MISSING_BLOCK_LABEL_147;
        cache.getReadWriteLock().readLock().lock();
        List list1;
        List cachedList = (List)cache.getObject(key);
        if(cachedList == null)
            break MISSING_BLOCK_LABEL_105;
        list1 = cachedList;
        cache.getReadWriteLock().readLock().unlock();
        cache.getReadWriteLock().readLock().unlock();
        cache.getReadWriteLock().readLock().unlock();
        //调用代理查询
        List list = _flddelegate.query(ms, parameterObject, rowBounds, resultHandler, key, boundSql);
        tcm.putObject(cache, key, list);
        return list;
        return _flddelegate.query(ms, parameterObject, rowBounds, resultHandler, key, boundSql);
    }

    public List flushStatements()
        throws SQLException
    {
        return _flddelegate.flushStatements();
    }

    public void commit(boolean required)
        throws SQLException
    {
        _flddelegate.commit(required);
        tcm.commit();
        dirty = false;
    }
   
    public void rollback(boolean required)
        throws SQLException
    {
        _flddelegate.rollback(required);
        dirty = false;
        if(required)
            tcm.rollback();
        break MISSING_BLOCK_LABEL_43;
        if(required)
            tcm.rollback();
        throw exception;
    }
       public void clearLocalCache()
    {
        _flddelegate.clearLocalCache();
    }
}

从上可以看出CachingExecutor是SimpleExecutor,BatchExecutor等执行器代理执行器;
事务的获取,清除缓存,更新,查询操作实际上,是调用Executor的相应方法。SimpleExecutor,
BatchExecutor为实际执行器,继承BatchExecutor;
下面根据DefaultSqlSession,来看执行器的query,update,提交,回滚,清除缓存,刷新Statement,
关闭SqlSession
public class DefaultSqlSession
    implements SqlSession
{
    private Configuration configuration;
    private Executor executor;
    private boolean dirty;
    public DefaultSqlSession(Configuration configuration, Executor executor)
    {
        this.configuration = configuration;
        this.executor = executor;
        dirty = false;
    }
    //查询
    public Object selectOne(String statement)
    {
        return selectOne(statement, null);
    }
    public Object selectOne(String statement, Object parameter)
    {
        List list = selectList(statement, parameter);
        if(list.size() == 1)
            return list.get(0);
        if(list.size() > 1)
            throw new TooManyResultsException((new StringBuilder()).append("Expected one result (or null) to be returned by selectOne(), but found: ").append(list.size()).toString());
        else
            return null;
    }
    public List selectList(String statement)
    {
        return selectList(statement, null);
    }

    public List selectList(String statement, Object parameter)
    {
        return selectList(statement, parameter, RowBounds.DEFAULT);
    }
    public List selectList(String statement, Object parameter, RowBounds rowBounds)
    {
        List list;
        try
        {
            org.apache.ibatis.mapping.MappedStatement ms = configuration.getMappedStatement(statement);
	    //调用executor的查询方法
            List result = executor.query(ms, wrapCollection(parameter), rowBounds, Executor.NO_RESULT_HANDLER);
            list = result;
        }
    }
    //插入
     public int insert(String statement)
    {
        return insert(statement, null);
    }

    public int insert(String statement, Object parameter)
    {
       //委托给update方法
        return update(statement, parameter);
    }

    public int update(String statement)
    {
        return update(statement, null);
    }

    public int update(String statement, Object parameter)
    {
        int i;
        try
        {
            dirty = true;
            org.apache.ibatis.mapping.MappedStatement ms = configuration.getMappedStatement(statement);
            //委托给executor的update
	    i = executor.update(ms, wrapCollection(parameter));
        }
    }
    //删除
     public int delete(String statement)
    { 
        //委托给update
        return update(statement, null);
    }

    public int delete(String statement, Object parameter)
    {
        return update(statement, parameter);
    }
    //提交
     public void commit()
    {
        commit(false);
    }

    public void commit(boolean force)
    {
        try
        {
	    //委托executor的commit
            executor.commit(isCommitOrRollbackRequired(force));
            dirty = false;
        }
    }
    //回滚
     public void rollback()
    {
        rollback(false);
    }

    public void rollback(boolean force)
    {
        try
        {
	    //委托executor的rollback
            executor.rollback(isCommitOrRollbackRequired(force));
            dirty = false;
        }
    }
    //清除缓存
    public void clearCache()
    {
	////委托executor的clearLocalCache
        executor.clearLocalCache();
    }
    //刷新Statements
    public List flushStatements()
    {
        List list;
        try
        {
	    //委托executor的flushStatements
            list = executor.flushStatements();
        }
    }
    //关闭SqlSession
    public void close()
    {
        //委托executor的close
        executor.close(isCommitOrRollbackRequired(false));
        dirty = false;
    }
}

先来看SqlSession
public List selectList(String statement, Object parameter, RowBounds rowBounds)
    {
        List list;
        try
        {
            org.apache.ibatis.mapping.MappedStatement ms = configuration.getMappedStatement(statement);
	    //调用executor的查询方法
            List result = executor.query(ms, wrapCollection(parameter), rowBounds, Executor.NO_RESULT_HANDLER);
            list = result;
        }
    }

代理执行器调用实际执行器BatchExecutor,ReuseExecutor,SimpleExecutor的query的方法
//CachingExecutor
//查询
   
public List query(MappedStatement ms, Object parameterObject, RowBounds rowBounds, ResultHandler resultHandler)
        throws SQLException
    {
        BoundSql boundSql = ms.getBoundSql(parameterObject);
        CacheKey key = createCacheKey(ms, parameterObject, rowBounds, boundSql);
        return query(ms, parameterObject, rowBounds, resultHandler, key, boundSql);
    }
    //查询
    public List query(MappedStatement ms, Object parameterObject, RowBounds rowBounds, ResultHandler resultHandler, CacheKey key, BoundSql boundSql)
        throws SQLException
    {
        List list = _flddelegate.query(ms, parameterObject, rowBounds, resultHandler, key, boundSql);
        tcm.putObject(cache, key, list);
        return list;
        return _flddelegate.query(ms, parameterObject, rowBounds, resultHandler, key, boundSql);
    }

查看BatchExecutor,ReuseExecutor,SimpleExecutor的query的方法,实际上是在BaseExecutor
//BaseExecutor
public List query(MappedStatement ms, Object parameter, RowBounds rowBounds, ResultHandler resultHandler)
        throws SQLException
    {
        BoundSql boundSql = ms.getBoundSql(parameter);
        CacheKey key = createCacheKey(ms, parameter, rowBounds, boundSql);
	//委托给query(ms, parameter, rowBounds, resultHandler, key, boundSql);
        return query(ms, parameter, rowBounds, resultHandler, key, boundSql);
    }

    public List query(MappedStatement ms, Object parameter, RowBounds rowBounds, ResultHandler resultHandler, CacheKey key, BoundSql boundSql)
        throws SQLException
    {
        ErrorContext.instance().resource(ms.getResource()).activity("executing a query").object(ms.getId());
        if(closed)
            throw new ExecutorException("Executor was closed.");
        if(queryStack == 0 && ms.isFlushCacheRequired())
            clearLocalCache();
        List list;
        queryStack++;
        list = resultHandler != null ? null : (List)localCache.getObject(key);
        if(list != null)
	    //从本地获取查询结果
            handleLocallyCachedOutputParameters(ms, key, parameter, boundSql);
        else
	    //从数据库查询结果
            list = queryFromDatabase(ms, parameter, rowBounds, resultHandler, key, boundSql);
        return list;
    }
    //从数据库查询结果
     private List queryFromDatabase(MappedStatement ms, Object parameter, RowBounds rowBounds, ResultHandler resultHandler, CacheKey key, BoundSql boundSql)
        throws SQLException
    {
        localCache.putObject(key, ExecutionPlaceholder.EXECUTION_PLACEHOLDER);
	//委托给doQuery
        List list = doQuery(ms, parameter, rowBounds, resultHandler, boundSql);
        localCache.removeObject(key);
        break MISSING_BLOCK_LABEL_53;
        Exception exception;
        exception;
        localCache.removeObject(key);
        throw exception;
        localCache.putObject(key, list);
        if(ms.getStatementType() == StatementType.CALLABLE)
            localOutputParameterCache.putObject(key, parameter);
        return list;
    }
    //doQuery为抽象方法,待子类扩展
     protected abstract List doQuery(MappedStatement mappedstatement, Object obj, RowBounds rowbounds, ResultHandler resulthandler, BoundSql boundsql)
        throws SQLException;

这里我们来看一下SimpleExecutor
//SimpleExecutor
public List doQuery(MappedStatement ms, Object parameter, RowBounds rowBounds, ResultHandler resultHandler, BoundSql boundSql)
        throws SQLException
    {
        Statement stmt = null;
        List list;
        Configuration configuration = ms.getConfiguration();
	//构造StatementHandler
        StatementHandler handler = configuration.newStatementHandler(this, ms, parameter, rowBounds, resultHandler, boundSql);
        //获取Statement
	stmt = prepareStatement(handler, ms.getStatementLog());
	//执行查询
        list = handler.query(stmt, resultHandler);
	//关闭statement
        closeStatement(stmt);
        return list;
        Exception exception;
        exception;
        closeStatement(stmt);
        throw exception;
    }

//构造StatementHandler
StatementHandler handler = configuration.newStatementHandler(this, ms, parameter, rowBounds, resultHandler, boundSql);

//configuration
public StatementHandler newStatementHandler(Executor executor, MappedStatement mappedStatement, Object parameterObject, RowBounds rowBounds, ResultHandler resultHandler, BoundSql boundSql)
    {
        //创建RoutingStatementHandler
        StatementHandler statementHandler = new RoutingStatementHandler(executor, mappedStatement, parameterObject, rowBounds, resultHandler, boundSql);
        //拦截器处理statementHandler,
	statementHandler = (StatementHandler)interceptorChain.pluginAll(statementHandler);
        return statementHandler;
    }

//RoutingStatementHandler
public class RoutingStatementHandler
    implements StatementHandler
{
    private final StatementHandler _flddelegate;
    public RoutingStatementHandler(Executor executor, MappedStatement ms, Object parameter, RowBounds rowBounds, ResultHandler resultHandler, BoundSql boundSql)
    {
        static class _cls1
        {

            static final int $SwitchMap$org$apache$ibatis$mapping$StatementType[];

            static 
            {
                $SwitchMap$org$apache$ibatis$mapping$StatementType = new int[StatementType.values().length];
                try
                {
                    $SwitchMap$org$apache$ibatis$mapping$StatementType[StatementType.STATEMENT.ordinal()] = 1;
                }
                catch(NoSuchFieldError ex) { }
                try
                {
                    $SwitchMap$org$apache$ibatis$mapping$StatementType[StatementType.PREPARED.ordinal()] = 2;
                }
                catch(NoSuchFieldError ex) { }
                try
                {
                    $SwitchMap$org$apache$ibatis$mapping$StatementType[StatementType.CALLABLE.ordinal()] = 3;
                }
                catch(NoSuchFieldError ex) { }
            }
        }
       //根据StatementType,创建对应的StatementHandler
        switch(_cls1..SwitchMap.org.apache.ibatis.mapping.StatementType[ms.getStatementType().ordinal()])
        {
        case 1: // '\001'
            _flddelegate = new SimpleStatementHandler(executor, ms, parameter, rowBounds, resultHandler, boundSql);
            break;

        case 2: // '\002'
            _flddelegate = new PreparedStatementHandler(executor, ms, parameter, rowBounds, resultHandler, boundSql);
            break;

        case 3: // '\003'
            _flddelegate = new CallableStatementHandler(executor, ms, parameter, rowBounds, resultHandler, boundSql);
            break;

        default:
            throw new ExecutorException((new StringBuilder()).append("Unknown statement type: ").append(ms.getStatementType()).toString());
        }
    }

    public Statement prepare(Connection connection)
        throws SQLException
    {
        return _flddelegate.prepare(connection);
    }

    public void parameterize(Statement statement)
        throws SQLException
    {
        _flddelegate.parameterize(statement);
    }

    public void batch(Statement statement)
        throws SQLException
    {
        _flddelegate.batch(statement);
    }

    public int update(Statement statement)
        throws SQLException
    {
        return _flddelegate.update(statement);
    }

    public List query(Statement statement, ResultHandler resultHandler)
        throws SQLException
    {
        return _flddelegate.query(statement, resultHandler);
    }

    public BoundSql getBoundSql()
    {
        return _flddelegate.getBoundSql();
    }

    public ParameterHandler getParameterHandler()
    {
        return _flddelegate.getParameterHandler();
    }
}

从RoutingStatementHandler可以看出,更新,查询,预编译都是通过代理StatementHandler,具体根据StatementType创建对应的StatementHandler,SimpleStatementHandler,PreparedStatementHandler,CallableStatementHandler
//获取Statement
stmt = prepareStatement(handler, ms.getStatementLog());
 private Statement prepareStatement(StatementHandler handler, Log statementLog)
        throws SQLException
    {
        //获取连接,这里实际上调用的为BaseExector的getConnection,从执行器的事务管理器获取连接
        java.sql.Connection connection = getConnection(statementLog);
	//预编译
        Statement stmt = handler.prepare(connection);
	//参数设置
        handler.parameterize(stmt);
        return stmt;
    }

//预编译
Statement stmt = handler.prepare(connection);

实际为RoutingStatementHandler,通过本地代理,预编译Statement,
public abstract class BaseStatementHandler
    implements StatementHandler
{
   //获取PrepareStatement
public Statement prepare(Connection connection)
        throws SQLException
    {
        protected final Configuration configuration;
        protected final ObjectFactory objectFactory;
        protected final TypeHandlerRegistry typeHandlerRegistry;
        protected final ResultSetHandler resultSetHandler;
        protected final ParameterHandler parameterHandler;
        protected final Executor executor;
        protected final MappedStatement mappedStatement;
        protected final RowBounds rowBounds;
        protected BoundSql boundSql;
        Statement statement;
        ErrorContext.instance().sql(boundSql.getSql());
        statement = null;
	//实例化Statement
        statement = instantiateStatement(connection);
        setStatementTimeout(statement);
        setFetchSize(statement);
        return statement;
    }
    //带子类扩展
     protected abstract Statement instantiateStatement(Connection connection)
        throws SQLException;
    
    //设置statement的超时时间
     protected void setStatementTimeout(Statement stmt)
        throws SQLException
    {
        Integer timeout = mappedStatement.getTimeout();
        Integer defaultTimeout = configuration.getDefaultStatementTimeout();
        if(timeout != null)
            stmt.setQueryTimeout(timeout.intValue());
        else
        if(defaultTimeout != null)
            stmt.setQueryTimeout(defaultTimeout.intValue());
    }
   //设置statement的FetchSize
    protected void setFetchSize(Statement stmt)
        throws SQLException
    {
        Integer fetchSize = mappedStatement.getFetchSize();
        if(fetchSize != null)
            stmt.setFetchSize(fetchSize.intValue());
    }
}

我们来看statement实例化:
//PreparedStatementHandler,这里我们来看PreparedStatementHandler的实例化
public class PreparedStatementHandler extends BaseStatementHandler
{

    public PreparedStatementHandler(Executor executor, MappedStatement mappedStatement, Object parameter, RowBounds rowBounds, ResultHandler resultHandler, BoundSql boundSql)
    {
        super(executor, mappedStatement, parameter, rowBounds, resultHandler, boundSql);
    }
    //实例化Statement
    protected Statement instantiateStatement(Connection connection)
        throws SQLException
    {
        //获取sql
        String sql = boundSql.getSql();
        if(mappedStatement.getKeyGenerator() instanceof Jdbc3KeyGenerator)
        {
            String keyColumnNames[] = mappedStatement.getKeyColumns();
            if(keyColumnNames == null)
                return connection.prepareStatement(sql, 1);
            else
	       //从connection返回PreparedStatement
                return connection.prepareStatement(sql, keyColumnNames);
        }
        if(mappedStatement.getResultSetType() != null)
            return connection.prepareStatement(sql, mappedStatement.getResultSetType().getValue(), 1007);
        else
            return connection.prepareStatement(sql);
    }
}

我们再看一下
//CallableStatementHandler
public class CallableStatementHandler extends BaseStatementHandler
{
protected Statement instantiateStatement(Connection connection)
        throws SQLException
    {
        String sql = boundSql.getSql();
        if(mappedStatement.getResultSetType() != null)
            return connection.prepareCall(sql, mappedStatement.getResultSetType().getValue(), 1007);
        else
	   //从connection返回CallableStatement
            return connection.prepareCall(sql);
    }
}

从上面可以看出构造StatementHandler,实际上为RoutingStatementHandler,
RoutingStatementHandler更新,查询,预编译都是通过代理StatementHandler,具体根据StatementType创建对应的StatementHandler,SimpleStatementHandler,
PreparedStatementHandler,CallableStatementHandler,
由具体的StatementHandler,创建Statement
//参数设置
handler.parameterize(stmt);

//PreparedStatementHandler
public void parameterize(Statement statement)
        throws SQLException
    {
        parameterHandler.setParameters((PreparedStatement)statement);
    }

parameterHandler在BaseStatementHandler中
public abstract class BaseStatementHandler
    implements StatementHandler
{
    protected final Configuration configuration;
    protected final ObjectFactory objectFactory;
    protected final TypeHandlerRegistry typeHandlerRegistry;
    protected final ResultSetHandler resultSetHandler;
    protected final ParameterHandler parameterHandler;
    protected final Executor executor;
    protected final MappedStatement mappedStatement;
    protected final RowBounds rowBounds;
    protected BoundSql boundSql;
    protected BaseStatementHandler(Executor executor, MappedStatement mappedStatement, Object parameterObject, RowBounds rowBounds, ResultHandler resultHandler, BoundSql boundSql)
    {
        configuration = mappedStatement.getConfiguration();
        this.executor = executor;
        this.mappedStatement = mappedStatement;
        this.rowBounds = rowBounds;
        typeHandlerRegistry = configuration.getTypeHandlerRegistry();
        objectFactory = configuration.getObjectFactory();
        if(boundSql == null)
        {
            generateKeys(parameterObject);
            boundSql = mappedStatement.getBoundSql(parameterObject);
        }
        this.boundSql = boundSql;
	//configuration创建ParameterHandler
        parameterHandler = configuration.newParameterHandler(mappedStatement, parameterObject, boundSql);
        resultSetHandler = configuration.newResultSetHandler(executor, mappedStatement, rowBounds, parameterHandler, resultHandler, boundSql);
    }
}

来看一下
//configuration创建ParameterHandler
public ParameterHandler newParameterHandler(MappedStatement mappedStatement, Object parameterObject, BoundSql boundSql)
    {
        //从mappedStatement获取LanguageDriver,创建ParameterHandler
        ParameterHandler parameterHandler = mappedStatement.getLang().createParameterHandler(mappedStatement, parameterObject, boundSql);
        //拦截器链处理ParameterHandler
	parameterHandler = (ParameterHandler)interceptorChain.pluginAll(parameterHandler);
        return parameterHandler;
    }

//XMLLanguageDriver
public class XMLLanguageDriver
    implements LanguageDriver
{
    public ParameterHandler createParameterHandler(MappedStatement mappedStatement, Object parameterObject, BoundSql boundSql)
    {
        return new DefaultParameterHandler(mappedStatement, parameterObject, boundSql);
    }

//DefaultParameterHandler
public class DefaultParameterHandler
    implements ParameterHandler
{
    private final TypeHandlerRegistry typeHandlerRegistry;
    private final MappedStatement mappedStatement;
    private final Object parameterObject;
    private BoundSql boundSql;
    private Configuration configuration;
    public DefaultParameterHandler(MappedStatement mappedStatement, Object parameterObject, BoundSql boundSql)
    {
        this.mappedStatement = mappedStatement;
        configuration = mappedStatement.getConfiguration();
        typeHandlerRegistry = mappedStatement.getConfiguration().getTypeHandlerRegistry();
        this.parameterObject = parameterObject;
        this.boundSql = boundSql;
    }
    //设置PreparedStatement的参数
    public void setParameters(PreparedStatement ps)
        throws SQLException
    {
        ErrorContext.instance().activity("setting parameters").object(mappedStatement.getParameterMap().getId());
        //从boundSql获取参数映射
	List parameterMappings = boundSql.getParameterMappings();
        if(parameterMappings != null)
        {
            MetaObject metaObject = parameterObject != null ? configuration.newMetaObject(parameterObject) : null;
            for(int i = 0; i < parameterMappings.size(); i++)
            {
	        //获取parameterMapping
                ParameterMapping parameterMapping = (ParameterMapping)parameterMappings.get(i);
                if(parameterMapping.getMode() == ParameterMode.OUT)
                    continue;
                String propertyName = parameterMapping.getProperty();
                Object value;
                if(boundSql.hasAdditionalParameter(propertyName))
                    value = boundSql.getAdditionalParameter(propertyName);
                else
                if(parameterObject == null)
                    value = null;
                else
                if(typeHandlerRegistry.hasTypeHandler(parameterObject.getClass()))
                    value = parameterObject;
                else
                    value = metaObject != null ? metaObject.getValue(propertyName) : null;
		//获取具体的TypeHandler
                TypeHandler typeHandler = parameterMapping.getTypeHandler();
                if(typeHandler == null)
                    throw new ExecutorException((new StringBuilder()).append("There was no TypeHandler found for parameter ").append(propertyName).append(" of statement ").append(mappedStatement.getId()).toString());
                JdbcType jdbcType = parameterMapping.getJdbcType();
                if(value == null && jdbcType == null)
                    jdbcType = configuration.getJdbcTypeForNull();
		//typeHandler设置PreparedStatement参数
                typeHandler.setParameter(ps, i + 1, value, jdbcType);
            }

        }
    }
}

//BaseTypeHandler
public abstract class BaseTypeHandler extends TypeReference
    implements TypeHandler
{
public void setParameter(PreparedStatement ps, int i, Object parameter, JdbcType jdbcType)
        throws SQLException
    {
        if(parameter == null)
        {
            if(jdbcType == null)
                throw new TypeException("JDBC requires that the JdbcType must be specified for all nullable parameters.");
            try
            {
                ps.setNull(i, jdbcType.TYPE_CODE);
            }
        } else
        {
	    //设置参数
            setNonNullParameter(ps, i, parameter, jdbcType);
        }
    }
    //待父类扩展
    public abstract void setNonNullParameter(PreparedStatement preparedstatement, int i, Object obj, JdbcType jdbctype)
        throws SQLException;
}

BaseTypeHandler的子类有Integer,Float,Double,Boolean,Day,TimeStamp,Clob,StringTypeHandler
这里我们来看StringTypeHandler
public class StringTypeHandler extends BaseTypeHandler
{
public void setNonNullParameter(PreparedStatement ps, int i, String parameter, JdbcType jdbcType)
        throws SQLException
    {
        ps.setString(i, parameter);
    }
}

从上面可以看出,参数初始化实际上,是通过ParameterHandler来处理,ParameterHandler默认为DefaultParameterHandler,
DefaultParameterHandler初始化参数实际上,
是从boundSql获取statement参数映射parameterMappings,遍历parameterMappings
根据具体的parameterMapping,从parameterMapping获取TypeHandler
(Integer,Float,Double,Boolean,Day,TimeStamp,Clob,StringTypeHandler)
;最后由TypeHandler,去设置statement参数
//执行查询
l
ist = handler.query(stmt, resultHandler);

//PreparedStatementHandler
public List query(Statement statement, ResultHandler resultHandler)
        throws SQLException
    {
        PreparedStatement ps = (PreparedStatement)statement;
        ps.execute();
        return resultSetHandler.handleResultSets(ps);
    }

//CallableStatementHandler
 
public List query(Statement statement, ResultHandler resultHandler)
        throws SQLException
    {
        CallableStatement cs = (CallableStatement)statement;
        cs.execute();
        List resultList = resultSetHandler.handleResultSets(cs);
        resultSetHandler.handleOutputParameters(cs);
        return resultList;
    }

//关闭statement
closeStatement(stmt);

//BaseStatementHandler
protected void closeStatement(Statement statement)
    {
        if(statement != null)
            try
            {
                statement.close();
            }
            catch(SQLException e) { }
}

总结:
Sqlsession查询,通过CachingExecutor代理,CachingExecutor是SimpleExecutor,BatchExecutor等执行器代理执行器;
事务的获取,清除缓存,更新,查询操作实际上,是调用Executor的相应方法。SimpleExecutor,BatchExecutor为实际执行器,继承BatchExecutor。SimpleExecutor查询,如果有缓存,则利用缓存,没有则用从数据库中查询,查询过程,构造StatementHandler,获取Statement,执行查询,关闭statement。


分享到:
评论

相关推荐

    易语言DnsQuery解析DNS

    易语言DnsQuery解析DNS源码,DnsQuery解析DNS,DnsFlushResolverCache,DnsQuery_A1,DnsQuery_A,DnsQuery_W,DnsModifyRecordsInSet_A,DnsGetCacheDataTable,inet_addr,DnsRecordListFree,GetAddrInfo,LocalSize_DNS_...

    易语言源码易语言DnsQuery解析DNS源码.rar

    易语言源码易语言DnsQuery解析DNS源码.rar 易语言源码易语言DnsQuery解析DNS源码.rar 易语言源码易语言DnsQuery解析DNS源码.rar 易语言源码易语言DnsQuery解析DNS源码.rar 易语言源码易语言DnsQuery解析DNS源码....

    易语言DnsQuery解析DNS源码

    1. **发起查询**:程序通过调用DnsQuery函数,向DNS服务器发送一个查询请求,包含待解析的域名。 2. **构建DNS报文**:在请求中,DNS报文会包含DNS头、问题部分(包含查询的域名和类型)、以及可能的答案、权威记录...

    DnsQuery解析DNS.rar

    DnsQuery解析DNS.rar

    Power Query Excel数据处理利器.zip

    1. **数据源连接**:Power Query支持连接到多种数据源,包括Excel表格、数据库、文本/CSV文件、Web、SQL Server、Oracle、PDF等,允许用户轻松地从不同来源获取数据。 2. **数据预处理**:Power Query提供了丰富的...

    pg_query_go, 使用PostgreSQL解析器解析和规范化SQL查询.zip

    pg_query_go, 使用PostgreSQL解析器解析和规范化SQL查询 pg_query_go 转到 https://github.com/lfittl/pg_query的版本。这个go库及其扩展使用实际的PostgreSQL服务器源解析SQL查询,并返回内部PostgreSQL解析树。请...

    phpQuery下载

    phpQuery是基于PHP开发的一个强大的网页解析库,它的设计灵感来源于JavaScript库jQuery,因此在使用上有着类似jQuery的语法风格,使得PHP开发者可以方便地在服务器端进行DOM操作,提取和修改HTML或XML文档内容。...

    Power Query第一课模板

    Power Query第一课模板

    易语言DnsQuery解析DNS源码-易语言

    在这个“易语言DnsQuery解析DNS源码”中,我们主要探讨的是如何使用易语言来实现DNS查询功能。 DNS(Domain Name System)域名系统是互联网的一项核心服务,它将人类可读的域名转换为IP地址,从而实现网络的访问。...

    phpQuery_qwpmrj_phpQuery_

    - 获取元素内容:`$doc-&gt;find('h1')-&gt;text()`返回第一个h1元素的文本内容。 - 遍历元素集合:`foreach ($doc-&gt;find('img') as $img)`遍历所有的图片元素并进行操作。 - 修改元素属性:`$doc-&gt;find('a')-&gt;attr('href'...

    5、http请求的query参数1

    $pageInt = $request-&gt;query-&gt;getInt('page', 1); // 输出或使用$page和$pageInt ... } ``` 这里,`$request-&gt;query`是一个`QueryBag`对象,它提供了`get()`和`getInt()`等方法来获取query参数。`get()`方法...

    jurl一个快速简单的URL解析Java库

    1. **快速解析**:`jurl`库设计时考虑了性能,它提供了快速的URL解析功能,可以高效地分解URL的各个组成部分,如协议、主机、端口、路径、查询参数等。 2. **UTF-8编码支持**:在处理URL时,字符编码是一个重要的...

    使用phpQuery轻松实现采集帮助文档

    比如,选择 class 为 "blkTop" 的第一个 `h1` 标签: ```php pq(".blkTop h1:eq(0)") ``` 4. **操作节点**:选取的元素可以通过各种方法进行操作。例如,获取 `html()` 内容或 `text()` 内容: ```php echo pq("....

    power query 入门手册

    2. **获取文本文件**:介绍如何使用Power Query读取和加载文本文件,这包括CSV、TXT等格式的数据,是数据导入的第一步。 3. **更改数据类型**:数据预处理的重要环节,Power Query提供了方便的工具来转换列的数据...

    sap abap query高级功能

    SAP ABAP Query 是 SAP 系统中一种用于创建自定义报表的强大工具,尤其适合那些对 SQL 不太熟悉或者没有数据库直接访问权限的用户。它提供了丰富的功能,使得开发人员可以构建复杂的数据查询,而无需编写大量的 ABAP...

    SAP- Query报表事务代码分配及配置操作手册

    SAP Query 报表是SAP系统中一种用于生成自定义报表的重要工具,它允许用户根据特定需求定制数据报告,从而提高数据分析和决策制定的效率。本操作手册旨在为SAP业务顾问和运维顾问提供关于如何分配和配置SAP Query...

    PowerQuery 中文 2020最新文档

    Power Query是一种强大的数据预处理工具,由微软开发,旨在简化数据获取、清洗和转换的过程。它在Excel和Power BI Desktop中都有集成,极大地提升了用户处理和分析数据的能力。Power Query的核心是M语言(也称为...

    http-query-parse:解析并缓存 http 请求的查询字符串

    一个非常简单的函数,您可以在多个地方调用传入请求,而无需担心性能/缓存,也无需事先解析请求/url。 如果您喜欢这种风格,请查看: 如果可用,使用缓存在_parsedUrl结果,例如 。 安装 npm install ...

    QUERY报表制作和传输

    在SAP系统中,"QUERY报表制作和传输"是一个关键任务,主要涉及到SAP Query工具的使用。SAP Query是SAP R/3系统中的一种报告工具,它允许用户无编程地创建自定义报告,特别适合于那些需要定期生成但不需要复杂逻辑...

Global site tag (gtag.js) - Google Analytics