Struts标签属性如何工作?

时间:2010-02-04 09:58:54

标签: attributes struts

在此代码中:

<html:text property="txtItem5" disabled="disTxtItem5">

我可以看到“txtItem5”来自ActionForm中的getTxtItem5(),但是在项目中搜索“disTxtItem5”的其他子串似乎没有发现任何远程相关的内容,但显然框架从这个字符串中拉出了一个布尔值,这显然意味着它比我目前的理解更复杂。

有人可以很好地解释这些表达式的评估方式,还是指向一个方向?

1 个答案:

答案 0 :(得分:2)

编辑:在我原来的回复中(见下文)我说Struts管理转换,但我错了。我不记得到底发生了什么,所以我拿出了Struts的资料并看了一眼。事实证明转换是由服务器完成的。 JSP在执行之前转换为servlet,并且在这里将false用于非布尔值。

例如,我使用了以下标记:

<html:text property="nr" disabled="BlaBla" />

哪个被翻译成以下html(没有禁用):

<input type="text" name="nr" value="123">

这发生在servlet中。以下是我的servlet包含的上述标记:

//  html:text
    org.apache.struts.taglib.html.TextTag _jspx_th_html_005ftext_005f0 = (org.apache.struts.taglib.html.TextTag) _005fjspx_005ftagPool_005fhtml_005ftext_005fproperty_005fdisabled_005fnobody.get(org.apache.struts.taglib.html.TextTag.class);
    _jspx_th_html_005ftext_005f0.setPageContext(_jspx_page_context);
    _jspx_th_html_005ftext_005f0.setParent((javax.servlet.jsp.tagext.Tag) _jspx_th_html_005fform_005f0);
    _jspx_th_html_005ftext_005f0.setProperty("nr");
    _jspx_th_html_005ftext_005f0.setDisabled(false);
    int _jspx_eval_html_005ftext_005f0 = _jspx_th_html_005ftext_005f0.doStartTag();

可以看出,禁用值是直接生成的。我做了一些深入研究Jasper编译器(我使用Tomcat),我认为它是负责转换的org.apache.jasper.compiler.JspUtil类,使用以下代码:

public static boolean booleanValue(String s) {
  boolean b = false;
  if (s != null) {
    if (s.equalsIgnoreCase("yes")) {
       b = true;
    } else {
       b = Boolean.valueOf(s).booleanValue();
    }
  }
  return b;
}

由于我在禁用字段中插入BlaBla,因此应该回退到Boolean.valueOf(s).booleanValue();,执行以下操作:

public static Boolean valueOf(String s) {
  return toBoolean(s) ? TRUE : FALSE;
}

private static boolean toBoolean(String name) { 
  return ((name != null) && name.equalsIgnoreCase("true"));
}

这样,BlaBla导致错误。

ORIG: 以下是我原来的回复,但不正确。我所描述的实际上是将请求参数绑定到操作表单时会发生什么。

disabled属性的类型为boolean,因此它只应接收映射到布尔值的值。 disabled="disTxtItem5"将抛出ConversionException,因为文本disTxtItem5未映射到布尔值。

Struts使用CommonBeanUtils进行转换,因此将使用BooleanConverter,代码如下:

String stringValue = value.toString();
if (stringValue.equalsIgnoreCase("yes") ||
   stringValue.equalsIgnoreCase("y") ||
   stringValue.equalsIgnoreCase("true") ||
   stringValue.equalsIgnoreCase("on") ||
   stringValue.equalsIgnoreCase("1")) {
   return (Boolean.TRUE);
} else if (stringValue.equalsIgnoreCase("no") ||
   stringValue.equalsIgnoreCase("n") ||
   stringValue.equalsIgnoreCase("false") ||
   stringValue.equalsIgnoreCase("off") ||
   stringValue.equalsIgnoreCase("0")) {
   return (Boolean.FALSE);
} else if (useDefault) {
   return (defaultValue);
} else {
   throw new ConversionException(stringValue);
}

此时我不记得Struts是否只记录异常并且无法以参数值的方式静默设置false,或者传播异常(自从我使用Struts以来已经有一段时间了:D但我更多倾向于认为它只是设置错误并继续)。

即使被忽略,日志也应该指出异常。为org.apache.commons.beanutilsorg.apache.struts设置记录器应指出任何转换错误。