如果与准备语句一起使用,没有输入验证的 PHP 联系表单安全吗?
我的网站上有一个联系我们的表格,我试图不限制用户使用的字符,因为我们希望支持多语言名称。我们只检查名称/电子邮件等的长度和结构。
我知道如果将变量直接插入到查询语句中可能会很危险,但我正在使用准备好的语句,如下所示。
$stmt = $conn->prepare("INSERT INTO contact_us_form (id,available_id,user_id,foreName,surName,mail,message) VALUES (?,?,?,?,?,?,?)");
$stmt->bind_param("iiissss",$num,$availableID,$userID,$foreName,$surName,$mail,$message);
$stmt->execute();
$stmt->close();
$conn->close();
这是在我的 mysql 数据库中保存原始数据的正确方法吗?我也会给自己发送一封电子邮件,但在这样做之前我会转义特殊字符。[UTF-8]
I have a contact-us form on my website and I am trying to not limit users on the characters that they use, since we would like to support multilingual names. We only check the length and the structure of the name/e-mail, etc.
I know that it could be dangerous if the variables would be inserted directly into the query statement, but I am using prepared statements, like below.
$stmt = $conn->prepare("INSERT INTO contact_us_form (id,available_id,user_id,foreName,surName,mail,message) VALUES (?,?,?,?,?,?,?)");
$stmt->bind_param("iiissss",$num,$availableID,$userID,$foreName,$surName,$mail,$message);
$stmt->execute();
$stmt->close();
$conn->close();
Is this the proper way to save raw data in my mysql database? I would also send an e-mail to myself, but I would escape special characters before doing that.[UTF-8]
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(2)
使用准备好的语句可以很好地防止 SQL 注入攻击。然而,这不足以防范其他类型的攻击。这些数据还将如何使用?
如果此消息曾经显示在网页中(例如向要阅读该消息的人),则需要使用 HTML 实体对其进行转义。
如果此消息作为电子邮件发送,则需要从电子邮件地址、姓名和放入电子邮件标头的其他字段中删除对电子邮件标头不安全的换行符等字符。
基本上,无论何时在任何地方使用这些数据,您都需要确保将其视为用户提交的、不受信任的数据。它始终需要以适合其插入的特定上下文的方式进行转义或清理。
Using prepared statements is good protection against SQL injection attacks. However that isn't sufficient to protect against other types of attacks. How else is this data going to be used?
If this message is ever shown in a web page (for example to the person who is going to read the message) it needs to be escaped with HTML entities.
If this message is ever sent as an email, characters like new lines that are not safe for email headers need to be stripped from the email address, name and other fields that are put into email headers.
Basically, any time you use this data anywhere, you need to make sure that it is treated as user-submitted, untrusted data. It will always need to be escaped or sanitized in a way that is appropriate for the particular context in which it is inserted.
输入验证与安全性并不真正相关,但它可以被视为深度防御。输入验证还可以防止其他滥用行为。例如,某人可能会向您的联系表单提交 1GB 的数据。这是您的应用程序期望并且可以处理的事情吗?您的数据库列能够存储这么多数据吗?如果您不验证输入,您的应用程序可能会崩溃。拒绝无效输入。
如果使用正确,准备好的语句可以防止 SQL 注入。您不需要对数据进行“清理”或类似的操作。使用准备好的语句时没有“特殊字符”。您的数据库也没有将任何字符定义为特殊字符;它会保存你给它的任何东西。您必须确保以正确的字符集保存数据,并告诉 mysqli 连接该字符集是什么。
当然,在 HTML 中显示数据时,请确保其格式正确,这样数据就不会破坏 HTML 结构。为此,请使用
htmlspecialchars()
。Input validation isn't really related to security, but it can be considered defense-in-depth. Input validation also prevents other vectors of abuse. For example, someone might submit 1GB of data to your contact form. Is this something that your application expects and can handle? Is your database column capable of storing this amount of data? If you don't validate the input, your application might crash. Reject invalid input.
Prepared statements prevent you from SQL injection if used correctly. You don't need to "sanitize" or do anything like that to the data. There are no "special characters" when using prepared statements. Your database also doesn't define any characters as specials; it will save whatever you give it. You must ensure though that you save the data in the correct character set and that you tell mysqli connection what that charset is.
And of course, when displaying the data in the HTML make sure that you format it properly so that your data doesn't break your HTML structure. Use
htmlspecialchars()
for that purpose.