Struts的HTML标记库

Posted by 冰河 at 18:56 Add comments 19,463 Views
282010
<html:html>
<html:html>标记可以说是Struts所 有标记中最简单的了。它简单的在页面开始处和结尾处产生一个的标记。在 Struts1.1以前的 版本中,该标记有一个locale属性。如下所示:
<html:html locale=”true”>
该 属性的作用是读取用户session中的locale属 性并显示出来。比如用户使用的是zh-CN,那么,生成的页面代码将如下所示:
<html locale=”zh-CN”>
不过,从Struts1.2开始,该属性被lang所取代。原 因是locale属性当其值为true时, 会读取session中的locale信 息。但是当HttpSession不存在时,它会强制创建一个新的session并将HTTP请求中的locale信息放入session中去。这种方式 时显并不合理,因此,从Struts1.2开始,locale属 性被lang属性所取代
<html:html lang=”true”>
当 使用lang属性后,若没有session对 象时,就根据Http请求中的locale信 息来输出相应的语言信息。
<html:base>
<html:base>用于在网页的head部 分生成一个base标记。它的用法很简单,只需在head部 分加入如下标记就可以了
<html:base/>
当经过Web容器编译后,会生成如下的一段标记。
<base href=”http://localhost:8080/taglib1/html-base.jsp”>
这也就是本网页的实际的URL地 址。请记住,base标记将不会被显式的显示在网页上,只有通过查看生成的 html源代码才可以看得见。其实,base标记的含义 不仅是生成本网页的URL,它更重要的功能是为该页面内的所有其它链接提供相对的位置。例如,在本 网页使用了<html:base>标记后,生成了如上的URL地址。倘若此时需要指定一张图片,只须使用相对的位置链接就可以了。假设在 taglib1的根目录下有一个image目录,里面 有一张叫image.gif的图片,则引用的代码如下所示:
<img src=”image/image.gif”>
这 张图片的实际URL就是:
http://localhost:8080/taglib1/image/image.gif
<html:link>
<html:link>标记是用来生成HTML中 的<a>标记的,它带有多种参数,可以和Struts框 架结合生成多种不 同形式的链接。
1.外部完整URL链接
<html:link>标 记最简单的用法就是直接链到一个外部的完整URL链接,比如用户需要创建一个到新浪网的链接。可以 使用 href属性,代码如下:
<html:link href=”http://www.sina.com.cn”>
新浪网
</html:link>
以上代码经编译后会生成如下html代 码:
<a href=”http://www.sina.com.cn”>新浪网</a>
2.相对URL链接
当需要从同一个应用中的某个网页链接到另一个网页时,可以使用page属性,代码如下:
<html:link page=”/index.jsp”>
首页
</html:link>
当 需要向所链接的页面传输某些参数时,可以将参数直接加在请求的尾部就可以了。例如,下面的代码示例将向测试页面传递一个字符串参数和一个整型参 数:
<html:link page=”/test.do?testString=a+new+string&testInt=10000″>
测试页面
</html:link>
由它生成的页面html代 码如下所示:
<a href=”/taglib1/test.do?testString=a+new+string&testInt=10000″>
试页面
</a>
下面的链接是一个测试,它向测试页面传递两个参数,一个是testString,它的值为”a new string”, 另一个是testInt,它的值为10000。
3.全局转发URL链接
在Struts的struts-config.xml文 件中定义了<global-forward>全局转发变量,可以通 过<html:link> 来链接到这种全局转发的URL链 接,使用forward属性,示例代码如下所示:
<html:link forward=”index”>
回到主页
</html:link>
生 成的页面html代码如下所示:
<a href=”/taglib1/index.jsp”>
回到主页
</a>
4.带有页面变量的URL链接
在创建链接时常常需要访问一些页面的变量,将它们的值作为参数传递给将 要链到的网页。<html:link>标记也提供了这样的功能。
如果仅需传递单个参数,可以使用paramID与paramName这两个属性。以下为代码示例
<%
String test1 = “testABC”;
request.setAttribute(“stringtest”,test1);
%>
<html:link page=”/test.do” paramId=”testString” paramName=”stringtest”>
试页面
</html:link>
在 这段程序中,首先定义一个变量为test1它的值为testABC。 然后将它存入request对象中,命名为stringtest。 接着,使 用<html:link>标记的paramName属 性指定欲从内建对象中读取值的变量名,此处也就是stringtest。然后,使用 paramId属性指定传值的目标参数,此处为testString。 点击下面的链接可以通过测试页面查看运行效果:
如果需要传递 的参数有多个,则可使用<html:link>标记的name属性来实现,name属性的值是一个 java.util.HashMap类型的对象名称,它的每一个”键/值”对就代表一对的”参数名/参数值”, 以下为代码示例:
<%
HashMap para_map = new HashMap();
para_map.put(“testString”,”testABC”);
para_map.put(“testInt”,new Integer(10000));
request.setAttribute(“map1″,para_map);
%>
<html:link page=”/test.do” name=”map1″>
测试页面</html:link>
在 上面的代码中,首先在页面上声明一个HashMap类型的变量para_map用来存储将要传递的参数,接着,向 para_map中 存入两个对象。然后再将该对象存入页面的request对象中。使用<html:link>标记的name属性 来将参数带 入目标页面中。实际生成的html代码如下所示:
<a href=”/taglib1/test.do?testString=testABC&testInt=10000″>测试页面< /a>
<html:rewrite>
<html:rewrite>标记是用来输出链接中的URI的。 所谓URI就是指一个完整URL地址去掉协 议,主机地址和端口号以后的 部分。它的众多属性都和<html:link>一样,只 是它输出的仅是一个URI字符串,而非链接。示例代码如下:
<html:rewrite page=”/test.do?testString=testABC”/>
它 生成的html如下:
/struts/test.do?testString=testABC
可以看出,它输出的内容只是实际URL中除去协议,主机地址和端口号以后的部分。实际的URL应 为:
http://localhost:8080/taglib1/test.do?testString=testABC
它也可以使用paramId和paramName等属性,如下面的例 子:
<%
String str = “testABC”;
request.setAttribute(“test1″,str);
%>
<html:rewrite page=”/test.do” paramId=”testString” paramName=”test1″ />
实际生成的html代码如下所示:
/struts/test.do?testString=testABC
下面的例子将演示当有多个参数要传递时<html:rewrite>生成的URI样 式。它与<html:link> 一样,都使用name属 性来传递多个参数。
<%
HashMap para_map = new HashMap();
para_map.put(“testString”,”testABC”);
para_map.put(“testInt”,new Integer(10000));
request.setAttribute(“map1″,para_map);
%>
<html:rewrite page=”/test.do” name=”map1″/>
实 际生成的html代码如下所示:
/struts/test.do?testString=testABC&testInt=10000
这里有一点需要注意的,当从网页源代码上看 生成的多参数链接时,在多个参数间连接符并不是简单的& 而是一个&amp;,在html代码中它就代表&。
<html:img>
<html:img>标记是用来显示图片的,它的用法很简单,如下所示:
<html:img page=”/a.jpg”/>
此处值得注意的一点是,在page属 性后图片的路径并没有因为设定了<html:base>而使用了相对路径,而是依然使 用了绝对路 径。如果使用非Struts的<img src=”a.jpg”>标记则可以正确显示图片。
<html:form>
<html:form>标记生成页面表单,这个由Struts标 记生成的表单和普通的HTML表单略有不同。普通的表单用法如下所示:
<form method=”post” action=”/loginServlet”>
<input type=”text” name=”username”>
<input type=”text” name=”username”>
</form>
可以看到,在普通的form标 记后的action属性的值是一个Servlet(当 然也可以是一个JSP文件),而使用 了<html:form> 标记后,代码则变成了下面的样子:
<html:form action=”/test.do”>
其 中action属性后跟的是一个在struts-config.xml文 件中定义的Action,而这个Action也 必定要对应一个 ActionForm才能完成其应有的功能。所以,对每个<html:form>标记来说,都该对应一个ActionForm。 而这个 ActionForm中的属性值也将和网页上的<html:form>表 单中的各个表单项相对应。这些表单相将会是类似 于<html:text>的一些表单 元素。下面有一段示例代码:
<html:form action=”/test.do”>
输入字 符串testString:<html:text property=”testString”/>
提 交:<html:submit property=”submit”/>
</html:form>
这 段代码将在页面上显示一个文本框和一个提交按钮,当用户在文本框中输入一个字符串后并点击按钮,将会触发test这 个Action。在初始化这个 JSP页面 时,JSP引擎在初始化<html:form>标 记时将会初始化test这个Action所 对应的ActionForm,当用户提 交表单时,表单项中的testString刚好对应ActionForm中的 这一项(只需名称相同)。
此处值得注意的一点是,在<html:form>表 单中的各个表单项一定要在ActionForm可以找到一个对应的项,这样才能在提 交的时候进行赋值,否则,Struts将会报一个错,显示无法找到某表单项在ActionForm的对应get方法
<html:text>
<html:text>标记比较简单,是用来在页面上生成一个文本框,该标记通常被用在一个<html:form>中。以 下是一段示例代码:
<html:form action=”/test.do”>
输入字 符串testString:<html:text property=”testString”/>
输入整数 testInt:<html:text property=”testInt”/>
<html:submit property=”submit” value=”submit”/>
</html:form>
通常,<html:text property=”testString”/>语句将生成以下的html代 码:
<input type=”text” name=”testString”>
可以看到,<html:text>标记的property属 性指定了文本框的名称,如果它位于<html:form>表单 内部,那么, property的值若刚好与ActionForm中 的一项对应时,该文本框内的值就将被赋给该ActionForm中的该项。以test这个 Action所对应的ActionForm为例,它其中就有这么一段代码刚好与上面的<html:text>相 对应:
private String testString = null;
public void setTestString(String testString){
this.testString = testString;
}
public String getTestString(){
return testString;
}
从 上面的代码可以看出用户在提交表单后,Struts会自动将property=”testString”的<html:text>文 本框的值赋给 ActionForm中的testString字段。
<html:password>
<html:password>用来在页面上产生一个密码框。所谓密码框其实就是一个文本框,只 不过对它的任何输入都将显示为”*”。 它的用法和<html:text>差 不多,property属性用来表示它的名称。
<html:form action=”/test.do”>
<html:password property=”testString”/>
<html:submit property=”submit” value=”查看测试页面”/>
</html:form>
上面的代码中将一个<html:password>标 记放在一个表单中,这也是必须的,否则Struts框架会报错。以下是上面代码的 运行效果,无论用户输入什么,都只会显示”*”。点击提交钮后,会在测试页面看到用户输入的内容。
<html:textarea>标 记和&html:textarea基本相同,只不过它会产生一个更大的文本输入域。同样 的, 它也需要存在于一个<html:form>表单中,下面是示例代码:
<html:form action=”/test.do”>
<html:textarea property=”testString” rows=”8″/>
<html:submit property=”submit” value=”查看 测试页面”/>
</html:form>
<html:hidden>
<html:hidden>标记用于在网页上生成一个隐藏的字段。众所周知,网页上总有一些信息不 希望被用户看到,但在提交的时候却需 要传递到服务器上以帮助业务逻辑进行处理。在传统的html中, 隐藏字段是用下面的方式表示的:
<input type=”hidden” name=”testString” value=”hiddenString”>
<html:hidden>标 记不需要被限定在一个表单的内部来使用,以下的例子还是将它放在一个表单的内部。当用户点击 “查 看测试页面”的按钮时,会看到测试页面中testString被 赋与了”hiddenString”的值。
在<html:hidden>标记中有一个write属 性,可以决定在页面上是否显示出这个隐藏的值,如下面的代码:
<html:hidden property=”testString” value=”hiddenString” write=”true”/>
运行效果如下所示,虽然只有短短的一个字符串,但可以看出标记还是把testString的value打印出来了。
hiddenString
<html:submit>
<html:submit>标记生成一个提交按钮,用于提交表单。它的用法很简单,如下所示:
<html:submit property=”submit” value=”提 交“/>
它 会生成如下的html代码
<input type=”submit” name=”submit” value=”提交“>
另 外,<html:submit>标记还可以写成如下的形式,它也将生成同样的html代码。
<html:submit> 提交</html:submit>
<html:reset>
<html:reset>标记生成一个复位按钮,用于复位表单内的各项元素。代码如下:
<html:form action=”/test.do”>
<html:text property=”testString”/>
<html:submit property=”submit” value=”Submit”/>
<html:reset property=”reset” value=”reset”/>
</html:form>

