Thymeleaf チートシート

cheatsheet

モデル属性などの値をHTMLコンテンツや属性に表示するための基本的な方法です。

属性 説明 使用例
th:text 要素のボディを指定されたテキスト値で置き換えます。特殊文字はエスケープされます。安全です。🛡️
<p th:text="${welcomeMessage}">Welcome!</p>
th:utext 要素のボディを指定されたHTMLコンテンツで置き換えます。エスケープされません (Unescaped Text)。XSS脆弱性に注意が必要です。⚠️
<div th:utext="${formattedHtml}"><strong>Default</strong> content</div>
インライン [[...]] th:text と同様の効果を持ちます。テキストノード内に直接記述できます。
<p>ようこそ、[[${username}]] さん!</p>
インライン [(...)] th:utext と同様の効果を持ちます。テキストノード内に直接記述できます。エスケープされません。
<p>お知らせ: [(${noticeHtml})]</p>

条件分岐 🤔

条件に基づいてHTML要素のレンダリングを制御します。

属性 説明 使用例
th:if 条件式が true の場合にのみ要素をレンダリングします。
<div th:if="${user.isAdmin()}" class="notification is-warning">管理者メニュー</div>
th:unless 条件式が false の場合にのみ要素をレンダリングします。th:if の逆です。
<p th:unless="${user.isActive()}" class="has-text-danger">アカウントが無効です。</p>
th:switch / th:case 複数の条件分岐を記述します。th:switch で評価する値を指定し、th:case で各条件を指定します。th:case="*" はデフォルトケース(どのケースにも一致しない場合)です。
<div th:switch="${user.role}">
  <p th:case="'ADMIN'">管理者権限</p>
  <p th:case="'MANAGER'">マネージャー権限</p>
  <p th:case="*">一般ユーザー権限</p>
</div>

繰り返し処理 🔄

コレクション(リスト、セット、配列など)やマップの要素を反復処理してHTML要素を生成します。

属性 説明 使用例
th:each 指定されたコレクションの各要素に対して、その要素自身をレンダリングします。
<ul>
  <li th:each="item : ${items}" th:text="${item.name}">Item 1</li>
</ul>
状態変数 (Iteration Status) th:each 内で反復処理の状態(インデックス、カウント、サイズ、奇数/偶数など)を取得できる変数。デフォルト名は iterStat ですが、th:each="item, itemStat : ${items}" のように指定できます。
<tr th:each="user, stat : ${users}" th:class="${stat.odd}? 'is-striped' : ''">
  <td th:text="${stat.count}">1</td>
  <td th:text="${user.name}">Username</td>
</tr>

利用可能なプロパティ: index (0始まり), count (1始まり), size, current, even, odd, first, last

マップの繰り返し マップを繰り返す場合、キーと値の両方にアクセスできます。
<dl th:each="entry : ${settingsMap}">
  <dt th:text="${entry.key}">Key</dt>
  <dd th:text="${entry.value}">Value</dd>
</dl>

属性値の設定 ⚙️

HTML要素の属性値を動的に設定します。

属性 説明 使用例
th:href <a> タグなどの href 属性の値を設定します。URL式 @{...} と共に使うことが多いです。🔗
<a th:href="@{/users/{id}(id=${user.id})}">ユーザー詳細</a>
th:src <img><script> タグなどの src 属性の値を設定します。
<img th:src="@{/images/{name}(name=${product.imageName})}" alt="商品画像" />
th:value <input> タグなどの value 属性の値を設定します。
<input type="text" th:value="${searchKeyword}" />
th:classappend 既存の class 属性値に、指定したクラスを追加します。
<div class="box" th:classappend="${user.isAdmin()} ? 'has-background-warning' : ''">...</div>
th:styleappend 既存の style 属性値に、指定したスタイルを追加します。
<span th:styleappend="${error} ? 'color: red;' : 'color: green;'">メッセージ</span>
th:attrappend / th:attrprepend 既存の属性値の前(prepend)または後(append)に値を追加します。区切り文字を指定することも可能です。
<input type="button" value="Do it!" th:attrappend="class=${' ' + cssClass}" />
th:attr 任意の属性とその値を設定します。複数の属性を一度に設定することも可能です。
<button th:attr="data-user-id=${user.id}, data-action='delete'">削除</button>
th:checked, th:selected, th:disabled, etc. 真偽値属性を設定します。式が true の場合、属性が追加されます(例: checked="checked")。false の場合、属性は追加されません。
<input type="checkbox" th:checked="${isActive}" />
<option th:each="c : ${countries}" th:value="${c.code}" th:text="${c.name}" th:selected="${c.code == selectedCountry}">Country</option>
<button type="submit" th:disabled="${form.isProcessing}">送信</button>
th:data-* HTML5の data-* 属性を設定するためのシンタックスシュガーです。
<div th:data-item-id="${item.id}" th:data-item-name="${item.name}">...</div>

