package cloud.agileframework.mybatis.page;
import cloud.agileframework.common.util.clazz.TypeReference;
import cloud.agileframework.common.util.object.ObjectUtil;
import com.google.common.collect.Lists;
import com.google.common.collect.Maps;
import org.apache.ibatis.binding.MapperMethod;
import org.apache.ibatis.cache.CacheKey;
import org.apache.ibatis.cursor.Cursor;
import org.apache.ibatis.executor.ErrorContext;
import org.apache.ibatis.executor.Executor;
import org.apache.ibatis.executor.ExecutorException;
import org.apache.ibatis.executor.loader.ResultLoader;
import org.apache.ibatis.executor.loader.ResultLoaderMap;
import org.apache.ibatis.executor.parameter.ParameterHandler;
import org.apache.ibatis.executor.result.DefaultResultContext;
import org.apache.ibatis.executor.result.DefaultResultHandler;
import org.apache.ibatis.executor.result.ResultMapException;
import org.apache.ibatis.executor.resultset.ResultSetHandler;
import org.apache.ibatis.executor.resultset.ResultSetWrapper;
import org.apache.ibatis.mapping.BoundSql;
import org.apache.ibatis.mapping.Discriminator;
import org.apache.ibatis.mapping.MappedStatement;
import org.apache.ibatis.mapping.ParameterMapping;
import org.apache.ibatis.mapping.ParameterMode;
import org.apache.ibatis.mapping.ResultMap;
import org.apache.ibatis.mapping.ResultMapping;
import org.apache.ibatis.reflection.MetaClass;
import org.apache.ibatis.reflection.MetaObject;
import org.apache.ibatis.reflection.ReflectorFactory;
import org.apache.ibatis.reflection.factory.ObjectFactory;
import org.apache.ibatis.session.AutoMappingBehavior;
import org.apache.ibatis.session.Configuration;
import org.apache.ibatis.session.ResultContext;
import org.apache.ibatis.session.ResultHandler;
import org.apache.ibatis.session.RowBounds;
import org.apache.ibatis.type.TypeHandler;
import org.apache.ibatis.type.TypeHandlerRegistry;
import java.lang.reflect.Constructor;
import java.sql.CallableStatement;
import java.sql.ResultSet;
import java.sql.ResultSetMetaData;
import java.sql.SQLException;
import java.sql.Statement;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.HashSet;
import java.util.List;
import java.util.Locale;
import java.util.Map;
import java.util.Set;
/**
* 描述:
* <p>创建时间:2018/12/14<br>
*
* @author 佟盟
* @version 1.0
* @since 1.0
*/
public class CustomResultSetHandler implements ResultSetHandler {
private static final int LENGTH = 16;
private static final Object DEFERED = new Object();
private final Executor executor;
private final Configuration configuration;
private final MappedStatement mappedStatement;
private final RowBounds rowBounds;
private final ParameterHandler parameterHandler;
private final ResultHandler<?> resultHandler;
private final BoundSql boundSql;
private final TypeHandlerRegistry typeHandlerRegistry;
private final ObjectFactory objectFactory;
private final ReflectorFactory reflectorFactory;
// nested resultmaps
private final Map<CacheKey, Object> nestedResultObjects = new HashMap<>();
private final Map<String, Object> ancestorObjects = new HashMap<>();
// multiple resultsets
private final Map<String, ResultMapping> nextResultMaps = new HashMap<>();
private final Map<CacheKey, List<PendingRelation>> pendingRelations = new HashMap<>();
// Cached Automappings
private final Map<String, List<UnMappedColumnAutoMapping>> autoMappingsCache = new HashMap<>();
private Object previousRowValue;
// temporary marking flag that indicate using constructor mapping (use field to reduce memory usage)
private boolean useConstructorMappings;
public CustomResultSetHandler(Executor executor, MappedStatement mappedStatement, ParameterHandler parameterHandler, ResultHandler<?> resultHandler, BoundSql boundSql, RowBounds rowBounds) {
this.executor = executor;
this.configuration = mappedStatement.getConfiguration();
this.mappedStatement = mappedStatement;
this.rowBounds = rowBounds;
this.parameterHandler = parameterHandler;
this.boundSql = boundSql;
this.typeHandlerRegistry = configuration.getTypeHandlerRegistry();
this.objectFactory = configuration.getObjectFactory();
this.reflectorFactory = configuration.getReflectorFactory();
this.resultHandler = resultHandler;
}
@Override
public void handleOutputParameters(CallableStatement cs) throws SQLException {
final Object parameterObject = parameterHandler.getParameterObject();
final MetaObject metaParam = configuration.newMetaObject(parameterObject);
final List<ParameterMapping> parameterMappings = boundSql.getParameterMappings();
for (int i = 0; i < parameterMappings.size(); i++) {
final ParameterMapping parameterMapping = parameterMappings.get(i);
if (parameterMapping.getMode() == ParameterMode.OUT || parameterMapping.getMode() == ParameterMode.INOUT) {
if (ResultSet.class.equals(parameterMapping.getJavaType())) {
handleRefCursorOutputParameter((ResultSet) cs.getObject(i + 1), parameterMapping, metaParam);
} else {
final TypeHandler<?> typeHandler = parameterMapping.getTypeHandler();
metaParam.setValue(parameterMapping.getProperty(), typeHandler.getResult(cs, i + 1));
}
}
}
}
private void handleRefCursorOutputParameter(ResultSet rs, ParameterMapping parameterMapping, MetaObject metaParam) throws SQLException {
if (rs == null) {
return;
}
try {
final String resultMapId = parameterMapping.getResultMapId();
final ResultMap resultMap = configuration.getResultMap(resultMapId);
final DefaultResultHandler defaultResultHandler = new DefaultResultHandler(objectFactory);
final ResultSetWrapper rsw = new ResultSetWrapper(rs, configuration);
handleRowValues(rsw, resultMap, defaultResultHandler, new RowBounds(), null);
metaParam.setValue(parameterMapping.getProperty(), defaultResultHandler.getResultList());
} finally {
// issue #228 (close resultsets)
closeResultSet(rs);
}
}
//
// HANDLE OUTPUT PARAMETER
//
@Override
public List<Object> handleResultSets(Statement stmt) throws SQLException {
ErrorContext.instance().activity("handling results").object(mappedStatement.getId());
final List<Object> multipleResults = new ArrayList<Object>();
int resultSetCount = 0;
ResultSetWrapper rsw = getFirstResultSet(stmt);
List<ResultMap> resultMaps = mappedStatement.getResultMaps();
int resultMapCount = resultMaps.size();
validateResultMapsCount(rsw, resultMapCount);
while (rsw != null && resultMapCount > resultSetCount) {
ResultMap resultMap = resultMaps.get(resultSetCount);
handleResultSet(rsw, resultMap, multipleResults, null);
rsw = getNextResultSet(stmt);
cleanUpAfterHandlingResultSet();
resultSetCount++;
}
String[] resultSets = mappedStatement.getResultSets();
if (resultSets != null) {
while (rsw != null && resultSetCount < resultSets.length) {
ResultMapping parentMapping = nextResultMaps.get(resultSets[resultSetCount]);
if (parentMapping != null) {
String nestedResultMapId = parentMapping.getNestedResultMapId();
ResultMap resultMap = configuration.getResultMap(nestedResultMapId);
handleResultSet(rsw, resultMap, null, parentMapping);
}
rsw = getNextResultSet(stmt);
cleanUpAfterHandlingResultSet();
resultSetCount++;
}
}
return collapseSingleResultList(multipleResul
没有合适的资源?快使用搜索试试~ 我知道了~
温馨提示
结果POJO映射 查询返回结果可以直接声明为POJO或POJO集合,其映射过程是依赖于cloud.agileframework:common-util对象深度转换器实现,所以支持 识别驼峰与下划线等风格属性的互转。只需声明,无需额外调用,以最低的代码入侵实现类似ORM映射效果。分页拦截器 分页方式是通过扩展Mybatis拦截器,当入参中包含接口MybatisPage类(及其实现类)且返回参数为Page形式时触发分页拦截器,解析总条数 total及页内容content。只需声明,无需额外调用,以最低的代码入侵实现Mybatis分页。低代码入侵 不改变任何Mybatis原生编码方式及能力
资源推荐
资源详情
资源评论
收起资源包目录
agile-mybatis-master.zip (21个子文件)
agile-mybatis-master
pom.xml 10KB
src
test
resources
application.properties 585B
testMapper.xml 388B
test-data.sql 2KB
test.sql 306B
java
com
agile
repository
MyRepository.java 3KB
entity
SysApiEntity.java 960B
TestService.java 6KB
App.java 421B
main
resources
META-INF
spring.factories 125B
java
cloud
agileframework
mybatis
page
MybatisInterceptor.java 5KB
MybatisPage.java 406B
CustomConfiguration.java 1KB
Page.java 955B
CustomCursor.java 6KB
CustomResultSetHandler.java 56KB
PageExecutor.java 9KB
config
MyBatisAutoConfiguration.java 2KB
LICENSE 11KB
pom.xml.versionsBackup 10KB
.gitignore 35B
共 21 条
- 1
资源评论
Java程序员-张凯
- 粉丝: 1w+
- 资源: 6656
上传资源 快速赚钱
- 我的内容管理 展开
- 我的资源 快来上传第一个资源
- 我的收益 登录查看自己的收益
- 我的积分 登录查看自己的积分
- 我的C币 登录后查看C币余额
- 我的收藏
- 我的下载
- 下载帮助
最新资源
- Qt开发知识、经验总结 包括Qss,数据库,Excel,Model/View等
- IV数据.xlsx
- foldcraftlauncher_262944.apk
- 珍藏多年的基于matlab实现潮流计算程序源代码集合,包含多个潮流计算程序.rar
- 使用FPGA实现串-并型乘法器
- 基于matlab实现针对基于双曲线定位的DV-Hop算法中误差误差出一种基于加权双曲线定位的DV-Hop改进算法.rar
- 基于matlab实现由遗传算法开发的整数规划,车辆调度问题.rar
- 电视家7.0(对电视配置要求高).apk
- 免费计算机毕业设计-基于JavaEE的医院病历管理系统设计与实现(包含论文+源码)
- 手机端 我的世界融合植物大战僵尸版.apk
资源上传下载、课程学习等过程中有任何疑问或建议,欢迎提出宝贵意见哦~我们会及时处理!
点击此处反馈
安全验证
文档复制为VIP权益,开通VIP直接复制
信息提交成功