表现层设计考虑
会话管理
在客户端保存会话状态
优点:
①实现容易
②保存状态比较少时,效果好
③需要多台Server实现负载均衡时,无需在Server间复制会话状态。
实现策略:
①HTML隐藏字段
②HTTP Cookie
③直接放进URL里
1. HTML隐藏字段的缺点:
①需保存状态较多时,缺点尤其明显:系统性能下降;状态在请求和响应中都要通过网络往复传输。
②保存的状态只能是字符串形式的值,任何对象引用必须“字符串化”;加密处理。
2. HTTP Cookie的缺点:
①同上
②同上;对于Cookie header的大小有限制,也就限制了能够保存的数据量。
安全问题
在表现层保存会话状态
session ID
优点:
①状态保存在Server,不会受到数据量大小或是数据类型方面的限制。
②会话状态不会在每个请求中都通过网络传输一次,系统性能不会受到影响。
③在Server保存会话状态,可以按照需要和代价,在繁、简间灵活选择,兼顾可扩展性和性能。
缺点:
需要在集群的多个Server间复制会话状态。
在业务层或资源层保存会话状态
|| ||
EJB组件 关系型数据库
控制客户端访问
保护视图
策略:
①加入一种应用逻辑
②配置运行时系统
常见方法:
①采用一个控制器
②在视图中直接加入保护
1. 在视图内部中实现保护
a. 阻塞对整个资源的访问
b. 只阻塞对局部资源的访问
2. 每页加入“要么全部 - 要么没有”的保护
3. 加入对页面局部的保护
a. 根据用户角色不显示视图的局部内容
b. 根据系统状态或错误条件不显示视图的局部内容
通过配置实现保护
web.xml
1. 通过标准安全限制实现资源保护
2. 通过一个简单、通用的配置实现资源保护
只需把那些限制访问的资源放到Web应用的/WEB-INF/目录下即可。
重复的表单提交
同步器令牌(又名“时曾相识”令牌)
验证
客户端+服务器端验证
在客户端验证
JavaScript
在服务器端验证
1. 基于表单的验证
容易实现,比较高效;应用系统越大,造成的重复代码越多。
2. 基于抽象类型的验证
从状态中抽象出类型和限制信息,放入一个通用的框架中。
例如,可以使用一个组件或者一个子系统来封装验证逻辑。
缺陷:
①效率、性能上可能具有潜在的损失;
②通用解决方案强大,但难于理解、不易维护。
助手类属性——完整性和一致性
JavaBean助手类通常用于存放由客户端请求传来的中间状态。
<jsp:setProperty name="helper" property="*"/>
当请求中的参数值为空的时候,技术规范规定,不对该属性的值做任何变化。
解决方案:
在多次请求之间重置JavaBean的所有状态。
表现层不佳实践
多个视图中都包括控制代码
参照解决方案:
合并控制代码,引入一个控制器和相关的命令助手。
Ch4,“引入控制器”、“隔离不同逻辑”
Ch6,“命令与控制器策略”、“视图助手”
把表现层的数据结构暴露给业务层
表现层的数据结构,例如HttpServletRequest,应该只限于表现层。
参照解决方案:
Ch4,“对业务层隐藏表现细节”
把表现层数据结构暴露给业务领域对象
参照解决方案:
同上
允许重复提交表单
参照解决方案:
需要监管、控制请求流程。
Ch4,“引入同步器令牌”
把敏感资源暴露给客户端的直接访问
参照解决方案:
保护敏感资源、禁止客户端直接访问。
Ch4,“对客户端隐藏资源”
假定<jsp:setProperty>会重置Bean属性
参照解决方案:
记住<jsp:setProperty>的这种不太直观的赋值机制,在使用bean属性之前先做初始赋值。
创建出“胖控制器”
参照解决方案:
Ch4,“引入控制器”,Ch6,“命令与控制器策略”;
Ch4,“隔离不同逻辑”,Ch6,“视图助手”
把视图助手当作Scriptlet使用
参照解决方案:
视图中的Java Scriptlet;使用JSTL助手;使用标记库;标记文件助手