親バカエンジニアのナレッジ帳

webのエンジニアをやっており、日頃の開発で詰まったことや書き残しておきたいことを載せています。育児のイロハという育児サイト(https://ikujip.jp)の開発も行っているため、その開発で使用されている技術についても掲載しています。

ThymeleafでJavascriptエラー(SAXParseException)

Thymeleafでのorg.xml.sax.SAXParseException例外

Thymeleafは構文チェックが厳しく、Javascriptなどをそのまま文中に貼り付けると、以下のようなエラーが発生してしまいページが開けないことがあります。

org.xml.sax.SAXParseException: エンティティ"l"への参照は';'デリミタで終了する必要があります。

"l"はあくまで一例であって、Javascriptの内容によって変数名は変わってきます。
この場合ではなんとなくエンティティ"l"という箇所付近を調査しますよね。
でもこのメッセージだけで解決することは難しいです。

エラーが発生したJavascriptの中で、srcなどでURLを入力している箇所はありませんか?
もしあったら、その中で「&」という文字列がないか確認してください。
GETパラメータが複数ある場合などにきっと「&」があるはずです。

Thymeleafでは、「&」はそのままでは使えないのです。

解決方法としては2つあり、「&」をエスケープして使えるようにするか、エスケープしなくても使用できるようにコメントを挿入するかのいずれかになります。

解決方法1 「&」をエスケープ

エスケープする時は、「&」を「&」という文字に置き換えればOKです。

「&」→「&」

<script type="text/javascript" th:inline="javascript">
	(function()
	・
	src='https://www.test.com/test.js?id=1&amp;l=2
	・
	);
</script>

みたいな感じですね。

「&」が連続で複数存在している場合も同様です。
以下のように

「&&」→「&amp;&amp;」

とすれば問題ありません。

簡単と言えば簡単な解決策ですが、「&」がたくさんある場合は、どこをどう変えたのかややこしくなることがあります。

解決方法2 エスケープしなくても使用できるようにコメントを挿入する

Javascriptの前後にコメントを入れても解決できます。
具体的には構文の開始前に

/*<![CDATA[*/

を、構文の最後の後ろに

/*]]>*/

を入れれば大丈夫です。

こんな感じですね。

<script type="text/javascript" th:inline="javascript">
	/*<![CDATA[*/
	(function()
	・
	・
	・
	);
	/*]]>*/
</script>

こうするとThymeleafはJavascriptの構文チェックを無視してくれます。
個人的には解決方法2の方がおすすめですが、お好みの方をお使いください。