java - 使用 JdbcTemplace.query() 时,每行结果都会执行一个 SELECT 查询
问题描述
我意识到,当我使用 JdbcTemplace.query() 执行一个返回许多记录的简单选择时,数百个选择正在后台执行。实际上每行一个,由于我的 ACL 表中某些用户的记录数量很多,这最终成为一个性能问题。
private final String PERMISSIONS_QUERY = "SELECT acl.user_id, acl.permission FROM v_user_acls acl WHERE acl.principal = :userId ";
private NamedParameterJdbcTemplate jdbcTemplate;
MapSqlParameterSource params = new MapSqlParameterSource(DAOConstants.USER_ID_KEY, userId);
List<UserPermissionRow> userPermissions = jdbcTemplate.query(PERMISSIONS_QUERY, params,
new RowMapper<UserPermissionRow>() {
@Override
public UserPermissionRow mapRow(ResultSet rs, int rowNum) throws SQLException {
return new UserPermissionRow(rs.getString(1), rs.getString(2));
}
});
我查看了显示正在执行的查询的 P6Spy 日志。如您所见,一个查询是按行执行的(我认为效率不是很高)。
READ
1566811816536|-1||resultset|SELECT acl.user_id, acl.permission FROM v_user_acls acl WHERE acl.principal = '11582' |USER_ID = 10078, PERMISSION =
READ
1566811816536|-1||resultset|SELECT acl.user_id, acl.permission FROM v_user_acls acl WHERE acl.principal = '11582' |USER_ID = 10079, PERMISSION =
READ
1566811816536|-1||resultset|SELECT acl.user_id, acl.permission FROM v_user_acls acl WHERE acl.principal = '11582' |USER_ID = 10080, PERMISSION =
READ
1566811816536|-1||resultset|SELECT acl.user_id, acl.permission FROM v_user_acls acl WHERE acl.principal = '11582' |USER_ID = 10081, PERMISSION =
READ
1566811816536|-1||resultset|SELECT acl.user_id, acl.permission FROM v_user_acls acl WHERE acl.principal = '11582' |USER_ID = 10082, PERMISSION =
READ
1566811816536|-1||resultset|SELECT acl.user_id, acl.permission FROM v_user_acls acl WHERE acl.principal = '11582' |USER_ID = 10083, PERMISSION =
READ
1566811816538|-1||resultset|SELECT acl.user_id, acl.permission FROM v_user_acls acl WHERE acl.principal = '11582' |USER_ID = 10084, PERMISSION =
READ
1566811816538|-1||resultset|SELECT acl.user_id, acl.permission FROM v_user_acls acl WHERE acl.principal = '11582' |USER_ID = 10085, PERMISSION =
READ
1566811816538|-1||resultset|SELECT acl.user_id, acl.permission FROM v_user_acls acl WHERE acl.principal = '11582' |USER_ID = 10086, PERMISSION =
READ
1566811816538|-1||resultset|SELECT acl.user_id, acl.permission FROM v_user_acls acl WHERE acl.principal = '11582' |USER_ID = 10087, PERMISSION = READ
...
..
.
我想知道是否会有一种更有效的方法来检索如此大量的数据,只需一次选择到数据库。
我将非常感谢一些反馈。
问题中原始方法的响应时间为 5726 毫秒。
请参阅下面我尝试的替代方法。不幸的是,整体时间没有改善。
选项 1(状态)
Statement stmt = dataSource.getConnection().createStatement();
ResultSet rs = stmt.executeQuery(EXPERT_ACCESS_QUERY_2 + userId);
List<UserPermissionTest> list =new ArrayList<UserPermissionTest>();
// ============= Expert Access Query RAW: 79 ms
while(rs.next()){
UserPermissionTest e=new UserPermissionTest();
e.setIdentity(rs.getString(1));
e.setPermission(rs.getString(2));
list.add(e);
}
// ============ 5554 ms
选项 2(结果集提取器)
List <UserPermissionTest> userPerms = jdbcTemplate.query(EXPERT_ACCESS_QUERY_2 + userId,
new ResultSetExtractor<List<UserPermissionTest>>(){
@Override
public List<UserPermissionTest> extractData(ResultSet rs) throws SQLException, DataAccessException {
List<UserPermissionTest> list =new ArrayList<UserPermissionTest>();
while(rs.next()){
UserPermissionTest e=new UserPermissionTest();
e.setIdentity(rs.getString(1));
e.setPermission(rs.getString(2));
list.add(e);
}
return list;
}
});
//========= 5694 ms
解决方案
也许那是因为您在下面的 sql 脚本中使用了单个 userId:
private final String PERMISSIONS_QUERY = "SELECT acl.user_id, acl.permission FROM v_user_acls acl WHERE acl.principal = :userId ";
尝试使用 IN 并在 where 条件中使用 userID 列表作为参数?
如果这有帮助,我找到了这个参考: https ://www.technicalkeeda.com/spring-tutorials/spring-jdbctemplate-in-clause-example
推荐阅读
- python - 检查列表中特定元素的元素值
- python - 界面无法进行人脸识别的问题
- django - Django表单忽略保存与提交的验证
- jquery - 从选定的 Object.keys 获取和使用值
- python - 我试图制作一个代码来编辑任务管理器中的优先级
- go - Github REST API ... go-github 似乎缺少 PyGithub 中的功能?
- vue.js - axios 无法阅读 403 答案正文
- node.js - 尝试将代码部署到heroku时与mongo db集群的连接关闭
- c - 在 Linux 的 Raspberry Pi 上使用 C 语言从头开始进行 I²C 通信
- java - 如何在“Androidx”项目中使用支持“支持库”