




已阅读5页,还剩55页未读, 继续免费阅读
版权说明:本文档由用户提供并上传,收益归属内容提供方,若内容存在侵权,请进行举报或认领
文档简介
2010-02-24Struts2 学习笔记文章分类:Java编程 1. Struts2 与 Struts1 似乎没什么血缘关系了,承自于 WebWork,直害 WebWork 不再推出新版本了,原先的 WebWork 使用者只需顺其然,即是水道渠成;相反 Struts1 的开发经验对于 Struts2 却没有太大的帮助。 2. Struts1 的核心控制器是 ActionServlet,而 Struts2 的核心控制器是 FilterDispatcher。Struts2 的业务 Action 会在运行时生成 Action 代理。 3. Struts1 的 Action 须继承抽象 Action 类,侵入了 Servlet API;而 Struts2 的 Action 可以实现 ActionSupport,或者只要一个纯净的 POJO 来充当,完全与 Servlet 绝缘。也因此带来测试性 Struts2 要比 Struts1 强,可把 Struts TestCase 扔到一旁去了。 4. Struts1 在运行时一个 Action 只会生成一个实例,而 Struts2 中的 Action 会应对每个请求生成新的实例,在线程安全性方面,Struts1 要多些考虑。 5. Struts1 依靠 ActionForm 来接受数据,它也是依赖于 Servlet API ,并非普通的 JavaBean,而 Struts2 可在 Action 属性中获取请求的属性,当然也能封装在一个独立的 POJO 中。不过提醒一下,在 Struts1.3 中也可以用 POJO 来接受请求属性,但使用起来有点烦琐。 6. Struts2 使用了新的 OGNL 的表达式语言,可以访问值栈,在对集合和索引属性的支持上功能更强大。 7. Struts1 的配置文件只需 struts-config.xml;Struts2 的配置文件有 struts.xml 和 perties 中有两个 struts.devMode = fase 和 struts.configuration.xml.reload = true 很可爱,分别设置当前是开发还是生产模式,以及 struts.xml 改变后是否自动重新加载,免去了改配置手工重启应用的必须步骤。 8. Struts2 Action 的 execute() 无参,返回的是一个字符串,不像 Struts1 Action 的 execute() 有一大串且不说,光是返回 ActionForward,就让这个 Action 与 Struts1 脱不了干系;还是 Struts2 来得聪明,只返回个中性的 String,反正名字吗,猛然间这个 Action 也成 POJO 了,复用性增强了,难怪专门有一书,名为POJO In Action。 9. Struts1 的视图只支持 JSP,这也不怪它,只怨出身太早,那时就只有 JSP 一种表现层。相比,Struts2 更有艳福,能贴近于 FreeMarker、Velocity、XSLT、PDF 等视图技术。 10. Struts2 提供了功能强大复杂的标签库,统一化为 s 前缀。并顺应时代潮流地加入了 AJAX 的支持。还提供了更友好的验证功能。 1. 记得 Struts1 的 struts-config.xml 通常是放在 WEB-INF 目录下的,Struts2 的 struts.xml 却要放到 WEB-INF/classes 下的,傻眼了吧,反正我是。没看仔细之前,总给我报 There is no Action mapped for namespace / and action name Login. - unknown location 错误。因未在 web.xml 指定 struts.xml,所以用 ClassLoader 来加载它了。 2. 最简单的 Struts2 应用都要用到 freemarker-xxx.jar 包,因为 UI 标签要用到 FreeMarker ftl 的模板。 3. FilterDispatcher 要处理所有的 Web 请求,所以它的 url-pattern 是 /*,并自动对 *.action 转给业务 Action 处理。 4. struts.xml 中引入一个 节点来包裹 ,必须指定 的 name 属性,自定义命名即可,与 class 所在包无多大关系。 5. 把 ActionContext.getContext().getSession() 这个 Map 当 HttpSession 用即可,它与 HttSession 之间的转换 Struts2 的拦截器帮你完成。 6. 在 Action 接受客户端请求的数据,并且还可存放送给客户端的数据,这种做法个人觉得不怎么清爽,数据与控制器杂揉一块,也许是受 Struts1 的 ActionForm 的影响。Action 中的属性值会存放在类型为 ValueStack、名为 struts.valueStack 的属性中。 7. Struts2 的标签更是与 Struts1 的千差万别,只有 s:xxx 的标签了,所以只需在 jsp 前加 ,哪用 Struts1 那么分门别5类,但功能更强,这个吗,谁用谁知道。 8. 国际化支持要先在 perties 中指定资源束名,如 struts.custom.i18n.resources=messageResource,则在 classpath 下找 messageResource_语言代码_国家代码.properties。用 或 输出国际化消息。 9. Struts2 支持在 JSP 页面中临时加载资源文件,也支持通过全局属来加载资源文件,上一条就是全局的方式。 10. Action 中增加数据校验功能,可能它继承 ActionSupport 类,并实现 validate() 方法,产生的错误放到 ActionSupport 类的 fieldErrors 域中,由 OGNL 负责输出。有错误请求将转发到 input 逻辑视图。Struts2 的 默认已提供了输出校验错误的能力。是否觉得这种校验忒不尽人情了,别急,Struts2 可让你完全用配置来校验表单的,让你的 Action 还是那个 Action (继承 ActionSupport,无须实现 validate() 方法),只需写一个 ActionName-validattion.xml 文件扔在与 Action 同位置的目录中即可,这实质就是用的基于 XWork 的验证框架。 1. WebWork 的核心控制器是 ServletDispatcher,映射到 *.action 的 即可。在 WebWork 与 Struts2 的 struts.xml 和 perties 相对应的分别是 xwork.xml 和 perties,文件内容几乎一样,只几个关键字的差异。 2. Struts2 的 struts.xml 中 的 name 属性相当于 struts1 的 的 path 属性,但在这里不需要以 / 开始。 3. Action 中使用业务逻辑组件实例时,通常不直接 New,而会通过工厂方法或 IOC 容器。虽然 WebWork 有 IOC 容器,但 Struts2 通常会使用 Spring 的 IOC。 4. 可把 struts.xml 拆成多个文件,如 struts-part1.xml、struts-part2.xml . 等,然后在 struts.xml 中逐个 、 . 即可。看看 struts2-core-x.x.x.jar 中的 struts-default.xml 为你内建了多少东西吧。 5. Struts2 的官方说是它要求在支持 Servlet2.4/JSP2.0 的容器中运行,不过我仍然把那个简单的例子(web.xml 中用 web-app_2_3.dtd) 放到 Tomcat 4.1.30(支持到 Servlet2.3/JSP1.2) 下运行了一番,能正常工作,不知可能产生的问题有哪些。 6. Struts2 还提供一种类似 Eclipse 那种可插拔的方式来安装插件,看到下载的 Struts2 的 lib 目录下有好多 struts2-xxx-plugin.jar,这些包中都有一个 struts-plugin.xml(就是一个 struts.xml 配置文件),当把 struts2-xxx-plugin.jar 拷入到 WEB-INF/lib 下,这个 struts-plugin.xml 就会自动被加载。你也可以像这样做自己的插件包。perties 中属性 struts.configuration.files=struts-default.xml,struts- plugin.xml,struts.xml。 7. perties 中本人认为比较重要的属性 struts.action.extension、struts.serve.static.browserCache、 struts.enable.SlashesInActionNames、struts.devMode、struts.i18n.reload、 struts.configuration.xml.reload、struts.custom.i18n.resources、 struts.i18n.encoding。好多属性值都支持逗号分隔的多个值。默认的属性配置在 perties。 8. 默认情况,*.action 请求交给 Struts2 处理,你也可以改成其他扩展名,只要改 perties 中的 struts.action.extension 属性值,如 struts.action.extension=unmi,action,则*.unmi和*.action都会被 Struts2 处理了。 9. Struts2 比起 Struts1 来在开发时不仅改了 struts.xml 不用重启应用,就连改了国际化资源文件都可以不需要重启应用。设置 struts.i18n.reload = true 即可。 10. Struts2 提供了两种方式来管理 Struts2 属性,既可以写在 perties,也可以写在 struts.xml 中配置为 constant 元素,如 。相信大多数人还是倾向于写在 perties 中。 1. 按这个顺序加载 Struts2 的常量,struts-default.xml、struts-plugin.xml、struts.xml、web.xml;后加载的会覆盖前面的同名常量。强烈不推荐在 web.xml 中配置 Struts2 常量。 2. Struts1 中有一种 Action 类型是 ForwardAction,而在 Struts2 中相应的配置方式是 /showcase.jsp,Showcase.action 直接映射到 /showcase.jsp。 3. struts.xml 中 的 namespace (命名空间) 相当于 Struts1 的模块的概念,但比 Struts1 的模块间切换要便。例如,对于以下的配置 因 action GetBooks 所在的包指定了命名空间,所以 URL 就需要 /book/GetBooks.action 与它映射了。 如果未指定命名空间或指定为 就是默认命名空间,指定 / 就是根命名空间,URL 就应该是 /GetBooks.action。配置在默认命名空间中的 Action 相当于全局的,即类似于 Struts1 的 。也就是说当找不到指定命名空间(例如 /barspace/bar.action) 中的 Action (bar.action) 时,就会尝试去默认命名空间 () 里去找。 4. 系统不会严格区分 Action 里哪个属性是用于封装请求参数的属性,那个属性是封装处理结果的属性。对系统而言,封装请求参数的属性和封装处理结果的属性是完全平等的。 5. Struts2 的 Action 可以是一个 POJO,可以实现 Action 接口,也可以继承 ActionSupport。实际上 ActionSupport 类是 Struts2 默认的 Action 处理类,就是说,配置 Action 时未指定 class 属性时,系统自动指定为 ActionSupport 类。 6. Struts2 中要访问 Servlet API 必须借助于 ActionContext 类,其中有访问对 HttpServletRequest(request),HttpSession(session),ServletContext(application) 进行操作的方法 (操作的是各自的 attribute 属性),不过还没发现如何操作 HttpServletResponse(response) 对象。注意,这些方法都转换成了对 Map 实例的操作,而非真实的 Servlet API 实例,Struts2 会完成与实际存储的映射,所以 Action 仍然是脱离 Servlet API 的。ActionContext 直接的 get() 和 put() 方法针对的是 request 的属性。 7. Struts2 也可以直接访问 Servlet API 实例,让你的 Action 实现后面其中一个接口就能获取到相应 Servlet API 实例:ServletContextAware、ServletRequestAware、ServletResponseAware。注意要实现的接口 方法。如果觉得实现接口的方式麻烦,那么可以借助 ServletActionContext 的方法来拿到 Servlet API 的各个实例。这样却是让 Action 与 Servlet API 耦合起来了。 8. 即使我们在 Struts2 的 Action 中获得了 HttpServletResponse 对象,也不要尝试直接在 Action 中生成对客户端的输出,没效果的,因为 Action 只是一个控制器,它并不直接对浏览者生成任何响应。这也是为什么 ActionContext 未提供对 HttpServletResponse 的操作,只是操作 Cookie 要用到 response。在 Struts1 中,如果 Action 返回 null 时,可以通过 response.getWriter().println(Hello World.); 输出内容到页面。 9. Struts2 也有像 Struts1 那样的对 Action 动态方法调用的特性,它是通过指定 form 的 action=ActionName!methodName.action 来实现的,例如某表单的 action=Login!regist.action,提交后将会调用 name=Login 的 Action 类的 regist() 方法,而非默认的 execute() 方法。这种方式可以在一个 Action 中包含多个处理逻辑。是不是 Struts1 要方便,不需要在配置文件中对这个 Action 配置额外的属性。 10. 可为 action 配置指定一个 method 属性,同上,这种方式也在一个 Action 类中定义多个逻辑,每个处理方法映射成一个逻辑 Action,有不同的 name 属性,非常类似于 Struts1 的 MappingDispatchAction。缺点就是不像上面那样,被分开的多个逻辑 Action 不能共享 配置,并且 action 配置的 class 属性值产生冗余。 1. 动态 Action: 元素的一个前所未有的特性是,name 属性可以用通配符,class 和 method 属性中可以用 name 中的匹配参数,0/1 的形式。举两个例子说明: URL 是 registAction.action 时,会执行 LoginRegistAction 类实例的 regist() 方法 URL 是 Book_save.action 时,会执行 actions.BookAction 类实例的 save() 方法 说 明:1,2是用来匹配 name 属性中的 *,这和正则表达式一样的,0 表示的完整的 name 属性值。这也是托 Struts2 的每请求产生新的 Action 的实例才能这么用的,试想一下,Struts1 是没法针对通配符来预先加载好所有的 Action 实例的。 可由此定义一个能用的 Action, 里也能用参数。 /1.jsp 2. 关于在 中使用通配符时的校验文件命名规则。校验文件的搜索规则是: -validation.xml 为 name 属性值 -validation.xml 同时有这两个文件时,后面的规则能与前面的规则叠加或覆盖,例如 中有name域的校验, 中有password域的校验,这两个文件同时存在 所在路径时,会同时校验name和password域。 例如对于 URL 是 registAction.action 时,会搜索校验文件 LoginRegistAction-registAction-validation.xml 和 LoginRegistAction-validation.xml。 3. 使用通配符就会涉及到 URL 与哪个 Action 匹配的问题。例如匹配有name为 *、*Action、LoginAction 的 ,如果 URL 与某个 Action 的 name 完全相同(如 LoginAction.action),否则按顺序来匹配,而不是按匹配度来对应。如 abcAction.action 会匹配到 *,而不是 *Action。 4. 可配置默认的 Action,URL 匹配不到对应的 Action 时就用它,用 配置在 中。 5. Struts2 支持两种 ,配置在 中的局部 result,配置在 中的全局 result。 默认的 name 属性是 success;默认的 type 属性是 dispatcher,即使 JSP 类型。 6. type=plaintext 的 会显示页面的源文件,如果其中有中文一般会产生乱码,这时候可设置它的 charSet 属性为 GBK,用 标记。 7. 的 dispatcher 和 redirect 类型的区别就是一个是转发(带请求参数、属性、址址栏不变)和重定向(丢失请求参数、属性、重新产生请求,所以地址栏会变)。 8. redirect-action 类型是重定(不是转发)向到一个 Action 上,那么要为 指定两个参数 actionName 和 namespace。简写为 actionName。这种类型相当于在 Struts1 中的 /anotherAction.do 写法。当然在 Struts2 中也可以用 redirect 类型写成相同的形式。 9. 动态结果资源有两种,根据 的 name 属性的模式匹配后的参数和请求参数决定结果。 /1.jsp URL 为 crud_delete.action 处理成功后会转到 delete.jsp 页。 /show$user.type 要在 ShowAction 的设置了属性 $user.type。例如 $user.type 设置为 admin,就会转到 showadmin.jsp 页。 10. Struts2 的 、 意义与效果完全对应于 Struts1 的 、 。 1. Struts2 的 Action 中可直接用属性来封装请求参数和处理结果,此谓之属性驱动。也可以像 Struts1 那样使用专门的 ActionForm 来处理请求参数和结果,只不过 Struts2 用的是一个更单纯的 POJO,这就做模型驱动;此时的 Action 需要实现 ModelDriven 接口,并实现其 getModel() 方法将 Action 与对应 Model 相关联。 2. 例子说明采用模型驱动的 Action (UserBean 是一个普通 JavaBean,其中定义了 username 和 password 两个属性): public class LoginAction implments Action, ModelDriven UserBean model = new UserBean(); public UserBean getModel() return model; 上面例子使用了泛型,Struts2 的 Action 要使用一个模型不需要在配置文件中作额外的配置。 3. 请求参数自动封装到模型中是由配置 struts-default.xml 中的 ModelDrivenIntercepter 来完成的。要输出模型中值时用标记 。而倘若写成了,Struts2 也会作智能处理,要是这个 Action 中未定义 username 属性,并且彩用了模型驱动模式,也会输出模型 model.username 属性,就像 Struts1 显示 ActionForm 一样可不写 name 属性。 4. Struts2 的异常处理,基本和 Struts1 一样的思维,都提供了声明式异常处理方式,在 struts.xml 中配置。Struts2 的 、 分别与 Struts1 的 、 对应,作用都是声明 Action 中出现何种类型的异常,转到对应页面,你的 Action 的 execute() 方法只管 throws Exception 就行,剩下的事框架帮你处理。 5. 异常信息的输出, 输出异常对象本身; 输出异常堆栈信息,这是 Struts1 没有的功能; 输出异常的 message 属性。至于标签输出异常国际化消息,可就要借鉴前面的知识稍加斟酌一番,其实就是:如 execute() throw new Exception(name.error),要输出 name.error 对应消息用 即可,如果找不到 name.error 对应消息,会直接把 name.error 原本输出。 6. 页面请求数据或待显示的结果(它们总是字符串)与Java对象之间要一个类型转换器,例如,2007-01-01 提交后就是一个 Date 对象,Unmi,000 一提交就是一个 UserBean 对象(Unmi和000分别对应 UserBean 的用户名和密码),用 显示这个 UserBean 对象形式为 Unmi,000。可想而知,Struts2 肯定为我们内置了不少类型转换器。 7. 可以自定义类型转换器,实现 TypeConverter 接口或继承 DefaultTypeConverter 类。一般采用继承的方法。注意 DefaultTypeConverter 的 Object convertValue(map context, Object value, Class toType) 方法的写法,了解该方法的参数及返回值的类型与意义;该方法中依据 toType 的类型分别实现两个方向的转换逻辑,如果是从请求到 Java 对象的转换时,value 参数是一个字符串数组,实质是用 request.getParameterValues(name) 获取的值。 8. 自定义的类型转换器可注册为局部的(为某些个 Action 所用)或全局的(为所有 Action 所用)。局部类型转换器的注册方式是提供一个名为 ActionNperties 放在该 Action 的 class 所在路径下(记得校验文件也是放在同样的位置)。这个文件的内容格式为: Action中的属性名=类型转换器的全限类名 例如: user=com.unmi.struts2.converter.UserConverter user 该 Action 中的属性的名称,对该 Action 中的 user 属性用 UserConverter 转换。可有多行,分别为不同的属性设置转换器。 9. 注册为全局的类型转换器的方法。提供一个 perty 放在 classpath 下(基本就是 WEB-INF/classes 下),然后里面可加多个 属性类型=类型转换器的全限类名。如 com.unmi.vo.User=com.unmi.struts2.converter.UserConverter com.unmi.vo.User 为 Action 中的属性类型,碰到 User 类型属性就用 UserConverter 转换。可有多行,分别用于转换不同的属性类型。 10. 再回过头来与 Struts1 作个对比,Struts1 的类型转换器只能注册全局的,而不能只为个别 Action 服务,并且要通过编写代码来注册,注册代码如下: ConvertUtils.register(new DateConverter(), Date.class); 1. 前面讲的自定义类型转换器是基于 OGNL 的 DefaultTypeConverter 类并实现 convertValue() 方法,两个转换方向的逻辑都写在这一个方法中。而 Struts 2 为我们提供了一个 DefaultTypeConverter 的抽象子类 StrutsTypeConverter 来继承,并实现其中两个抽象方法 convertFromString() 和 convertToString(),这要简单易懂。对比 Struts 1 的转换器是要实现 mons.beanutils.Converter 接口,以及它的 convert() 方法的。 2. 注意,上面的 convertFromString() 的第二个参数是一个字符串数组,所以可为请求的数组(如请求串为 ?u=1&u=2&u=3)定义转换器,Action 中相应的属性就应为数组或 List,这一方法的返回值也该为相应的类型(数组或List,要通过第三个参数 toClass 来判断是返回数组还是 List 了)。 3. 字符串(如 user,pass) 转换成 Action 中的复合属性(如 User user) 前面是自定了类型转换器。除此之外,还可以 Struts 2 内置的 OGNL 表达式,更简单的转换,不用写转换器。例如,你的 Action 有属性 User user,只要在 jsp 页面的输入框命名为 和 user.pass 即可: 或用标签: 或用标签: 提交后,Struts 2 即会帮你构造 User 对象(user = new User(),并赋上属性值(user.setName(),user.setPass(),最后 user 对象赋给 Action (xxxAction.setUser(user)。所以要明白有三个必备的东西: 1) User 要用一个默认构造方法 2) User 要有对应 name 和 pass 的设置方法 setName() 和 setPass() 3) Action 要有 user 属性的设置方法 setUser(),getUser() 也是要的,至于功用后面能看到。 其实在 Struts 1 中也有这种用法,不过那是在 BeanUtils 中实现的。 4. 如果 Action 中的属性是 Map users; 那么与此对应的表单写法就是:(用标签来写) 应该不难想像,这个表单提交后,users 中存储的是什么吧! 如果是对于 Action 中的 List 属性,List users; 那么与此对应的表单写法就是: 5. 归纳前面3、4、5 几点,Struts2 的 Action 在设置每一个属性时都会 get 一下相应的元素 getUser() 或 getUsers()。 对于 3,在设置 和 user.pass 之前都会 getUser() 来获取 user 属性,如果 user 为 null 就构造 User 对象,然后设置相应的值。假如声明的时候就已构造好 User 对象,如有其他属性如 age=18,并不会被覆盖。 对于 4 和 5,也是在设置每一个属性前都会调用 getUsers() 判断声明的 Map 或 List 是否为 null,是则构造对应的 HashMap 或 ArrayList() 对象;接着根据 Key 或下标去获取相应位置的元素,如果不存在或为 null 则构造之,然后设置相应属性值。由此可见,若某元素的某个属性未重设值则保留原值,若原来Map或List 已有多个元素,也只会改变到 Key 或索引所对应元素的某个属性。对于 List 有可能出现跳空的情况,如页面只有索引不从 0 开始 提交后就会发现,List 属性 users 的第一个元素为 null 了。同时如果尝试一下,你就会发现这里的 List 不能替代为数组 User users。 这种样法,可在 Struts 1 中实现,但要略施些小节,见我的另一篇日志:提交多行数据到Struts的ActionForm的List属性中 ,行为表现完全一致,只是换到 Struts 2 中一切都不用自己操心。 6. 看第四点,Action 之所以知道该构造什么类型的元素完全是由泛型告诉它的。如果不用泛型(比如用的是 JDK1.4),Action 中仅仅声明的是 Map users; 或 List users; Action 该如何处理呢?它也不知道,只能够帮你构造出无类型的 HashMap 和 ArrayList(),填充不了元素。这就必须在局部类型转换的配置文件中来指定集合元素的类型。例如 Action 为 LoginAction,就要在 LoginAperties 中声明了,格式如下: #Element_xxx=复合类型,基中 Element 是固定的,xxx 为属性名 #下面表示为 List 属性 users 的元素为 com.unmi.vo.User 类型 Element_users=com.unmi.vo.User 对于 Map,须分别指定 Key 的类型和 Value 的类型 #Key_xxx=复合类型,基中 Key 是固定的,xxx 为 map 属性名,下面写成 String 都不行的 Key_users=java.lang.String 指定 Map 的 Value 的类型与指定 List 元素类型是一样的 Element_users=com.unmi.vo.User 难怪 Struts 2 要与 1.5 以上 JDK 使用,泛型比配置来得方便。如果硬要用 1.4 JDK,就只有配置类型了,会多很多 conversion 文件的。在 提交多行数据到Struts的ActionForm的List属性中 中类型的确定由 AutoArrayList() 的构造参数完成。 7. Set 是无序集合,所以无法像 List 那样用数字下标来访问,幸好 Struts 2 可为其指定索引属性。例如,LoginAction 声明为 Set users; (这里好像用泛型只能省得了 Element_users 说明,KeyProperty_users 少不了)。则需在 LoginAperties 中写下: #指定 Set 的元素类型 Element_users=com.unmi.vo.User #KeyProperty_集合属性名=集合元素的索引属性名,这里为 User 的 name 属性 KeyProperty_users=name 此时提交页面这么写,最好提交前能根据输入的用户名自动修动输入框的 name。 用户名: 密码: 显示的时候页面可用标签 用户名: 密码: 注意前面,访问 Set 元素是用的圆括号,而不同于 Map、List、数组是用中括号。我想一般也犯不着非要用 Set 而不用 List,Struts 2 中用 Set 比在 Struts 1 中似乎还麻烦。 8. Struts 2 内建了一批转换器:boolean、char、int、long、float、double 和它们的包装类型;Date,日期格式使用请求所在 Locale 的 SHORT 格式;数组,默认元素为字符串,其他类型则要转换每一个元素?(好像是一次性转换完成的); 集合,默认元素为字符串 XWorkList(String.class, Object),其他如 List ids,类型为 XWorkList(Integer.class, Object),XWorkList 继承自 ArrayList。 9. 类型转换出错由 Struts 来帮你处理,在默认拦截器栈中提供了 conversionError 拦截器,不用你写一点代码逻辑。conversionError 在出错时将错误封装成 fieldError,并放在 ActionContext 中。你所要做的就是遵循它的规则,1) 你的 Action 要继承自 ActionSupport,2)在 struts.xml 中声明名为 input 的 result,出错时会在 input 逻辑视图显示信息。3)尽量用标签来写输入域(如),这样转换出错后,就会像校验失败一样把错误信息显示在每个输入框上面(视模板而定),否则要手工用 输出在某处。 默认时输出错误信息为(比如是属性 number,输入的是字符串时):Invalid field value for field number.你可以改变默认显示,在全局国际化资源文件中加上 xwork.default.invalid.fieldvalue=0字段类型转换失败!。在某些时候,可能还需要对特定字段指定特别的提示信息,那么在名为 ActionNperties 的局部资源文件中加上 invalid.fieldvalue.属性名=提示信息 (如 invalid.fieldvalue.number=数量格式错误) 10. 最后是集合属性转换错误时的显示,对于页面中的同名输入框,有多个出错误,如果手工用 只会显示一条错误,但要是输入页是用标签(如),仍会在每一个出错的输入框上都提示。至此类型转换的内容也就完结了。 1. Struts
温馨提示
- 1. 本站所有资源如无特殊说明,都需要本地电脑安装OFFICE2007和PDF阅读器。图纸软件为CAD,CAXA,PROE,UG,SolidWorks等.压缩文件请下载最新的WinRAR软件解压。
- 2. 本站的文档不包含任何第三方提供的附件图纸等,如果需要附件,请联系上传者。文件的所有权益归上传用户所有。
- 3. 本站RAR压缩包中若带图纸,网页内容里面会有图纸预览,若没有图纸预览就没有图纸。
- 4. 未经权益所有人同意不得将文件中的内容挪作商业或盈利用途。
- 5. 人人文库网仅提供信息存储空间,仅对用户上传内容的表现方式做保护处理,对用户上传分享的文档内容本身不做任何修改或编辑,并不能对任何下载内容负责。
- 6. 下载文件中如有侵权或不适当内容,请与我们联系,我们立即纠正。
- 7. 本站不保证下载资源的准确性、安全性和完整性, 同时也不承担用户因使用这些下载资源对自己和他人造成任何形式的伤害或损失。
评论
0/150
提交评论