<html:cancel>
<html:cancel> 标记将在网页上生成一个取 消按钮,用户可以通过点击它触发一个取消事件。这个取消事件通常是在用户已经点击了提交按钮后,又临时想取消这次提交 时生成的。因此,取消按钮并不只是简单的页面效果,而要深入后台,其实也就是调用一个Action来对用户的提交进行处理,做一些清除的工作。<html:cancel>按钮要使用 在一个表单内部,可以用以下两种方式来使用该标记:
<html:cancel>Cancel</html:cancel>

<html:cancel property=”org.apache.struts.taglib.html.CANCEL” value=”Cancel”/><br>

上面的代码生成的 html代码如 下所示:
<input type=”submit” name=”org.apache.struts.taglib.html.CANCEL” value=”Cancel” onclick=”bCancel=true;”>
可以看到,在生成的 html标记最后有一个onclick=”bCancel=true;”, 这个onclick动作是在用户点击取消按钮时发生的,其实也就是运行一个 javascript脚本,它给一个名为bCancel的变量赋值为true。为什么要这样呢?先看看以下代码,这是一 段在用户点击cancel后执行的程序,其实它就是位于和提交表单后所执行的相同的Action内。 因为cancel动作和submit动作在 生成html代码后的类型都是一样的,都“submit”。这一点从上面的介绍中可以看到。
……
public ActionForward execute(ActionMapping mapping, ActionForm form, HttpServletRequest request, HttpServletResponse response) throws Exception{
…..
if (isCancelled(request)){
return mapping.findForward(“cancelled”);
}
……
}
这其中有一个 isCancelled(),该函数的作用就是从request对象中取出bCancel变量,并且判断其是否为真,若为真则转发到相应的Action处理,则不为真,则说明是普通的提交动作,继续下面的代 码。这个isCancelled()方法被定义在Action 类中,其代码如下:
protected boolean isCancelled(HttpServletRequest request) {
return (request.getAttribute(Globals.CANCEL_KEY) != null);
}
这个 Globals.CANCEL_KEY的值就是cancel按钮的name属性,也就 是 org.apache.struts.taglib.html.CANCEL
<html:checkbox>
<html:checkbox> 生成网页上的选择框,它必须存在于一个表单范围内,因此也就说明在ActionForm必须使用一个字段来接收从表单传过来的值。一般情况下,在 ActionForm中都使用布尔型变量来表示一个checkbox,这是因为它要么没被选中,要么就是被选中。以下是一段示例代码:
<html:form action=”/test.do”>
checkbox1:<html:checkbox property=”checkbox1″/>
checkbox2:<html:checkbox property=”checkbox2″/>
<html:submit property=”submit” value=”
测试“/> </html:form>
这样一段代码生成的html如下所示:
<form name=”testbean2″ method=”post” action=”/taglib1/test.do”>
checkbox1:<input type=”checkbox” name=”checkbox1″ value=”on”>
checkbox2:<input type=”checkbox” name=”checkbox2″ value=”on”>
<input type=”submit” name=”submit” value=”
测试“>
</form>
可以看到,checkboxvalueon,这一点需要特别注意。当某 个checkbox被选中时,使用checked属性 来表示,代码如下:
<input type=”checkbox” name=”checkbox1″ value=”on” checked=”checked”>
另外,有一点需要特别注意。为了让checkbox能够正确的显示,应当在ActionFormreset()方法中对其进行复 位。也就是在 ActionFormreset()方法中加入如下代码:
public void reset(ActionMapping mapping, HttpServletRequest request){
this.checkbox1 = false;
this.checkbox2 = false;
}
如果不checkbox进行复位,那么一个checkbox一旦被选中,就会永远处于被选中的状态。发生这种情况的原因是,在html中浏览器不会向Web务器发送一个类似于某某选择框没有被选中这样的信息,因此,当一个checkbox被选中后,即便下一次用户将它的勾去掉,Web服务器端也将 认为它是被选中的。
运行效果如下所示:
checkbox1:

