检查 JSP 中是不是存在属性
Posted
技术标签:
【中文标题】检查 JSP 中是不是存在属性【英文标题】:Checking attribute exists in JSP检查 JSP 中是否存在属性 【发布时间】:2011-02-01 03:04:34 【问题描述】:我有一些扩展超类的类,在 JSP 中我想展示这些类的一些属性。我只想做一个JSP,但是事先不知道对象有没有属性。所以我需要一个 JSTL 表达式或一个标签来检查我传递的对象是否具有此属性(类似于 javascript 中的 in 运算符,但在服务器中)。
<c:if test="$an expression which checks if myAttribute exists in myObject">
<!-- Display this only when myObject has the atttribute "myAttribute" -->
<!-- Now I can access safely to "myAttribute" -->
$myObject.myAttribute
</C:if>
我怎样才能得到这个?
谢谢。
【问题讨论】:
【参考方案1】:利用 JSTL c:catch
。
<c:catch var="exception">$myObject.myAttribute</c:catch>
<c:if test="$not empty exception">Attribute not available.</c:if>
【讨论】:
只有我一个人吗?我认为这是查看变量是否存在的一种丑陋方式。就像在 java 中捕获 NullPointerException 而不是?(if!=null)
@Shervin:这确实是一个糟糕的设计。但到目前为止,这是实现奇怪要求的唯一方法。
@Shervin Asgari 我认为“如果为空”很难看。除非你做第三方 api。您应该处理所有异常 - 方式更清洁。
@ShervinAsgari - 你是对的,但是 JSP/JSTL 经常出现“漂亮”解决方案不可用、冗长或极其迂回的情况(参见 sbk 的回答,它创建了一个 新标签库)。尝试做一个正确的if/else-if
块是另一个很好的例子。
如果要检查列表属性是否为空,请使用$list != null
,因为$not empty list
在列表为空列表时返回true。【参考方案2】:
您可以根据vivin's blog post 轻松创建自定义函数来检查属性。
简而言之,如果您已经拥有自己的 taglib,只需创建一个静态的“hasProperty”方法...
import java.beans.PropertyDescriptor;
import org.apache.commons.beanutils.PropertyUtils;
...
public static boolean hasProperty(Object o, String propertyName)
if (o == null || propertyName == null)
return false;
try
return PropertyUtils.getPropertyDescriptor(o, propertyName) != null;
catch (Exception e)
return false;
...并在您的 TLD 中添加五行...
<function>
<name>hasProperty</name>
<function-class>my.package.MyUtilClass</function-class>
<function-signature>boolean hasProperty(java.lang.Object,
java.lang.String)
</function-signature>
</function>
...并在您的 JSP 中调用它
<c:if test="$myTld:hasProperty(myObject, 'myAttribute')">
<c:set var="foo" value="$myObject.myAttribute" />
</c:if>
【讨论】:
【参考方案3】:当我只想测试对象是否有字段但不想输出字段的值时,接受的答案可能会产生一些副作用。在上述情况下,我使用下面的 sn-p:
<c:catch var="exception">
<c:if test="$object.class.getDeclaredField(field) ne null">
</c:if>
</c:catch>
希望这会有所帮助。
【讨论】:
【参考方案4】:BalusC 的一个更详细的(典型的?)用法很好的答案
<%--
[1] sets a default value for variable "currentAttribute"
[2] check if myObject is not null
[3] sets variable "currentAttribute" to the value of what it contains
[4] catches "property not found exception" if any
- if exception thrown, it does not output anything
- if not exception thrown, it outputs the value of myObject.myAttribute
--%>
<c:set var="currentAttribute" value="" /> <%-- [1] --%>
<c:if test="$not empty myObject"> <%-- [2] --%>
<c:set var="currentAttribute"> <%-- [3] --%>
<c:catch var="exception">$myObject.myAttribute</c:catch> <%-- [4] --%>
</c:set>
</c:if>
<%-- use the "currentAttribute" variable without worry in the rest of the code --%>
currentAttribute is now equal to: $currentAttribute
正如 Shervin 在 BalusC 的回答中指出的那样,这可能不是最干净的解决方案,但正如 BalusC 所回答的那样,“这是迄今为止实现奇怪要求的唯一方法”。
资源
Evaluate empty or null JSTL c tags http://docs.oracle.com/javaee/5/jstl/1.1/docs/tlddocs/c/set.html http://docs.oracle.com/javaee/5/jstl/1.1/docs/tlddocs/c/catch.html【讨论】:
【参考方案5】:你的意思是这样的:
<c:if test="$not null myObject.myAttribute">
<!-- Now I can access safely to "myAttribute" -->
</C:if>
或其他变体
<c:if test="$myObject.myAttribute != null">
<!-- Now I can access safely to "myAttribute" -->
</C:if>
如果是你可以做的列表
<c:if test="#not empty myObject.myAttribute">
【讨论】:
不,如果我执行 myObject.myAttribute 并且 myObject 没有 myAttribute 的 getter,我将得到 PropertyNotFoundException。一个对象有一个 null 值的属性和它没有这个属性是不一样的。 但是您还应该如何访问该属性?据我所知,它只能通过吸气剂访问。即使变量是公开的,我相信您也需要一个吸气剂。为什么不能只创建一个吸气剂? 该属性并不存在于每个子类中,因此当该属性存在时,我有一个 getter。问题是我不知道要传递哪个子类。 @Shervin 我相信您的答案是“仅”检查属性是否已设置(不是 null 也不是空字符串)以上是关于检查 JSP 中是不是存在属性的主要内容,如果未能解决你的问题,请参考以下文章