Sql.execute 中的 Groovy GString - 文本变量不被 ' 包围并且查询失败

发布于 2024-10-01 20:14:43 字数 536 浏览 3 评论 0原文

我遇到以下问题,当我将 GString 传递给 SQL.executeInsert 时,文本变量不会自动通过 ' 进行修改,因此插入查询失败:

String value4fa = "I would like to get know"
int value4fb = 2
def query = "INSERT INTO TAB_A (F_A, F_B) VALUES (${value4fa}, ${value4fb})"
sql.executeInsert(query);

如果我自己放置 '

 def query = "INSERT INTO TAB_A (F_A, F_B) VALUES ('${value4fa}', ${value4fb})"

Groovy 通知我引入了一个安全漏洞,因为 Groovy 无法使用PreparedStatement 来执行SQL 查询。

有人能解释一下如何强制 Groovy 正确评估查询主体并准备变量吗?

I have the following problem, when I pass GString to SQL.executeInsert, the text variables are not automatically souranded by ' so the insert query failes:

String value4fa = "I would like to get know"
int value4fb = 2
def query = "INSERT INTO TAB_A (F_A, F_B) VALUES (${value4fa}, ${value4fb})"
sql.executeInsert(query);

If I put ' by myself:

 def query = "INSERT INTO TAB_A (F_A, F_B) VALUES ('${value4fa}', ${value4fb})"

Groovy informs me that I have introduced a security hole, because Groovy can not use PreparedStatement to execute the SQL query.

Could anybody explain me how to force Groovy to evaluate query body correctly and prepare the variables?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(2

彻夜缠绵 2024-10-08 20:14:44

您不必用任何东西修饰字符串即可将它们自动转换为 PreparedStatement

sql.execute("INSERT INTO TAB_A (F_A, F_B) VALUES ($value4fa, $value4fb)")

将为所有接受 GString 作为单个参数的方法做正确的事情。 请注意缺少 {},它是 .toString() 的语法糖。

您引起投诉的原因是,

def query = "INSERT INTO TAB_A (F_A, F_B) VALUES (${value4fa}, ${value4fb})"
sql.execute(query)

与传递GString 直接到该方法。

它在将 query 传递给 .execute() 方法之前应用替换。根据您的示例数据,它将传递以下内容并且替换已经发生。 “INSERT INTO TAB_A (F_A, F_B) VALUES (I would like to get Know, 2)” 这甚至不是有效的 SQL 语句,因为字符串值缺少 ' 围绕它。

这在功能上等同于使用 String.format()StringBuilder/Buffer.append() 或使用 + 进行普通连接。

You should not have to decorate strings with anything to have them converted to PreparedStatement automatically.

sql.execute("INSERT INTO TAB_A (F_A, F_B) VALUES ($value4fa, $value4fb)")

will do the correct thing for all the methods that accept a GString as a single parameter. note the lack of {} which is syntactic sugar for .toString()

The reason yours causes the complaint is that,

def query = "INSERT INTO TAB_A (F_A, F_B) VALUES (${value4fa}, ${value4fb})"
sql.execute(query)

is different than passing the GString directly to the method.

it applies the substitutions before passing query to the .execute() method. Given your example data, it passes the following to and the replacements have already happened. "INSERT INTO TAB_A (F_A, F_B) VALUES (I would like to get know, 2)" which is not even a valid SQL statement because the string value is missing the ' around it.

This is functionally equivalent to using String.format(), StringBuilder/Buffer.append() or plain on concatenation using +.

难如初 2024-10-08 20:14:44

我没有测试过这个想法,但是2.4.4的代码 ​​在这里

execute(String sql, Listparams) 方法使用准备好的语句。

鉴于此,请考虑以下示例:

firstName = "yue"
lastName = "wu"
sql.execute("insert into people (firstName, lastName) "+
  " values (?,?)", [firstName, lastName])

如有必要,可以轻松向变量本身(而不是 SQL 字符串)添加单引号。

I have not tested this idea, but the code for 2.4.4 is here.

The execute(String sql, List<Object> params) method uses prepared statements.

Given that, consider this example:

firstName = "yue"
lastName = "wu"
sql.execute("insert into people (firstName, lastName) "+
  " values (?,?)", [firstName, lastName])

If necessary, it is easy to add single-quotes to the variables themselves (rather than the SQL string).

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文