<th:href>の使い方を完全ガイド!初心者でもわかるHTMLリンク生成の基本
新人
「Spring MVCでリンクをテンプレートに出力したいんですが、普通のhrefじゃダメなんですか?」
先輩
「もちろんhrefでも使えるけど、SpringアプリケーションではThymeleafのth:hrefを使うほうが柔軟で便利なんだよ。」
新人
「どんなふうに便利なんですか?
先輩
「それじゃ、基本から順番に解説していこう!」
1. th:hrefとは?
Spring MVCでWebアプリケーションを開発するときに使うテンプレートエンジンThymeleafには、リンクを動的に生成できる属性th:hrefがあります。
th:hrefは、HTMLのhref属性と似ていますが、Springアプリケーション内でパスやパラメータを@Controllerと連携させて柔軟に指定できるという特徴があります。
通常のhrefでは静的なリンクしか書けませんが、th:hrefを使うと、ルーティングやリクエストパラメータを簡単に組み込めるため、Spring MVC URL指定に最適です。
たとえば以下のように書きます。
<a th:href="@{/products}">商品一覧</a>
これは、Spring MVCの/productsというURLにリンクするテンプレートの記述です。動的にルートが変わる場合でも、自動的にURLを解決してくれます。
このように、Thymeleafでリンクを扱うにはth:hrefの使い方を理解することが重要です。
2. th:hrefを使うメリットとは?
th:href 使い方を学ぶと、以下のようなメリットがあります。
- Thymeleaf リンク生成でパスが自動解決される
- パラメータ付きURLも簡単に記述できる
- Spring MVC URL指定に沿ったテンプレートが書ける
- コントローラとの連携がシンプルになる
通常のHTMLのhrefでは、ルート変更時にリンクを書き直す必要がありますが、th:hrefではSpringのルーティング機能と統合されているため、変更に強いテンプレートが書けます。
以下のように動的にパスを生成することもできます。
<a th:href="@{/product/{id}(id=${product.id})}">商品詳細</a>
このようにth:hrefを使えば、URLの動的生成が可能となり、バックエンドとの連携がスムーズになります。
特にSpring MVCでは、URL構造をコントローラで管理するため、テンプレート側でth:hrefを使っておけば、将来的なURL変更にも柔軟に対応できます。
開発環境がPleiades + Gradleの場合でも、Spring Bootを使わず@Controllerを使う標準構成で問題なく動作します。
このように、静的なHTMLのリンクよりも遥かに柔軟性が高く、検索エンジンに最適化された構造を作ることもできます。
3. th:hrefの基本的な書き方と構文
th:hrefの基本的な構文は、Thymeleafの書き方に従ってURLを動的に生成します。書き方は非常にシンプルで、@{}の中にURLパスを書きます。
<a th:href="@{/users}">ユーザー一覧</a>
この例では、Spring MVCのコントローラで定義された/usersというURLにリンクします。Thymeleafはこの構文を解析して、実行時に正しいURLに置き換えてくれます。
HTMLのhrefと異なり、th:hrefでは動的なパスの生成やパラメータの挿入が可能になります。これにより、テンプレート内でリンクを一元管理しやすくなります。
4. Spring MVCのコントローラと連携するリンクの作成方法
Spring MVCでは、@Controllerクラスのメソッドに@GetMappingを使ってルートを定義します。th:hrefはそのルートにリンクするテンプレート側の指定です。
以下は、コントローラとテンプレートの連携例です。
@Controller
public class PageController {
@GetMapping("/about")
public String showAboutPage() {
return "about";
}
}
<a th:href="@{/about}">このサイトについて</a>
このように、テンプレート側でth:hrefを使うことで、Spring MVCのルートに正しくリンクさせることができます。
静的なHTMLと違って、アプリケーションが成長してもルート構造を柔軟に変更できるのがth:hrefの魅力です。th:href リンク生成という視点でも、保守性の高さは大きなメリットです。
5. URLにパラメータを含めて遷移する例
th:hrefでは、動的にURLパラメータを埋め込むことが可能です。これにより、例えば商品IDやユーザーIDなどをテンプレート内からURLに反映させて遷移できます。
@Controller
public class ProductController {
@GetMapping("/product/{id}")
public String viewProduct(@PathVariable int id, Model model) {
model.addAttribute("productId", id);
return "product-detail";
}
}
<a th:href="@{/product/{id}(id=${product.id})}">詳細を見る</a>
このように書くことで、テンプレート内のproduct.idがURLの{id}部分に自動的に置き換わります。
これはThymeleaf 動的URLの基本的な書き方であり、Spring MVC パラメータ付きリンクを使う場面では欠かせない技術です。
動的リンクを活用すれば、ユーザーが商品をクリックしたときに正しい詳細画面に誘導でき、ユーザー体験の向上にもつながります。
6. 相対パスと絶対パスの使い分け
th:href パスの違いを理解するためには、相対パスと絶対パスの違いを明確にしておく必要があります。テンプレートでリンクを作るとき、リンク先のURLが現在のページに対してどういう位置づけなのかによって書き方が異なります。
絶対パスは、Webアプリケーションのルートからの完全なパスを指定します。これはもっとも一般的で推奨される形式です。
<a th:href="@{/contact}">お問い合わせ</a>
この書き方は、http://localhost:8080/contactのようにルート直下のURLにアクセスします。
一方、相対パスは、現在のURLを基準にしてリンク先を指定します。たとえば/user/listというページから、../homeとすれば1階層上に移動して/homeに遷移します。
<a th:href="@{../home}">ホームに戻る</a>
ただし、相対パスは構造変更に弱いため、Spring MVC リンクの作り方としては絶対パスを使うのが基本です。
7. よくあるエラーとその対処法
Thymeleaf エラー対処法として、th:hrefを使っていると初心者が遭遇しやすいエラーについて見ていきましょう。
まず多いのが、指定したURLがコントローラに存在しない場合です。たとえば以下のようにテンプレートに書いていても、コントローラ側にそのルートがなければ404エラーになります。
<a th:href="@{/profile}">プロフィール</a>
この場合、コントローラ側に@GetMapping("/profile")が定義されているかを確認しましょう。
次に多いのが、リンク先のパラメータにnullや未定義の値が含まれている場合です。たとえば以下のように記述した場合、user.idがnullだとURLが正しく生成されずエラーになります。
<a th:href="@{/user/{id}(id=${user.id})}">ユーザー詳細</a>
このときは、nullチェックをテンプレート内で行うか、サーバ側で確実に値を設定してから表示しましょう。
また、URLの波括弧{}の使い方を間違えると、構文エラーになることもあります。スペルミスや変数の存在チェックも大切です。
8. 学習を深めるためのヒント
Spring MVC リンクの作り方をしっかり身につけるには、公式ドキュメントと実践が一番の近道です。まずはThymeleafの公式ドキュメントを参照し、th:hrefのパターンやオプションを確認しましょう。
次に、自分で小さなサンプルアプリを作って、コントローラからデータを渡してテンプレートでリンクを動的に生成する練習を繰り返すことが大切です。
おすすめの練習方法は次のとおりです:
- ユーザー一覧ページを作り、各ユーザーの詳細ページにリンクさせる
- 商品一覧ページを作り、IDを使って個別のページに遷移させる
- URLに複数のパラメータを含めてページ遷移する
また、Pleiades + Gradle環境では、Spring Bootを使わない@Controller構成で十分学習できます。依存関係はPleiadesのチェック機能から追加できるため、初心者でも簡単に環境構築できます。
テンプレートとコントローラの連携に慣れてくれば、より高度なパラメータの扱いや条件付きリンク生成も自然と理解できるようになります。
最後に、th:hrefの習得はThymeleafの理解を深める第一歩です。動的リンク生成がしっかりできるようになることで、他のテンプレート処理やリスト展開(th:each)とも組み合わせて、より実践的なアプリ開発が可能になります。