checkbox2:

<html:multibox>
<html:multibox> 标签生成网页上的复选框,其实它的功能和<html:checkbox>一样,所不同的是,在此复选框所在的ActionForm中使用一个数组来表示该复选框。先看看以下网页代码:
<html:form action=”/test.do”> <html:multibox property=”testStringArray” value=”China”/>中国
<html:multibox property=”testStringArray” value=”USA”/>
美国
<html:multibox property=”testStringArray” value=”England”/>
英国
<html:multibox property=”testStringArray” value=”Germany”/>
德国
<html:multibox property=”testStringArray” value=”France”/>
法国
</html:form>
当用户选中其 中的几项并点击提交后,ActionForm中 的testStringArray数组就会被赋上相应的值。这里有一点值得注意,例如用户选择了中国英国两项,ActionFormtestStringArray的 值就会是{“中国“,”英国“}

中国

美国

英国

德国

法国
<html:radio>
<html:radio> 标记生成一个单选框,示例代码如下:
<html:form action=”/test.do”>
<html:radio property=”testRadio” value=”testvalue1″/>
</html:form>
它有一个value性,用来指定当选中该单选框时ActionForm中对应的属性 的值。下面是另一种单选框的用法:
<html:form action=”/test.do”>
<html:radio property=”testRadio” value=”value1″>Choice1
<html:radio property=”testRadio” value=”value2″>Choice2
<html:radio property=”testRadio” value=”value3″>Choice3
</html:form>
在上面的代码 中,单选框一共有三个,这三个单选框组成一个单选框组,只能选取其中一个。无论选中哪一个,它的值在提交表单后都 将赋给ActionForm中相对应的属性,如果三个单选框一个都没有选 中,那么该属性的值将为一个空串。
运行效果如下所示:

Choice1

Choice2

Choice3
<html:select>
<html:select> 用来在网页上产生选择列表。通常它与<html:option>等选项标记连用。示例代码如下:
<html:select property=”testString” size=”1″>
<html:option value=”value1″>Show Value1</html:option>
<html:option value=”value2″>Show Value2</html:option>
<html:option value=”value3″>Show Value3</html:option>
<:html:submit property=”submit” value=”
提交“/> </html:select>
中,property表示该选择列表与ActionForm中对应的属性名。当用户点击提交后,会在测试页面看到用户所选中的选项的值。以下是代码的运行效果:

<html:select> 有一个size属性,它表示同时显示的选项的数目,如上例中的size1,则只同时显示一个选项。还有 一个multiple属性,当其为true时,该选择列表就允许多选。用户可以通过鼠标的拖动,或是按住Ctrl键进行多选。
以下是 multiple=”true”size=”8″例子
multiple性为true时,在ActionForm中 对应的属性应是一个数组类型以便同时向其赋上用户选中的多个值。
<html:option>
<html:option> 标记是<html:select>标记的选项,每个<html:option>将在选择框中代表一个选项。有如下代码所示:
<html:select property=”testString” size=”1″>
<html:option value=”value1″>Show Value1</html:option>
<html:option value=”value2″>Show Value2</html:option>
<html:option value=”value3″>Show Value3</html:option>
</html:select>
一个选项有两部分重要的内容。第一就是它所显示 给用户的内容,这可以通过以下方式来指定:
<html:option value=”value1″>Show Value1</html:option>
可以看出,使 用两<html:option>间的部分来表示用户所见到的内容。当然,也可以使用<html:option> 所带的keybundle等属性用来指定所在资源文件中的内容,以此来表示用户所见到的内容。其中,bundlekey属性的用法请参看配置文件相关章节。
另一个重要 的内容就是它所传递给ActionForm的 值。这是由标记的value属性指定的。如上面的例子中,value的值分别为 value1,value2value3,当用户选中某个标记时,JSP页面就会将该标记所对应的value传给ActionForm中相应的属性。
以下是运行 效果:

