Web 画面フォーム送信処理

このガイドでは、Spring を使用して Web フォームを作成および送信するプロセスを順を追って説明します。

構築するもの

このガイドでは、次の URL からアクセスできる Web フォームを作成します。http://localhost:8080/greeting

このページをブラウザーで表示すると、フォームが表示されます。id および content フォームフィールドに入力して、挨拶を送信できます。フォームが送信されると、結果ページが表示されます。

必要なもの

本ガイドの完成までの流れ

ほとんどの Spring 入門ガイドと同様に、最初から始めて各ステップを完了するか、すでに慣れている場合は基本的なセットアップステップをバイパスできます。いずれにしても、最終的に動作するコードになります。

最初から始めるには、Spring Initializr から開始に進みます。

基本をスキップするには、次の手順を実行します。

完了したときは、gs-handling-form-submission/complete のコードに対して結果を確認できます。

Spring Initializr から開始

IDE を使用する場合はプロジェクト作成ウィザードを使用します。IDE を使用せずにコマンドラインなどで開発する場合は、この事前に初期化されたプロジェクトからプロジェクトを ZIP ファイルとしてダウンロードできます。このプロジェクトは、このチュートリアルの例に合うように構成されています。

プロジェクトを手動で初期化するには:

  1. IDE のメニューまたはブラウザーから Spring Initializr を開きます。アプリケーションに必要なすべての依存関係を取り込み、ほとんどのセットアップを行います。

  2. Gradle または Maven のいずれかと、使用する言語を選択してください。

  3. 依存関係をクリックし、Spring Web と Thymeleaf を選択します。

  4. 生成をクリックします。

  5. 結果の ZIP ファイルをダウンロードします。これは、選択して構成された Web アプリケーションのアーカイブです。

Eclipse や IntelliJ のような IDE は新規プロジェクト作成ウィザードから Spring Initializr の機能が使用できるため、手動での ZIP ファイルのダウンロードやインポートは不要です。
プロジェクトを GitHub からフォークして、IDE または他のエディターで開くこともできます。

Web コントローラーを作成する

Spring の Web サイト構築手法では、コントローラーが HTTP リクエストを処理します。これらのコンポーネントは、@Controller (Javadoc) アノテーションによって容易に識別できます。以下のリストにある GreetingController は、View (Javadoc) (この場合は greeting)の名前を返すことで、/greeting への GET リクエストを処理します。次の View は、HTML コンテンツのレンダリングを担当します。

Java
package com.example.handlingformsubmission;

import org.springframework.stereotype.Controller;
import org.springframework.ui.Model;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.ModelAttribute;
import org.springframework.web.bind.annotation.PostMapping;

@Controller
public class GreetingController {

	@GetMapping("/greeting")
	public String greetingForm(Model model) {
		model.addAttribute("greeting", new Greeting());
		return "greeting";
	}

	@PostMapping("/greeting")
	public String greetingSubmit(@ModelAttribute Greeting greeting, Model model) {
		model.addAttribute("greeting", greeting);
		return "result";
	}

}
Kotlin
package com.example.handlingformsubmission

import org.springframework.stereotype.Controller
import org.springframework.ui.Model
import org.springframework.ui.set
import org.springframework.web.bind.annotation.GetMapping
import org.springframework.web.bind.annotation.ModelAttribute
import org.springframework.web.bind.annotation.PostMapping

@Controller
class GreetingController {

    @GetMapping("/greeting")
    fun greetingForm(model: Model): String {
        model["greeting"] = Greeting()
        return "greeting"
    }

    @PostMapping("/greeting")
    fun greetingSubmit(@ModelAttribute greeting: Greeting, model: Model): String {
        model["greeting"] = greeting
        return "result"
    }
}

このコントローラーは簡潔でシンプルですが、多くのことが行われています。このセクションの残りの部分では、ステップごとに分析します。

