Creating a form in Spring - spring

I have a simple contact form in my spring project, which is meant to access a backing object, but I get this error
"Neither BindingResult nor plain target object for bean name 'indexBacking' available as request attribute"
My form looks like this:
<form:form action="index.htm" enctype="multipart/form-data" method="post" commandName="indexBacking" accept-charset="UTF-8">
<form:label path="personName">Name</form:label>
<form:input id="personName" path="personName" autocomplete="false" /><br />
<form:label path="personEmail">Email</form:label>
<form:input id="personEmail" path="personEmail" autocomplete="false" /><br />
<form:label path="personComments">Your Comments</form:label>
<form:input id="personComments" path="personComments" autocomplete="false" /><br />
<input type="submit" alt="Submit"/>
</form:form>
Which is meant to access my controller and save the fields "personName", "personEmail" and "personComments" into my backing object called "indexBacking".
My controller method that I am trying to access is here:
#RequestMapping(value = PAGE_NAME, method = RequestMethod.POST)
public String handleContactForm(ModelMap map, HttpServletRequest request, #ModelAttribute("indexBacking") IndexBacking bo, BindingResult result) {
return MODEL_NAME;
}
But I am not sure hot it links with the backing object. Any ideas what I am doing wrong?
Thanks
Jon

Try using modelAttribute="indexBacking" on form:form instead of commandName="indexBacking".
Also, take a look at this answer; it might have useful information for your case.

The problem was very simple, I was just being an idiot. I saw a colleague of mine working on a form and assumed a few of his classes were part of Spring as default. All I had to do was handle the received data at the other end properly (by calling the appropriate methods in the controller) and it worked fine.
Thanks for your help chaps - credit to #nobeh for pointing me in the right direction.

The problem is in your controller!
The following may help you much for your request Check This

Related

Why do I lose information after submit a form with Spring MVC?