<html:options>
<html:options> 标记用来表示一组选择项,也就是相当于一组的<html:option>标记。在一个 <html:select>标记中可以包含多个<html:options>标记。以下是一段代码示例:
<%
ArrayList list = new ArrayList();
list.add(new org.apache.struts.util.LabelValueBean(“Show value1″,”value1″));
list.add(new org.apache.struts.util.LabelValueBean(“Show value2″,”value2″));
list.add(new org.apache.struts.util.LabelValueBean(“Show value3″,”value3″));
list.add(new org.apache.struts.util.LabelValueBean(“Show value4″,”value4″));
pageContext.setAttribute(“valuelist”,list);
%>
<html:form action=”/test.do”>
<html:select property=”testString”>
<html:options collection=”valueslist” property=”value” labelProperty=”label”/>
</html:select>
</html:form>
这是一<html:options>标记的应用方式。首先,页面创建一个ArrayList型的对象list,以此作为 存放所有选项的容器。接下来,将四个org.apache.struts.util.LabelValueBean类型的对象放入list中,在初始 化这四个 LabelValueBean对象时,对每个对象 的构造函数传入两个字符型参数。第一个参数将赋给LabelValueBean对象 中的label变量,这个变量的值将成为页面选项中用户所见到的部 分;第二个参数将赋给LabelValueBean对象中的value变量,该变量的值就是用户在选择页面中这个选项后传递给后台ActionForm的值,也就是<html:option>标记中value属性的 值。
在四个对象都存入 list对象后,程序把list对象放入pageContext中。这样做的目的是为了让<html:options>标记来引用它。<html:options>标记有一个collection属 性,它可以在页面上下文pageContext中指定一个实现了List 接口的对象,然后将该对象列表中所有存储的对象遍历,取出每一个对象相应的属性值,用来作为页面选项(也就是每一个option)value label。如在本例中,collection属性首先指定了从pageContext中取出valuelist对象,由于valuelist对象中存储的是一个 org.apache.struts.util.LabelValueBean类 型的对象列表,所以,<:html:options>标记会将每个对象取出,用 org.apache.struts.util.LabelValueBean对象中的value属性值赋 给标记的property属性,再用对象中的 label属性值赋给标记的 labelProperty属性。这样就将存储在valuelist中的对象和页面 上的每一个选项建立起了一一对应的关系,<:html:options> 的功能也就实现了。
以下是代码实际运行效果:

<html:optionsCollection>
<html:optionsCollection> 标记用来表示一组选择项,与<html:options>所不同的是,它不从pageContext中取出对象,而是从与表单相关联的 ActionForm中取出同 名的数组,并将该数组中的各个对象当作选项表示出来。先看以下ActionForm中 的代码片断:
private TestPageBean [] pagebean = new TestPageBean[4];
public TestBean2 ()
{
super();
for (int i=0;i<4;i++){
pagebean[i]=new TestPageBean(“name” + i,”value” + i);
}
}
ActionForm中,定义一个叫做pagebean的 数组对象,它的类型是TestPageBean,这个Bean只有两个属性,value label。接下来,在ActionForm调 用构造函数进行初始化时将这个pagebean数组对象进行初始化,存入四个TestPageBean类型的对象。这四个对象的valuelabel分别从value1value4以及name1name4。以下是TestPageBean的代码:
public class TestPageBean {

private String name = “”;
private String value = “”;
public TestPageBean(String n, String v){
name = n;
value = v;
}

public String getName() {
return name;
}

public void setName(String name) {
this.name = name;
}

public String getValue() {
return value;
}

public void setValue(String value) {
this.value = value;
}
}

以下<html:optionsCollection>的使用方法:
<html:form action=”/test.do”>
<html:select property=”testString” size=”1″>
<html:optionsCollection property=”pagebean” label=”name” value=”value”/>
</html:select>
<html:submit property=”submit” value=”submit” />
</html:form>
可以从代码中看到,<html:optionsCollection>标记使用property属 性来指定ActionForm的数组属性,用label性来指定数组元素对象中用于代表选项页面显示的值,而用value属性来指定数组元素对象中用于代表选项被选中后传入ActionForm 的值。
以下是以上代码的运行效果,若用户选择了name1则可在测试页面上看到与其对应的value1

<html:file>
<html:file> 标签用于上传文件。上传文件指的是从客户端将文件上传到服务器上,这一过程和通过表单提交请求到服务器端并 没有本质上的不同。在这一过程中有以下两点需要注意:
1. 文件存储于客户端的机器上,因此在服务器端不能使用获得文件路径的方式来获取文件对象。
2. 由于使用GET方式提交表单时,可提交的串长度受到限制,所 以,在上传文件时必须使用POST方式。
文件上传是一 项从页面开始的工作,下面首先看一下页面上的代码:
<html:form action=”/upload.do” enctype=”multipart/form-data”>
<html:file property=”file” />
<html:submit property=”submit” value=”submit”/>
</html:form>

您上传的文件是:<bean:write name=”upload” property=”filename”/>
它的大小为:<bean:write name=”upload” property=”size”/>

上面的代码中使用<html:file>标记来进行文件的上传。前面已经说过,上传过程实际上和通过表单提交请求到服务器没有不同,因此,该标记 也必须存在于一个表单中。这个表单所进行的操作是/upload.do。通过查找struts-config.xml可以知道,该表单类型应为 org.apache.struts.webapp.exercise.UploadBean,以下是它的代码:
public class UploadBean extends ActionForm{

private FormFile file = null;
private String filename = “”;
private String size = “”;

public UploadBean(){
}

public FormFile getFile() {
return file;
}

public void setFile(FormFile file) {
this.file = file;
}

public String getFilename() {
return filename;
}

public void setFilename(String filename) {
this.filename = filename;
}

public String getSize() {
return size;
}

public void setSize(String size) {
this.size = size;
}
}

在上面的代码中,定义了一个FormFile类型的对象file。这个FormFile类是Struts提供的 专门用于文件上传的类。在这个ActionForm 中,FormFile类的对象file的名称与网 页上<html:file>标记的property属 性相对应,这一点非常重要!
用户点击上传按钮后执行的是upload的操作,这个操作与后台的UploadAction关联。以下是UploadAction的代码:
public class UploadAction extends Action {

public ActionForward execute(ActionMapping mapping,ActionForm form,HttpServletRequest request,HttpServletResponse response) throws Exception {

UploadBean filebean = (UploadBean) form;

FormFile file = filebean.getFile();
if (file == null){
return mapping.findForward(“input”);
}

String filename = file.getFileName();
filebean.setFilename(filename);
String size = Integer.toString(file.getFileSize()) + “bytes”;
filebean.setSize(size);

InputStream is = file.getInputStream();
String store_path = servlet.getServletContext().getRealPath(“/fileupload”);
System.out.println(store_path);
OutputStream os = new FileOutputStream(store_path + “/” + filename);

int bytes = 0;
byte [] buffer = new byte[8192];
while ((bytes = is.read(buffer,0,8192))!=-1){
os.write(buffer,0,bytes);
}

os.close();
is.close();
file.destroy();

return mapping.findForward(“input”);
}
}