マッピングアノテーションを使用すると、HTTP リクエストを特定のコントローラーメソッドにマッピングできます。このコントローラーの 2 つのメソッドは、両方とも /greeting にマップされます。@RequestMapping を使用できます(デフォルトでは、GET、POST などのすべての HTTP 操作をマップします)。ただし、この場合、greetingForm() メソッドは @GetMapping を使用して GET に特別にマップされ、greetingSubmit() は @PostMapping を使用して POST にマップされます。このマッピングにより、コントローラーは /greeting エンドポイントへのリクエストを区別できます。

greetingForm() メソッドは、Model (Javadoc) オブジェクトを使用して新しい Greeting をビューテンプレートに公開します。次のコードの Greeting オブジェクトには、greeting ビューのフォームフィールドに対応する id や content などのフィールドが含まれており、フォームから情報を取得するために使用されます。

Java
package com.example.handlingformsubmission;

public class Greeting {

	private long id;
	private String content;

	public long getId() {
		return id;
	}

	public void setId(long id) {
		this.id = id;
	}

	public String getContent() {
		return content;
	}

	public void setContent(String content) {
		this.content = content;
	}

}
Kotlin
package com.example.handlingformsubmission

data class Greeting(
    val id: Long = 0,
    val content: String? = null
)

メソッド本体の実装は、ビュー技術を利用して、ビュー名(greeting)をレンダリング用のテンプレートに変換することで、サーバー側で HTML のレンダリングを実行します。この場合、Thymeleaf (英語) を使用します。Thymeleaf (英語) は greeting.html テンプレートを解析し、さまざまなテンプレート式を評価してフォームをレンダリングします。以下に greeting テンプレートを示します。

<!DOCTYPE HTML>
<html xmlns:th="https://www.thymeleaf.org">
<head> 
    <title>Getting Started: Handling Form Submission</title>
    <meta http-equiv="Content-Type" content="text/html; charset=UTF-8" />
</head>
<body>
	<h1>Form</h1>
    <form action="#" th:action="@{/greeting}" th:object="${greeting}" method="post">
    	<p>Id: <input type="text" th:field="*{id}" /></p>
        <p>Message: <input type="text" th:field="*{content}" /></p>
        <p><input type="submit" value="Submit" /> <input type="reset" value="Reset" /></p>
    </form>
</body>
</html>

th:action="@{/greeting}" 式はフォームを /greeting エンドポイントに POST するように指示し、th:object="${greeting}" 式はフォームデータを収集するために使用するモデルオブジェクトを宣言します。th:field="*{id}" と th:field="*{content}" で表される 2 つのフォームフィールドは、Greeting オブジェクト内のフィールドに対応します。

以上で、フォームを表示するためのコントローラー、モデル、ビューについて説明しました。次に、フォームの送信プロセスを確認しましょう。前述のとおり、フォームは POST 呼び出しを使用して /greeting エンドポイントに送信されます。greetingSubmit() メソッドは、フォームによって入力された Greeting オブジェクトを受け取ります。Greeting は @ModelAttribute なので、受信したフォームの内容にバインドされます。また、送信されたデータは、名前 (デフォルトではメソッドパラメーターの名前、この場合は greeting ) で参照することで、result ビューにレンダリングできます。id は <p th:text="'id: ' + ${greeting.id}" /> 式でレンダリングされます。同様に、content は <p th:text="'content: ' + ${greeting.content}" /> 式でレンダリングされます。次のリストは、結果テンプレートを示しています。

<!DOCTYPE HTML>
<html xmlns:th="https://www.thymeleaf.org">
<head> 
    <title>Getting Started: Handling Form Submission</title>
    <meta http-equiv="Content-Type" content="text/html; charset=UTF-8" />
</head>
<body>
	<h1>Result</h1>
    <p th:text="'id: ' + ${greeting.id}" />
    <p th:text="'content: ' + ${greeting.content}" />
    <a href="/greeting">Submit another message</a>
</body>
</html>

わかりやすくするために、この例では、フォームのレンダリングと送信されたデータの表示に 2 つの個別のビューテンプレートを使用しています。ただし、両方の目的に単一のビューを使用できます。

