带有/多个参数的 JDBCTemplate 传递

Posted

技术标签:

【中文标题】带有/多个参数的 JDBCTemplate 传递【英文标题】:JBDCTemplate Pass w/ multiple parameters 【发布时间】:2016-01-08 12:11:31 【问题描述】:

事情是这样的……我无法通过以下代码传递以下语句“this”从未打印,因此结果集为 0,但查询似乎正确。

查询:

从 title = 1 和 (zipcode = 11738 或 zipcode = 11720 或 zipcode = 11727 或 zipcode = 11741 或 zipcode = 11742 或 zipcode = 11755 或 zipcode = 11763 或 zipcode = 11776 或 zipcode = 11779 或 zipcode 的机会中选择 * = 11784 或邮政编码 = 11953)


上面的查询确实返回了结果。***

代码(只是切换了标题和邮政编码位置,运行代码时仍然会返回 0 个结果)

public Opportunity[] getOpportunitiesBy(String title, String zipcode, double miles) 
    title = ""+Constants.TITLES_MAP.get(title.toLowerCase());
    String[] nearbyZipcodes = getZipcodesWithinRadius(zipcode, miles);
    StringBuilder builder = new StringBuilder();
    builder.append("(zipcode = "+zipcode+" or zipcode = "); 
    for(String otherZips : nearbyZipcodes) 
        builder.append(otherZips+" or zipcode = ");
    
    String formattedZips = Utilities.replaceLast(builder.toString(), " or zipcode = ", ")");
    System.out.println(title+","+formattedZips);
    List<Opportunity> opportunities = this.jdbcTemplate.query("select * from opportunities where ? and title = ?",
            new Object[]  formattedZips, title, new RowMapper<Opportunity>() 
                public Opportunity mapRow(ResultSet rs, int rowNum) throws SQLException 
                    Opportunity temp = new Opportunity();
                    System.out.println("this");
                    String[] candidateIds = rs.getString("candidateIds").split(",");
                    temp.setCandidateIds(Utilities.StringToIntArray(candidateIds));
                    temp.setCompany(rs.getString("company"));
                    temp.setId(rs.getLong("id"));
                    temp.sethtml(rs.getString("post_data"));
                    temp.setZipcode(rs.getString("zipcode"));
                    temp.setTitle(rs.getInt("title"));
                    try 
                        temp.setLogoImg(new URI(rs.getString("logo_img")));
                     catch (Exception e) 
                    
                    return temp;
                
            );
    return opportunities.toArray(new Opportunity[opportunities.size()]);

初始 println(title+","+formattedZips) 的输出

1,(邮编 = 11738 或邮编 = 11720 或邮编 = 11727 或邮编 = 11741 或邮编 = 11742 或邮编 = 11755 或邮编 = 11763 或邮编 = 11776 或邮编 = 11779 或邮编 = 11784 或邮编 = 11953)

【问题讨论】:

【参考方案1】:

您的设置有 2 个问题。

首先,您不应该使用串联来创建(部分)查询,其次这不是参数化查询的工作方式。参数在放入之前被转义,所以我怀疑查询是你所期望的。

SQL 使用 in 子句而不是 zipcode or zipcode or zipcode) 在查询中使用单个 in 子句。但是,当您想传入数组时,您又遇到了问题。要解决这个问题,请使用 NamedParameterJdbcTemplate 而不是普通的 JdbcTemplate。然后重写您的查询以使用命名参数和in 子句。

public Opportunity[] getOpportunitiesBy(String title, String zipcode, double miles) 
   String sql = "select * from opportunities where title = :title and zipcode in (:zips)";
   title = ""+Constants.TITLES_MAP.get(title.toLowerCase());
   String[] nearbyZipcodes = getZipcodesWithinRadius(zipcode, miles);

   Map<String, Object> params = new HashMap<>();
   params.put("title", nearbyZipcodes);
   params.put("zips", near)

   return this.jdbcTemplate.query(sql, params, new RowMapper<Opportunity>() 
       public Opportunity mapRow(ResultSet rs, int rowNum) throws SQLException 
           Opportunity temp = new Opportunity();
           System.out.println("this");
           String[] candidateIds = rs.getString("candidateIds").split(",");
           temp.setCandidateIds(Utilities.StringToIntArray(candidateIds));
           temp.setCompany(rs.getString("company"));
           temp.setId(rs.getLong("id"));
           temp.setHtml(rs.getString("post_data"));
           temp.setZipcode(rs.getString("zipcode"));
           temp.setTitle(rs.getInt("title"));
           try 
               temp.setLogoImg(new URI(rs.getString("logo_img")));
            catch (Exception e) 
           
           return temp;
       );


类似的东西应该可以解决问题,但是如果您的 getZipCodesWithinRadius 也在使用查询,您甚至可以将其用作 in 子句中的子选择并简单地传入给定的 zipcode 和 @ 987654331@,这样您将有一个查询一次性获得结果(而不是 2 个查询和所有的 jdbc 内容)。

【讨论】:

以上是关于带有/多个参数的 JDBCTemplate 传递的主要内容,如果未能解决你的问题,请参考以下文章

将不同类型的参数传递给 jdbctemplate 查询

Spring JdbcTemplate / NamedParameterJdbcTemplate 传递空值作为参数值

带有命名参数和行映射器的列表的Java Jdbctemplate查询?

使用 JDBCTemplate 在“IN”子句中将 List<String> 作为查询参数传递时获取 PSQL 异常

如何将带有管道符号的多个参数传递到bash脚本案例语句中

如何将向量中的值传递给带有多个参数的函数