フォームの基礎

前回のまとめ

  • @ResponseBodyアノテーションをつけない場合はテンプレートエンジンを使う設定なる。
  • 使うテンプレートはメソッドの戻り値で指定する。
  • テンプレートに値を渡すには、ModelMapクラスを使う。
  • テンプレートで文字列を埋め込むには、要素(タグ)の属性として「th:text=”${モデルの名前}”」を指定する。

フォームを使う

「BMIの計算」を例として、「ブラウザから何か入力して、サーバで処理を行い、結果をブラウザで表示する」ということを行ってみよう。サーバに何か送るにはフォーム(HTMLのformタグとその関連タグ)を使う。

処理の流れを次のシーケンス図に示す。

sequence

テンプレートとコントローラを作成しよう。

ポイント:

  • テンプレート:
    • form要素の内側でinput要素を使う。
    • form要素のaction属性で値をどこにリクエストするか指定する。
    • form要素のmethod属性の違い: getはフォームの値がURLに含まれる。postはURLに含まれない(リクエストボディに記述される)
    • input要素のtype属性で種類が指定できる: textはテキストフォーム、submitは送信ボタン。
    • input要素の区別はname属性で行う。
  • コントローラ(主に14〜26行目):
    • フォームからの値を受け取るには、メソッドに引数を加え、@RequestParamアノテーションをつける。
    • @RequestMappingアノテーションはgetでもpostでも動作する。

formt要素のaction属性を書かない場合は、同じURLにリクエストを送ることになる。action属性を使わない例は次のようになる。

ポイント:

  • テンプレート:
    • form要素のaction属性を書かない場合は同じURLにリクエストする。
  • コントローラ(主に28〜40行目):
    • @GetMappingアノテーションはgetだけで動作し、@PostMappingアノテーションはpostだけで動作する。
    • @GetMappingアノテーションと@PostMappingアノテーションで同じパスを指定することができる。

復習

テンプレートを使う

前回のまとめ

  • Spring BootのアプリケーションはSPRING INITIALIZRでプロジェクトの雛形を作成することができる。
  • @Controllerアノテーション: クラスに付与するアノテーションで、そのクラスがコントローラであることを示す。「コントローラとは何か」は今回解説する。
  • @RequestMappingアノテーション: アクセス先のパス(URLの後ろ側)を表す。クラスとメソッドにそれぞれつけることができ、結合したものが最終的なパスを表す。
  • @ResponseBodyアノテーション: メソッドに付与するアノテーションで、戻り値をそのままブラウザに返すことを表す。
  • サーバのポート番号はデフォルトで8080だが、application.propertiesファイルに設定を記述することで変えることができる。

初学者のためのFAQ

 

  • Q: これまでクラスを作った(書いた、定義した)ら、new演算子でインスタンス化しないと使えなかったけど、コントローラのインスタンス化は?

    A: フレームワークがインスタンス化してくれる。フレームワークとは「全体の処理・流れ定義(実装)されており、その中の一部に自分のコードを組み込んでいくシステム」のこと。わかりやすい解説としてSoftware frameworkソフトウエアのフレームワークとはなにか等。


テンプレートを使う

前回は、文字をブラウザに表示したが、これでは表現力がなさすぎる。HTMLで表示するようにしてみよう。もちろん、コントローラからHTMLで出力するようにしてもいいが、ものすごく大変なので、テンプレートを用意しそこに文字をはめ込んで表示するようにしよう。

Spring Web MVC framework