これは以下と同等です:

<div th:attr="data-item-id=${item.id}, data-item-name=${item.name}">...</div>

フォームの扱い 📝

フォームの表示、入力値のバインディング、エラー表示などをサポートします。

属性 説明 使用例
th:object フォーム全体でバインドするオブジェクト(フォームバッキングビーン)を指定します。子要素では選択変数式 *{...} を使用してプロパティにアクセスできます。
<form th:action="@{/users/save}" th:object="${userForm}" method="post">
  ...
</form>
th:field フォーム要素(input, select, textarea)と、th:object で指定されたオブジェクトのプロパティをバインドします。id, name, value (または checked/selected) 属性を自動的に設定します。選択変数式 *{...} を使用します。
<input type="text" th:field="*{name}" />
<!-- 生成例: <input type="text" id="name" name="name" value="..." /> -->

<select th:field="*{country}">
  <option th:each="c : ${countries}" th:value="${c.code}" th:text="${c.name}">...</option>
</select>
th:errors 指定したフィールド(または全体 "*")に関連するバリデーションエラーメッセージを表示します。通常、エラーメッセージを含む要素を生成します。
<span th:if="${#fields.hasErrors('name')}" th:errors="*{name}" class="help is-danger">Name Error</span>

<div th:if="${#fields.hasGlobalErrors()}" class="notification is-danger">
  <p th:each="err : ${#fields.globalErrors()}" th:text="${err}">Global error message</p>
</div>
th:errorclass 関連するフィールドにエラーがある場合に、指定したCSSクラスを要素に追加します。
<input type="text" th:field="*{email}" th:errorclass="is-danger" />

#fields ユーティリティオブジェクトは、フォームのエラー処理に役立ちます (例: #fields.hasErrors(...), #fields.errors(...), #fields.hasGlobalErrors(), #fields.globalErrors())。

テンプレートレイアウト 🧩

テンプレートの断片(フラグメント)を定義し、他のテンプレートから再利用することで、共通レイアウトなどを実現します。

属性 / 式 説明 使用例
th:fragment テンプレートの一部をフラグメントとして定義します。名前を付けて他の場所から参照できるようにします。
<!-- in layout.html -->
<footer th:fragment="copy">
  &copy; 2025 Your Company
