JSF 标准验证能否防止代码注入?
在我的项目中,我在表示层和持久层进行重复验证,希望提高安全性。所以我的问题是:标准 JSF 验证能否防止代码注入。
<h:inputText id="name" value="#{bean.customer.name}" required="true" requiredMessage="Validation Error: Value is required." title="Name" >
<f:validateLength maximum="40"/>
</h:inputText>
这里我验证该字段是否为空,并验证字段长度。我知道验证字段长度会使代码注入变得更困难,但有时你需要很长的字段长度,例如 textArea
。如果这是脆弱的,我将如何修复它?预先非常感谢您。
In my project, I do duplicate validation at the presentation layer as well as the persistence layer with the hope to increase security. So my question is: can standard JSF validation prevent code injections.
<h:inputText id="name" value="#{bean.customer.name}" required="true" requiredMessage="Validation Error: Value is required." title="Name" >
<f:validateLength maximum="40"/>
</h:inputText>
Here I validate if the field is empty, and validate field length. I know validate field length will make it harder to do code injection, but sometimes you need a long field length, such as textArea
. And if this is vulnerable, how will I fix it? Thank you so much in advance.
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(2)
默认情况下,JSF 已阻止 XSS 通过在
UIInput
和UIOutput
组件中转义用户控制的输入来进行攻击。这可以通过设置escape="false"
属性在h:outputText
中进行控制。你不需要担心这个。预防SQL注入 攻击 不是 JSF 的责任。您需要在持久层中处理这个问题。例如,JPA 和/或 Hibernate,如果使用得当(即不在 SQL/命名查询字符串中连接用户控制的输入),默认情况下也已经阻止了它。在普通 JDBC 中,您需要确保使用
PreparedStatement
而不是Statement
在 SQL 字符串中包含用户控制的输入。如果使用得当,您也不需要在 JSF 方面担心这个问题。相关问题:
JSF by default already prevents XSS attacks by escaping user-controlled input in
UIInput
andUIOutput
components. This is controllable inh:outputText
by settingescape="false"
attribute. You don't need to worry about this.Prevention against SQL injection attacks, on the other hand, is not the responsibility of JSF. You need to handle this in the persistence layer. For example JPA and/or Hibernate, when well used (i.e. do not concatenate user-controlled input in SQL/named query strings), also by default already prevents it. In plain vanilla JDBC, you need to ensure that you're using
PreparedStatement
instead ofStatement
to include user-controlled input in a SQL string. When well used, you also don't need to worry about this in JSF side.Related questions:
注入攻击有一个共同的主题:由于应用程序中的各种缺陷,输入数据在某个时间点被转换并解释为代码。最常见的缺陷是未正确编码或转义的未经清理的数据。编码的存在或不存在本身并不能保护应用程序免受攻击 - 允许将代码转换为数据的字符必须进行编码,以便它们不会被区分为代码。
现在,从 JSF 的角度来看,设计者已经考虑到包括针对某些类型的攻击的保护。由于它是一个表示层框架,因此可以防止 XSS 攻击(以及 CSRF 攻击,尽管它与注入无关)。保护机制及其安全使用在 Seam 框架页面 跨站脚本 和 < a href="http://www.seamframework.org/Documentation/CrossSiteRequestForgery" rel="noreferrer">跨站请求伪造。 Seam 使用 JSF,因此在保护 JSF 应用程序和 Seam 应用程序免受 XSS 和 CSRF 侵害方面没有太大区别;这些页面中的大多数建议都一定适用于 JSF 应用程序。
但是,如果您需要保护自己免受其他突出的注入攻击,尤其是 SQL 注入,则需要查看持久性框架提供的功能(假设您将使用其中一个)。如果您手动编写 SQL 查询并直接在代码中执行它们,请使用PreparedStatement 对象来保护自己免受最常见的 SQL 注入的影响。如果您正在使用 JPA、JDO 等,您需要考虑安全地使用此类框架 - 大多数框架在向它们提供查询时默认创建PreparedStatement 对象,因此通常无需担心。
防止 JPA 中的 SQL 注入攻击
命名查询和本机查询将在内部转换为使用参数化查询的准备好的语句。这是 JPA 提供商的责任。人们需要担心在移交给提供商之前构建的 SQL 查询。基本上,传递给 EntityManager.createQuery() 和 EntityManager.createNativeQuery() 的字符串不应包含连接的用户输入。
PS:CSRF 保护功能存在于 JSF 2 中,而不是存在于 JSF 1.x 中。它也仅存在于 Seam 的某些版本(2.1.2 及更高版本)中。
Injection attacks have one common theme: input data is transformed and interpreted as code, at some point in time due to various flaws in the application. The most commonly observed flaw is that of unsanitized data that is not encoded or escaped correctly. The presence or absence of encoding alone does not protect an application from attacks - the characters that allow for transformation of code into data must be encoded so that they're not distinguished as code.
Now, from the point of view of JSF, the designers have been thoughtful to include protection against certain kinds of attacks. Since it is a presentation tier framework, protection against XSS attacks (and CSRF attacks, although it is not related to injection) are present. The protection mechanisms and their safe usage is dealt in detail, in the Seam framework pages on Cross Site Scripting and Cross Site Request Forgery. Seam uses JSF, so there isn't a lot of difference in protecting a JSF application and Seam application from XSS and CSRF; most of the advice in those pages are bound to hold good in a JSF application.
However, if you need to protect yourself against other prominent injection attacks, especially SQL injection, you need to look at the features offered by your persistence framework (assuming that you will use one). If you're hand-coding SQL queries and executing them in your code directly, use PreparedStatement objects to protect yourself from the most common varieties of SQL injection. If you are using JPA, JDO etc. you'll need to look at using such frameworks securely - most of them create PreparedStatement objects by default, when queries are fed to them so there is often little need to worry.
Protection against SQL injection attacks in JPA
Named and native queries will be internally converted into a prepared statement that uses parameterized queries. That is the responsibility of the JPA provider. One will need to worry about SQL queries that are constructed before handing off to the provider. Basically the strings passed to EntityManager.createQuery() and EntityManager.createNativeQuery() should not have concatenated user input.
PS: The CSRF protection feature is present in JSF 2, and not in JSF 1.x. It is also present only in certain releases of Seam (2.1.2 onwards).