2011-09-14 39 views
4

這裏我的測試設置:如何玩框架提交對象的列表

的型號:

package models; 

    import javax.persistence.Entity; 
    import play.db.jpa.Model; 

    @Entity 
    public class Item extends Model { 

     public String propertyA; 
     public String propertyB; 

     public String getFullName() { 
      return this.propertyA + " - " + this.propertyB; 
     } 
    } 

控制器:

package controllers; 

import play.*; 
import play.mvc.*; 

import java.util.*; 

import models.*; 

public class Application extends Controller { 

    public static void index() { 
     List<Item> allItems = Item.findAll(); 
     render(allItems); 
    } 

    public static void save(List<Item> items) { 
     if (items == null) { 
      Logger.info("no items"); 
     } else { 
      for (Item item : items) { 
       Logger.info("item: %s",item); 
      } 
      Logger.info("-------"); 
     } 
     index(); 
    } 
} 

的看法:

#{extends 'main.html' /} 
#{set title:'Home' /} 
#{form @Application.save()} 

Select Items: 
<div> 
    <select name="items" style="width: 200px;" multiple="multiple" size="10"> 
     #{list items:allItems, as: 'item'} 
     <option value=${item.id} >${item.fullName}</option> 
     #{/list} 
    </select> 
</div> 
<input type="submit" value="Save" /> 
#{/form} 

當我選擇的選擇框兩個項目,我得到了下面的日誌輸出:

06:22:20,560 INFO ~ ------- 
06:22:26,991 INFO ~ item: null 
06:22:26,991 INFO ~ item: null 

它看起來像劇中選擇映射到null對象的名單。即使當我將視圖更改爲:

<option value=${item} >${item.fullName}</option> 

我得到null值。

但是,當我控制器更改爲:

public static void save(List<Long> items) { 
... 
} 

我至少得到正確的ID列表。

我該如何改變這一點,以便爲我的物品創建正確的貼圖。我更喜歡List<Item>而不是List<Long>(這裏我必須執行查詢以查看項目列表)。

BR,劉若英

更新:

如果我運行:

curl -d "items[0].id=3&items[0].propertyA=bla&items[0].propertyB=blo&items[1].id=4" http://localhost:9000/application/save 

至極做了POST上述參數,我得到:

A02:39:53,072 INFO ~ item: bla - blo 
02:39:53,072 INFO ~ item: null - null 
02:39:53,072 INFO ~ ------- 

像這工作,但我不明白我可以如何改變視圖,s Ø它張貼上述參數:-(

更新2:

與費利佩的幫助,我得到它的工作。必須添加此控制器方法:

@Before(only = {"save"}) 
static void parseParams() { 
    String[] items = params.getAll("items"); 
    params.remove("items"); 
    for (int i = 0; i < items.length; i++) { 
     Item item = Item.findById(Long.parseLong(items[i])); 
     params.put("items[" + i + "].id", items[i]); 
     params.put("items[" + i + "].propertyA", item.propertyA); 
     params.put("items[" + i + "].propertyB", item.propertyB); 
    } 
} 
+0

有一種方式與@Before攔截器做...你迴應,我會更新我的答案.. – Felipe

回答

2

這是一個綁定問題,play不綁定它接收的long []參數。

從遊戲中的文檔狀況:http://www.playframework.org/documentation/1.2.3/controllers#objectbinding 您需要在您的選擇將名稱更改爲items.id

這是可能的,它不會工作,如播放期望列表有索引items[i].id ...

無論如何,如果這不能解決你的問題,你可以做一個自定義的約束,但這種選擇是好大多時候你會需要在很多地方這種綁定,如果你這樣做只有一次,沒有理由不按照你在帖子末尾所說的去做這個查詢。 (播放將使這個查詢要做到這一點綁定,這樣你就不會丟失或做自己贏得任何性能)

更新 東西沿着線:

@Before(only={"save"}) 
static void parseParams() { 
    String[] itens = params.getAll("items") 
    for (int i=0;i<itens.length;i++) { 
     params.put("items["+i+"].id",itens[i]) 
    } 
} 

應該工作。

另一種方式是JavaScript的,但它是更硬,更容易發生錯誤。

+0

感謝。請看看我的更新。 – reen

+0

由於現在的作品,我添加了工作版本,以更新2。 – reen