</footer>
th:insert 指定したフラグメントを、この属性が指定された要素の子要素として挿入します。元の要素は保持されます。
<!-- in page.html -->
<div th:insert="~{layout :: copy}"></div>
<!-- Result: <div><footer>&copy; 2025 Your Company</footer></div> -->
th:replace 指定したフラグメントで、この属性が指定された要素自体を置き換えます。元の要素は削除されます。
<!-- in page.html -->
<div th:replace="~{layout :: copy}">Placeholder for footer</div>
<!-- Result: <footer>&copy; 2025 Your Company</footer> -->
th:include (非推奨) 指定したフラグメントの内容を、この属性が指定された要素の子要素として挿入します。フラグメントのルート要素は含まれません。th:insertth:replace の使用が推奨されます。
<!-- in page.html -->
<div th:include="~{layout :: copy}"></div>
<!-- Result: <div>&copy; 2025 Your Company</div> -->
フラグメント式 ~{...} フラグメントを指定するための式です。~{テンプレート名 :: フラグメント名} または ~{テンプレート名 :: #idセレクタ} または ~{:: フラグメント名} (同じテンプレート内) の形式で使用します。
<div th:replace="~{fragments/common :: header}"></div>
<div th:insert="~{this :: menu}"></div> <!-- 同じテンプレート内の'menu'フラグメント -->
パラメータ付きフラグメント フラグメント定義側で引数を定義し、呼び出し側で値を渡すことができます。
<!-- fragment definition (in components.html) -->
<div th:fragment="alert(type, message)" th:classappend="'alert-' + ${type}" role="alert">
  [[${message}]]
</div>

<!-- fragment usage -->
<div th:replace="~{components :: alert(type='success', message=${successMsg})}"></div>
<div th:replace="~{components :: alert('warning', '注意してください')}"></div>
th:remove 要素とその子要素をテンプレートから削除します。値によって削除するかどうかを制御できます (all, body, tag, all-but-first, none)。条件式と組み合わせて使うこともあります。
<!-- 開発時のみ表示する要素 -->
<div th:remove="${productionMode} ? 'all' : 'none'">開発用情報</div>

<!-- tableのヘッダーやフッターのプレースホルダを削除 -->
<table>
  <thead>
    <tr><th>Name</th></tr>
  </thead>
  <tbody>
    <tr th:remove="all-but-first"> <!-- 最初のtr以外を削除 (ループと組み合わせる) -->
      <td>Placeholder</td>
    </tr>
    <tr th:each="p : ${products}">
      <td th:text="${p.name}">Product Name</td>
    </tr>
  </tbody>
</table>

式の種類 🧮

Thymeleaf で使用できる主な式を紹介します。

説明 使用例
変数式 ${...} モデル属性、リクエストパラメータ、セッション属性、アプリケーション属性などにアクセスします。OGNL (Object-Graph Navigation Language) または Spring Expression Language (SpEL) に基づいて評価されます。
<p th:text="${user.name}">User Name</p>
<p th:text="${param.query}">Query Param</p>
<p th:text="${session.lastAccessTime}">Session Time</p>
選択変数式 *{...} th:object で選択されたオブジェクトのプロパティにアクセスします。変数式 ${...} よりも短く記述できます。
<div th:object="${product}">
  <p>商品名: <span th:text="*{name}">...</span></p>
  <p>価格: <span th:text="*{price}">...</span></p>
</div>
メッセージ式 #{...} 外部化されたメッセージ(国際化対応など)にアクセスします。messages.properties などのファイルから値を取得します。
<h1 th:text="#{welcome.title}">Welcome!</h1>
<p th:text="#{user.greet(${user.name})}">Hello User!</p>
リンクURL式 @{...} アプリケーションのコンテキストパスを考慮したURLを生成します。パス変数やリクエストパラメータを含めることができます。
<a th:href="@{/home}">ホーム</a>
<a th:href="@{/users/{id}/profile(id=${userId}, tab='details')}">プロファイル</a>
<!-- Result: /myapp/users/123/profile?tab=details -->

サーバー相対URL (@{~/path})、プロトコル相対URL (@{ //... })、絶対URL (@{http://...}) も生成可能です。

フラグメント式 ~{...} テンプレートフラグメントを指定します。「テンプレートレイアウト」セクションで詳述。
<div th:insert="~{commons :: footer}"></div>

リテラルと演算子 ✨

式の中で使用できるリテラル(定数値)と演算子です。

リテラル

種類 説明
テキストリテラル シングルクォート '...' で囲みます。 'Hello World', 'ユーザー名'
数値リテラル 通常の数値です。 123, 3.14
真偽値リテラル true または false です。 th:if="${user.active == true}"
Nullリテラル null です。 th:if="${user.email == null}"
リテラルトークン シングルクォートなしで書ける特別なテキストリテラル。英数字、[].-_ のみで構成される場合。 th:classappend=${isAdmin}? main : secondary (mainsecondary がリテラルトークン)

演算子

種類 演算子 (例) 説明
算術演算子 +, -, *, /, % 加算、減算、乗算、除算、剰余
比較演算子 > (gt), < (lt), >= (ge), <= (le), == (eq), != (ne) 大小比較、等価比較。HTMLエンティティ形式も使用可能。
論理演算子 and, or, not (!) 論理積、論理和、否定
条件演算子 (三項演算子) (condition) ? then : else 条件に基づいて値を返します。
エルビス演算子 (value) ?: defaultValue 値が null でない場合はその値を、null の場合はデフォルト値を返します。
No-Op演算子 _ (アンダースコア) プレースホルダーとして機能し、何も行いません。特にプロトタイプ作成時に役立ちます。th:text="_"

演算子の優先順位は一般的なプログラミング言語に準じます。括弧 () を使って明示的に評価順序を指定できます。

ユーティリティオブジェクト 🛠️

テンプレート内で共通のタスクを実行するための便利なオブジェクト群です。#オブジェクト名.メソッド名(...) の形式で使用します。

オブジェクト 説明 代表的なメソッド例
#strings 文字列操作ユーティリティ。 isEmpty(), contains(), startsWith(), endsWith(), equals(), equalsIgnoreCase(), toUpperCase(), toLowerCase(), substring(), replace(), trim(), length(), arrayJoin(), listJoin(), capitalize(), capitalizeWords(), abbreviate()
#numbers 数値操作・フォーマットユーティリティ。 formatInteger(), formatDecimal(), formatCurrency(), formatPercent(), sequence()
#dates java.util.Date オブジェクトのフォーマット・操作ユーティリティ。 format(), createNow(), createToday(), day(), month(), year(), dayOfWeek(), dayOfWeekName(), monthName()
#calendars java.util.Calendar オブジェクトのフォーマット・操作ユーティリティ。#dates と似ています。 format(), createNow(), createToday(), day(), month(), year(), etc.
#temporals (Thymeleaf 3+) Java 8 Date/Time API (java.time) オブジェクトのフォーマット・操作ユーティリティ。 format(), day(), month(), year(), dayOfWeek(), hour(), minute(), second(), createNow(), createToday()
#lists java.util.List のユーティリティ。 toList(), size(), isEmpty(), contains(), containsAll(), sort()
#arrays 配列のユーティリティ。 toArray(), length(), isEmpty(), contains(), containsAll()
#sets java.util.Set のユーティリティ。 toSet(), size(), isEmpty(), contains(), containsAll()
#maps java.util.Map のユーティリティ。 size(), isEmpty(), containsKey(), containsValue()
#aggregates 配列やコレクションの集計ユーティリティ。 sum(), avg()
#messages メッセージ式 #{...} と同様の機能を提供します。 msg(), msgOrNull(), arrayMsg(), listMsg(), setMsg()
#uris / #urls URL/URIエンコーディング・デコーディング。 encode(), decode(), encodePath(), encodeQueryParam()
#ids 繰り返し処理などで動的な id 属性値を生成するのに役立ちます。 seq(), prev(), next()
#ctx / #request / #response / #session / #servletContext Webコンテキスト関連オブジェクトへのアクセス。(環境によっては利用できない場合があります) #request.getParameter(), #session.getAttribute(), #ctx.locale, #servletContext.contextPath
#locale 現在のリクエストのロケール (java.util.Locale) を取得します。 #locale.country, #locale.language
#execInfo テンプレート処理に関する情報 (テンプレート名、処理日時など) を取得します。 #execInfo.templateName, #execInfo.processedDate
#objects オブジェクト操作ユーティリティ (null チェックなど)。 nullSafe(), arrayIsNull(), listIsNull(), setIsNull(), mapIsNull()
#bools 真偽値操作ユーティリティ。 isTrue(), isFalse()

これらは標準で提供される主なユーティリティオブジェクトです。Spring Framework と連携している場合は、さらに Spring 固有のユーティリティオブジェクト (#themes, #mvc など) が利用可能になることがあります。

インライン処理 📜

HTML タグの属性を使わずに、テキストノードや JavaScript / CSS コード内に直接 Thymeleaf の式を埋め込む方法です。

構文 / 属性 説明 使用例
[[...]] テキストインライン。th:text と同等で、エスケープされます。
<p>こんにちは、 [[${user.name}]] さん!</p>
[(...)] テキストインライン(アンエスケープ)。th:utext と同等で、エスケープされません。
<p>アナウンス: [(${noticeHtml})]</p>
th:inline="text" 要素全体でテキストインライン処理 [[...]] / [(...)] を有効にします。通常 <body> や特定の <div> に設定します。
<body th:inline="text">
  ようこそ、[[${user.name}]] さん。
</body>
th:inline="javascript" <script> タグ内で JavaScript インライン処理を有効にします。Thymeleaf 式の結果を JavaScript の構文として適切に出力します(文字列はクォートされ、オブジェクトは JSON にシリアライズされるなど)。
<script th:inline="javascript">
  /*

/*[[...]]*/ 形式のコメント構文は、静的プロトタイプとしても機能し、JavaScript エラーを防ぎます。/* で囲むことで、<& などの文字をエスケープせずに済みます。

th:inline="css" <style> タグ内で CSS インライン処理を有効にします。主に式の結果を CSS の値として埋め込む際に使用します。
<style th:inline="css">
  .highlight {
    background-color: /*[[${highlightColor}]]*/ yellow;
  }
</style>
th:inline="none" 親要素でインライン処理が有効になっている場合に、特定の要素でインライン処理を無効にします。
<body th:inline="text">
  User: [[${user.name}]]
  <!-- この部分はインライン処理しない -->
  <div th:inline="none">[[this is literal]] [(${this too})]</div>
</body>

コメントとブロック 🧱

テンプレート内にコメントを記述する方法や、特定の属性を持たないコンテナとして機能する要素について説明します。

種類 説明 使用例
標準HTML/XMLコメント <!-- ... --> 通常のコメント。最終的な出力にも含まれます。
<!-- This is a standard HTML comment -->
パーサーレベルコメントブロック <!--/* ... */--> Thymeleaf パーサーによって処理され、最終的な出力からは削除されます。テンプレートのロジックに関するコメントに適しています。
<!--/* Authenticated users only */-->
<div th:if="${isAuthenticated}">...</div>
プロトタイプオンリーコメントブロック <!--/*/ ... /*/--> 静的なプロトタイプとしてテンプレートを開いた場合にのみ表示され、Thymeleaf によって処理される際には削除されます。
<!--/*/
<div class="sample-data">This is only for prototyping</div>
/*/-->
th:block 属性を適用するためだけの、出力されない匿名の要素です。th:eachth:if などを適用したいが、適切なHTMLタグがない場合に使用します。
<th:block th:each="user : ${users}">
  <div>[[${user.name}]]</div>
  <div>[[${user.email}]]</div>
</th:block>

<th:block th:if="${isAdmin}">
  <!-- 管理者向けコンテンツ -->
</th:block>

コメント

タイトルとURLをコピーしました