https://github.com/leizongmin/js-xss/blob/master/README.zh.md

根据白名单过滤 HTML(防止 XSS 攻击)


xss是一个用于对用户输入的内容进行过滤,以避免遭受 XSS 攻击的模块(什么是 XSS 攻击?)。主要用于论坛、博客、网上商店等等一些可允许用户录入页面排版、格式控制相关的 HTML 的场景,xss模块通过白名单来控制允许的标签及相关的标签属性,另外还提供了一系列的接口以便用户扩展,比其他同类模块更为灵活。

项目主页: http://jsxss.com

在线测试: http://jsxss.com/zh/try.html


特性

  • 白名单控制允许的 HTML 标签及各标签的属性
  • 通过自定义处理函数,可对任意标签及其属性进行处理

参考资料

性能(仅作参考)

  • xss 模块:8.2 MB/s
  • validator@0.3.7 模块的 xss()函数:4.4 MB/s

测试代码参考 benchmark 目录

安装

NPM

$ npm install xss

Bower

$ bower install xss

或者

$ bower install https://github.com/leizongmin/js-xss.git

使用方法

在 Node.js 中使用

var xss = require("xss");
var html = xss('<script>alert("xss");</script>');
console.log(html);

在浏览器端使用

Shim 模式(参考文件 test/test.html):

<script src="https://raw.github.com/leizongmin/js-xss/master/dist/xss.js"></script>
<script>
// 使用函数名 filterXSS,用法一样
var html = filterXSS('<script>alert("xss");</scr' + 'ipt>');
alert(html);
</script>

AMD 模式(参考文件 test/test_amd.html):

<script>
require.config({
baseUrl: './',
paths: {
xss: 'https://raw.github.com/leizongmin/js-xss/master/dist/xss.js'
},
shim: {
xss: {exports: 'filterXSS'}
}
})
require(['xss'], function (xss) {
var html = xss('<script>alert("xss");</scr' + 'ipt>');
alert(html);
});
</script>

使用命令行工具来对文件进行 XSS 处理

处理文件

可通过内置的 xss 命令来对输入的文件进行 XSS 处理。使用方法:

xss -i <源文件> -o <目标文件>

例:

$ xss -i origin.html -o target.html

在线测试

执行以下命令,可在命令行中输入 HTML 代码,并看到过滤后的代码:

$ xss -t

详细命令行参数说明,请输入 $ xss -h 来查看。

自定义过滤规则

在调用 xss() 函数进行过滤时,可通过第二个参数来设置自定义规则:

options = {}; // 自定义规则
html = xss('<script>alert("xss");</script>', options);

如果不想每次都传入一个 options 参数,可以创建一个 FilterXSS 实例(使用这种方法速度更快):

options = {};  // 自定义规则
myxss = new xss.FilterXSS(options);
// 以后直接调用 myxss.process() 来处理即可
html = myxss.process('<script>alert("xss");</script>');

options 参数的详细说明见下文。

白名单

通过 whiteList 来指定,格式为:{'标签名': ['属性1', '属性2']}。不在白名单上的标签将被过滤,不在白名单上的属性也会被过滤。以下是示例:

// 只允许a标签,该标签只允许href, title, target这三个属性
var options = {
whiteList: {
a: ["href", "title", "target"]
}
};
// 使用以上配置后,下面的HTML
// <a href="#" onclick="hello()"><i>大家好</i></a>
// 将被过滤为
// <a href="#">大家好</a>

默认白名单参考 xss.whiteList

自定义匹配到标签时的处理方法

通过 onTag 来指定相应的处理函数。以下是详细说明:

function onTag(tag, html, options) {
// tag是当前的标签名称,比如<a>标签,则tag的值是'a'
// html是该标签的HTML,比如<a>标签,则html的值是'<a>'
// options是一些附加的信息,具体如下:
// isWhite boolean类型,表示该标签是否在白名单上
// isClosing boolean类型,表示该标签是否为闭合标签,比如</a>时为true
// position integer类型,表示当前标签在输出的结果中的起始位置
// sourcePosition integer类型,表示当前标签在原HTML中的起始位置
// 如果返回一个字符串,则当前标签将被替换为该字符串
// 如果不返回任何值,则使用默认的处理方法:
// 在白名单上: 通过onTagAttr来过滤属性,详见下文
// 不在白名单上:通过onIgnoreTag指定,详见下文
}