上面的代码首 先从表单 ActionForm中获取FormFile对象,然后创建输入流读取文件内容,再创建一个输出流,将上传的文件保存到工程目录下的fileupload 目录中。最后关闭输出流和输入流,并将与客户端的文件连接断开。整个过程非常清楚,简单。其中,有两句代 码分别将文件名和文件大小保存到 UploadBean中去,这是为了在JSP页面上可以显示出文件名和文件大小。在上面的页面代码中可以看到这样两句:
您上传的文件是:<bean:write name=”upload” property=”filename”/>
它的大小为:<bean:write name=”upload” property=”size”/>
这里使用了 Struts Bean标记库的标签来显示与页面相关的ActionForm的变量值。
以下是程序的运行效果,用户可以在/tablig/fileupload目录下看到上传的文件。

<html:errors>
Struts 1.1中该标签的使用方法
<html:errors> 标签用来在网页上输出错误消息。以下是一段实际运行效果,当用户选中下面的选 择框后并提交表单时,页面上就会显示错误消息,而当用户不选中直接点击时,会出现不同的错误消息。
选择框:

这里使用到的代码如下所示:
<html:form action=”/testerr.do”>
择框:<html:checkbox property=”checkbox1″/>
<html:submit/>
</html:form>
<html:errors bundle=”error”/>
错误信息是通 过什么方式添加的呢,<html:errors>标记又是通过什么方式将错误信息显示出来的呢?在前面的章节中曾提到过ActionForm中的 validate()方法,它的作用是检验用户的输入,当用户的输入不符合某种条件时,就返回一个 ActionErrors对象,倘若返回的对象不为空,Struts框架就会将请求发回页面。此时,倘若页面上有相应的显示错误的标记,就会将在 validate()方法中所添加的错误显示出来。
另外,除了在 ActionFormvalidate()方法中可以添加ActionErrors外,在Action中也可 以添加。通过查看struts- config.xml文件可以知 道,与这个表单相关联的ActionFormAction分别是ErrBeanErrAction。以下先看看 ErrBean的 代码:
public class ErrBean extends ActionForm{

private boolean checkbox1;
public boolean isCheckbox1() {
return checkbox1;
}

public void setCheckbox1(boolean checkbox1) {
this.checkbox1 = checkbox1;
}

public void reset(ActionMapping mapping, HttpServletRequest request){
this.setCheckbox1(false);
}

public ActionErrors validate(ActionMapping mapping, HttpServletRequest request){
ActionErrors errors = new ActionErrors();
if (checkbox1){
errors.add(ActionMessages.GLOBAL_MESSAGE,new ActionError(“html.errors.error1″));
errors.add(“checkbox1″,new ActionError(“html.errors.error2″));
}
return errors;
}
}

<html:checkbox> 标记一节已经说过,用于在ActionForm中表示一个选择框的类型通常使用boolean型。此处在ErrBean中就声明了一个boolean型的变量checkbox1用于表示页面上的选择框。当用户在页面上点击了该选择框时,选择框的值被设置为true。然后用户点击提交按钮,此时,Struts框架从struts-config.xml文件中得知这个提交的ActionFormvalidate属性为true,因此需要 调用 ErrBeanvalidate()方法进行验证。
ErrBean validate()方法中,首先初始化一个ActionErrors对象,然后判断checkbox1是 否被选中。若选中,则向 ActionErrors 对象中添加两个ActionError。添加ActionError时采用的是ActionErrorsadd()方法。该方法有两个参数,第一个参数是所添加ActionError key,然后是ActionError的值。这样做的原因是因为在ActionErrors内部保存了一个HashMap,以 此来将所有的 ActionError保存。其中,添加第一个ActionError的代码如下:
errors.add(ActionMessages.GLOBAL_MESSAGE,new ActionError(“html.errors.error1″));
这里的 ActionMessages.GLOBAL_MESSAGE的值“org.apache.struts.action.GLOBAL_MESSAGE”,它是一个常量,表示全局消息。对于每一个key来说,都可以存入多个ActionError。这是因为ActionErrors的内置的HashMap中并不是仅仅存入一个简单的ActionError 对象,而是存入一个List对象,再将多个ActionError对象存入该List中。ActionError的构造函数中的参数是资源文件中的key 值,将来在页面上就将显 示该key值对应的value。下面是 添加第二个ActionError的代码:
errors.add(“checkbox1″,new ActionError(“html.errors.error2″));
这个 ActionErrorkey值为checkbox1,它表示和特定的表单元素相关的错误信息。在页面中的<html:errors>标签中使用 property属性来指定。
通过上面的代码可以看到,用户在提交表单时由ActionForm产生了错误信息,然后转交回页面。此时,就该由页面上的<html:errors> 来显示相应的错误信息了。这时,考虑另一种情形,如果页面上用户输入的信息并 无错误,通过了ActionFormvalidate()方法的检查,但在 Action中 经由业务逻辑处理后,返回了一些错误信息。此时,仍然需要将ActionErrors对象存储进request对象中。但Action中并 validate方法了,该怎么办呢?Action类的saveErrors()方法解决了这一困难。看看 下面ErrActionexecute()法的代码:
public ActionForward execute(ActionMapping mapping, ActionForm form, HttpServletRequest request, HttpServletResponse response) throws Exception {

ActionErrors errors = new ActionErrors();
errors.add(ActionMessages.GLOBAL_MESSAGE,new ActionError(“html.errors.error3″));
saveErrors(request,errors);
return mapping.findForward(“input”);
}

