6月16日

リストで複数項目を選択する

複数項目を選択できるようにするために、SelectModelのselect1をString配列に変更する。
getterの戻り値の型と、setterの引数の型も変更する。

package jp.abc;

public class SelectModel {
	private String[] select1;

	public String[] getSelect1() {
		return select1;
	}

	public void setSelect1(String[] select1) {
		this.select1 = select1;
	}
}

コントローラもテキストの通りに変更する。

package jp.abc;

import java.util.ArrayList;
import java.util.List;

import org.springframework.stereotype.Controller;
import org.springframework.ui.Model;
import org.springframework.web.bind.annotation.ModelAttribute;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;

@Controller
public class SelectController {
	private List<ListDataModel> getList() {
		List<ListDataModel> list = new ArrayList<ListDataModel>();
		list.add(new ListDataModel("マック", "Mac"));
		list.add(new ListDataModel("ウィンドウズ", "Windows"));
		list.add(new ListDataModel("リナックス", "Linux"));
		list.add(new ListDataModel("アイフォン", "iOS"));
		list.add(new ListDataModel("アンドロイド", "Android"));
		return list;
	}

	@RequestMapping(value = "/select", method=RequestMethod.GET)
	public String select(Model model) {
		model.addAttribute("title", "Sample");
		model.addAttribute("message", "Selectのサンプルです。");
		SelectModel sm = new SelectModel();
		sm.setSelect1(new String[]{"Mac"});
		model.addAttribute("selectModel", sm);
		model.addAttribute("optionlist", getList());
		return "select";
	}

	@RequestMapping(value = "/select", method = RequestMethod.POST)
	public String form(@ModelAttribute SelectModel sm, Model model) {
		model.addAttribute("title", "Sample");
		String[] sels = sm.getSelect1();
		String res = "<ol>";
		for (String item : sels) {
			res += "<li>" + item + "</li>";
		}
		res += "</ol>";
		model.addAttribute("message", res);
		model.addAttribute("selectModel", sm);
		model.addAttribute("optionlist", getList());
		return "select";
	}
}

JSPはmultiple属性をtrueに変更する。

		<form:select path="select1" size="5" multiple="true">

リストの項目を複数選択する場合は、Ctrlキーを押しながら選択する。

バリデーションの利用

サンプルとして買い物メモを作成する。
テキストではFormModelを変更しているが、ここではMemoModelを新規作成する。

package jp.abc;

import java.util.Date;

public class MemoModel {
	private String item;
	private Integer price;
	private Date buydate;
	private String memo;

	public String getItem() {
		return item;
	}
	public void setItem(String item) {
		this.item = item;
	}
	public Integer getPrice() {
		return price;
	}
	public void setPrice(Integer price) {
		this.price = price;
	}
	public Date getBuydate() {
		return buydate;
	}
	public void setBuydate(Date buydate) {
		this.buydate = buydate;
	}
	public String getMemo() {
		return memo;
	}
	public void setMemo(String memo) {
		this.memo = memo;
	}
}

JSPもmemo.jspとして新規作成する。

<!DOCTYPE html>
<%@ taglib prefix="form" uri="http://www.springframework.org/tags/form" %>
<%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core" %>
<%@ page language="java" contentType="text/html; charset=UTF-8" pageEncoding="UTF-8"%>

<html>
	<head>
		<meta charset="utf-8">
		<title>${title}</title>
	</head>
	<body>
		<h1>${title}</h1>
		<p>${message}</p>
		<table>
		<form:form modelAttribute="memoModel">
			<tr>
				<td><form:label path="item">商品名</form:label></td>
				<td><form:input path="item" size="20"/></td>
			</tr>
			<tr>
				<td><form:label path="price">金額</form:label></td>
				<td><form:input path="price" size="20" /></td>
			</tr>
			<tr>
				<td><form:label path="memo">メモ</form:label></td>
				<td><form:textarea path="memo" cols="20" rows="5" /></td>
			</tr>
			<tr><td><input type="submit" /></td></tr>
		</form:form>
		</table>
		<hr>
		<c:if test="${datalist != null}">
		<table>
			<tr><th>商品名</th><th>価格</th></tr>
			<c:forEach var="obj" items="${datalist}" varStatus="status">
				<tr>
				<td><c:out value="${obj.item}" /></td>
				<td><c:out value="${obj.price}" /></td>
				</tr>
			</c:forEach>
		</table>
		</c:if>
	</body>
</html>

コントローラもMemoControllerとして新規作成する。
まずはGETメソッドの部分だけ作成して動作確認する。
ボタンを押して送信すると POST not supported のエラーとなる。

package jp.abc;

import java.util.ArrayList;
import java.util.List;

import org.springframework.stereotype.Controller;
import org.springframework.ui.Model;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;

@Controller
public class MemoController {
	private List<MemoModel> buylist = new ArrayList<MemoModel>();

	@RequestMapping(value = "/memo", method = RequestMethod.GET)
	public String memo(Model model) {
		model.addAttribute("title", "Sample");
		model.addAttribute("message", "買い物メモです");
		MemoModel mm = new MemoModel();
		model.addAttribute("memoModel", mm);
		model.addAttribute("datalist", buylist);
		return "memo";
	}
}