これから作るウェブアプリケーションはSpringのWeb MVCフレームワークを利用している。このフレームワークにおける処理の流れを次の図に示す(http://docs.spring.io/spring/docs/current/spring-framework-reference/htmlsingle/#mvc-servletより引用)。

Mvc

フロントコントローラがリクエストを適切なコントローラに渡し、コントローラが出力するデータをビュー(テンプレート)が表示するという仕組みだ。このうち、自分で作るのは、「コントローラ」と「ビューテンプレート」である。コントローラからビューに「モデル(要するにデータ)」を渡すことによって表示内容を動的に(つまりメソッド実行時に)変えることができる。

テンプレートエンジン(テンプレートに関する処理を行うソフトウェア)は、前回、SPRING INITIALIZRでプロジェクト作成時に指定したThymeleafが使われる。

コントローラ

テンプレートを利用するコントローラを作成しよう。

前回との違い:

  • メソッドに@ResponseBodyがつかなくなること。これによりメソッドのreturnで指定した文字列がブラウザに直接送られるのではなく、テンプレートを使うようになる。メソッドのreturnで指定する文字列は「どのテンプレートを使うか」を指定するために使う。
  • テンプレートに値を渡すには、ModelMapクラスを使う。メソッド引数としてModelMapを指定すると使えるようになる(フレームワークがテンプレートに引き渡すためのインスタンスを作ってくれる)。ModelMapのaddAttributeメソッドでテンプレートに渡すモデルの「名前」と「値」を指定する。

テンプレート

テンプレートを置く場所(基点)はResourcesのtemplatesだ。コントローラで「lect02/hello」とした場合、templatesの中にlect02というディレクトリを作り、その中にhello.htmlというファイルを作る。

NetBeansのパッケージの表示の仕方によっては、作業が難しい。プロジェクトウィンドウの背景部分を右クリックし、「Javaパッケージの表示方法」を「ツリー」にすると階層構造がわかりやすい。または、プロジェクト表示ではなく、ファイル表示にするとわかりやすい。

templates

コントローラでは3つのテンプレートを指定している。それぞれ作成しよう。

ポイント

  • 単に表示をするだけの場合は素のHTMLで良い。Thymeleafの機能を使う場合は「th:」から始まる要素(タグ)や属性を使う。
  • htmlタグの属性に追加した「xmlns:th=”http://www.thymeleaf.org”」は名前空間の指定。最近のThymeleafならなくても動くが、つけておいたほうが良い。
  • 文字列を埋め込む場合は、要素(タグ)の属性として「th:text=”${モデルの名前}」を指定する。子ノード(要するにタグに挟まれたところ)がモデルの値で置き換わる。他にも指定方法がある。counter.htmlにいくつか例を示す。

実行・確認

実行して、確認しよう。

どのようなHTMLが出力されているかはChromeのデベロッパーツール等を使うと良い。


復習

NetBeansでSpring Bootアプリケーションの開発を始める

プロジェクトの雛形を作成

  1. ブラウザで「http://start.spring.io」にアクセスする。
  2. 「Gradle Project」を選択する。
  3. 「Java」を選択する。
  4. 「2.0.1」を選択する。
  5. グループIDとして、ここでは「ユーザ名」を使う。
  6. アーティファクトIDは、ここでは「webapp」とする。
  7. 利用する依存ライブラリを入力する。名前の一部を入力すると選択肢が現れるのでクリックして選択する。ここでは「Web」と「Thymeleaf」を選択する。
  8. 選択されたものが表示されているので「Web」と「Thymeleaf」が選択されていることを確認する。
  9. クリックするとプロジェクトのファイル(ZIPファイル)のダウンロードが始まる。

Spring Initializr

NetBeansでインポート

メニューから[ファイル]→[プロジェクトをインポート]→[ZIPから]を選択し、ダウンロードしたファイル(webapp.zip)を指定してインポートする。

project

Spring Bootアプリケーションの実行

アプリケーションを実行するためのタスクが定義されているため、それを使う。

プロジェクトを右クリックして、[Task]→[boot]→[bootRun]を選択する。

アプリケーションが立ち上がると、出力ウィンドウの最後に「Started WebappApplication」と表示される。

その1行前に「Tomcat started on port(s): 8080 (http)」と出力されているということは、8080番ポートにアクセスすれば何らかの反応があるはずである。http://localhost:8080/にアクセスしてみよう。

サーバが出力したエラーページ

エラーメッセージが表示されたが、これは、まだコンテンツを返すプログラムを作っていないために表示されるもので、正常な動作である。アプリケーションを終了するには、出力ウィンドウの左側にあるStopボタンをクリックする。

8080ポートが使えない場合(演習室では使えない)はポート番号を変える必要がある。18080に変えるにはapplication.propertiesに次の1行を追加する。

何か表示してみる

Lect01Controllerクラスを作成して実行し、次のURLにアクセスしてみよう。