springmvc傳多個物件且引數重名
SpringMVC 多個物件的相同欄位引數傳遞解決方案,在SpringMVC中,有時需要傳遞多個物件(除了Model和web元素)
眾所周知,在SpringMVC中不支援類似struts2的點語法傳參法則,因此多個物件同名引數傳遞勢必會造成一定的問題。
-
SpringMVC的引數傳遞非常智慧,可自動裝配引數到物件
public class User{ private String name; private String id; private String gender, private String age; //getter 和setter } ---------------------------------- public class Food{ private String name; private String id; private String price, private String date; //getter 和setter } ------- <form method='post' action='url'> 使用者名稱 <input type='text' name='name'> 使用者id <input type='text' name='id'> 食品名 <input type='text' name='name'> 食品id <input type='text' name='id'> <input type='text' name='gender'> <input type='text' name='age'> <input type='text' name='price'> <input type='text' name='date'> </form> -------- @requestMap(value={'/order/book'}) public string show(User u,Food f){}
在上述情況下User 和food都不能得到正確的name和id,或者說更本得不到,這要是struts2就方便多了,直接使用點語法 u.name,u.id,f.name,f.id....
為了解決上述問題,有2中方案:
1.是建立一個DTO
優點是可以認為的避免參數的傳遞,直接改dto的欄位名 u_name,u_id,f_name,f_id,gender,age,date,price都要列出來,然後作如下操作
然後修改表單欄位和contoller
<form method='post' action='url'> 使用者名稱 <input type='text' name='u_name'> 使用者id <input type='text' name='u_id'> 食品名 <input type='text' name='f_name'> 食品id <input type='text' name='f_id'> <input type='text' name='gender'> <input type='text' name='age'> <input type='text' name='price'> <input type='text' name='date'> </form> @requestMap(value={'/order/book'}) public string show(UserFoodDto dto){ //然後拆分,將欄位 User u = new User(); Food f = new Food(); u.setName(dto.getUname()); f.setName(dto.getname()); u.setUid(dto.getUid()); f.setFid(dto.getFid()); u.setAge(dto.getAge); f.setPrice(dto.getPrice); ..... }
缺點是:如果資料量大,100百個欄位,修改的地方自然越多,而且一個dto,拆分也很費力,因此不建議使用在資料量大的情況下
2.使用橋連線,將不同的部分專門封裝成一個物件(推薦)
優點:減少了衝突,減少了工作量
缺點:衝突欄位/總欄位趨近於1時顯得沒必要(不過,這種情況幾乎很少出現,除非是繼承關係,但繼承關係完全可以使用子類來傳值,所以這個問題你就當沒遇到過)
表單如下
<form method='post' action='url'> 使用者名稱 <input type='text' name='u_name'> 使用者id <input type='text' name='u_id'> 食品名 <input type='text' name='f_name'> 食品id <input type='text' name='f_id'> <input type='text' name='gender'> <input type='text' name='age'> <input type='text' name='price'> <input type='text' name='date'> </form> -----將衝突的欄位專門建立一個javaBean public String UFBridge{ private String uname; private String uid; private String fname; private String fid; } -------------------------- @requestMap(value={'/order/book'}) public string show(User u,Food f,UFBridge ufb){ u.setName(ufb.getUname()); f.setName(ufb.getUname()); u.setId(ufb.getUid); f.setId(ufb.getFid); }
3.使用相應的註解@InitBinder,可以做出類似struts2的方案(不推薦,程式碼量增加,靈活度不夠)
springController:
- @Controller
- @RequestMapping("/user")
- public UserController extends BaseController{
- @RequestMapping("/addUser")
- publicvoid testBinderOuput(@ModelAttribute User user, HttpServletRequest request, HttpServletResponse response){
- System.out.println(user);
- }
- }
Use物件:
- public Class User{
- private String name;
- privateint sex;
- private String address;
- privateint id;
- publicint getSex() {
- return sex;
- }
- publicvoid setSex(int sex) {
- this.sex = sex;
- }
- public String getAddress() {
- return address;
- }
- publicvoid setAddress(String address) {
- this.address = address;
- }
- publicint getId() {
- return id;
- }
- publicvoid setId(int id) {
- this.id = id;
- }
- publicvoid setName(String name) {
- this.name = name;
- }
- }
請求路徑:
localhost/user/addUser?user.name="test"
那麼在後臺接受到的引數中,user物件的name屬性是null。如果路徑換為localhost/user/addUser?name="test",則user物件的name屬性是test。
這裡必須用name="test"而不是user.name="test",因為預設情況下springMVC是不支援user.name這種傳參方式的。
如果有個物件manager中也有name這個相同的屬性,那麼可以採用user.name,manager.name來傳輸引數。但是這個需要在controller中新增一個字首繫結:
新增繫結字首後的controller類如下:
- @Controller
- @RequestMapping("/user")
- public UserController extends BaseController{
- @InitBinder("manager")
- publicvoid initBinder1(WebDataBinder binder) {
- binder.setFieldDefaultPrefix("manager.");
- }
- @InitBinder("user")
- publicvoid initBinder2(WebDataBinder binder) {
- binder.setFieldDefaultPrefix("user.");
- }
- @RequestMapping("/addUser")
- publicvoid testBinderOuput(@ModelAttribute User user, HttpServletRequest request, HttpServletResponse response){
- System.out.println(user.getName);
- }
- @RequestMapping("/addManager")
- publicvoid testBinderOuput(@ModelAttribute Manager manager, HttpServletRequest request, HttpServletResponse response){
- System.out.println(manager.getName);
- }
- }
有個專門討論這個問題的主題:http://www.iteye.com/topic/1124433?page=2可以參考下