GETメソッドが正常に動作し、POSTでエラーとなることを確認したら、POSTに対応するメソッドを追加する。

	@RequestMapping(value = "/memo", method = RequestMethod.POST)
	public String form(@ModelAttribute MemoModel mm,
			BindingResult result, Model model) {
		buylist.add(mm);
		model.addAttribute("title", "Sample");
		String res = "<ol>";
		res += "<li>" + mm.getItem() + "</li>";
		res += "<li>" + mm.getPrice() + "</li>";
		res += "<li>" + mm.getMemo() + "</li>";
		res += "<li>" + Calendar.getInstance().getTime() + "</li>";
		res += "</ol>";
		res += "<p>" + buylist.size() + "</p>";
		model.addAttribute("message", res);
		model.addAttribute("datalist", buylist);
		model.addAttribute("memoModel", new MemoModel());
		return "memo";
	}

バリデーション用のライブラリをロードする

pom.xml を開き、最後の dependencies タグの手前に以下の設定を追加する。

		<dependency>
			<groupId>javax.validation</groupId>
			<artifactId>validation-api</artifactId>
			<version>1.1.0.Final</version>
		</dependency>
		<dependency>
			<groupId>org.hibernate</groupId>
			<artifactId>hibernate-validator</artifactId>
			<version>5.0.1.Final</version>
		</dependency>

追加して保存したら、「プロジェクトの更新」と「maven install」を実行する。

エラーが解決できない場合、次の手順を試してみること。
・tomcatサーバーを停止→tomcatサーバーを削除→tomcatサーバーを作成

それでもエラーが解決できない場合、
[ユーザー]\.m2\repository 以下のファイルを全て削除し、「プロジェクトの更新」と「Maven install」を再実行する。

MemoModel.java にバリデーションのアノテーションを追加する。

package jp.abc;

import java.util.Date;

import javax.validation.constraints.Min;

import org.hibernate.validator.constraints.NotEmpty;

public class MemoModel {
	@NotEmpty
	private String item;
	@Min(0)
	private Integer price;
	private Date buydate;
	private String memo;

	public String getItem() {
		return item;
	}
	public void setItem(String item) {
		this.item = item;
	}
	public Integer getPrice() {
		return price;
	}
	public void setPrice(Integer price) {
		this.price = price;
	}
	public Date getBuydate() {
		return buydate;
	}
	public void setBuydate(Date buydate) {
		this.buydate = buydate;
	}
	public String getMemo() {
		return memo;
	}
	public void setMemo(String memo) {
		this.memo = memo;
	}
}

JSPにエラーメッセージを表示する要素を追加する。

<!DOCTYPE html>
<%@ taglib prefix="form" uri="http://www.springframework.org/tags/form" %>
<%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core" %>
<%@ page language="java" contentType="text/html; charset=UTF-8" pageEncoding="UTF-8"%>

<html>
	<head>
		<meta charset="utf-8">
		<title>${title}</title>
	</head>
	<body>
		<h1>${title}</h1>
		<p>${message}</p>
		<table>
		<form:form modelAttribute="memoModel">
			<tr>
				<td></td><td><form:errors path="*" element="div" />
			</tr>
			<tr>
				<td><form:label path="item">商品名</form:label></td>
				<td><form:input path="item" size="20"/></td>
			</tr>
			<tr>
				<td><form:label path="price">金額</form:label></td>
				<td><form:input path="price" size="20" /></td>
			</tr>
			<tr>
				<td><form:label path="memo">メモ</form:label></td>
				<td><form:textarea path="memo" cols="20" rows="5" /></td>
			</tr>
			<tr><td><input type="submit" /></td></tr>
		</form:form>
		</table>
		<hr>
		<c:if test="${datalist != null}">
		<table>
			<tr><th>商品名</th><th>価格</th></tr>
			<c:forEach var="obj" items="${datalist}" varStatus="status">
				<tr>
				<td><c:out value="${obj.item}" /></td>
				<td><c:out value="${obj.price}" /></td>
				</tr>
			</c:forEach>
		</table>
		</c:if>
	</body>
</html>

コントローラを修正する。
エラーチェックはPOSTメソッドが呼ばれる前に行われている。

package jp.abc;

import java.util.ArrayList;
import java.util.Calendar;
import java.util.List;

import javax.validation.Valid;

import org.springframework.stereotype.Controller;
import org.springframework.ui.Model;
import org.springframework.validation.BindingResult;
import org.springframework.web.bind.annotation.ModelAttribute;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;

@Controller
public class MemoController {
	private List<MemoModel> buylist = new ArrayList<MemoModel>();

	@RequestMapping(value = "/memo", method = RequestMethod.GET)
	public String memo(Model model) {
		model.addAttribute("title", "Sample");
		model.addAttribute("message", "買い物メモです");
		MemoModel mm = new MemoModel();
		model.addAttribute("memoModel", mm);
		model.addAttribute("datalist", buylist);
		return "memo";
	}

	@RequestMapping(value = "/memo", method = RequestMethod.POST)
	public String form(@Valid @ModelAttribute MemoModel mm,
			BindingResult result, Model model) {
		if (result.hasErrors()) {
			model.addAttribute("title", "Sample [ERROR]");
			model.addAttribute("message", "値を再チェックしてください!");
		} else {
			buylist.add(mm);
			model.addAttribute("title", "Sample");
			String res = "<ol>";
			res += "<li>" + mm.getItem() + "</li>";
			res += "<li>" + mm.getPrice() + "</li>";
			res += "<li>" + mm.getMemo() + "</li>";
			res += "<li>" + Calendar.getInstance().getTime() + "</li>";
			res += "</ol>";
			res += "<p>" + buylist.size() + "</p>";
			model.addAttribute("message", res);
			model.addAttribute("memoModel", new MemoModel());
		}
		model.addAttribute("datalist", buylist);
		return "memo";
	}
}

コメントを残す

メールアドレスが公開されることはありません。 * が付いている欄は必須項目です