自定义匹配到标签的属性时的处理方法

通过 onTagAttr 来指定相应的处理函数。以下是详细说明:

function onTagAttr(tag, name, value, isWhiteAttr) {
// tag是当前的标签名称,比如<a>标签,则tag的值是'a'
// name是当前属性的名称,比如href="#",则name的值是'href'
// value是当前属性的值,比如href="#",则value的值是'#'
// isWhiteAttr是否为白名单上的属性
// 如果返回一个字符串,则当前属性值将被替换为该字符串
// 如果不返回任何值,则使用默认的处理方法
// 在白名单上: 调用safeAttrValue来过滤属性值,并输出该属性,详见下文
// 不在白名单上:通过onIgnoreTagAttr指定,详见下文
}

自定义匹配到不在白名单上的标签时的处理方法

通过 onIgnoreTag 来指定相应的处理函数。以下是详细说明:

function onIgnoreTag(tag, html, options) {
// 参数说明与onTag相同
// 如果返回一个字符串,则当前标签将被替换为该字符串
// 如果不返回任何值,则使用默认的处理方法(通过escape指定,详见下文)
}

自定义匹配到不在白名单上的属性时的处理方法

通过 onIgnoreTagAttr 来指定相应的处理函数。以下是详细说明:

function onIgnoreTagAttr(tag, name, value, isWhiteAttr) {
// 参数说明与onTagAttr相同
// 如果返回一个字符串,则当前属性值将被替换为该字符串
// 如果不返回任何值,则使用默认的处理方法(删除该属)
}

自定义 HTML 转义函数

通过 escapeHtml 来指定相应的处理函数。以下是默认代码 (不建议修改) :

function escapeHtml(html) {
return html.replace(/</g, "&lt;").replace(/>/g, "&gt;");
}

自定义标签属性值的转义函数

通过 safeAttrValue 来指定相应的处理函数。以下是详细说明:

function safeAttrValue(tag, name, value) {
// 参数说明与onTagAttr相同(没有options参数)
// 返回一个字符串表示该属性值
}

自定义 CSS 过滤器

如果配置中允许了标签的 style 属性,则它的值会通过cssfilter 模块处理。 cssfilter 模块包含了一个默认的 CSS 白名单,你可以通过以下的方式配置:

myxss = new xss.FilterXSS({
css: {
whiteList: {
position: /^fixed|relative$/,
top: true,
left: true
}
}
});
html = myxss.process('<script>alert("xss");</script>');

如果不想使用 CSS 过滤器来处理 style 属性的内容,可指定 css 选项的值为 false

myxss = new xss.FilterXSS({
css: false
});

要获取更多的帮助信息可看这里:https://github.com/leizongmin/js-css-filter

快捷配置

去掉不在白名单上的标签

通过 stripIgnoreTag 来设置:

  • true:去掉不在白名单上的标签
  • false:(默认),使用配置的escape函数对该标签进行转义

示例:

当设置 stripIgnoreTag = true时,以下代码

code:<script>alert(/xss/);</script>

过滤后将输出

code:alert(/xss/);

去掉不在白名单上的标签及标签体

通过 stripIgnoreTagBody 来设置:

  • false|null|undefined:(默认),不特殊处理
  • '*'|true:去掉所有不在白名单上的标签
  • ['tag1', 'tag2']:仅去掉指定的不在白名单上的标签

示例:

当设置 stripIgnoreTagBody = ['script']时,以下代码

code:<script>alert(/xss/);</script>

过滤后将输出

code:

去掉 HTML 备注

通过 allowCommentTag 来设置:

  • true:不处理
  • false:(默认),自动去掉 HTML 中的备注

示例:

当设置 allowCommentTag = false 时,以下代码

code:<!-- something --> END

过滤后将输出

code: END

应用实例

