let’s say we need now we need a method
is all the information in the query table
we’ll write
@Override
public List<User> selectAll() {
SqlSession sqlSession = factory.openSession();
List<User> userList = sqlSession.selectList("com.tubai.dao.UserDao.selectAll");
sqlSession.close();
return userList;
}
is mainly through the sqlSession selectList to achieve the function
so how does Mybatis do this work for us?
pursue source
let’s start
in debug mode and step into
when this sentence is executed
userDao = sqlSession.getMapper(UserDao.class);
to p>
public <T> T getMapper(Class<T> type) {
return this.configuration.getMapper(type, this);
}
next->
public <T> T getMapper(Class<T> type, SqlSession sqlSession) {
return this.mapperRegistry.getMapper(type, sqlSession);
}
->
public <T> T getMapper(Class<T> type, SqlSession sqlSession) {
MapperProxyFactory<T> mapperProxyFactory = (MapperProxyFactory)this.knownMappers.get(type);
if (mapperProxyFactory == null) {
throw new BindingException("Type " + type + " is not known to the MapperRegistry.");
} else {
try {
return mapperProxyFactory.newInstance(sqlSession);
} catch (Exception var5) {
throw new BindingException("Error getting mapper instance. Cause: " + var5, var5);
}
}
}
we found that
was executed
return mapperProxyFactory.newInstance(sqlSession);
continue into ->
public T newInstance(SqlSession sqlSession) {
MapperProxy<T> mapperProxy = new MapperProxy(sqlSession, this.mapperInterface, this.methodCache);
return this.newInstance(mapperProxy);
}
->
protected T newInstance(MapperProxy<T> mapperProxy) {
return Proxy.newProxyInstance(this.mapperInterface.getClassLoader(), new Class[]{this.mapperInterface}, mapperProxy);
}
here we find that the newProxyInstance method that calls the dynamic proxy
so let’s go straight to the third parameter
open the class MapperProxy
find the invoke method inside
public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
try {
if (Object.class.equals(method.getDeclaringClass())) {
return method.invoke(this, args);
}
if (this.isDefaultMethod(method)) {
return this.invokeDefaultMethod(proxy, method, args);
}
} catch (Throwable var5) {
throw ExceptionUtil.unwrapThrowable(var5);
}
MapperMethod mapperMethod = this.cachedMapperMethod(method);
return mapperMethod.execute(this.sqlSession, args);
}
finds that it finally calls
mapperMethod.execute(this.sqlSession, args);
open the source code for this method and continue
public Object execute(SqlSession sqlSession, Object[] args) {
Object param;
Object result;
switch(this.command.getType()) {
case INSERT:
param = this.method.convertArgsToSqlCommandParam(args);
result = this.rowCountResult(sqlSession.insert(this.command.getName(), param));
break;
case UPDATE:
param = this.method.convertArgsToSqlCommandParam(args);
result = this.rowCountResult(sqlSession.update(this.command.getName(), param));
break;
case DELETE:
param = this.method.convertArgsToSqlCommandParam(args);
result = this.rowCountResult(sqlSession.delete(this.command.getName(), param));
break;
case SELECT:
if (this.method.returnsVoid() && this.method.hasResultHandler()) {
this.executeWithResultHandler(sqlSession, args);
result = null;
} else if (this.method.returnsMany()) {
result = this.executeForMany(sqlSession, args);
} else if (this.method.returnsMap()) {
result = this.executeForMap(sqlSession, args);
} else if (this.method.returnsCursor()) {
result = this.executeForCursor(sqlSession, args);
} else {
param = this.method.convertArgsToSqlCommandParam(args);
result = sqlSession.selectOne(this.command.getName(), param);
}
break;
case FLUSH:
result = sqlSession.flushStatements();
break;
default:
throw new BindingException("Unknown execution method for: " + this.command.getName());
}
if (result == null && this.method.getReturnType().isPrimitive() && !this.method.returnsVoid()) {
throw new BindingException("Mapper method '" + this.command.getName() + " attempted to return null from a method with a primitive return type (" + this.method.getReturnType() + ").");
} else {
return result;
}
}
in Case:SELECT we find
result = this.executeForMany(sqlSession, args);
let’s do
private <E> Object executeForMany(SqlSession sqlSession, Object[] args) {
Object param = this.method.convertArgsToSqlCommandParam(args);
List result;
if (this.method.hasRowBounds()) {
RowBounds rowBounds = this.method.extractRowBounds(args);
result = sqlSession.selectList(this.command.getName(), param, rowBounds);
} else {
result = sqlSession.selectList(this.command.getName(), param);
}
if (!this.method.getReturnType().isAssignableFrom(result.getClass())) {
return this.method.getReturnType().isArray() ? this.convertToArray(result) : this.convertToDeclaredCollection(sqlSession.getConfiguration(), result);
} else {
return result;
}
}~
and finally we found
sqlSession.selectList
div>
Read More:
- Related configuration of mybatis project
- The method of Java jumping out of loop
- Java gets the type t.class of generic t
- How to Use the object of ES6 to clear the object value
- Detailed explanation of Python__ new__() method
- Java uses the same event listener for the same type of component
- Error type referred to is not an annotation type:RedisCache
- error: a label can only be part of a statement and a declaration is not a statement (How to Fix)
- Vue: How to prompt this .$message
- Python switch / case statement implementation method
- Springboot integration redis reports non null key required (solved)
- Java compareto() method
- Exception of browser accessing servlet404
- Pit encountered by entity class data type BigDecimal
- Implementation of Python switch / case statements
- Get the height of mobile phone status bar through reflection
- Java retainAll throws an unsupported operation exception record
- java.lang.AbstractMethodError: Receiver class com.alibaba.cloud.sentinel.feign.SentinelContractHolde
- IOS reverse error: use of undeclared identifier ‘mshookivar’
- 21. Merge Two Sorted Lists [easy] (Python)