As I say int the title I loose information in the object that comes back from JSP to Controller.
From my Controller I pass a ModelAndView with an object of class Historic.
In the JSP page I have access to all of the values of this object, but when I submit I just get part of this information, some looses on the way on.
Controller:
#GetMapping("/tt")
public ModelAndView index(Model model) {
HistoricBO historic = new HistoricBO();
// ... I fulfill this object ...
return new ModelAndView("tt", "historic", historic);
}
In JSP I have access to all the information that I passed.
I use the values in two different ways. The first one (information that later I won't be able to recover) is:
<form:form method="POST" action="/addInput" modelAttribute="historic">
....
<form:label path="userHistoric[0].user.name" />
<form:input path="userHistoric[0].user.name" disabled="true" />
Being userHistoric a list inside HistoricBO object.
And the other way that I use the object values is daoing loop to the registers and show them. I can have these values after submit:
c:forEach items="${historic.userHistoric[0].periods[0].registers}" var="reg" varStatus="rog">
...
<td class="tab-odd">
<form:input path="userHistoric[0].periods[0].registers[${rog.index}].hours[0]" class="monin" type="number" />
</td>
The method that catch the submit is as follows:
#PostMapping("/addInput")
public String savePeriod(
#ModelAttribute("historic") HistoricBO inputs,
BindingResult result, ModelMap model) {
if (result.hasErrors()) {
return "error";
}
...
And here the object inputs only has setted the hours values, the rest of the object is empty.
Can you please why is the info loosing and how to solve it?
Thanks
Remove disabled="true" and use readonly="true" or readonly="readonly" instead like below.
<form:input path="userHistoric[0].user.name" readonly="readonly" />
Disabled values will not be submitted with the form.
See this values-of-disabled-inputs-will-not-be-submitted and demo here.

Spring mvc: I cant map form action url to controller action

I apologize in advance if this or a similar question has already been asked, but I could not find a suitable answer.
I have a simple form like this in EditUser.jsp (mapped to: .../admin/users/edit/{userId}):
<form action="/admin/users/edit/addRole/${user.userId}" method="POST">
<select name="role">
<c:forEach var="role" items="${roles}">
<option value="${role}">${role}</option>
</c:forEach>
</select>
<button type="submit" value="AddRole">Add Role</button>
</form>
And #RequestMapping like this:
#RequestMapping(value = "/admin/users/edit/addRole/${userId}", method = RequestMethod.POST)
public String addUserRole(
Model model,
#RequestParam("role") String role,
#PathVariable(value="userId") long userId)
{
...
return "redirect:/admin/users/edit/${userId}";
}
The problem is the result of the request: HTTP Status 404 - /admin/users/edit/addRole/7- "The requested resource is not available" (7 is some user id). A cannot map the POST request to the controller action. I already tried with th:action but it redirects me to the previous page .../admin/users.
Any help pointers appreciated .
I think you url is wrong. As long as you do not deploy the application in the servlets container root path, it will not work because the url is missing the applications name. So a correct url would be something like:
<form action="myAppName/admin/users/edit/addRole/${user.userId}" method="POST">
But better would been using <c:url> or <spring:url>-tag this adds the application name to the url (if the given url starts with an /)
<form action="<c:url value="/admin/users/edit/addRole/${user.userId}" />" method="POST">
for some more information have a look at this two answers:
How to use relative paths without including the context root name? (the highes ranked answer of BalusC is for an quite old jsp version (<2.0)) so take the answer with the c:url tag
How to use with an tag?
I finally found the error - $ sign in #RequestMapping annotation. A just removŠµ $ from annotation and from return "...url" and that's all.

Thymeleaf, Spring nested backing object is not binding the values on form submit

I have a nested object and I'm using it as a model for a form.
public AgeBracketSet implements Serializable{
private String id;
private List<AgeBracket> ageBrackets;
/* Getters and Setters */
}
I have successfully bound all the properties of this object to the form and I can visualize their values when the view state is rendered. Here's a simplified version of how I'm doing it with Thymeleaf. Essentially, I loop through the items of the list and get their attributes.
<form id="bracketForm" role="form" th:action="${flowExecutionUrl}" th:object="${ageBracketSet}" method="post">
<input th:id="'bracketSet_'+*{id}" th:field="*{id}" />
<th:block th:each="bracket,loop : *{ageBrackets}" th:id="'bracket_'+${bracket.id}">
<input th:id="'fromAge_'+${bracket.id}" th:field="*{ageBrackets[__${loop.index}__].fromAge}" />
<input th:id="'toAge_'+${bracket.id}" th:field="*{ageBrackets[__${loop.index}__].toAge}" />
</th:block>
</form>
However, when I make changes in the form and submit it, the model remains unchanged. I have confirmed this by debugging the service that receives the form data. The model does not have the changes made in the form. Am I doing anything wrong here?
I am embarrassed to say I've found the solution. The values simply weren't posted to the webflow for a lack of a 'name' attribute in each input. Using the same dynamically generated ID as a name did the job, and the bindings were correct for each item of the list. Like this:
<input th:id="'fromAge_'+${bracket.id}" th:name="'fromAge_'+${bracket.id}" th:field="*{ageBrackets[__${loop.index}__].fromAge}" />
Thanks to everyone who took the time to read this silly post. I'll be more careful next time ;)

spring:bind error using in a List

I have a list containing users. I am trying to print it in JSP but some how I am not able to get it to print it. Getting this exception HTTP Status 500 - javax.servlet.ServletException: javax.servlet.jsp.JspTagException: Neither BindingResult nor plain target object for bean name 'users[0]' available as request attribute
Code in JSP
<c:forEach items="${users}" var="user" varStatus="status">
<spring:bind path="users[${status.index}].name">
<c:out value="${status.value}" />
</spring:bind>
</c:forEach>
Controller
ModelAndView modelAndView = new ModelAndView("go_some_JSP_page");
List<UserEntity> users = userManager.getAllObjects();
modelAndView.addObject("users", users);
BTW, UserEntity has name field. If I remove the binding and try to print the user.name using <c:out value="user.name" /> it prints the value
Where am I going wrong and what do I need to do? Thanks
Not working code below. [I have to invoke formatting on field #NumberFormat so have to try it using status variable]
<spring:bind path="user.name">
<c:out value="${status.value}" />
</spring:bind>
Gets this error --> javax.servlet.ServletException: javax.servlet.jsp.JspTagException: Neither BindingResult nor plain target object for bean name 'user' available as request attribute
So added a bean binding and then I get empty table :(. I believe thats because the instance is empty. So this does not seems like a right approach.
#ModelAttribute("user")
public UserEntity userEntityBinding() {
return UserEntity.newInstance();
}
A working code exists at https://github.com/hth/StatusInvoke.git
Let me know if you face any problem deploying it.
This question has been solved. Thanks for looking at it.
You can try using LazyList instead of simple list. If you want to take a look at the example then you can refer one of my question. In the question statement I have mentioned how to use the LazyList.
Hope that helps you. Cheers.
this, if the modelandview are returned, is the correct way to populate the list
ModelAndView modelAndView = new ModelAndView("go_some_JSP_page");
List<UserEntity> users = userManager.getAllObjects();
modelAndView.addObject("users", users);
And this is the correct way to reference the list
<c:forEach items="${users}" var="user" varStatus="status">
<spring:bind path="user.name">
<c:out value="${status.value}" />
</spring:bind>
</c:forEach>
Your problem must be elsewhere is the name field definitely populated, is the correct jsp being called... the above code is correct and should work.
The correct answer to invoke #NumberFormat annotation is by using spring:eval expression tag
<spring:eval expression="user.balance" />
This invokes the annotation and performs formatting as mentioned in the annotation
I don't think you can use spring:bind in that case, AFAIK it tries to get the variable from the ModelMap, it's not able to get it from the "for" var.

SpringMVC - JSP Iteration Issue

I have the following class that I am attempting to use as a command object
public class Member {
private String datePeriod;
private String status;
private ArrayList <Project> projectList;
}
On the JSP, I would like the form to prefill with a pre-existing values.
<c:forEach items="${member.projectList}" var="project">
<tr>
<td><form:input path="**<var???>**" value="${project.projectEntry.projectDesc}" /></td>
</tr>
</c:forEach>
I am making an error with path which is causing an error in jsp. Does anyone know the proper syntax with regards to each iteration? Thanks.
My Spring MVC is bit rusty but if I remember correctly, path gets translated as the input name property in HTML eventually. So you can put any Label value in there and that should work.
<form:input path="ProjectDescription" value="${project.projectEntry.projectDesc}" type="text" />
This should get translated to:
<input name="ProjectDescription" type="text" value="<whatever_you_have_in_backing_bean>"/>
Do you want to look up name from a backing bean instead? If so you should be able to do something like below. Without knowing your data structure I am assuming it to be status.
<form:input path="member.status" value="${project.projectEntry.projectDesc}" type="text" />
More on the form tag here.

Resources