V2EX = way to explore
V2EX 是一个关于分享和探索的地方
现在注册
已注册用户请  登录
推荐关注
Meteor
JSLint - a JavaScript code quality tool
jsFiddle
D3.js
WebStorm
推荐书目
JavaScript 权威指南第 5 版
Closure: The Definitive Guide
moonlord
V2EX  ›  JavaScript

为什么 XSS 的防御,很多人要用前后端 转码、过滤、报错 的方法,直接在前端当做文本显示不香吗?

  •  
  •   moonlord · 2020-04-24 17:59:42 +08:00 · 6525 次点击
    这是一个创建于 1435 天前的主题,其中的信息可能已经有所发展或是发生改变。

    比如就有人问 XSS 防御,一堆的人说 “转码、过滤、报错”
    根本睁着眼,都看不见 V2EX 的输入框就是输入啥,显示啥,毛的转码过滤报错。。。

    防止 xss 和 sql 注入而进行非法字符过滤,js 前端有什么几乎一劳永逸的方式?
    https://www.v2ex.com/t/665687?p=1#r_8874716

    V2EX 的留言接口
    https://www.v2ex.com/api/replies/show.json?topic_id=665687

    36 条回复    2020-05-18 11:52:09 +08:00
    airplayxcom
        1
    airplayxcom  
       2020-04-24 18:06:13 +08:00 via iPhone
    你可真是个人才
    retanoj
        2
    retanoj  
       2020-04-24 18:10:53 +08:00
    其实。。我很赞同前端的问题交给前端解决
    SilentDepth
        3
    SilentDepth  
       2020-04-24 18:11:47 +08:00
    咋又单独开了个帖……

    你这个方案是要讲前提的。比如博客平台,自定义挂件功能,就是需要用户自己写 HTML 啊,你不能把 HTML 文本渲染出来啊 = =
    huijiewei
        4
    huijiewei  
       2020-04-24 18:15:27 +08:00
    简直搞笑,一大片 HTML 编辑器怎么办

    innerText 说的人都不知道一样
    Cmdhelp
        5
    Cmdhelp  
       2020-04-24 18:16:00 +08:00
    现在得前端又不是早期的前端了,
    zhuisui
        6
    zhuisui  
       2020-04-24 18:18:25 +08:00
    "topic_id": 665687, "content": "<img onerror=\"alert(111)\"/>", "content_rendered": "&lt;img onerror=\"alert(111)\"/&gt;",

    json 里这段是什么,这叫没转码吗。
    moonlord
        7
    moonlord  
    OP
       2020-04-24 18:24:39 +08:00
    @retanoj 对吧,我就这个意思。而且,数据是啥就应该是啥,明天万一搞 APP 呢,他么数据都被转码了不是扯淡了。。。
    moonlord
        8
    moonlord  
    OP
       2020-04-24 18:25:40 +08:00
    @huijiewei HTML 编辑器不是普遍需要。讨论的是通用的防御。
    jinmaoi
        9
    jinmaoi  
       2020-04-24 19:50:25 +08:00
    我看下面好多人的都误解你的意思啊,都在说什么过滤被绕过,被发包之类,还有个家伙说别人没做过黑客什么的,我就觉得如果是通用一点的照你这种过滤输出是挺方便的啊.
    moonlord
        10
    moonlord  
    OP
       2020-04-24 20:23:48 +08:00
    @jinmaoi 那些人可能说的是 sql 注入(笑),我也觉得 xss 照我说的这个没啥毛病
    sagaxu
        11
    sagaxu  
       2020-04-24 20:41:06 +08:00 via Android
    为什么要防御 xss,
    billlee
        12
    billlee  
       2020-04-24 21:10:27 +08:00
    其实就是输入转义和输出转义的区别。首先过滤是不太好的,粗暴过滤是破坏功能的。输入过滤的好处是一劳永逸,坏处是如果一份数据除了 web 显示,还有其它用途,做转义就会破坏数据;有些公司的安全部门也会要求输入时做转义或过滤。现在很多框架组件都是显示时默认做转义的,这样也很安全。
    mxT52CRuqR6o5
        13
    mxT52CRuqR6o5  
       2020-04-25 00:51:44 +08:00 via Android
    讨论 xss 我就默认是在类似富文本的需求如何解决
    普通输入框在我这必定是 innerText 没有讨论空间
    aawei
        14
    aawei  
       2020-04-25 01:27:37 +08:00 via iPhone
    一般的内容,前端当转义一下当文本输出就行,在 script 里输出点,需要特别注意一下某些特殊字符。富文本的话,后端做标签白名单,禁用动作事件,然后再输出到前端渲染。一直都是这么建议开发小哥这样修复的
    Hyduan
        15
    Hyduan  
       2020-04-25 02:53:46 +08:00
    简单文本渲染情况 我支持楼主 不仅能防止 XSS 还可以保障用户体验
    falcon05
        16
    falcon05  
       2020-04-25 06:10:53 +08:00 via iPhone
    如果是传统后端渲染,直接是什么就什么输出,不经过转码,就把 script 输出页面了,xss 还没轮到你的 js 处理就执行了,怎么搞?前后端分离的情况讨论前端 xss 过滤可能还有意义。
    Archeb
        17
    Archeb  
       2020-04-25 07:52:28 +08:00
    楼主是不是最近前后端分离的 SPA 写多了,前端 API 调多了才会产生后端渲染已经没有应用场景的错觉。
    hshpy
        18
    hshpy  
       2020-04-25 09:16:46 +08:00
    过滤要后端做,DOM 型 XSS 是 js 动态加载 html 。
    你的网站做成只显示 txt 文件?
    hshpy
        19
    hshpy  
       2020-04-25 09:18:40 +08:00
    @hshpy 还有存储型 xss,用户体验不打算要了
    wy315700
        20
    wy315700  
       2020-04-25 09:24:52 +08:00   ❤️ 2
    吃饭容易噎着怎么办。

    那就不吃饭喽。
    hshpy
        21
    hshpy  
       2020-04-25 09:32:49 +08:00
    @hshpy 改下,DOM 型 XSS 是前端的事但不是过滤,过滤反射型存储型要后端做。
    codehz
        22
    codehz  
       2020-04-25 09:43:21 +08:00 via Android
    @hshpy (不应该存 html,可以存另一个结构化的表示,然后前端再重新处理回 dom 结构,全程不需要 innerHTML
    gamexg
        23
    gamexg  
       2020-04-25 10:08:39 +08:00   ❤️ 2
    我没理解你的意思?


    >都看不见 V2EX 的输入框就是输入啥,显示啥,毛的转码过滤报错


    回复文本框输入的 <html> ,实际后端输出时已经转码为了 &lt;html&gt; ,你可以搜索下本贴的源码,就能看到源码里面并没有 <html>,而是被转码为了 &lt;html&gt; 。


    json 也是如此, " 会被转码为 \" 。你可以搜索下你提供的那个 留言接口里面,可以找到类似下面的字符串。

    <a target=\"_blank\" href=\"https
    gamexg
        24
    gamexg  
       2020-04-25 10:11:35 +08:00
    @gamexg #23 的确过滤、报错是个大坑,除了敏感词,不然不建议搞出来过滤、报错。
    hshpy
        25
    hshpy  
       2020-04-25 11:38:12 +08:00
    @codehz 用户返回数据都是后端拼接的 html 页面,只能由后端清理数据。攻击者可以绕过前端清理数据的 js 。后端获取用户 IP,攻击者在请求头注入,还是得由后端处理。
    codehz
        26
    codehz  
       2020-04-25 12:14:07 +08:00
    @hshpy (所以问题就在这里了,按拼接 html 的模式就没法解决了,要解决就只能通过让后端输出结构化数据,前端做转换才可以(
    hshpy
        27
    hshpy  
       2020-04-25 13:47:28 +08:00
    @codehz 前端还要多请求几次数据,只要页面有 js 操作就有可能出现 DOM 型 XSS.
    纯静态它不香吗。。。
    lscho
        28
    lscho  
       2020-04-25 13:58:16 +08:00 via iPhone
    如果只是 xss,那纯前端确实可以解决。。但是能出现 xss 的地方一般都需要防注入,所以实际操作中都是后台顺便处理了。
    lscho
        29
    lscho  
       2020-04-25 14:00:20 +08:00 via iPhone
    而且前面答主说了,xss 不止有 dom 型,还有反射型和存储型,这些不表现在 dom 结构内,这些必须要后台处理的。
    chinvo
        30
    chinvo  
       2020-04-25 14:26:43 +08:00
    对纯文本, 自然是 innerText

    对富文本, 可以用 bbcode 或者 markdown, 关闭 html 标签支持
    dengjscn
        31
    dengjscn  
       2020-04-25 14:29:13 +08:00 via iPhone
    @chinvo markdown ??前端的东西最终还得是 HTML
    chinvo
        32
    chinvo  
       2020-04-25 15:14:43 +08:00 via iPhone
    @dengjscn #31 前端渲染啊,禁用渲染器的 HTML 支持

    当然这个的可靠性是建立在 markd.js 之类的前端渲染器能正确过滤 HTML 标签的前提下
    shenqi
        33
    shenqi  
       2020-04-25 15:20:49 +08:00
    不是不行,也可以。
    codehz
        34
    codehz  
       2020-04-25 15:26:41 +08:00
    @hshpy google 的做法是渲染到 script 块里,也不需要额外请求
    iyangyuan
        35
    iyangyuan  
       2020-04-26 10:08:35 +08:00 via iPhone
    http only
    SYM01
        36
    SYM01  
       2020-05-18 11:52:09 +08:00
    如果是富文本数据,可以在输出的时候做一次 HTML 白名单过滤。

    - 提供开箱即用的默认白名单( Go ): https://github.com/SYM01/htmlsanitizer
    - 一个广泛使用的富文本过滤器( Go ): https://github.com/microcosm-cc/bluemonday
    关于   ·   帮助文档   ·   博客   ·   API   ·   FAQ   ·   我们的愿景   ·   实用小工具   ·   2483 人在线   最高记录 6543   ·     Select Language
    创意工作者们的社区
    World is powered by solitude
    VERSION: 3.9.8.5 · 32ms · UTC 15:44 · PVG 23:44 · LAX 08:44 · JFK 11:44
    Developed with CodeLauncher
    ♥ Do have faith in what you're doing.