Eva*_*les 3 jsf attributes el jsf-2
我无法检索到包含EL的属性ViewHandler。
作为最小的示例,这是我的ViewHandler。它只是寻找一个属性"attributeName"并打印出它的值。
public class MiniViewHandler extends ViewHandlerWrapper
{
private ViewHandler defaultViewHandler = null;
public MiniViewHandler()
{
}
public MiniViewHandler(ViewHandler defaultViewHandler)
{
super();
this.defaultViewHandler = defaultViewHandler;
}
@Override
public void renderView(FacesContext context, UIViewRoot viewToRender) throws IOException, FacesException
{
viewToRender.visitTree(VisitContext.createVisitContext(context),
new VisitCallback()
{
@Override
public VisitResult visit(VisitContext context, UIComponent target)
{
if (target.getAttributes().containsKey("attributeName"))
{
System.out.println("Found it: " + target.getAttributes().get("attributeName"));
}
return VisitResult.ACCEPT;
}
}
);
defaultViewHandler.renderView(context, viewToRender);
}
@Override
public ViewHandler getWrapped()
{
return defaultViewHandler;
}
}
Run Code Online (Sandbox Code Playgroud)
这是在中注册的faces-config.xml。我正在击中的xhtml:
<!DOCTYPE html>
<html lang="en" xmlns="http://www.w3.org/1999/xhtml"
xmlns:h="http://java.sun.com/jsf/html"
xmlns:f="http://java.sun.com/jsf/core">
<h:body>
<f:view>
<f:attribute name="attributeName" value="#{2 + 5}"/>
</f:view>
<f:view>
<f:attribute name="attributeName" value="2 + 5"/>
</f:view>
</h:body>
</html>
Run Code Online (Sandbox Code Playgroud)
记录的输出显示仅拾取了非EL属性。
INFO [stdout] (http-/127.0.0.1:8080-1) Found it: 2 + 5
Run Code Online (Sandbox Code Playgroud)
错误在这里:
if (target.getAttributes().containsKey("attributeName"))
Run Code Online (Sandbox Code Playgroud)
您正在containsKey()检查是否已指定属性。但是,如果属性为,则此方法将无效ValueExpression。以下是UIComponent#getAttributes()javadoc的摘录,重点是:
getAttributes
public abstract java.util.Map<java.lang.String,java.lang.Object> getAttributes()返回一个可变的变量,
Map该变量表示与此this关联的属性(和属性,请参见下文)UIComponent,并以属性名称(必须为String)作为关键字。返回的实现必须支持所有标准和可选Map方法,并支持以下附加要求:
- 该
Map实现必须实现该java.io.Serializable接口。- 任何添加
null键或值的尝试都必须抛出NullPointerException。- 任何添加非
String必需键的尝试都必须抛出ClassCastException。- 如果指定为键的属性名称与此
UIComponent实现类的属性匹配,则以下方法将具有特殊行为:
containsKey()-返回false。get()-如果该属性可读,则调用getter方法并返回返回的值(将原始值包装在其相应的包装器类中);否则抛出IllegalArgumentException。put()-如果该属性是可写的,则调用setter方法以设置相应的值(将原始值包装在其相应的包装器类中)。如果该属性不可写,或者尝试将原始类型的属性设置为nullthrowIllegalArgumentException。remove()-扔IllegalArgumentException。
因此,它总是返回false了containsKey对组件的属性(读:组件的ValueExpression多个)。这是因为动态属性未存储在属性映射中,而是通过UIComponent#setValueExpression()调用存储在组件实例本身中。他们只会在打电话时解决get()。
您基本上需要按以下方式更改错误的行,这也适用于“静态”属性:
Object value = target.getAttributes().get("attributeName");
if (value != null) {
System.out.println("Found it: " + value);
}
Run Code Online (Sandbox Code Playgroud)
如果您想检查该属性是否真的被设置,即使它的评估结果为nulllike value="#{bean.returnsNull}",那么您还是想检查该属性是否UIComponent#getValueExpression()未返回null。
if (target.getValueExpression("attributeName") != null) {
System.out.println("Found it: " + target.getAttributes().get("attributeName"));
}
Run Code Online (Sandbox Code Playgroud)
反过来,这对于“静态”属性也不起作用。根据具体的功能要求,您可以仅在必要时组合检查。
| 归档时间: |
|
| 查看次数: |
1805 次 |
| 最近记录: |