将循环变量从Freemarker模板传递到Spring控制器
问题描述:
我在列表中查看我列表中的对象。我希望能够使用表格中的按钮编辑对象。将循环变量从Freemarker模板传递到Spring控制器
<#list products as product>
<tr>
<td>${product.productName}</td>
<td>${product.price}</td>
<td>${product.quantity}</td>
<td>
<form name="product" method="post" action="/product/edit">
<input type="submit" name="submit" value="Edit this product"/>
</form>
</td>
</tr>
</#list>
目的然后应传递给控制器方法:
@RequestMapping(value="/edit", method = RequestMethod.POST)
public ModelAndView edit(@ModelAttribute("product") Product product){
ModelAndView mav = new ModelAndView("product/edit");
mav.addObject("product", product);
return mav;
}
然而,由edit
方法获得的product
为空。我该如何解决?我试图使用下面的代码绑定产品内部的形式,但那也不起作用。
<form name="product" method="post" action="/product/edit">
<@spring.bind "product" />
<input type="hidden" name="${spring.status.expression}" value="${spring.status.value}"/>
<input type="submit" name="submit" value="Edit this product"/>
</form>
我想使用POST方法。
答
我想建议一种不同的方法。如果我没有弄错,你只是想选择一个物体供以后编辑 - 你不会真的在这个视图中编辑它。
如果是这样,你所要做的就是将你的对象的标识符传递给你的控制器,而不是选定的对象本身。
如果没有,您应该给我们洞的故事,并提供其余的视图。
假设我是对的下一个问题是为什么你需要使用表单提交。传递一个id是最好的链接进行 - 无论是作为参数,或者,如果你遵循REST风格的,作为URI本身的一部分:
<!-- Link parameter -->
<#list products as product>
<tr>
<td>${product.productName}</td>
<td>${product.price}</td>
<td>${product.quantity}</td>
<td>
<a href="yourURI?pid=${product.productName}">Edit ${product.productName}</a>
</td>
</tr>
</#list>
<!-- REST-style -->
...
<a href="product/{product.productName}/edit">Edit ${product.productName}</a>
...
productName
当然不是一个好的ID。如果products
是一个列表(意思是,java.util.List
)列表的索引是方便的。即使在HashMap
或Set
我会创建一个唯一的ID,而不是使用产品名称。
既然您可以识别您的对象,请在后面的代码中选择它以便以后进行编辑,但不能在视图中进行编辑。 您会发现如何在控制器中获取链接参数的大量示例。所以,这里不需要详细介绍。
然而,如果你坚持使用形式和POST方法再去做这样的:(下文版本10)
<form method="post" action="/product/edit">
<#list products as product>
<tr>
<td>${product.productName}</td>
<td>${product.price}</td>
<td>${product.quantity}</td>
<td>
<button value="${product.productName}" name="product" type="submit">Edit ${product.productName}</button>
</td>
</tr>
</#list>
</form>
请注意,这不会对旧的IE浏览器,因为他们不要返回值,而是返回按钮标签中的所有内容。
隐藏的输入和单个提交按钮根本没有帮助,因为所有输入被提交,并且使用不同的形式也不是这样。
谢谢你的回答。您是正确的,该产品只是为进一步编辑选择。产品存储在数据库中并作为列表返回。当然,产品有一个ID。我只是想避免通过id从数据库获取产品,因为它已经在列表中,并且没有真正需要再次调用服务层。 明天我会测试你的解决方案。谢谢。 – RK1
我明白了!我了解你的动机。但不幸的是,对象列表必须在某个地方“存活”请求响应圈。这是在会话中还是在数据库中。渲染你的Freemaker模板后,只是HTML。剩下的就是文字。因此,没有办法进行选择并返回客户端对象,因为它们根本就不在那里。没有办法使用服务层,即使是在异步请求中。 – MyBrainHurts
当然,这是有道理的。 “剩下的就是文字”,完美地总结了它。谢谢! – RK1