在SQL中使用Java插入Java变量

时间:2010-02-13 04:45:11

标签: java oracle jdbc

我试图这样做:

 String sql = "INSERT INTO CURRENT_WEATHER_US VALUES("+city_code+",   
"+object.city+","+object.region+","+object.country+","+object.wind_chill+",  
"+object.wind_direction+", "+object.wind_speed+","+object.humidity+","+object.visibility+", 
"+object.pressure+","+object.rising+",  
"+object.sunrise+","+object.sunset+","+object.textual_description+",  
"+object.condition_code+","+object.temp+","+object.for_temp_high+",  
"+object.for_temp_low+","+object.for_description+","+object.forecast_code+")";   

  stmt.execute(sql);  

错误缺少逗号

请帮助

3 个答案:

答案 0 :(得分:27)

这不是你应该用变量构造和执行SQL INSERT查询的方式。这不仅容易出现SQL injection attacks,而且也很容易......很麻烦;)可能是一个包含单引号的值,导致您的查询在语法上无效。

只是不要将变量字符串连接成SQL字符串。相反,将PreparedStatementtutorial here)与?结合使用作为SQL字符串中变量的占位符。通过这种方式,您可以通过值索引很好地将完整的Java对象(包括DateInputStream!)放入SQL语句中,而无需担心字符串中可能在语法上破坏SQL查询的字符(从而也会导致SQL注射风险)。

以下是基于原始SQL查询的启动示例:

private static final String SQL_INSERT = "INSERT INTO CURRENT_WEATHER_US"
    + " VALUES(?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)";

public void create(String cityCode, Weather weather) throws SQLException {
    try (
        Connection connection = database.getConnection();
        PreparedStatement statement = connection.prepareStatement(SQL_INSERT);
    ) {
        statement.setString(1, cityCode);
        statement.setString(2, weather.getCity());
        statement.setString(3, weather.getRegion());
        // ...
        statement.setString(20, weather.getForecastCode());
        statement.executeUpdate();
    }
}

要了解有关正确使用基本JDBC 的更多信息,您可能会发现this article非常有用。

希望这有帮助。

答案 1 :(得分:3)

您应该考虑使用PrepairedStatements而不是构建字符串。他们更快,并处理与引用和逃避价值相关的许多陷阱。

答案 2 :(得分:0)

与其他所有人一样,出于多种原因,您确实应该将其转换为使用PreparedStatements。您最有可能收到错误(您没有发布确切的ORA错误),因为您传入了String类型值,但是您没有在硬编码查询中将它们包装在单引号中。

如果textual_description和for_description中查询中唯一的String类型列,则您的查询需要如下所示:

String sql = "INSERT INTO CURRENT_WEATHER_US VALUES( " +
    city_code + ", " +
    object.city + ", " +
    object.region + ", " +
    object.country + ", " +
    object.wind_chill  + ", " +
    object.wind_direction + ", " +
    object.wind_speed + ", " +
    object.humidity + ", " +
    object.visibility + ", " +
    object.pressure + ", " +
    object.rising + ", " +
    object.sunrise + ", " +
    object.sunset + ", " +
    "'" + object.textual_description + "', " +
    object.condition_code + ", " +
    object.temp + ", " +
    object.for_temp_high + ", " +
    object.for_temp_low + ", " +
    "'" + object.for_description + "', " +
    object.forecast_code + 
    " )";   

stmt.execute(sql);  

请注意现在围绕这些值的单引号。