/*
 * Copyright (c) 2018-2999 广州市蓝海创新科技有限公司 All rights reserved.
 *
 * https://www.mall4j.com/
 *
 * 未经允许，不可做商业用途！
 *
 * 版权所有，侵权必究！
 */

package com.yami.shop.common.xss;

import org.jsoup.Jsoup;
import org.jsoup.nodes.Document;
import org.jsoup.safety.Safelist;

/**
 * `XssUtil` 是一个工具类，主要用于过滤 HTML 标签中可能存在的 XSS（跨站脚本攻击）代码，通过使用 `Jsoup` 库提供的相关功能，
 * 基于预定义的白名单（`Safelist`）对输入的内容进行清理，确保在处理包含 HTML 内容的文本时，能够去除潜在的恶意脚本代码，
 * 保障系统的安全性，防止恶意用户通过注入脚本等方式进行攻击，常用于对用户输入的富文本内容或者其他可能包含 HTML 的文本进行安全过滤处理。
 *
 * @author lgh
 */
public class XssUtil {

    /**
     * 定义一个 `Safelist` 类型的静态常量 `WHITE_LIST`，它使用了 `Jsoup` 库自带的 `relaxed` 白名单（`basicWithImages` 白名单），
     * 这个白名单定义了允许存在的 HTML 标签和属性集合，在进行 XSS 代码过滤时，只有白名单中的标签和属性会被保留，
     * 其他未在白名单内的 HTML 元素和属性将会被移除，以此来防止恶意的脚本代码混入合法的 HTML 内容中。
     */
    private static final Safelist WHITE_LIST = Safelist.relaxed();

    /**
     * 定义一个 `Document.OutputSettings` 类型的静态常量 `OUTPUT_SETTINGS`，用于配置 HTML 内容的输出设置，
     * 这里将 `prettyPrint` 属性设置为 `false`，表示不对过滤后的 HTML 代码进行格式化操作，
     * 即输出的 HTML 内容会保持原始的紧凑格式，而不会进行额外的美化排版处理，主要关注代码的安全性过滤而不是展示格式。
     */
    private static final Document.OutputSettings OUTPUT_SETTINGS = new Document.OutputSettings().prettyPrint(false);

    /**
     * 静态代码块，用于在类加载时进行一些初始化配置操作。在这个类中，由于富文本编辑时可能会通过 `style` 属性来实现一些样式设置，
     * 比如设置红色字体（`style="color:red;"`）等情况，所以需要将 `style` 属性添加到所有允许的 HTML 标签（`:all` 表示所有标签）中，
     * 确保在过滤 XSS 代码的同时，不会误删这些用于样式设置的合法 `style` 属性，使得富文本内容在经过安全过滤后依然能保留必要的样式信息。
     */
    static {
        // 富文本编辑时一些样式是使用 style 来进行实现的
        // 比如红色字体 style="color:red;"
        // 所以需要给所有标签添加 style 属性
        WHITE_LIST.addAttributes(":all", "style");
    }

    /**
     * 核心的静态方法，用于对输入的字符串内容进行 XSS 代码过滤清理操作，它调用了 `Jsoup` 库的 `clean` 方法，
     * 传入要清理的内容字符串、空字符串（此处可能是用于指定文档的基本 URL，这里不需要所以传入空字符串）、
     * 预定义的白名单（`WHITE_LIST`）以及配置好的输出设置（`OUTPUT_SETTINGS`）作为参数，
     * 经过 `Jsoup` 内部的处理逻辑，会按照白名单规则对输入内容中的 HTML 标签和属性进行筛选过滤，去除不符合白名单要求的元素，
     * 最终返回过滤后的安全的字符串内容，确保该内容不存在 XSS 安全风险。
     *
     * @param content 需要进行 XSS 代码过滤的输入字符串内容，通常是包含 HTML 标签的文本，比如用户输入的富文本信息等。
     * @return 经过 XSS 代码过滤后的安全字符串内容，已去除了潜在的恶意脚本代码以及不符合白名单规则的 HTML 元素和属性。
     */
    public static String clean(String content) {
        return Jsoup.clean(content, "", WHITE_LIST, OUTPUT_SETTINGS);
    }
}