允许标签以 data-开头的属性

var source = '<div a="1" b="2" data-a="3" data-b="4">hello</div>';
var html = xss(source, {
onIgnoreTagAttr: function(tag, name, value, isWhiteAttr) {
if (name.substr(0, 5) === "data-") {
// 通过内置的escapeAttrValue函数来对属性值进行转义
return name + '="' + xss.escapeAttrValue(value) + '"';
}
}
}); console.log("%s\nconvert to:\n%s", source, html);

运行结果:

<div a="1" b="2" data-a="3" data-b="4">hello</div>
convert to:
<div data-a="3" data-b="4">hello</div>

允许名称以 x-开头的标签

var source = "<x><x-1>he<x-2 checked></x-2>wwww</x-1><a>";
var html = xss(source, {
onIgnoreTag: function(tag, html, options) {
if (tag.substr(0, 2) === "x-") {
// 不对其属性列表进行过滤
return html;
}
}
}); console.log("%s\nconvert to:\n%s", source, html);

运行结果:

<x><x-1>he<x-2 checked></x-2>wwww</x-1><a>
convert to:
&lt;x&gt;<x-1>he<x-2 checked></x-2>wwww</x-1><a>

分析 HTML 代码中的图片列表

var source =
'<img src="img1">a<img src="img2">b<img src="img3">c<img src="img4">d';
var list = [];
var html = xss(source, {
onTagAttr: function(tag, name, value, isWhiteAttr) {
if (tag === "img" && name === "src") {
// 使用内置的friendlyAttrValue函数来对属性值进行转义,可将&lt;这类的实体标记转换成打印字符<
list.push(xss.friendlyAttrValue(value));
}
// 不返回任何值,表示还是按照默认的方法处理
}
}); console.log("image list:\n%s", list.join(", "));

运行结果:

image list:
img1, img2, img3, img4

去除 HTML 标签(只保留文本内容)

var source = "<strong>hello</strong><script>alert(/xss/);</script>end";
var html = xss(source, {
whiteList: [], // 白名单为空,表示过滤所有标签
stripIgnoreTag: true, // 过滤所有非白名单标签的HTML
stripIgnoreTagBody: ["script"] // script标签较特殊,需要过滤标签中间的内容
}); console.log("text: %s", html);

运行结果:

text: helloend

授权协议

Copyright (c) 2012-2017 Zongmin Lei(雷宗民) <leizongmin@gmail.com>
http://ucdok.com The MIT License Permission is hereby granted, free of charge, to any person obtaining
a copy of this software and associated documentation files (the
"Software"), to deal in the Software without restriction, including
without limitation the rights to use, copy, modify, merge, publish,
distribute, sublicense, and/or sell copies of the Software, and to
permit persons to whom the Software is furnished to do so, subject to
the following conditions: The above copyright notice and this permission notice shall be
included in all copies or substantial portions of the Software. THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.

