2014-01-30 23 views
5

我在玩2.2的java中構建應用程序。玩框架 - 在路由中綁定枚舉

我有一個java enum作爲我在路由中使用的函數的參數。

這是我的枚舉類。我周圍搜索,發現我需要實現QueryStringBindable在路由中使用它。

public enum Something implements QueryStringBindable<Something> { 
    a, 
    b, 
    c; 

    @Override 
    public F.Option<ClientStatus> bind(String key, Map<String, String[]> params) { 
     String[] arr = params.get(key); 
     if (arr == null || arr.length == 0) { 
      return F.Option.None(); 
     } else { 
      Something status = Something.valueOf(arr[0]); 
      return F.Option.Some(status); 
     } 
    } 

    @Override 
    public String unbind(String key) { 
     return null; 
    } 

    @Override 
    public String javascriptUnbind() { 
     return null; 
    } 
} 

但我想在我的路線:

GET /someurl  controllers.Application.function(status: util.enums.Something) 

但因爲它返回一個錯誤信息錯誤的請求:

對於請求 'GET/someurl'[util.enums.Something ]

我GOOGLE了一下,沒有找到任何答案在我的情況下工作。我錯過了什麼或玩不支持綁定枚舉?

回答

7

我有同樣的問題,我終於發現它是不可解決的。

通過閱讀文檔PathBindableQueryStringBindable我發現,遊戲框架需要可綁定提供無參數公共構造函數。根據定義,在Java中使用enum是不可能的。所以我不得不包裝我的枚舉來解決這個問題。在您的例子中,我們會碰到這樣的:

public enum Something { 
    a, 
    b, 
    c; 

    public static class Bound implements QueryStringBindable<Bound>{ 
     private Something value; 

     @Override 
     public F.Option<ClientStatus> bind(String key, Map<String, String[]> params) { 
      String[] arr = params.get(key); 
      if (arr != null && arr.lenght > 0) { 
       this.value = Something.valueOf(arr[0]); 
       return F.Option.Some(this); 
      } else { 
       return F.Option.None(); 
      } 
     } 

     @Override 
     public String unbind(String key) { 
      return this.value.name(); 
     } 

     @Override 
     public String javascriptUnbind() { 
      return this.value.name(); 
     } 

     public Something value(){ 
      return this.value; 
     } 
    } 
} 

,然後你必須使用類型some.package.Something.Bound在你的路由文件類型。

編輯:在模板中使用它稍微更棘手。你必須知道一點scala。 ,關注@阿列克謝的評論

<a href="@routes.MyController.showStuff(myEnumVar)">link</a> 

應該成爲

<a href="@{ 
    routes.MyController.showStuff(new MyEnumVarWrapper(myEnumVar)).url 
}">link</a> 
+1

我對同樣的解決方案給了一個想法,但對我來說聽起來太難聽。所以我結束了字段綁定到一個字符串,並解析我的控制器中的字符串以獲得一個枚舉。儘管如此,這個冒險解決方案是最接近第2場比賽的。 – Tony

+0

這種方式似乎更多的工作,但至少你玩框架照顧爲你返回正確的http錯誤代碼,如果有人得到拼寫錯誤。 –

+0

當您需要從模板調用操作時,您的解決方案並不十分清晰。我的意思是這樣的代碼: 'link' 我需要放置什麼而不是'myEnumVar'? –

0

我想提供一個小的修正答案: (返回類型不是ClientStatus,以及解除綁定功能應使用關鍵參數,它的URL generatiion)

public enum Something { 
a, 
b, 
c; 

public static class Bound implements QueryStringBindable<Bound>{ 
    private Something value; 

    @Override 
    public F.Option<Bound> bind(String key, Map<String, String[]> params) { 
     String[] arr = params.get(key); 
     if (arr != null && arr.lenght > 0) { 
      this.value = Something.valueOf(arr[0]); 
      return F.Option.Some(this); 
     } else { 
      return F.Option.None(); 
     } 
    } 

    @Override 
    public String unbind(String key) { 
     return key + "=" + this.value.name(); 
    } 

    @Override 
    public String javascriptUnbind() { 
     return this.value.name(); 
    } 

    public Something value(){ 
     return this.value; 
    } 
} 

}

+1

歡迎使用堆棧溢出!這實際上是對現有答案的評論。有了更多的代表,[你將能夠發表評論](// stackoverflow.com/privileges/comment)。如果你想提供這個作爲一個不同的答案,請解釋爲什麼你認爲這是正確的或比現有的答案更好。 – Ram