使用Java清理数据库输入而不使用PreparedStatement

时间:2014-05-28 00:27:23

标签: java mysql database sanitization

是否有可靠的方法在不使用预准备语句的情况下清理Java中的数据库输入?

我发现的所有答案建议使用PreparedStatement,但我试图避免额外的数据库服务器往返。

- 其他信息 -

  • 我的查询非常简单,很少会分享相同的格式,因此任何查询计划缓存都没有什么性能优势。
  • 数据库服务器将位于单独的物理位置,但仍位于同一个局域网中,因此在使用预准备语句时需要额外的往返时会有额外的网络瓶颈。

我希望找到的是这样的,它存在于C,Python和PHP中: http://dev.mysql.com/doc/refman/5.0/en/mysql-real-escape-string.html

2 个答案:

答案 0 :(得分:3)

您可以在escapeSql

中使用org.apache.commons.lang.StringEscapeUtils
username="'; or 1=1";
sane_username=StringEscapeUtils.escapeSql(username);
// turns into "''; or 1=1"

sql= "select username from users where username = '" + sane_username + "'";
// select username from users where username = '''; 1 or 1'

但这是非常糟糕的做法。你应该总是使用准备好的陈述。

  • 在sql server上保存内存
  • 允许您在没有重新分析sql的情况下重用sql语句, 提高绩效
  • 更安全,你可能会忘记理解一些意见。

答案 1 :(得分:0)

这听起来像premature optimization的经典案例。是的,PreparedStatement做了一些不必要的工作,就像ArrayList分配不必要的内存一样。但是,这些实用程序的好处远远超过了它们的额外成本,JIT(或PreparedStatement案例中的JDBC驱动程序)可以随着时间的推移而改进,使它们更便宜。

另一方面,如果您手动重新发明轮子,您可能会犯错误,并且永远处于困境,以确保未来确实能够保持这种性能。假设您投入了大量精力来构建PreparedStatement的安全替代方案,但明年才发现驱动程序更新实际上使PreparedStatement调用比您的实现更有效 - 它不是牵强附会的想法。

性能问题很重要,但要避免因为挤压应用程序中的每一个问题而陷入困境。简单地做一些有效的事情可能会比将大量时间投入到项目的一个小方面更快,更安全,更容易升级。换句话说,为什么要解决PreparedStatement所带来的好处,直到你最后确定它会阻止你进一步改善?