根据白名单过滤 HTML(防止 XSS 攻击)的更多相关文章

  1. 特殊字符的过滤,防止xss攻击

    概念 XSS攻击全称跨站脚本攻击,是为不和层叠样式表(Cascading Style Sheets, CSS)的缩写混淆,故将跨站脚本攻击缩写为XSS,XSS是一种在web应用中的计算机安全漏洞,它允 ...

  2. 变量安全过滤,防止xss攻击

    下面这个方法不管是字符串还是数组,都可以进行过滤 /** * @purpose : 对变量进行安全过滤,使 $_GET.$_POST.$q->record 等变量更安全 * @author : ...

  3. Nginx 配置GeoIP2 禁止访问,并允许添加白名单过滤访问设置

    配置环境:Centos 7.6 + Tengine 2.3.2 GeoIP2 下载地址:https://dev.maxmind.com/geoip/geoip2/geolite2/ 1. Nginx  ...

  4. 过滤关键字防止XSS攻击

    public static string ClearXSS(string str) { string returnValue = str; if (string.IsNullOrEmpty(retur ...

  5. Request获取用户真实IP(用作白名单过滤)

    在Servlet里,获取客户端的IP地址的方法是:request.getRemoteAddr(),这种方法在大部分情况下都是有效的.但是在通过了Apache,Squid,Nginx等反向代理软件就不能 ...

  6. Spring Boot XSS 攻击过滤插件使用

    XSS 是什么 XSS(Cross Site Scripting)攻击全称跨站脚本攻击,为了不与 CSS(Cascading Style Sheets)名词混淆,故将跨站脚本攻击简称为 XSS,XSS ...

  7. AntiXSS - 支持Html同时防止XSS攻击

    AntiXSS - 支持Html同时防止XSS攻击 跨站脚本攻击(XSS)已经不是什么新鲜的话题了,甚至很多大公司也为此吃尽苦头.最简单直接的防范方法,就是不允许任何html标签输入,对用户输入进行编 ...

  8. xss攻击和csrf攻击的定义及区别

    1.CSRF的基本概念.缩写.全称 CSRF(Cross-site request forgery):跨站请求伪造. PS:中文名一定要记住.英文全称,如果记不住也拉倒. 2.CSRF的攻击原理 用户 ...

  9. 富文本编辑器、日期选择器、软件天堂、防止XSS攻击、字体icon、转pdf

    [超好用的日期选择器] Layui:http://www.layui.com/laydate/ 备注:日期选择器,用过很多很多,自己也写过一些:相信这个简单而又不简单的选择器,能够给你多些美好的时光 ...

随机推荐

  1. vue进阶用法-深入响应式原理

    异步更新队列 当vue异步执行更新DOM时,只要观察到数据变化,vue经开启一个队列,并缓冲在同一时间循环中发生的所有数据改变.如果同一个watch被多次触发,只会一次推入到队列中.然后在下一个事件循 ...

  2. 腾讯云短信服务使用记录与.NET Core C#代码分享

    1.即使是相同的短信签名与短信正文模板,也需要针对“国内文本短信”与“海外文本短信”分别申请.开始不知道,以为只要申请一次,给国外手机发短信时给api传对应的国家码就行,后来才发现需要分别申请. 2. ...

  3. 各种可再发行组件包Redistributable及framework 下载

    安装包名称 版本号 下载地址 Visual C++ 2005 Redistributable Package (x64)   下载 Visual C++ Redistributable Package ...

  4. CH 1201 - 最大子序和 - [单调队列]

    题目链接:传送门 描述输入一个长度为n的整数序列,从中找出一段不超过m的连续子序列,使得整个序列的和最大. 例如 $1,-3,5,1,-2,3$. 当 $m=4$ 时,$S=5+1-2+3=7$:当 ...

  5. [No000011E]Python教程1/9-Python简介

    Python是一种计算机程序设计语言.你可能已经听说过很多种流行的编程语言,比如非常难学的C语言,非常流行的Java语言,适合初学者的Basic语言,适合网页编程的JavaScript语言等等. 那P ...

  6. hive拉链表

    前言 本文将会谈一谈在数据仓库中拉链表相关的内容,包括它的原理.设计.以及在我们大数据场景下的实现方式. 全文由下面几个部分组成:先分享一下拉链表的用途.什么是拉链表.通过一些小的使用场景来对拉链表做 ...

  7. OC,nil,NULL,Nil,kCFNull

    YYModel源码中有一句:kCFNull //解析model属性并附值 + (instancetype)yy_modelWithDictionary:(NSDictionary *)dictiona ...

  8. RabbitMQ性能优化

    修改rabbitmq.config文件 rabbitmq.config文件时rabbitmq的配置文件,他遵守Erlang配置文件定义. rabbitmq.config文件位置: Unix $RABB ...

  9. Chap1 引言[The Linux Command Line]

    附上链接:http://billie66.github.io/TLCL/book/chap01.html Content: part1-Introduction part2-Learning The ...

  10. [archlinux][plasma][screensaver] plasma5配置屏保程序,没成功(-_-#)

    plamsa用了好久,一直没有屏保.我想要玄酷的屏保! 用xscreensaver, 之前用FVWM2的时候,就用过了,很玄酷. 一,安装 pacman -S xscreensaver 二,配置 xs ...