💻

JsRender にて HTML エスケープしつつ <br> は適用する

2023/12/19に公開

目的

以下のようなデータを JsRender を利用しレンダリングする要件があるとします。

{
    "id": 1,
    "description": "<p>タグ:\r\n<p>タグは要素が段落であることを示します"
}

description には改行コードが含まているため、<br> タグに変換したうえで表示することが目的ですが、文章に含まれている HTMLタグ等はエンコードして表示する必要があります。

解決策

テンプレートタグ {{> ...}} は使用せず、コンバータを作成して対応する。

テンプレートタグ {{> ...}} を使用することでタグ等のエンコードは可能ですが、 <br> タグもエンコードされてしまいます。

そこで、HTMLエンコードを行ったうえで改行コードの変換を行うコンバータを作成して利用します。

JavaScript
const data = {
    "id": 1,
    "description": "<p>タグ:\r\n<p>タグは要素が段落であることを示します"
};

// コンバータ作成
$.views.converters("escape", function(val) {
  return $.views.converters.html(val).replace(/(\r\n|\r|\n)/g, "<br>"); // 改行コード変換
});

const template = $.templates("#template");
const htmlOutput = template.render(data);
$("#result").html(htmlOutput);
HTML
<script id="template" type="text/x-jsrender">
    <p>{{escape:description}}</p>
</script>

<div id="result"></div>

説明

コンバータはレンダリング前にデータ変換処理など任意の処理を挟む機能で、コンバータの登録は以下の部分で行っています。

$.views.converters("escape", function(val) {
  return $.views.converters.html(val).replace(/(\r\n|\r|\n)/g, "<br>"); // 改行コード変換
});

ここでは、HTML エンコード処理と改行コードの変換処理を行っています。
テンプレート HTML 側で {{escape:description}} というように表記することで、上記の処理が行われた結果がレンダリングされます。

改行コード変換前の HTML エンコード処理ですが、自前で作成するのではく組み込みの HTML エンコード処理 $.views.converters.html(val) を利用することで流用しています。
( 上記のメソッドで {{>...}} と同じエンコーダーを宣言的に利用できます)

Built-in HTML encoder | JsRender/JsViews

JsRender includes an HTML encoder, which you can use programmatically as follows:

var myHtmlEncodedString = $.views.converters.html(myString);

The same encoder is accessed declaratively as a converter, as in the following two > examples:

{{html:myExpression}}
{{>myExpression}}

今回はコンバータを利用しましたが、ヘルパーでも同様の対応が可能です。
特定のテンプレートやレンダリングで適用させたい場合はヘルパーを用いると良いかもしれません。

おわり。

Discussion