我的代码目前如下:
public List<DeviceOrganizationMetadataHolder> getChildrenByParentId(List<String> parentIds) throws DeviceOrganizationDAOException {
List<DeviceOrganizationMetadataHolder> children = new ArrayList<>();
Connection conn;
PreparedStatement stmt = null;
ResultSet rs = null;
DeviceOrganizationMetadataHolder deviceMetadataHolder;
String[] data = parentIds.toArray(new String[parentIds.size()]);
try {
conn = this.getConnection();
String sql = "SELECT * FROM DEVICE_ORGANIZATION_MAP WHERE DEVICE_PARENT IN (?)";
stmt = conn.prepareStatement(sql);
data = parentIds.toArray(data);
stmt.setObject(1, data);
rs = stmt.executeQuery();
while (rs.next()) {
deviceMetadataHolder = this.loadOrganization(rs);
children.add(deviceMetadataHolder);
}
} catch (SQLException e) {
throw new DeviceOrganizationDAOException("Error occurred for device list with while retrieving children.", e);
} finally {
DeviceManagementDAOUtil.cleanupResources(stmt, rs);
return children;
}
}
然而,即使在单元测试中我尝试使用parentIds传递数组,但返回仍然为null。 我可以从中判断出以下情况之一:
我在哪里错了?
编辑 - 标记了类似的duplicate question。虽然它建议使用StringBuilder和循环,但我一直在寻找一个答案,说明如何使用查询本身以更干净的方式完成它。
答案 0 :(得分:1)
尝试将参数设置为列表而不是数组,即替换
stmt.setObject(1, data);
与
stmt.setObject(1, Arrays.asList(data));
答案 1 :(得分:0)
想出来。
在h2database GitHub上发布了issue关于这个确切问题的信息。按照建议的编辑和工作!
编辑后的代码如下:
public List<DeviceOrganizationMetadataHolder> getChildrenByParentId(List<String> parentIds) throws DeviceOrganizationDAOException {
List<DeviceOrganizationMetadataHolder> children = new ArrayList<>();
Connection conn;
PreparedStatement stmt = null;
ResultSet rs = null;
DeviceOrganizationMetadataHolder deviceMetadataHolder;
Object[] data = parentIds.toArray();
try {
conn = this.getConnection();
String sql = "SELECT * FROM DEVICE_ORGANIZATION_MAP WHERE DEVICE_PARENT IN (SELECT * FROM TABLE(x VARCHAR = ?))";
stmt = conn.prepareStatement(sql);
stmt.setObject(1, data);
rs = stmt.executeQuery();
while (rs.next()) {
deviceMetadataHolder = this.loadOrganization(rs);
children.add(deviceMetadataHolder);
}
} catch (SQLException e) {
throw new DeviceOrganizationDAOException("Error occurred for device list with while retrieving children.", e);
} finally {
DeviceManagementDAOUtil.cleanupResources(stmt, rs);
return children;
}
}
正如您所看到的,我已经使用Object数组代替数据,并在主查询中添加了一个额外的查询。 按照GitHub问题中的说明进行开球,它完美无缺。