8月26日

BookshelfとBookを連携する

src/main/java/
└jp.abc
 └Bookshelf.java

package jp.abc;

import java.util.List;

import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.GeneratedValue;
import javax.persistence.GenerationType;
import javax.persistence.Id;
import javax.persistence.OneToMany;
import javax.validation.constraints.NotEmpty;
import javax.validation.constraints.NotNull;

@Entity
public class Bookshelf {
	@Id
	@GeneratedValue(strategy = GenerationType.AUTO)
	@Column
	@NotNull
	private long id;

	@Column(length = 200, nullable = false)
	@NotEmpty
	private String name;

	@OneToMany
	private List<Book> books;

	public long getId() {
		return id;
	}

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

	public String getName() {
		return name;
	}

	public void setName(String name) {
		this.name = name;
	}

	public List<Book> getBooks() {
		return books;
	}

	public void setBooks(List<Book> books) {
		this.books = books;
	}
}

src/main/java/
└jp.abc
 └Book.java

package jp.abc;

import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.GeneratedValue;
import javax.persistence.GenerationType;
import javax.persistence.Id;
import javax.persistence.ManyToOne;
import javax.validation.constraints.NotEmpty;
import javax.validation.constraints.NotNull;

@Entity
public class Book {
	@Id
	@GeneratedValue(strategy = GenerationType.AUTO)
	@Column
	@NotNull
	private long id;

	@Column(length = 200, nullable = false)
	@NotEmpty
	private String title;

	@Column(length = 200, nullable = false)
	@NotEmpty
	private String author;

	@ManyToOne
	private Bookshelf bookshelf;

	public long getId() {
		return id;
	}

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

	public String getTitle() {
		return title;
	}

	public void setTitle(String title) {
		this.title = title;
	}

	public String getAuthor() {
		return author;
	}

	public void setAuthor(String author) {
		this.author = author;
	}

	public Bookshelf getBookshelf() {
		return bookshelf;
	}

	public void setBookshelf(Bookshelf bookshelf) {
		this.bookshelf = bookshelf;
	}

}

HTMLテンプレートを修正する。

src/main/resources/
└templates
 └book.html

<!DOCTYPE html>
<html xmlns:th="http://www.thymeleaf.org">
<head>
<meta charset="UTF-8">
<title>Book</title>
<style type="text/css">
h1 {
  font-size: 18pt;
  font-weight: bold;
  color: gray;
}
body {
  font-size: 13pt;
  color: gray;
  margin: 5px 25px;
}
tr {
  margin: 5px;
}
th {
  padding: 5px;
  color: white;
  background: darkgray;
}
td {
  padding: 5px;
  color: black;
  background: #f0f0f0;
}
.err {
  color: red;
}
</style>
</head>
<body>
<h1>Book</h1>
<p th:text="${msg}"></p>
<form method="post" action="/book" th:object="${formModel}">
  <table>
    <tr>
      <td><label for="title">タイトル</label></td>
      <td>
        <input type="text" name="title" th:value="*{title}"
      			th:errorclass="err" />
      	<div th:if="${#fields.hasErrors('title')}" th:errors="*{title}"
      		th:errorclass="err"></div>
      </td>
    </tr>
    <tr>
      <td><label for="author">著者</label></td>
      <td>
        <input type="text" name="author" th:value="*{author}"
      			th:errorclass="err" />
      	<div th:if="${#fields.hasErrors('author')}" th:errors="*{author}"
      		th:errorclass="err"></div>
      </td>
    </tr>
    <tr>
      <td><label for="bookshelf">本棚</label></td>
      <td>
        <input type="text" name="bookshelf" th:value="*{bookshelf}"
                th:errorclass="err"/>
        <div th:if="${#fields.hasErrors('bookshelf')}" th:errors="*{bookshelf}"
            th:errorclass="err"></div>
      </td>
    </tr>
    <tr>
      <td></td>
      <td><input type="submit" /></td>
    </tr>
  </table>
</form>

<hr />
<table>
  <tr>
    <th>ID</th><th>タイトル</th><th>著者</th><th>本棚</th>
  </tr>
  <tr th:each="obj : ${datalist}">
    <td th:text="${obj.id}"></td>
    <td th:text="${obj.title}"></td>
    <td th:text="${obj.author}"></td>
    <td th:if="${obj.bookshelf != null}" th:text="${obj.bookshelf.name}"></td>
    <td th:if="${obj.bookshelf == null}" th:text="本棚なし"></td>
  </tr>
</table>

</body>
</html>

本を編集できるようにする

HTMLテンプレートを用意する。

src/main/resources/
└templates
 └edit.html

<!DOCTYPE html>
<html xmlns:th="http://www.thymeleaf.org">
<head>
<meta charset="UTF-8">
<title>本の編集</title>
<meta http-equiv="Content-type" content="text/html; charset=UTF-8" />
<style type="text/css">
h1 {
  font-size: 18pt;
  font-weight: bold;
  color: gray;
}
body {
  font-size: 13pt;
  color: gray;
  margin: 5px 25px;
}
pre {
  border: solid 3px #ddd;
  padding: 10px;
}
tr {
  margin: 5px;
}
th {
  padding: 5px;
  color: white;
  background: darkgray;
}
td {
  padding: 5px;
  color: black;
  background: #f0f0f0;
}
</style>
</head>
<body>

