我不确定是否有办法在Velocity中执行此操作:
我有一个名为Status的用户POJO,它看起来像一个枚举(但它不是,因为我被困在Java 1.4上),定义看起来像这样:
public class User {
// default status to User
private Status status = Status.USER;
public void setStatus(Status status) {
this.status = status;
}
public Status getStatus() {
return status;
}
状态是一个静态内部类:
public static final class Status {
private String statusString;
private Status(String statusString) {
this.statusString = statusString;
}
public final static Status USER = new Status("user");
public final static Status ADMIN = new Status("admin");
public final static Status STATUS_X = new Status("blah");
//.equals() and .hashCode() implemented as well
}
使用此模式,可以在条件中轻松测试用户状态,例如
if(User.Status.ADMIN.equals(user.getStatus())) ...
...无需引用状态ID,任何幻数等任何常量
但是,我无法弄清楚如何使用VTL在Velocity模板中测试这些条件。我想根据用户的状态打印一个简单的字符串,例如:
Welcome <b>${user.name}</b>!
<br/>
<br/>
#if($user.status == com.company.blah.User.Status.USER)
You are a regular user
#elseif($user.status == com.company.blah.User.Status.ADMIN)
You are an administrator
#etc...
#end
但是这会引发一个看起来像org.apache.velocity.exception.ParseErrorException: Encountered "User" at webpages/include/dashboard.inc[line 10, column 21] Was expecting one of: "[" ...
从the VTL User Guide开始,没有提到直接在VTL中访问Java类/静态成员,看来条件的右侧(RHS)只能是一个数字文字,字符串文字,属性参考或方法参考。
那么有什么办法可以在Velocity模板中访问静态Java属性/引用吗?我知道作为一种解决方法,我可以在我的控制器中嵌入状态ID或其他标识符作为参考(这是一个使用Velocity作为View技术的web MVC应用程序),但我强烈不想嵌入任何魔法视图层中的数字或常量。
答案 0 :(得分:8)
我找到了一种解决方法,允许我将每个User.Status
对象添加到Velocity上下文中,这样可以避免对模板中的常量或幻数进行任何类型的引用。
在控制器/ Java端:
// put the statuses directly into the model
Map statusMap = new HashMap();
statusMap.put("user", User.Status.USER);
statusMap.put("groupOperator", User.Status.ADMIN);
...
modelAndView.addObject("statusmap", statusMap);
然后在模板中可以像这样引用这些值:
#if($user.status == $statusmap.user)
You are a regular user
#elseif($user.status == $statusmap.admin)
You are an administrator
##etc...
#end
答案 1 :(得分:6)
是的,Velocity本身并没有使用类和包。您可以执行您所做的操作,或使用FieldMethodizer类自动执行该操作。另一种选择是VelocityTools 2.0中的FieldTool。
答案 2 :(得分:3)