在我们的Web应用程序中,我们对Java bean进行了一些重构,由于这种重构,一些操作/获取器不再可用。例如,在以下示例中:
public class MyBean implements Serializable {
// Old name
// public String getFoo() { return "foo"; }
// New name
public String getBar() { return "bar"; }
}
如果我的JSF代码仍然如下:
<h:inputText value="#{myBean.foo}" .../>
然后会产生异常。
我主要担心的是,某些EL表达式现在可能指向Java bean上的未使用方法,而且当我浏览适当的页面时,我只能看到它。当EL表达式位于特定条件下呈现的部分和/或由Ajax重新呈现时,它变得更难。
所以我的问题是如何静态检查这些EL表达式的正确性?
我已经检查了JSFUnit工具,因为它提供了这样的工具。所以我尝试this example,但它似乎没有按预期工作。在一个简单的测试页面上,只有很少的EL表达式(一些是正确的,另一些是未出现的bean和/或方法的错误),测试成功,这是不正确的。
非常重要的一点:我的bean是在我的Spring配置中定义的,而{strong>不是在faces-config.xml
中。
另请注意,我只需要检查EL表达式是否引用现有的bean和方法,而不一定是否正确执行此操作...
技术信息:
Java 1.6,Spring 2.5,JSF 1.2,EL Functor,Facelets和Richfaces 3.3
答案 0 :(得分:1)
我找不到符合我要求的工具。所以我在我的应用程序上写了一个小bean。此bean将提供一个操作,该操作将读取目录并分析其中的每个.xhtml
文件(并以递归方式执行此操作)。当然,我将不得不运行我的应用程序(因此分析并不是真正的静态),但这个解决方案的优点是我可以访问ELContext
和ELExpressionFactory
我真正使用的web-application,都链接到我的Spring上下文。
这是代码中有趣的部分:
// Analyse a XHTML file
private void analyzeXHTMLFile(File f) throws IOException {
List<String> lines = FileUtils.readLines(f);
for (String l : lines) {
List<String> els = getEL(l);
for (String el : els) {
evaluateEL(el);
}
}
}
// Get a List of EL on the line.
private List<String> getEL(String line) {
List<String> el = new ArrayList<String>();
int i = line.indexOf("#{");
if (i == -1) {
return el;
}
while (i != -1) {
int j = line.indexOf("}", i);
if (j == -1) {
return el;
}
el.add(line.substring(i, j + 1));
i = line.indexOf("#{", i + 1);
}
return el;
}
// Evaluate the EL
private void evaluateEL(String el) {
FacesContext context = FacesContext.getCurrentInstance();
ELContext elContext = context.getELContext();
ValueExpression ve = context.getApplication().getExpressionFactory().createValueExpression(elContext, el, Object.class);
if (ve != null) {
Object o = null;
try {
o = ve.getValue(elContext);
} catch (PropertyNotFoundException pnfe) {
// Handle this error
}
if (o == null) {
// Handle another error
}
}
}