アプリケーションを実行可能にする

このサービスは、デプロイ用の従来の WAR ファイルとして外部アプリケーションサーバーにパッケージ化することもできますが、より簡単な方法はスタンドアロンアプリケーションを作成することです。main() メソッドによって駆動される単一の実行可能 JAR ファイルにすべてをパッケージ化します。その際、外部インスタンスにデプロイする代わりに、Spring の Tomcat サーブレットコンテナーを HTTP ランタイムとして組み込むサポートを利用します。アプリケーションクラスは次のようになります。

Java
package com.example.handlingformsubmission;

import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;

@SpringBootApplication
public class HandlingFormSubmissionApplication {

	public static void main(String[] args) {
		SpringApplication.run(HandlingFormSubmissionApplication.class, args);
	}

}
Kotlin
package com.example.handlingformsubmission

import org.springframework.boot.autoconfigure.SpringBootApplication
import org.springframework.boot.runApplication

@SpringBootApplication
class HandlingFormSubmissionApplication

fun main(args: Array<String>) {
    runApplication<HandlingFormSubmissionApplication>(*args)
}

@SpringBootApplication は、次のすべてを追加する便利なアノテーションです。

  • @Configuration: アプリケーションコンテキストの Bean 定義のソースとしてクラスにタグを付けます。

  • @EnableAutoConfiguration: クラスパス設定、他の Bean、さまざまなプロパティ設定に基づいて Bean の追加を開始するよう Spring Boot に指示します。例: spring-webmvc がクラスパスにある場合、このアノテーションはアプリケーションに Web アプリケーションとしてフラグを立て、DispatcherServlet のセットアップなどの主要な動作をアクティブにします。

  • @ComponentScan: Spring に、com/example パッケージ内の他のコンポーネント、構成、サービスを探して、コントローラーを検出させるように指示します。

main() メソッドは、Spring Boot の SpringApplication.run() メソッドを使用してアプリケーションを起動します。XML が 1 行もないことに気付きましたか? web.xml ファイルもありません。この Web アプリケーションは 100% 純粋な Java であり、接続機能やインフラストラクチャの構成に対処する必要はありませんでした。

実行可能 JAR を構築する

コマンドラインから Gradle または Maven を使用してアプリケーションを実行できます。必要なすべての依存関係、クラス、リソースを含む単一の実行可能 JAR ファイルを構築して実行することもできます。実行可能な jar を構築すると、開発ライフサイクル全体、さまざまな環境などで、アプリケーションとしてサービスを簡単に提供、バージョン管理、デプロイできます。

Gradle を使用する場合、./gradlew bootRun を使用してアプリケーションを実行できます。または、次のように、./gradlew build を使用して JAR ファイルをビルドしてから、JAR ファイルを実行できます。

java -jar build/libs/gs-handling-form-submission-0.0.1-SNAPSHOT.jar

Maven を使用する場合、./mvnw spring-boot:run を使用してアプリケーションを実行できます。または、次のように、./mvnw clean package で JAR ファイルをビルドしてから、JAR ファイルを実行できます。

java -jar target/gs-handling-form-submission-0.0.1-SNAPSHOT.jar

ロギング出力が表示されます。サービスは数秒以内に起動して実行されるはずです。

サービスをテストする

Web サイトが稼働したら、http://localhost:8080/greeting にアクセスしてください。すると、次のフォームが表示されます。

Form

ID とメッセージを送信して結果を確認します。

Result

要約

おめでとう! Spring を使用して、フォームを作成して送信しました。

関連事項

次のガイドも役立つかもしれません:

新しいガイドを作成したり、既存のガイドに貢献したいですか? 投稿ガイドラインを参照してください [GitHub] (英語) 。

すべてのガイドは、コード用の ASLv2 ライセンス、およびドキュメント用の帰属表示、NoDerivatives クリエイティブコモンズライセンス (英語) でリリースされています。

コードを入手する