我有以下情况:我需要根据提供的URL参数呈现模板。例如:
http://localhost:9000/abc -> renders abc.scala.html
http://localhost:9000/def -> renders def.scala.html
最简单的解决方案是在路径文件中定义这些要求:
GET /abc controllers.Application.abc()
GET /def controllers.Application.def()
...
然后在应用程序控制器中:
public static Result abc() {
return ok(abc.render());
}
但我正在寻找更“通用”的解决方案。像这样:
GET /:myparameter controllers.Application.test(myparameter: String)
不幸的是我不知道如何在我的控制器中“调用”相应的视图。我正在考虑某种地图,其中每个参数都映射到视图但没有成功。我试过这样的
Map<String, play.api.templates.Html>
当然,这只能为我提供HTML内容,而不是我想要呈现的“模板”。
信息:我正在使用Play 2 with Java
祝你好运
答案 0 :(得分:1)
我实际上认为您建议自己维护参数值映射到Html
类型的提案是可行的选择:
public class Application extends Controller {
private static final Map<String, Html> views = new HashMap<>();
static {
views.put("abc", abc.render());
views.put("def", def.render());
...
}
public static Result test(final String myparameter) {
final Html view = views.get(myparameter);
if (view != null) {
return ok(view);
} else {
// Unsupported parameter
return badRequest();
}
}
}
在上面的代码中,所有模板都在静态块中预渲染。根据您描述问题的方式判断,您的模板似乎没有任何参数,因此这种早期渲染模板的方法应该适合您。
但是,您可能会/将拥有接收参数且无法提前呈现的模板。在这种情况下,您可以采用的另一种方法是使用操作组合的解决方案:
/*
* This action is composed of many different actions that form a
* chain of responsibility.
*/
@Abc
@Def
...
public static Result test(final String myparameter) {
....
}
这种方法更具有前瞻性,但涉及更多代码和类,可能不像您目前所寻求的那样通用。
答案 1 :(得分:0)
如果您使用的是Java 1.7,则可以使用简单的开关
public static Result test(final String myparameter) {
switch(myparameter){
case "abc":
//Initialize x,y
abc.render(x,y);
break;
case "def":
//Initialize x,y,z
defview.render(x,y,z);
break;
}
}
答案 2 :(得分:0)
以下是如何使用反射执行此操作的示例。如果您拥有未知数量的模板和/或每次添加模板时都不想更新代码,则上述方法不实用。
className是您要呈现的模板的绝对路径
Class<?> clazz = Class.forName(className);
Method renderMethod = clazz.getMethod("render");
Object result = renderMethod.invoke(null);
return ok((Html) result);