前提・実現したいこと
現在個人で各エンタメや劇場などにおける集客管理ツールのようなものを作成しています。
現在2つのテーブルにある
・公演日(live_list)親テーブルの日付情報 dateId(Prymary Key)
・顧客リスト(customer_list)子テーブルの日付情報 dateId
を結合し、それぞれのテーブルごとにCRUD処理を実装しています。
機能としては
公演日を登録 → その公演日の顧客リストを登録 というアプリケーションになります
実際の処理として顧客リストの新規登録をする際には、公演日の日付と同一のdateIdでしか登録できないようにcontroller側から公演日のdateIdを渡し、それをhiddenで編集できないようにしています。
そのバリデーションチェックがうまくいきません。
発生している問題・エラーメッセージ
各所省略しています
org.thymeleaf.exceptions.TemplateInputException: An error happened during template parsing (template: "class path resource [templates//customer/customerNew.html]") at org.thymeleaf.templateparser.markup.AbstractMarkupTemplateParser.parse(AbstractMarkupTemplateParser.java:241) ~[thymeleaf-3.0.11.RELEASE.jar:3.0.11.RELEASE] at org.thymeleaf.templateparser.markup.AbstractMarkupTemplateParser.parseStandalone(AbstractMarkupTemplateParser.java:100) ~[thymeleaf-3.0.11.RELEASE.jar:3.0.11.RELEASE] …… 2020-12-12 12:50:45.889 ERROR 20136 --- [nio-8080-exec-7] o.a.c.c.C.[.[.[/].[dispatcherServlet] : Servlet.service() for servlet [dispatcherServlet] in context with path [] threw exception [Request processing failed; nested exception is org.thymeleaf.exceptions.TemplateInputException: An error happened during template parsing (template: "class path resource [templates//customer/customerNew.html]")] with root cause java.lang.IllegalStateException: Neither BindingResult nor plain target object for bean name 'liveList' available as request attribute ......
該当のソースコード
LiveList.java
java
1package product.domain; 2 3import java.util.List; 4 5import javax.validation.constraints.Digits; 6import javax.validation.constraints.NotBlank; 7import javax.validation.constraints.NotNull; 8import javax.validation.constraints.Size; 9 10import lombok.Data; 11 12@Data 13public class LiveList { 14 15 /** 日付ID */ 16 @NotNull 17 @Digits(integer = 8, fraction = 0) 18 private Long dateId; 19 20 /** 会場 */ 21 @NotBlank 22 @Size(max = 32, message = "{error.maxsize}") 23 private String place; 24 25 /** 備考 */ 26 private String remarks; 27 28 /** 子クラス(来場客リスト)の要素定義 */ 29 private List<CustomerList> customers; 30 31} 32 33
CustomerList.java
java
1package product.domain; 2 3import javax.validation.constraints.Digits; 4import javax.validation.constraints.NotBlank; 5import javax.validation.constraints.NotNull; 6import javax.validation.constraints.Size; 7 8import lombok.Data; 9 10@Data 11public class CustomerList { 12 13 /** ID */ 14 private Long id; 15 16 /** 日付ID */ 17 @NotNull 18 @Digits(integer = 8, fraction = 0) 19 private Long dateId; 20 21 /** 名前 */ 22 @NotBlank 23 @Size(min = 1, max = 50) 24 private String name; 25 26 /** 枚数 */ 27 @NotNull 28 private int number; 29 30 /** 備考 */ 31 private String comment; 32 33}
customerNew.html
html
1<!DOCTYPE html> 2<html xmlns:th="http://www.thymeleaf.org"> 3<head> 4<meta charset="utf-8" /> 5<title>新規登録ページ</title> 6<link rel="stylesheet" href="/css/bootstrap.css" /> 7<script src="/js/jquery.js"></script> 8<script src="/js/bootstrap.js"></script> 9</head> 10<body> 11 <div class="container"> 12 <h1>取り置きを新規登録</h1> 13 14 <form th:action="@{/customer}" th:method="post" th:object="${customerList}"> 15 <p th:object="${liveList}"> 16 <div class="form-group"> 17 <input class="form-control" 18 type="hidden" name="id"> 19 <input class="form-control" 20 type="hidden" name="dateId" th:object="${liveList}" th:field="${liveList.dateId}" /> 21 </div> 22 <p/> 23 <div class="form-group"> 24 <label class="control-label">名前</label> <input class="form-control" 25 type="text" name="name" /> 26 <span class="text-danger" th:if="${#fields.hasErrors('name')}" th:errors="*{customerList.name}"></span> 27 </div> 28 <div class="form-group"> 29 <label class="control-label">枚数</label> <input class="form-control" 30 type="number" name="number" /> 31 <span class="text-danger" th:if="${#fields.hasErrors('number')}" th:errors="*{customerList.number}"></span> 32 </div> 33 <div class="form-group"> 34 <label class="control-label">メモ</label> <input class="form-control" 35 type="text" name="comment" /> 36 </div> 37 <button class="btn btn-Primary" type="submit">登録</button> 38 </form> 39 <div class="pull-right"> 40 <a class="btn btn-link" href="/liveList">一覧画面へ</a> 41 </div> 42 </div> 43</body> 44</html>
試したこと
Controllerから受け渡す値の確認
BindingResultの位置確認(@validのあとにする)
view側でのth:objectで受け取る値の変更、追加
エラー文にある「Neither BindingResult nor plain target object for bean name 'liveList' available as request attribute」にあるように、画面から送る値か受け取っている値に何らかの問題があるとみているのですがどう問題があるかがわからない状態です。
初学者のため初歩の質問かもしれませんが、何卒ご教授いただけると幸いです。
補足情報(FW/ツールのバージョンなど)
OS Windows10
IDE Eclipse Version: 2020-06 (4.16.0)
java 11
Spring Boot 2.4.0
###追記
customerNew.html(変更後)
<!DOCTYPE html> <html xmlns:th="http://www.thymeleaf.org"> <head> <meta charset="utf-8" /> <title>新規登録ページ</title> <link rel="stylesheet" href="/css/bootstrap.css" /> <script src="/js/jquery.js"></script> <script src="/js/bootstrap.js"></script> </head> <body> <div class="container"> <h1>取り置きを新規登録</h1> <form th:action="@{/customer}" th:method="post" th:object="${customerList}"> <div class="form-group"> <input class="form-control" type="hidden" name="id"> <input class="form-control" type="hidden" name="dateId" th:field="${customerList.dateId}" /> </div> <div class="form-group"> <label class="control-label">名前</label> <input class="form-control" type="text" name="name" /> <span class="text-danger" th:if="${#fields.hasErrors('name')}" th:errors="*{customerList.name}"></span> </div> <div class="form-group"> <label class="control-label">枚数</label> <input class="form-control" type="number" name="number" /> <span class="text-danger" th:if="${#fields.hasErrors('number')}" th:errors="*{customerList.number}"></span> </div> <div class="form-group"> <label class="control-label">メモ</label> <input class="form-control" type="text" name="comment" /> </div> <button class="btn btn-Primary" type="submit" >登録</button> <!-- th:href="@{/customer/customerNew/{dateId}(dateId=*{dateId})}" --> </form> <div class="pull-right"> <a class="btn btn-link" href="/liveList">一覧画面へ</a> </div> </div> </body> </html>
CustomerListController.java(変更箇所コメントアウト)
package product.controller; import javax.validation.Valid; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.stereotype.Controller; import org.springframework.transaction.annotation.Transactional; import org.springframework.ui.Model; import org.springframework.validation.BindingResult; import org.springframework.web.bind.annotation.GetMapping; import org.springframework.web.bind.annotation.ModelAttribute; import org.springframework.web.bind.annotation.PathVariable; import org.springframework.web.bind.annotation.PostMapping; import org.springframework.web.bind.annotation.RequestMapping; import product.domain.CustomerList; import product.service.CustomerListService; import product.service.LiveListService; /** * お客さんのリストを操作するコントローラー * @author keita * */ @Controller @RequestMapping("customer") public class CustomerListController { @Autowired private CustomerListService customerListService; @Autowired private LiveListService liveListService; // お客さん情報新規作成画面の表示 @GetMapping("/customerNew/{dateId}") public String newCustomerList(@PathVariable("dateId") Long dateId, @ModelAttribute CustomerList customerList, Model model) { //LiveList liveList = liveListService.findOne(dateId); //model.addAttribute("liveList", liveList); model.addAttribute("customerList", customerList); return "customer/customerNew"; } // お客さん情報編集画面の表示 @GetMapping("{id}/edit") public String edit(@PathVariable Long id, Model model) { CustomerList customerList = customerListService.findOne(id); model.addAttribute("customerList", customerList); return "customer/customerEdit"; } // customerデータの保存 @PostMapping public String customerCreate( @Valid @ModelAttribute CustomerList customerList, BindingResult result, Model model) { if (result.hasErrors()) { return "/customer/customerNew"; } customerListService.insert(customerList); return "redirect:/liveList"; } // お客さんデータの更新 @GetMapping("/update/{id}") @Transactional(readOnly = false) public String update(@PathVariable Long id, @Valid @ModelAttribute CustomerList customerList, BindingResult result) { if (result.hasErrors()) { return "/customer/customerEdit"; } customerList.setId(id); customerListService.update(customerList); return "redirect:/liveList"; } // お客さんデータの削除 @PostMapping("/{id}") public String delete(@PathVariable Long id) { customerListService.delete(id); return "redirect:/liveList"; } }
回答1件
あなたの回答
tips
プレビュー