I have a rather simple use case. The actor is a manager who provides feedback to a list of employees.
The view displays a list of employees. The manager (user) can click on each employee upon which a feedback form opens up (inline) to capture the feedback.
I have a List<Employee>
which I am using to construct the listing of employees on the page. I am not able to understand how to structure and capture the feedback. I intend to have a separate bean, Feedback
which correspond to the feedback of a particular Employee
.
I started by building <form:form>
in a loop and did this:
<c:forEach var="employee" items="${employees}" varStatus="stat">
<form:form action="${saveURL}" method="post" modelAttribute="feedback-${stat.index + 1}">
<input type="submit" value="Submit Feedback"/>
</form:form>
</c:forEach>
I am trying to keep the signature of my processAction
method as follows:
@RequestMapping(params = "action=save")
public void saveFeedback(ActionRequest request, ActionResponse response, @ModelAttribute("feedback") Feedback feedback, Model model)
Unfortunately, I am not able to proceed with this as I feel I am missing some important design piece here.
How should I be structuring my <form:form>
or saveFeedback
method in order to achieve what I am trying to do?
This is how I solved the problem. Instead of having a list of feedback forms for holding data specific to each iteration, I had to create a single feedback form with a list of Feedback
domain objects.
My FeedbackForm
looks like this now:
public class FeedbackForm {
private List<Feedback> feedbacks;
...
getters and setters
}
And typically, the Feedback
class would look like:
public class Feedback {
private String feedback;
private int rating;
...
getters and setters
}
Now my JSP looks like:
<portlet:actionURL var="saveURL">
<portlet:param name="action" value="save" />
<portlet:param name="index" value="${stat.index}" />
</portlet:actionURL>
<c:forEach var="employee" items="${employees}" varStatus="stat">
<form:form action="${saveURL}" method="post" modelAttribute="feedbackForm">
<form:input path="feedbacks[${stat.index}].feedback" />
<form:input path="feedbacks[${stat.index}].rating" />
<input type="submit" value="Submit Feedback"/>
</form:form>
</c:forEach>
And lastly, my controller method looks like:
@RequestMapping(params = "action=save")
public void saveFeedback(ActionRequest request, ActionResponse response,
@RequestParam("index") int index,
@ModelAttribute("feedbackForm") FeedbackForm feedbackForm, Model model)
throws PortletException {
Feedback feedback = feedbackForm.getFeedbacks().get(index);
logger.debug("Submitted feedback is {}", feedback);
}
The idea is that it is impossible to have multiple forms being submitted at the same time, although they may appear on the page at the same time. Basically, one can only click one submit button per form.
Hope this helps someone in a similar situation.