
isomorphic-dompurify というライブラリを使用してエラーが発生
Next.jsがサーバーサイドでCommonJS(CJS)とES Modules(ESM)のインポートが混在したパッケージ(この場合、jsdom)を扱う際に発生する一般的な依存関係の解決エラー
カスタムセクション作成時に、「isomorphic-dompurify」という安全なHTMLサニタイズライブラリをインストールしました。
しかし、サーバー側で以下のエラーが発生しました。
▼エラーメッセージ
ule /home/beyond/beyond-front/node_modules/jsdom/node_modules/parse5/dist/index.js from /home/beyond/beyond-front/node_modules/jsdom/lib/jsdom/browser/parser/html.js not supported. ome/beyond/beyond-front/node_modules/jsdom/lib/jsdom/browser/parser/html.js to a dynamic import() which is available in all CommonJS modules. t/node_modules/next/dist/server/require-hook.js:64:28) nd-front/node_modules/jsdom/lib/jsdom/browser/parser/html.js:3:16) { onents render. The specific message is omitted in production builds to avoid leaking sensitive details. A digest property is included on this error instance which may provide additional details about the nature of the error.] { ule /home/beyond/beyond-front/node_modules/jsdom/node_modules/parse5/dist/index.js from /home/beyond/beyond-front/node_modules/jsdom/lib/jsdom/browser/parser/html.js not supported. ome/beyond/beyond-front/node_modules/jsdom/lib/jsdom/browser/parser/html.js to a dynamic import() which is available in all CommonJS modules. t/node_modules/next/dist/server/require-hook.js:64:28) nd-front/node_modules/jsdom/lib/jsdom/browser/parser/html.js:3:16) { onents render. The specific message is omitted in production builds to avoid leaking sensitive details. A digest property is included on this error instance which may provide additional details about the nature of the error.] { onents render. The specific message is omitted in production builds to avoid leaking sensitive details. A digest property is included on this error instance which may provide additional details about the nature of the error.] { ule /home/beyond/beyond-front/node_modules/jsdom/node_modules/parse5/dist/index.js from /home/beyond/beyond-front/node_modules/jsdom/lib/jsdom/browser/parser/html.js not supported. ome/beyond/beyond-front/node_modules/jsdom/lib/jsdom/browser/parser/html.js to a dynamic import() which is available in all CommonJS modules. t/node_modules/next/dist/server/require-hook.js:64:28) nd-front/node_modules/jsdom/lib/jsdom/browser/parser/html.js:3:16) { onents render. The specific message is omitted in production builds to avoid leaking sensitive details. A digest property is included on this error instance which may provide additional details about the nature of the error.] { ule /home/beyond/beyond-front/node_modules/jsdom/node_modules/parse5/dist/index.js from /home/beyond/beyond-front/node_modules/jsdom/lib/jsdom/browser/parser/html.js not supported. ome/beyond/beyond-front/node_modules/jsdom/lib/jsdom/browser/parser/html.js to a dynamic import() which is available in all CommonJS modules. t/node_modules/next/dist/server/require-hook.js:64:28) nd-front/node_modules/jsdom/lib/jsdom/browser/parser/html.js:3:16) { onents render. The specific message is omitted in production builds to avoid leaking sensitive details. A digest property is included on this error instance which may provide additional details about the nature of the error.] { onents render. The specific message is omitted in production builds to avoid leaking sensitive details. A digest property is included on this error instance which may provide additional details about the nature of the error.] { ule /home/beyond/beyond-front/node_modules/jsdom/node_modules/parse5/dist/index.js from /home/beyond/beyond-front/node_modules/jsdom/lib/jsdom/browser/parser/html.js not supported. ome/beyond/beyond-front/node_modules/jsdom/lib/jsdom/browser/parser/html.js to a dynamic import() which is available in all CommonJS modules. t/node_modules/next/dist/server/require-hook.js:64:28) nd-front/node_modules/jsdom/lib/jsdom/browser/parser/html.js:3:16) { onents render. The specific message is omitted in production builds to avoid leaking sensitive details. A digest property is included on this error instance which may provide additional details about the nature of the error.] { ule /home/beyond/beyond-front/node_modules/jsdom/node_modules/parse5/dist/index.js from /home/beyond/beyond-front/node_modules/jsdom/lib/jsdom/browser/parser/html.js not supported. ome/beyond/beyond-front/node_modules/jsdom/lib/jsdom/browser/parser/html.js to a dynamic import() which is available in all CommonJS modules. t/node_modules/next/dist/server/require-hook.js:64:28) nd-front/node_modules/jsdom/lib/jsdom/browser/parser/html.js:3:16) { onents render. The specific message is omitted in production builds to avoid leaking sensitive details. A digest property is included on this error instance which may provide additional details about the nature of the error.] { onents render. The specific message is omitted in production builds to avoid leaking sensitive details. A digest property is included on this error instance which may provide additional details about the nature of the error.] { ule /home/beyond/beyond-front/node_modules/jsdom/node_modules/parse5/dist/index.js from /home/beyond/beyond-front/node_modules/jsdom/lib/jsdom/browser/parser/html.js not supported. ome/beyond/beyond-front/node_modules/jsdom/lib/jsdom/browser/parser/html.js to a dynamic import() which is available in all CommonJS modules. t/node_modules/next/dist/server/require-hook.js:64:28) nd-front/node_modules/jsdom/lib/jsdom/browser/parser/html.js:3:16) { onents render. The specific message is omitted in production builds to avoid leaking sensitive details. A digest property is included on this error instance which may provide additional details about the nature of the error.] { ule /home/beyond/beyond-front/node_modules/jsdom/node_modules/parse5/dist/index.js from /home/beyond/beyond-front/node_modules/jsdom/lib/jsdom/browser/parser/html.js not supported. ome/beyond/beyond-front/node_modules/jsdom/lib/jsdom/browser/parser/html.js to a dynamic import() which is available in all CommonJS modules. t/node_modules/next/dist/server/require-hook.js:64:28) nd-front/node_modules/jsdom/lib/jsdom/browser/parser/html.js:3:16) { onents render. The specific message is omitted in production builds to avoid leaking sensitive details. A digest property is included on this error instance which may provide additional details about the nature of the error.] { onents render. The specific message is omitted in production builds to avoid leaking sensitive details. A digest property is included on this error instance which may provide additional details about the nature of the error.] { ule /home/beyond/beyond-front/node_modules/jsdom/node_modules/parse5/dist/index.js from /home/beyond/beyond-front/node_modules/jsdom/lib/jsdom/browser/parser/html.js not supported. ome/beyond/beyond-front/node_modules/jsdom/lib/jsdom/browser/parser/html.js to a dynamic import() which is available in all CommonJS modules. t/node_modules/next/dist/server/require-hook.js:64:28) nd-front/node_modules/jsdom/lib/jsdom/browser/parser/html.js:3:16) { onents render. The specific message is omitted in production builds to avoid leaking sensitive details. A digest property is included on this error instance which may provide additional details about the nature of the error.] { ule /home/beyond/beyond-front/node_modules/jsdom/node_modules/parse5/dist/index.js from /home/beyond/beyond-front/node_modules/jsdom/lib/jsdom/browser/parser/html.js not supported. ome/beyond/beyond-front/node_modules/jsdom/lib/jsdom/browser/parser/html.js to a dynamic import() which is available in all CommonJS modules. t/node_modules/next/dist/server/require-hook.js:64:28) nd-front/node_modules/jsdom/lib/jsdom/browser/parser/html.js:3:16) { onents render. The specific message is omitted in production builds to avoid leaking sensitive details. A digest property is included on this error instance which may provide additional details about the nature of the error.] { onents render. The specific message is omitted in production builds to avoid leaking sensitive details. A digest property is included on this error instance which may provide additional details about the nature of the error.] {✅ エラーの原因(結論)
isomorphic-dompurify をインストールしたことで、SSR(サーバー側)で DOMPurify が動こうとし、その内部で jsdom が読み込まれる → jsdom が parse5 を ESM として読み込めずクラッシュした。
つまり:
❌ Next.js(SSR環境)で jsdom を読み込む
➜ jsdom 内で parse5(ESM)が require() される
➜ 「CommonJS で ESM 読み込みはサポートされない」というエラーが発生
という流れです。
(超やさしく)
isomorphic-dompurify というパッケージは、 「危ないHTML(悪意のあるコード)を安全なHTMLに変換する」ための道具です。
でも、その道具の奥にある部品(jsdom と parse5)が、 最新バージョン同士だとケンカしちゃってる状態なんです。
Next.js(サーバー側)で動かすと、 「この部品、読み方が古いよ!新しい書き方に直して!」 と怒られて、画面が真っ白になってしまいます(エラーがいっぱい出る)
🧩 1. jsdom(ジェイエスドム)とは?
👉 Node.js 上でブラウザの DOM を再現するためのライブラリ
Node.jsはサーバー環境であり、本来DOM(HTMLの構造を操作する仕組み)を持っていません。
しかし、DOMPurifyのようなブラウザの機能(DOM)に依存するライブラリをサーバー側で動かしたいときに、JSDOMが必要になります。
DOMPurify をサーバーで動かすときよく使われます。
🧩 2. parse5 とは?
👉 HTML を解析するためのライブラリ
HTMLのテキストを読み込み、コンピュータが理解できるDOMツリー構造に変換する作業(解析)を行います。
JSDOMは、仮想DOMを構築するために、読み込むHTMLを解析する必要があります。
Parse5は、そのJSDOMが内部で利用している主要なHTMLパーサー(解析エンジン)の一つです。
🧩 3. ESM(ES Modules)とは?
👉 JavaScript の新しい標準モジュール方式
書き方は:
import parse5 from "parse5";
特徴:
ブラウザと Node.js で同じ書き方が使える
import / export を使う
🧩 4. CommonJS(CJS)とは?
👉 Node.js で昔から使われていたモジュール方式
書き方は:
const parse5 = require("parse5");
特徴:
Node.js で長年使われてきた
require() を使う
🧩 5. CJS/ESM 問題(トラブルの原因)とは?
👉 “古い書き方(CJS)” と “新しい書き方(ESM)” が混ざって壊れること
今回出たエラーはこれ。
具体的には:
jsdom(古い CJS)
parse5(新しい ESM)
この組み合わせで:
CJS(require)で、ESM(import用)を読み込もうとして失敗した!
というエラーが起きています。
例えると:
昔の VHS(CJS)プレーヤーで、ブルーレイディスク(ESM)を再生しようとして「再生できません!」と言われている状態。
✨Gemini解説
Next.jsがサーバーサイドでCommonJS(CJS)とES Modules(ESM)のインポートが混在したパッケージ(この場合、jsdom)を扱う際に発生する一般的な依存関係の解決エラーです。
isomorphic-dompurifyは、Node.js環境(Next.jsのサーバー側)では**jsdom**を利用してDOM環境をエミュレートします。このエラーは、jsdomがその内部でparse5をインポートする際に、Next.jsの新しいモジュールシステム(ESMを意識したもの)と衝突しているために起きています。
🌎Grok解説
このエラーは、Next.jsのサーバーサイドレンダリング(SSR)中に発生する、jsdomライブラリとその依存関係であるparse5の互換性問題が原因です。具体的には、以下の点が問題となっています。
isomorphic-dompurify は、サーバー側でHTMLサニタイズを行うために jsdom を使用します。
最近の jsdom のバージョン(v27.0.1 以降)では、依存ライブラリの parse5 が ESM(ECMAScript Modules)専用になったにもかかわらず、jsdomの内部コードがこれを CommonJS の require() で読み込もうと試みています。
Next.js のサーバーサイド処理(next/dist/server/require-hook.js)は CommonJS ベースのため、この require() が失敗し、「require() of ES Module not supported」というエラーが繰り返し出力されます。
この問題は jsdom のリグレッションバグ(jsdom/jsdom#3966)で、v27.0.1 で導入されたものです。エラーメッセージの「Convert ... to a dynamic import()」は、静的な require() を動的な import() に置き換えるよう提案していますが、ライブラリ側で修正が必要な根本原因です。
✅ 【最も簡単で確実な解決策】 → isomorphic-dompurify を使うのをやめる
Next.js では SSR(サーバー側)とブラウザ側の両方で DOMPurify を動かす必要はありません。
むしろ SSR 側で DOMPurify を動かすと
今回のように jsdom が勝手に動き出してエラーになります。
なぜ SSR とブラウザで両方 sanitize する必要がないのか?
理由 | 内容 |
|---|---|
技術的 | SSR は DOM がない → DOMPurify は本来動作不可 |
安全性 | XSS が起きるのはブラウザ → 最終防衛はブラウザのみで良い |
運用 | 保存時にサーバーで一度 sanitize → SSR 時にする必要がない |
パフォーマンス | jsdom は重い → SSR を遅くする |
互換性 | SSR と CSR の HTML がズレると Hydration Error |
✔️ 結論(もう一度)
Next.js の DOMPurify は「クライアント側だけで実行」が最も安全・最速・最適。
SSR 側では sanitize しなくていいし、しないほうが良い。
よくある質問
この商品について質問がありますか?コミュニティや専門家に質問してください。
