Spring MVC form not supported by model object

I am new to Spring MVC, so please be calm.

I find it difficult to figure out how to achieve the following requirements in Spring MVC:

  • JSP list form to indicate users from the database (service, storage is working fine).
  • The form is not supported by the model attribute object. This is a list / search form!
  • I need to specify users that meet some criteria taken from several filter fields:
    • Region (drop-down list)
    • Is the user archived? (drop-down list yes / no)

userList.jsp

<spring:url value="strFormAction" var="/rest/security/user/list" /> <form:form id="userListForm" method="GET" action="${strFormAction}" modelAttribute="user"> <form:select id="strRegionId" path="${strRegionId}" cssClass="form-control" onchange="updateUsersList('1');"> <spring:message var="strSelectRegionLabel" code="select.region" /> <form:option value="0" label="${strSelectRegionLabel}" /> <form:options items="${regions}" itemValue="intId" itemLabel="strNameFr" /> </form:select> <form:select id="strArchived" path="${strArchived}" cssClass="form-control"> <spring:message var="strYesLabel" code="yes" /> <form:option value="true" label="${strYesLabel}"/> <spring:message var="strNoLabel" code="no" /> <form:option value="false" label="${strNoLabel}"/> </form:select> <table> ... <c:forEach items="${users}" var="user"> ...rows generated here... </c:forEach> ... </table> </form:form> 

UserController.java

 @RequestMapping(value = "/list", method = RequestMethod.GET) public String processUserList( @ModelAttribute("user") User user, @RequestParam(value = "strRegionId", required = false) String strRegionId, @RequestParam(value = "strArchived", required = false) String strArchived, @RequestParam(value = "strSortBy", required = false) String strSortBy, Model model) { int intRegionId = strRegionId != null && strRegionId.equals("0") == false ? Integer.valueOf(strRegionId) : 0; boolean booArchived = strArchived != null && strArchived.length() > 0 ? Boolean.valueOf(strArchived) : false; int intSortBy = strSortBy != null && strSortBy.length() > 0 ? Integer.valueOf(strSortBy) : 1; List<Region> regions = this.locationService.lstRegions(); model.addAttribute("strRegionId", String.valueOf(intRegionId)); model.addAttribute("strArchived", String.valueOf(booArchived)); model.addAttribute("strSortBy", String.valueOf(intSortBy)); List<User> users = this.securityService.listUsersByRegionAndArchiveState(intRegionId, booArchived, intSortBy); model.addAttribute("user", new User()); model.addAttribute("users", users); model.addAttribute("regions", regions); return "user/userList"; } 

It seems like I can't use the spring formlib tag at all without providing the modelAttribute attribute on the form. Then I set the dummy attribute of the model from my controller, but now I get:

javax.servlet.ServletException: javax.servlet.jsp.JspException: org.springframework.beans.NotReadablePropertyException: invalid property '0' from bean class [spring4base.model.security.User]: bean property '0' cannot be read or has invalid getter method: does the return type of getter match the type of the setter parameter?

As I said earlier, this page is not intended to support any particular POJO. This is a search page that should return a list of users (a custom bean) based on previously selected filters (region, archived state). The form should be sent by itself each time the drop-down list is changed (the user selects a region, the submission is performed according to the same mapping, and then the list of users is reloaded only by users from this particular region).

I come from Struts 1, in which we need to create an ActionForm for each individual page. From what I read from the documentation, forms are not needed these days, so I'm really waiting to solve this problem.

Any help would be greatly appreciated.

+6
source share
1 answer

I would just create a helper class containing your search criteria, for example:

 public class UserSearchCriteria { private String regionId; private Boolean archived; private String sortBy; // Getters and setters } 

Then I would change your controller method like this (some code is missing, but this should give you an idea).

 @RequestMapping(value = "/list", method = RequestMethod.GET) public String processUserList(@ModelAttribute("searchCriteria") UserSearchCriteria userSearchCriteria, Model model) { // Retrieve users and perform filtering based on search criteria List<User> users = this.securityService.listUsers(searchCriteria); model.addAttribute("users", users); model.addAttribute("regions", regions); return "user/userList"; } 

And then you will use your filtering form as follows:

 <spring:url value="/rest/security/user/list" var="formAction" /> <form:form id="userListForm" method="GET" action="${formAction}" modelAttribute="searchCriteria"> <form:select path="regionId" cssClass="form-control" onchange="updateUsersList('1');"> <spring:message var="strSelectRegionLabel" code="select.region" /> <form:option value="0" label="${strSelectRegionLabel}" /> <form:options items="${regions}" itemValue="intId" itemLabel="strNameFr" /> </form:select> <form:select path="archived" cssClass="form-control"> <spring:message var="strYesLabel" code="yes" /> <form:option value="true" label="${strYesLabel}"/> <spring:message var="strNoLabel" code="no" /> <form:option value="false" label="${strNoLabel}"/> </form:select> 

You had some form errors in your snippet. For example, the path attribute takes a string containing the name (or path) of the property to bind to, you passed it a variable. In addition, you used value and var in your <spring:url> .

Try it, this is not a complete solution, but hopefully it will give you some guidance on how to implement this. If you have any problems, leave a comment and I will update the answer.

+4
source

Source: https://habr.com/ru/post/977996/


All Articles