テンプレートの差し込み欄を、ユーザーが入力した文字列に置き換える。正規表現を使わず replaceAll の検索語を文字列にしたから、置換する側もそのまま入ると思っていませんか。
検索語が文字列でも、置換文字列の $& や $$ には意味があります。今回はNode.js v24.14.1で、置換する値にドル記号が含まれる場合を確認しました(2026-10-19)。
Before:入力した文字列の一部が、差し込み欄へ戻る
const template = "名前:{{name}}";
const input = "前$&後";
console.log(template.replaceAll("{{name}}", input));
// 名前:前{{name}}後
欲しかったのは 名前:前$&後 です。しかし、$& の部分が検索に一致した {{name}} に変わりました。replaceAll が置換を忘れたわけではありません。
この例で特別に解釈されたのは、検索する {{name}} ではなく、2つ目の引数に入れた置換文字列のほうです。
検索語が文字列の場合も、置換文字列の $$ はドル記号1つ、$& は一致した文字列を表します。置換したい値が利用者の自由入力なら、その記号を意図していないかもしれません。
After:関数から文字列を返すと、そのまま入る
const template = "名前:{{name}}";
const input = "前$&後";
console.log(template.replaceAll("{{name}}", () => input));
// 名前:前$&後
2つ目の引数を関数にし、その戻り値としてinputを渡しました。この戻り値では、置換文字列用の $& などが再解釈されません。
「一致した内容を組み合わせて置換したい」と「入力された文字列をそのまま入れたい」を、書き方で分けられます。
同じ入力で、文字列版と関数版を比べる
for (const replacement of ["$&", "$$", "$1", "前$&後"]) {
console.log({
replacement,
string: "A-X-B-X".replaceAll("X", replacement),
callback: "A-X-B-X".replaceAll("X", () => replacement),
});
}
Node.jsで出た結果です。
| 置換する値 | 文字列を渡す | 関数から返す |
|---|---|---|
$& |
A-X-B-X |
A-$&-B-$& |
$$ |
A-$-B-$ |
A-$$-B-$$ |
$1 |
A-$1-B-$1 |
A-$1-B-$1 |
前$&後 |
A-前X後-B-前X後 |
A-前$&後-B-前$&後 |
検索語を文字列の "X" としているこの例では、キャプチャがないため $1 はそのまま残りました。「ドル記号があると、どんな文字列でも壊れる」という話ではありません。
また、$& の行では元の文字列と同じ結果になります。見た目だけでは「置換が走っていない」と見誤りやすいところです。比較するテストデータには、ドル記号のない普通の名前だけでなく、実際に記号を含めた値も入れておきます。
replaceをreplaceAllへ変えるだけでは、この差は直らない
console.log("X-X".replace("X", "$&")); // X-X
console.log("X-X".replaceAll("X", "$&")); // X-X
console.log("X-X".replaceAll("X", () => "$&")); // $&-$&
1つ目のreplaceは先頭だけを置換していますが、結果は同じXです。2つ目は全て置換しても、やはり同じX。3つ目で初めて、今回欲しい「文字そのもの」が入ります。
置換の回数と、置換文字列の解釈は別の問題です。正規表現のgフラグやreplaceAllへの非global正規表現の渡し方は、以前の記事で扱いました。今回は正規表現を使わず、2つ目の引数に絞っています。
なお、関数版に変えてもHTMLとして安全になるわけではありません。置換結果をHTMLとして描画するかどうか、必要なエスケープをどこで行うかは別に確認します。
AIが生成したテンプレート処理を読むときも、2つ目の引数が「置換用の書式」なのか「文字をそのまま渡す値」なのかを見ておくと、変更の目的を説明できます。
参考: MDNのreplaceAll
未経験者向けの講座を運営しています
未経験から Next.js + Supabase + Claude Code で Webアプリを公開するまで を、全24セッションで体系化した教材です。
- ▶ ライブデモ(インストール不要・無料)→ https://trial-web-ayies128s-projects.vercel.app/?ref=qiita
- 教材完全版+月5,500円のメンタリング→ https://menta.work/plan/20251?ref=qiita
- 無料体験版(最初の数セッション分・⭐ Starもよろしくお願いします)→ https://github.com/ayies128/next-ai-camp-trial
- YouTube『AIエンジニア情報局』(AI×開発ニュースを扱う別運営チャンネル・無料)→ https://www.youtube.com/channel/UC1rXVD9WYsQPQEWZyd-A1KA/?ref=qiita
※ 中上級者には易しすぎる内容なので、初心者の知り合いへの紹介や社内研修の参考としてどうぞ。