Next.js DOMPurify.sanitize() 显示 TypeError: dompurify__WEBPACK_IMPORTED_MODULE_6___default.a.sanitize is not a function

时间:2021-01-09 18:16:02

标签: javascript next.js dompurify getserversideprops

我在 DOMPurify.sanitize() 中使用 dangerouslySetInnerHTML={{}} 来显示从数据库返回的 innerHtml。出于最初的目的,我在此页面中使用 getServersideProps()next-redux-wrapper

我安装了 dompurify:npm i -S dompurify,当前版本是:“^2.2.6”。

我的代码:

    import DOMPurify from 'dompurify';
    import { useSelector } from 'react-redux';
    import { END } from 'redux-saga';
    import wrapper from '../redux/storeSetup';

    const EmployeePage = () => {
    
        const blog = useSelector(state => state.data);

        const html_body = blog[0].body_html;
    
        const clean = DOMPurify.sanitize(html_body);
    
        return(
           <div className="mainContainer">
                <div dangerouslySetInnerHTML ={{ __html: clean }} />
                <ul>
                    {blog.map((item) => (
                        <li key={item.author}>
                            <span>{item.author}</span><br/>
                            <span>{item.title}</span>
                            <h4>{item.body_delta}</h4>
                            <p>{item.body_html}</p>
                            <p>{item.created_on}</p>
                        </li>
                    ))}
                </ul>
            </div>
        );
    }

    export const getServerSideProps = wrapper.getServerSideProps( async ({store}) => {
        store.dispatch({type: GET_DATA});
        store.dispatch(END);
        await store.sagaTask.toPromise();    
    });
    export default EmployeePage;

但是当我用 npm run dev 运行它时,我收到了这个错误: TypeError: dompurify__WEBPACK_IMPORTED_MODULE_1___default.a.sanitize is not a function

这里有什么问题?我尝试使用更简单的代码,但一切都显示相同的错误!我做错了什么?

4 个答案:

答案 0 :(得分:0)

根据这个: https://github.com/cure53/DOMPurify/issues/29#issuecomment-466626162

尝试以下操作(来自上面的示例):

f2(x)
#[1] TRUE
f2(y)
#[1] FALSE
f2(z)
#[1] FALSE

答案 1 :(得分:0)

我找到了一个可行的解决方案:我没有在服务器端清理innerHtml,而是在提交富文本博客后立即在客户端清理它,在我的例子中,react-quill

import dynamic from 'next/dynamic'
import {useState} from 'react'
import DOMPurify from 'dompurify';

const QuillNoSSRWrapper = dynamic(import('react-quill'), {
    ssr: false,
    loading: () => <p>Loading...</p>,
})

// quill modules definitions
//...

export default function articles() {
    const [text, setText] = useState(preData);

    function handleTextChange(content, delta, source, editor) {
        //let str = JSON.stringify(editor.getContents());
        //let parsed = JSON.parse(str)
        setText(editor.getContents());
        const cleaned = DOMPurify.sanitize(editor.getHTML());
        console.log('Cleaned Html: ', cleaned);

    return (
        <div className="quill_container">
            <div id="editor" className="editor">
                <QuillNoSSRWrapper
                    id="quilleditor"
                    modules={modules}
                    formats={formats}
                    theme="snow"
                    value={text}
                    onChange={handleTextChange}
                  />
             </div>
        </div>
    );
};

答案 2 :(得分:0)

使用Isomorphic dompurify

它可以在服务器端和浏览器上呈现

答案 3 :(得分:0)

昨天使用 TypeScript/React 设置遇到了这个问题。

select * from (
        (select * from banners where type = 1 order by rand() limit 1) union
        (select * from banners where type = 3 order by rand() limit 1) union
        (select * from banners order by rand() limit 1)
) as r limit 1

这段代码在 Jest 测试中运行良好,但在浏览器中失败,因为 DOMPurify 对象未定义。 在挖掘时,我发现在窗口范围内附加了一个 DOMPurify 对象。我最终不得不进行 hack 以处理在节点中运行和在浏览器中运行之间的不同行为:

import DOMPurify from 'dompurify';

export const sanitize = (html: string): string => DOMPurify.sanitize(html);

有一个编译器警告,但它是有效的。 我可以通过直接导入库的 es.js 版本来消除编译器警告:import DOMPurify from 'dompurify'; interface IDOMPurifyWindow extends Window { DOMPurify: typeof DOMPurify; } const purify = ((window as unknown) as IDOMPurifyWindow)?.DOMPurify || DOMPurify; export const sanitize = (html: string): string => DOMPurify.sanitize(html); 但这导致 Jest 无法运行,因为它需要 vanilla JavaScript。

这个库做的很棒,但如果您使用 TypeScript 并在浏览器中运行,则使用起来不是非常友好。