Struts2框架
Struts
一、Struts2 概述
- 应用于
JavaEE
三层结构中web
层框架Struts2
框架是在Struts1
和WebWork
基础之上发展的全新框架- 有一个过滤器,根据不同的操作,在类里面写不同的方法
1.1 - 简单案例
1.1.1 - 引入 Jar 包
asm-7.1.jar
asm-commons-7.1.jar
asm-tree-7.1.jar
commons-fileupload-1.4.jar
commons-io-2.6.jar
commons-lang3-3.8.1.jar
freemarker-2.3.28.jar
javassist-3.20.0-GA.jar
log4j-api-2.12.1.jar
log4j-core-2.12.1.jar
ognl-3.1.26.jar
struts2-core-2.5.22.jar
1.1.2 - 新建 struts.xml
1 |
|
1.1.3 - 配置 action
1 | <struts> |
1.1.4 - 配置 filter
1 | <filter> |
1.1.5 - 书写 Java 文件
Java
文件要重写以下方法
1
2
3 public 返回类型 execute() {
}
1.2 - 过滤器
外来请求首先会被汇总到过滤器
过滤器在服务器启动时创建,执行
init
方法过滤器要做的事
过滤器会获取请求路径
截取请求路径中的有效字符串
到
src
下面找到struts.xml
使用dom4j
进行解析用截取到的字符串与
struts.xml
中的action
进行匹配如果匹配到对应的
action
则根据其中的全路径,反射创建对应Java
类
反射:
Class clazz = Class.forName("全路径"); // 反射创建类 Method m = clazz.getMethod("execute"); // 获取方法 Object obj = m.invoke(); // 方法执行并获取返回值
1
1将返回值与该
action
中的result
进行匹配
- 如果匹配成功,则跳转到相应页面
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
### 1.2.1 - init()
加载自己创建的配置文件和 `struts2` 自带配置文件
### 1.2.2 - doFilter()
**request = warpRequest(request);**
增强
## 1.3 - struts.xml
### 1.3.1 - <package >
类似于代码包,用于区分不同的 `action` ,必须首先写 `package` 标签,在 `package` 标签中才能配置 `action`,在一个 `package` 中可以有多个 `action`
#### - name
和功能本身没有任何关系,只要重复,可以随便取
#### - extends
属性值是固定的,写了这个属性之后,在 `package` 中配置的 `action` 才具有 `action` 该有的功能
#### - namespace
要和 `action` 标签的 `name` 构成访问路径,默认值是 `/`
### 1.3.2 - <action >
配置 `action` 的访问路径及 `Java` 文件的绑定
#### - name
要和 `package` 标签的 `name` 构成访问路径
可以用通配符 ***** 进行匹配
#### - class
`action` 所绑定 `Java` 文件的全路径
#### - method
指定执行 `Java` 文件中的哪一个方法
在通配符模式下,用 `{1}` 来获取方法,获取到的方法名即 ***** 所代替的字符串
#### - action 的另外两种编写方式
- `implements Action`
- `extends ActionSupport`
### 1.3.3 - <result >
根据 `action` 方法返回值,配置到不同的路径
#### - name
和 `action` 返回值一样
#### - type
指定如何到达配置路径的方法
- `dispatcher` 请求转发,默认
- `redirect` 重定向
- `chain` 转发到 `action`
- `redirectAction` 重定向到 `Action`
### 1.3.4 - <constant >
#### - name
#### - value
另外两种常量修改方式
- 在 `src` 下创建 `struts.properties`
- 在 `web.xml` 配置
### 1.3.5 - <include >
#### - file
文件路径
### 1.3.6 - <global-results >
当有多个 `action` 返回值相同、且其 `result` 返回的内容也相同,则可以使用这个
# 二、数据处理
## 2.1 - 使用 ActionContext 类
- 需要创建 `ActionContext` 对象
- 不是 `new` 出来的
## 2.2 - 使用 ServletActionContext 类
## 2.3 - 使用 Interface 注入
```java
public class A implements ServletRequestAware {
private HttpServletRequest request;
public void setServletRequest(HttpServletRequest request) {
this.request = request;
}
}
三、数据封装
3.1 - 属性驱动
- 直接把表单提交属性封装到
action
属性- 实现步骤
- 在
action
成员变量位置定义变量 – 变量名和表单输入项的name
属性值一样- 生成变量的
setter
和getter
- 使用属性封装获取表单数据到属性里面,不能把数据直接封装到实体类
3.2 - 模型驱动
使用模型驱动方式,可以直接把表单数据封装到实体类对象里面
实现步骤
action
实现接口ModelDriven
实现接口里的方法
getModel
在
action
里创建实体类对象```java
public class A extends ActionSupport implements ModelDriven <类型> {
1
2
3
4
5
6
7
8
9
10
11
private 类型 a = new 类型();
public 类型 getModel() {
return a;
}
}属性驱动和模型封装不能同时使用,如果同时使用,只会执行模型封装
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
## 3.3 - 表达式封装
- 实现过程
- 使用表达式封装可以把表单数据封装到实体类对象里面
- 在 `action` 里面声明实体类
- 生成实体类的 `setter` 和 `getter` 方法
# 四、Ognl 概述
- `EL` 表达式:在 `JSP` 中获取域对象里面的值
- `Ognl` 表达式:在 `Struts2` 实现值栈数据
- 一般把 `Ognl` 在 `Struts2` 里操作,和 `Struts2` 标签一起使用操作值栈
- 不是 `Struts2` 的一部分,只是经常和 `Struts2` 一起使用
## 4.1 - 获取值栈对象
### 4.1.1 - 常用方式
使用 `ActionContext` 类里面的方法得到值栈对象
- 获取 `ActionContext` 对象
- `ActionContext context = ActionContext.getContext();`
- 调用方法得到值栈对象
- `ValueStack stack = context.getValueStack();`
## 4.2 - 值栈内部结构
### 4.2.1 - 第一部分:root
- 结构是 `List` 集合
- 一般操作的都是 `root` 里的数据
### 4.2.2 - 第二部分: context
- 结构是 `Map` 集合
- 很少操作
- 几个键值对
- `request`:`request` 引用
- `session`:`HttpSession` 引用
- `application`: `ServletContext` 引用
- `parameters`:传递相关参数
- `attr`: 获取域对象
## 4.3 - 向值栈放数据
**调用 set()**
```java
ActionContext context = ActionContext.getContext();
ValueStack stack = context.getValueStack();
stack.set("key", "value");调用 push()
1 | ActionContext context = ActionContext.getContext(); |
生成 get()
1 | private String name; |
4.3.1 - 向值栈放对象
- 定义对象变量
1 private User user = new User();
- 生成变量的
get
方法
1
2
3 public User getUser() {
return user;
}
- 在执行的方法里面向对象中设置值
4.3.2 - 向值栈放 List 对象
- 定义
List
集合- 生成变量的
getter
- 在执行的方法里面向
List
集合设置值
4.4 - 从值栈获取数据
- 使用
Struts2
的标签 +Ognl
表达式获取值栈数据
<s:property value="Ognl 表达式"/>
4.4.1 - 获取字符串
action
1 | public class A extends ActionSupport { |
struts.xml
1 | <action name="自定义名称" class="action 全路径"> |
jsp
1 | <s:property value="变量名"/> |
4.4.2 - 获取对象
action
1 | public class A extends ActionSupport { |
struts.xml
1 | <action name="自定义名称" class="action 全路径"> |
jsp
1 | <s:property value="对象.属性"/> |
4.4.3 - 获取 List 对象
action
1 | public class A extends ActionSupport{ |
struts.xml
1 | <action name="自定义名称" class="action 全路径"> |
jsp
第一种方式
1 | <s:property value="list[0].属性"/> |
第二种方式
1 | <s:iterator value="list"> |
第三种方式
1 | <s:iterator value="list" var="自定义名称"> |
4.4.4 - 其他操作
- 获取 setter 方法存放的数据
1 | <s:property value="栈的key"/> |
- 获取 push 方法存放的数据
1 | <s:property value="[下标].top"/> |
4.5 - 两种符号的使用
4.5.1 -
先在 action 向域中添加对象
1 | public String execute() throws Exception { |
struts.xml
1 | <action name="自定义名称" class="action 全路径"> |
jsp
1 | <s:property value="#context域的key.域对象名称"/> |
4.5.2 - %
在
struts2
标签里使用Ognl
表达式,如果直接在struts2
表单标签里面使用Ognl
表达式不识别,只有 % 之后才会识别
1 | <s:textfield name="" value=%{#context域的key.域对象名称}></s:textfield> |
五、拦截器
5.1 - 概述
struts2
是框架,封装了很多功能,struts2
里面封装的功能都是在拦截器里面struts2
里面封装了很多的功能,又很多拦截器,不是每次这些拦截器都执行,每次执行默认的拦截器- 默认拦截器位置:
struts2-core-version.jar/struts-default.xml
- 在
action
创建之后,执行之前调用
5.2 - 底层原理
两大思想
Aop
思想- 职责链设计模式
- 要执行多个操作,有添加、修改、删除
- 首先执行添加操作,添加之后执行修改操作,最后执行删除操作
通过 AOP 将拦截器加入到执行过程
5.3 - 重要的概念
5.3.1 - 过滤器和拦截器
- 过滤器:理论上可以拦截任意内容
- 拦截器:只可以拦截
action
5.3.2 - Servlet 和 action
servlet
默认第一次访问时创建,创建一次,单实例对象action
每次访问时创建,创建多次,多实例对象
5.4 - 自定义拦截器
5.4.1 - 继承类
1 | class A extends AbstractInterceptor { |
5.4.2 - 重写方法
1 | void init(); |
5.4.3 - 建立关系
- 在要拦截的
action
标签所在的package
标签里面声明拦截器
1
2
3
4 <interceptors>
<interceptor name="自定义name" class="拦截器java文件全路径"/>
</interceptors>
- 在具体的
action
标签里面使用声明的拦截器
1
2 <interceptor-ref name="上面的自定义name"/>
如果在
struts.xml
中使用自定义的,则默认拦截器不会执行
- 解决方法:手动引入默认拦截器
1
2 <interceptor-ref name="paramsPrepareParamsStack"/>自定义拦截器会对
action
里所有方法都拦截
5.4.4 - 放不拦截某些方法
1 | <interceptor-ref name="上面的自定义name"> |
本博客所有文章除特别声明外,均采用 CC BY-NC-SA 4.0 许可协议。转载请注明来自 Cin's Home!