<h1>本の編集</h1>

<form method="post" action="/edit" th:object="${formModel}">
  <input type="hidden" name="id" th:value="*{id}" />
  <table>
    <tr>
      <td><label for="title">タイトル</label></td>
      <td><input type="text" name="title" th:value="*{title}" /></td>
    </tr>
    <tr>
      <td><label for="artist">著者</label></td>
      <td><input type="text" name="author" th:value="*{author}" /></td>
    </tr>
    <tr>
      <td><label for="bookshelf">本棚</label></td>
      <td th:if="*{bookshelf != null}">
        <input type="text" name="bookshelf" th:value="*{bookshelf.id}" />
      </td>
      <td th:if="*{bookshelf == null}">
        <input type="text" name="bookshelf" value="" />
      </td>
    </tr>
    <tr>
      <td></td>
      <td><input type="submit" /></td>
    </tr>
  </table>
</form>


</body>
</html>

コントローラに編集画面へのマッピングを追加する。

src/main/java/
└jp.abc
 └BookController.java

	@RequestMapping(value = "/edit/{id}", method = RequestMethod.GET)
	public ModelAndView edit(@ModelAttribute Book book,
	        @PathVariable long id,
	        ModelAndView mav) {
	    mav.setViewName("edit");
	    mav.addObject("title", "edit music");
	    Optional<Book> data = repository.findById(id);
	    mav.addObject("formModel", data.get());
	    return mav;
	}

POSTメソッドを受け取れるようにする。

	@RequestMapping(value = "/edit", method = RequestMethod.POST)
	public ModelAndView form(@ModelAttribute @Validated Book book,
	        Errors result,
	        ModelAndView mav) {
	    if (result.hasErrors()) {
	        return mav;
	    }
	    repository.saveAndFlush(book);
	    return new ModelAndView("redirect:/book");
	}

book.html に編集と削除のリンクを追加する。

src/main/resources/
└templates
 └book.html

<hr />
<table>
  <tr>
    <th>ID</th><th>タイトル</th><th>著者</th><th>本棚</th><th>編集</th><th>削除</th>
  </tr>
  <tr th:each="obj : ${datalist}">
    <td th:text="${obj.id}"></td>
    <td th:text="${obj.title}"></td>
    <td th:text="${obj.author}"></td>
    <td th:if="${obj.bookshelf != null}" th:text="${obj.bookshelf.name}"></td>
    <td th:if="${obj.bookshelf == null}" th:text="本棚なし"></td>
    <td><a th:href="@{'/edit/' + ${obj.id}}">編集</a></td>
    <td><a th:href="@{'/delete/' + ${obj.id}}">削除</a></td>
  </tr>
</table>

本を削除できるようにする

src/main/resources/
└templates
 └delete.html

<!DOCTYPE html>
<html xmlns:th="http://www.thymeleaf.org">
<head>
<meta charset="UTF-8">
<title>本の削除</title>
<meta http-equiv="Content-type" content="text/html; charset=UTF-8" />
<style type="text/css">
h1 {
  font-size: 18pt;
  font-weight: bold;
  color: gray;
}
body {
  font-size: 13pt;
  color: gray;
  margin: 5px 25px;
}
pre {
  border: solid 3px #ddd;
  padding: 10px;
}
tr {
  margin: 5px;
}
th {
  padding: 5px;
  color: white;
  background: darkgray;
}
td {
  padding: 5px;
  color: black;
  background: #f0f0f0;
}
</style>
</head>
<body>

<h1>本の削除</h1>

<form method="post" action="/delete" th:object="${formModel}">
  <input type="hidden" name="id" th:value="*{id}" />
  <table>
    <tr><td><p th:text="|タイトル : *{title}|"></p></td></tr>
    <tr><td><p th:text="|著者 : *{author}|"></p></td></tr>
    <tr><td><input type="submit" value="削除" /></td></tr>
  </table>
</form>


</body>
</html>

コントローラに削除ページへのマッピングを追加する。

src/main/java/
└jp.abc
 └BookController.java

	@RequestMapping(value = "/delete/{id}", method = RequestMethod.GET)
	public ModelAndView delete(@PathVariable int id,
	        ModelAndView mav) {
	    mav.setViewName("delete");
	    mav.addObject("title", "本の削除");
	    Optional<Book> data = repository.findById((long)id);
	    mav.addObject("formModel", data.get());
	    return mav;
	}

	@RequestMapping(value = "/delete", method = RequestMethod.POST)
	public ModelAndView remove(@RequestParam long id,
	        ModelAndView mav) {
	    repository.deleteById(id);
	    return new ModelAndView("redirect:/book");
	}

コメントを残す

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

このサイトはスパムを低減するために Akismet を使っています。コメントデータの処理方法の詳細はこちらをご覧ください