防止sql注入

php中文网
发布: 2016-06-06 20:16:46
原创
1633人浏览过

在网上看了些关于防止sql注入的文件和提问,比如使用预处理、过滤敏感字符。我一直想不明白的是,解决ssql注入问题非常非常简单啊,只要对用户输入的内容转义一下就可以了,就是讲用户输入的',"转义成\',\"就可以了,搞不懂为什么搞的那么复杂了?还是说我这种方法不能杜绝所有的sql注入

回复内容:

在网上看了些关于防止sql注入的文件和提问,比如使用预处理、过滤敏感字符。我一直想不明白的是,解决ssql注入问题非常非常简单啊,只要对用户输入的内容转义一下就可以了,就是讲用户输入的',"转义成\',\"就可以了,搞不懂为什么搞的那么复杂了?还是说我这种方法不能杜绝所有的sql注入

用htmlspecialchars/HTMLPurifier防御XSS注入,用预处理参数化查询防御SQL注入.

调用HTMLPurifier过滤XSS后输出HTML:

require dirname(__FILE__).'/htmlpurifier/library/HTMLPurifier.auto.php';
$purifier = new HTMLPurifier();
echo $purifier->purify($html);
登录后复制

MySQLi绑定参数查询:

$db = @new mysqli();
$stmt = $db->prepare('SELECT * FROM posts WHERE id=?'); //预处理
$stmt->bind_param('i', $id); //绑定参数
$stmt->execute(); //查询
var_export($stmt->get_result()->fetch_all());
登录后复制

WireShark里用tcp.port==3306过滤分析PHP和MySQL通信
防止sql注入

<?php
//MySQLi
$id = 1;
$mysqli = new mysqli('127.0.0.1', 'punbb', 'punbb', 'punbb');
$mysqli->set_charset('utf8');
$stmt = $mysqli->prepare("SELECT `username` FROM `pb_users` WHERE `id`=?");
$stmt->bind_param('i', $id);
$stmt->execute();
$stmt->store_result();
$stmt->bind_result($username);
while ($stmt->fetch()) echo $username;
$stmt->close();
$mysqli->close();

<?php
//PDO
$id = 1;
//$dbh = new PDO('sqlite:/path/to/punbb.db3');
$dsn = "mysql:dbname=punbb;host=127.0.0.1;port=3306;charset=utf8";
$dbh = new PDO($dsn, 'punbb', 'punbb');
$dbh->query('SET NAMES utf8');
$dbh->setAttribute(PDO::ATTR_EMULATE_PREPARES, false);
$sth = $dbh->prepare("SELECT `username` FROM `pb_users` WHERE `id`=?");
$sth->bindParam(1, $id, PDO::PARAM_INT);
$sth->execute();
print_r($sth->fetchAll(PDO::FETCH_ASSOC));
$sth = null;
$dbh = null;
登录后复制

在 Request Prepare Statement 里可以看到 SELECT username FROM pb_users WHERE id=?
在 Request Execute Statement 里可以看到 Parameter 内容为:
Type: FIELD_TYPE_LONGLONG (8)
Unsigned: 0
Value: 1
可见PHP将SQL模板和变量分两次发送给MySQL,由MySQL完成变量的转义处理.
既然SQL模板和变量是分两次发送的,那么就不存在SQL注入的问题了.

在MySQL的general_log里可以看到:
Prepare SELECT username FROM pb_users WHERE id=?
Execute SELECT username FROM pb_users WHERE id=1
如果ID绑定为string,则Execute时id赋值是这样的: id='1'
如果PDO没有关闭模拟预处理,则可以看到:
Query SELECT username FROM pb_users WHERE id=1

解决注入,还是PDO来的比较彻底,最不济也得mysqli,上bind,加类型.

只要对用户输入的内容转义一下就可以了,就是讲用户输入的',"转义成\',\"就可以了,搞不懂为什么搞的那么复杂了?还是说我这种方法不能杜绝所有的sql注入

你一定不知道有一种注入叫做宽字符注入,int型注入,orderBy注入,
其次注入其实非常容易防御,主要麻烦的是xss

最佳 Windows 性能的顶级免费优化软件
最佳 Windows 性能的顶级免费优化软件

每个人都需要一台速度更快、更稳定的 PC。随着时间的推移,垃圾文件、旧注册表数据和不必要的后台进程会占用资源并降低性能。幸运的是,许多工具可以让 Windows 保持平稳运行。

下载
相关标签:
来源:php中文网
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系admin@php.cn
最新问题
开源免费商场系统广告
热门教程
更多>
最新下载
更多>
网站特效
网站源码
网站素材
前端模板
关于我们 免责申明 意见反馈 讲师合作 广告合作 最新更新
php中文网:公益在线php培训,帮助PHP学习者快速成长!
关注服务号 技术交流群
PHP中文网订阅号
每天精选资源文章推送
PHP中文网APP
随时随地碎片化学习
PHP中文网抖音号
发现有趣的

Copyright 2014-2025 https://www.php.cn/ All Rights Reserved | php.cn | 湘ICP备2023035733号