How to pass an Integer Array to IN clause in MyBatis
YES, you can do that using annotations.
If you're using postgresql, you can do like in this post.
If you're using MySQL try this changes in your code sample:
Mybatis Method using Annotations
@Select(SEL_QUERY)
@Results(value = {@Result(property="id",column="ID")})
List<Integer> getIds(@Param("usrIds") String usrIds);
Query (using MySQL)
select distinct ID from table a where FIND_IN_SET( a.id, #{usrIds}) <> 0
Method call
Integer[] arr = new Integer[2];
arr[0] = 1;
arr[1] = 2;
String usrIds= "";
for (int id : ids) {
usrIds += id + ",";
}
mapper.getIds(usrIds)
The myBatis User Guide on Dynamic SQL has an example on how to use a foreach loop to build the query string, which works for lists and arrays.
Prior to release 3.2 you had to use xml configuration to use dynamic sql, with newer versions it should also be possible to use dynamic sql in annotations.
<select id="selectPostIn" resultType="domain.blog.Post">
SELECT *
FROM POST P
WHERE ID in
<foreach item="item" index="index" collection="list"
open="(" separator="," close=")">
#{item}
</foreach>
</select>
You can create a new type handler and use it only for your parameter. The query would change to:
SELECT ... WHERE FIND_IN_SET(id, #{usrIds, typeHandler=my.pkg.ListTypeHandler}) <> 0
And the type handler:
import java.sql.PreparedStatement;
import java.sql.SQLException;
import org.apache.ibatis.type.JdbcType;
import org.apache.ibatis.type.ObjectTypeHandler;
import com.google.common.base.Joiner;
public class ListTypeHandler extends ObjectTypeHandler {
@Override
public void setParameter(PreparedStatement ps, int i, Object parameter, JdbcType jdbcType) throws SQLException {
ps.setObject(i, Joiner.on(",").join((Iterable<?>) parameter), JdbcType.OTHER.TYPE_CODE);
}
}