Action类中提供了一个saveErrors()方法,可以将ActionErrors对象存入request中。通过这个方法<html:errors> 标签可以在request中找到它并将其显示在网页上。
前面已经看到了页面上显示的代码,下面就来讲解 一下<html:errors>标记的具体用法。
<html;errors> 标记可以放在网页上的任何位置,它有以下三个比较重要的属性:
name属性:它指定了存放在requestsession属性中的错误对象的值。我们知道,在requestsession中,对象的存储一般都以键/值对的方式来进行。ActionErrors对象在requestsession中的key默认为Globals.ERROR_KEY
property性:用于指定与ActionError对应的key值,如前面例 中的checkbox1
bundle属性:用于指定资源文件,即显示ActionErrors信息时去哪个资源文件中读取相应的消息文本。例如在taglib1中,struts- config.xml 文件中有这样一句代码:
<message-resources parameter=”message” key=”error”/>
则在页面<html:errors>标签中使用下面的方式来引用这个资源文件
<html:errors bundle=”error”/>
以下是几个代码示例:
<html:errors bundle=”error”/>
上面的代码表示显示所有的错误信息。
<html:errors property=”org.apache.struts.action.GLOBAL_MESSAGE” bundle=”error”/>
上面的代码 表示显示所有的全局消息,也就是在向ActionErrors中添加ActionError对象时,选用 ActionMessages.GLOBAL_MESSAGE 做为该ActionErrorkey的对象。
Struts 1.2中该标签的使用方法
到目前为止,所有有<html:errors>标签的讨论都是基于Struts 1.1的核心。但在2005Apache正式推出Struts 1.2后, 有许多东西已经被改变。其中很重要的一个改动就是与<html:errors>标记相关的改动,主要就是已经不再推荐使用 ActionError类和ActionErrors类,因此,如果要将现有的 使用到与<html:errors>标记相关的 代码从 Struts 1.1下移至Struts 1.2下,需要作以下改动。
1. 将代码中使用到ActionError类的地方换为ActionMessage类。
2. 将除了在ActionFormvalidate()方法以外使用到ActionErrors类的地方都替换为ActionMessages
这样做的主 要原因是,ActionErrorActionMessage的子类,而ActionErrorsActionMessages的 子类。开发者认为一个错误消息也是消息的一种,并没有必要专门将其分开存放。只需要使用Globals.MESSAGE_KEY,Globals.ERROR_KEY来进行区分就分。
例如,在 ErrAction中,若要使其支持Struts1.2, 则可将代码改为如下形式:
public ActionForward execute(ActionMapping mapping, ActionForm form, HttpServletRequest request, HttpServletResponse response) throws Exception {

ActionMessages messages = new ActionMessages();
messages.add(ActionMessages.GLOBAL_MESSAGE,new ActionMessage(“html.errors.error3″));
saveErrors(request,messages);
return mapping.findForward(“input”);
}

相关日志

Leave a Reply

(required)

(required)

You may use these HTML tags and attributes: <a href="" title=""> <abbr title=""> <acronym title=""> <b> <blockquote cite=""> <cite> <code> <del datetime=""> <em> <i> <q cite=""> <strike> <strong>

Protected by WP Anti Spam
© 2009 - 2024 冰河的博客