SQL 注入输入验证

Posted

技术标签:

【中文标题】SQL 注入输入验证【英文标题】:SQL Injection input validation 【发布时间】:2019-06-24 02:49:06 【问题描述】:

我有一个基于 Ruby on Rails 构建的 API,并且我不在 ActiveRecord 方法中使用字符串插值,例如 wherefind_by,.... 这会阻止我的代码执行任何 SQL 注入并处理 SQL 注入作为字符串。

但是,我想找到一种在处理请求之前验证参数的方法。如果参数中的任何字符串值包含 SQL 注入,我想立即拒绝该请求。

我一直在寻找可以帮助进行 的 gem,但我找不到任何东西。我可以使用 REGEX 通过在字符串中查找任何 selectfrom 关键字来验证字符串值,但这不是一个很好的方法,因为如果字符串值(注释)包含像 "We select this item from the collection A" 这样的文本,这如果我对selectfrom 关键字使用正则表达式,值可能会被拒绝。

我可以验证 SQL 注入输入的最佳方法是什么?谢谢!如果这篇文章恰好是重复的,请给我类似文章的链接,我会删除这篇文章。

【问题讨论】:

【参考方案1】:

这很难回答,因为它取决于你如何定义一个字符串是否危险。

通常情况下,字符串只有在包含单引号时才会造成伤害,所以这个 SQL 条件应该足够好了:

'''' || string || '''' <> quote_literal(string)

但是任何检查单引号的方法都应该这样做。

【讨论】:

如果输入的值为(select email from customers where 1 = 1 limit 1),如果代码写成Customer.where("email = #email"),这可能会造成伤害,如果代码是Customer.where(email: email),当然不会造成伤害。我尝试做的是,如果输入值为 "(select email from customers where 1 = 1 limit 1)",我想拒绝该请求,但是使用正则表达式可能会意外拒绝 “该项目(从集合 A 中选择它)” 这是一个合法的评论,而不是一个 sql 注入字符串 你展示的例子不是通常所说的SQL注入,因为你的字符串不包含像"WHERE email ='" + user_input + "''"这样的单引号。在您展示的情况下,用户输入无论如何都必须是 SQL 代码,也就是说,用户输入必须包含其单引号以形成正确的 SQL 语句。在我在此评论中展示的经典 SQL 注入场景中,任何单引号都是错误的。

以上是关于SQL 注入输入验证的主要内容,如果未能解决你的问题,请参考以下文章

如何验证用户字符串输入不包含 sql 注入?在Javascript中

SQL注入-预防

SQL注入绕过登录验证

简单的 SQL 注入无法验证用户

如何防止sql注入

ThinkPHP如何防止SQL注入?