简介:Struts2是一个用于构建企业级Java Web应用的框架,能够通过JSON插件高效地在服务器端和客户端之间交换数据。通过示例项目"Struts2Json example",展示了如何集成JSON插件到Struts2框架中,并通过配置和Action类的设计返回JSON格式的响应。文章详细说明了如何在Struts2配置文件中添加JSON插件依赖,创建返回JSON响应的Action类,以及在客户端使用JavaScript库解析JSON数据。
1. Struts2框架简介
Struts2作为Java社区中广泛使用的Web应用框架,自2001年首次发布以来,其发展历程见证了Java技术栈的变迁。它的核心设计基于MVC模式,旨在简化Web层的开发。
1.1 Struts2核心组件
Struts2框架的核心组件包括:
- Action : 业务逻辑处理的中心组件,负责接收输入并返回响应。
- Result : Action执行后的处理结果,如页面跳转或数据返回。
- Interceptor(拦截器) : 可以插入处理请求的自定义逻辑,比如权限验证。
- ValueStack(值栈) : 用于在Action和视图之间传递数据。
1.2 工作原理
Struts2通过FilterDispatcher或StrutsPrepareAndExecuteFilter将Web请求委托给Struts2框架处理。首先,请求会被拦截器链处理,然后由Action处理业务逻辑。处理结果将决定执行哪个结果(如JSP页面渲染或JSON数据返回)。
1.3 版本演进
从Struts2.0到Struts2.5,框架逐步引入了REST插件、JSON插件等增强功能,以适应现代Web开发需求。持续的迭代让Struts2能够与时俱进,满足日益复杂的业务场景。
通过本章,您将掌握Struts2的基本概念和结构,为深入学习和应用Struts2打下坚实基础。
2. ```
第二章:JSON在Web开发中的作用
JSON已经成为现代Web开发中不可或缺的一部分,无论是在前后端数据交互,还是在配置文件中,都能看到它的身影。在这一章中,我们将深入探讨JSON的作用及其在Web开发中的重要性。
JSON基础结构及优势
JSON的结构
JSON(JavaScript Object Notation)是一种轻量级的数据交换格式,它基于JavaScript的一个子集,尽管它是独立于语言的纯文本格式。JSON包含两种结构:对象(Object)和数组(Array)。对象以键值对(Key:Value)的形式存在,而数组则是有序值的列表,可以用0开始的索引来访问。
// JSON对象示例
{
"name": "JSON",
"type": "data-interchange format",
"properties": ["lightweight", "language-independent"]
}
JSON的优势
- 轻量级 : JSON文本易于阅读和编写,同时也易于机器解析和生成。
- 跨语言 : JSON是文本格式,可以使用任何编程语言轻松地处理JSON数据。
- 易于理解 : JSON使用了与JavaScript相同的语法结构,因此对于Web开发人员来说非常直观。
JSON在前后端交互中的应用
数据交换
在Web应用中,当浏览器(客户端)需要从服务器请求数据时,通常会使用AJAX技术。服务器响应的数据格式正是JSON,因为它可以很容易地被JavaScript解析并用于更新页面内容。
前后端分离的实践
JSON是前后端分离开发模式的关键。在这种模式下,前端开发人员专注于界面和用户体验,而服务器端开发人员负责业务逻辑和数据处理。JSON作为数据交换格式,实现了前后端的高效沟通。
配置文件中的JSON
不仅在动态数据交换中,JSON也常用于配置文件中。例如,Node.js的 package.json
文件描述了项目依赖和其他配置信息。在Web开发中,使用JSON格式存储配置信息,可以使得结构清晰,便于管理。
具体使用场景
API设计
Web API设计中,JSON广泛用作资源的表示方式。RESTful API中,响应数据通常以JSON格式返回。
前端JavaScript框架
现代前端框架(如Angular, React, Vue.js)在状态管理或组件间通信中,都大量依赖于JSON格式的数据。
小结
JSON为Web开发提供了一种高效、简洁的数据交换和配置方式。其轻量级、跨语言的特性,让其成为前后端交互的首选。无论是在传统的MVC架构中,还是在现代的前后端分离开发模式中,JSON都发挥着核心作用。
# 3. Struts2 JSON插件集成方法
随着Web应用的日益复杂,数据交互格式的多样化成为开发者必须面对的问题。Struts2框架本身不直接支持JSON格式的数据交互,因此集成一个JSON插件变得尤为重要。本章将详细指导如何将JSON插件成功集成到Struts2项目中,使***2框架具备处理JSON数据的能力。
## 3.1 JSON插件的选择与下载
在集成JSON插件之前,首先要选择一个合适的插件。Struts2社区提供了多种JSON插件,例如xwork2-json-plugin、Struts2-json-plugin等。选择时需要考虑插件的活跃度、兼容性、以及社区的支持情况。
一旦选定了合适的JSON插件,下一步就是在其官方网站或代码托管平台(如GitHub)上下载最新版本的插件包。这里以常用的Struts2-json-plugin为例,进行操作指导。
```bash
# 下载Struts2-json-plugin插件
wget ***
3.2 插件配置与依赖管理
下载完成后,需要将下载的jar包添加到项目的类路径中。对于大多数Java项目,可以通过Maven或Gradle等依赖管理工具来完成这一操作。
对于Maven项目,需要在pom.xml文件中添加以下依赖:
<dependency>
<groupId>com.opensymphony.xwork2</groupId>
<artifactId>struts2-json-plugin</artifactId>
<version>3.0.0</version>
</dependency>
对于Gradle项目,在build.gradle文件中添加如下依赖:
dependencies {
compile 'com.opensymphony.xwork2:struts2-json-plugin:3.0.0'
}
3.3 配置Struts2以使用JSON插件
添加插件依赖后,需要对Struts2的配置文件进行修改,以确保JSON插件能够被正确加载并集成。这涉及到修改 struts.xml
文件,以引入JSON插件模块,并设置必要的拦截器。
<struts>
<constant name="struts.objectFactory" value="org.apache.struts2.spring.StrutsSpringObjectFactory" />
<package name="default" extends="struts-default" namespace="/">
<interceptors>
<interceptor-ref name="json" />
</interceptors>
<action name="exampleAction" class="com.example.ExampleAction">
<result name="success" type="json">
<param name="root">example</param>
</result>
</action>
</package>
</struts>
上面的配置例子表明,已经添加了对JSON拦截器的引用,并通过一个名为 exampleAction
的Action类来演示如何返回JSON格式的响应。其中 <param name="root">example</param>
是告诉JSON拦截器,以哪个对象属性作为JSON数据的根节点。
3.4 与Struts2框架的兼容性调整
集成JSON插件之后,需要确保插件与现有的Struts2框架配置兼容。这可能涉及到修改过滤器配置,以确保Struts2能够处理特定的MIME类型,比如 application/json
。
<filter>
<filter-name>struts2</filter-name>
<filter-class>org.apache.struts2.dispatcher.filter.StrutsPrepareAndExecuteFilter</filter-class>
</filter>
<filter-mapping>
<filter-name>struts2</filter-name>
<url-pattern>/*</url-pattern>
<dispatcher>REQUEST</dispatcher>
<dispatcher>FORWARD</dispatcher>
</filter-mapping>
上面的配置确保了Struts2过滤器能够拦截到所有请求,并且允许它处理JSON格式的响应。 <dispatcher>
元素还允许通过FORWARD请求来传递JSON数据。
3.5 测试和验证JSON插件
集成和配置完成后,需要验证插件是否按预期工作。这通常涉及到编写单元测试或使用Postman等工具来测试JSON输出。
@Test
public void testExampleAction() {
ActionProxy proxy = ActionProxyFactory.getFactory().createActionProxy(
ActionContext.getContext().getActionInvocation().getInvocationContext().getProxy().getContainer(),
"exampleAction", null, null);
String result = (String) proxy.execute();
assertTrue(result.contains("\"example\""));
}
上面的测试代码演示了如何使用JUnit测试框架来验证 exampleAction
是否返回了正确的JSON格式。这里使用断言来检查返回的字符串是否包含JSON根对象。
3.6 总结
Struts2框架虽然强大,但其原生支持的数据格式有限。通过集成JSON插件,可以显著提升Struts2框架在Web应用开发中的灵活性和适用范围。本章详细介绍了如何选择合适的JSON插件,进行配置和集成,并提供了一些基本的配置和测试方法。在实际开发中,开发者需要根据具体需求来调整配置和优化集成效果。
请继续阅读下一章节,我们将深入探讨Struts2的配置文件中JSON插件的具体设置方法,包括拦截器配置、异常处理机制等高级配置技巧。
4. Struts2配置文件中JSON插件的设置
4.1 插件过滤配置详解
在Struts2框架中,过滤配置是确保请求正确路由到JSON插件处理的关键。首先,我们需要对过滤器链进行设置,以保证JSON相关的请求被正确捕获并处理。
4.1.1 过滤器配置的结构
Struts2默认使用 struts2.dispatcher
过滤器,该过滤器能够处理所有Struts2框架的请求。要将JSON请求单独处理,可以配置一个新的过滤器,指向特定的拦截器栈。
<filter>
<filter-name>struts2</filter-name>
<filter-class>org.apache.struts2.dispatcher.filter.StrutsPrepareAndExecuteFilter</filter-class>
</filter>
<filter-mapping>
<filter-name>struts2</filter-name>
<url-pattern>/*</url-pattern>
</filter-mapping>
为了进一步优化和控制JSON请求,可以添加自定义过滤器:
<filter>
<filter-name>jsonFilter</filter-name>
<filter-class>org.example.MyJsonFilter</filter-class>
</filter>
<filter-mapping>
<filter-name>jsonFilter</filter-name>
<url-pattern>*.json</url-pattern>
</filter-mapping>
4.1.2 过滤器的作用与配置
自定义过滤器 MyJsonFilter
需要实现 javax.servlet.Filter
接口。在此过滤器中,你可以根据需求进行一些预处理和后处理。
public class MyJsonFilter implements Filter {
public void init(FilterConfig config) throws ServletException {}
public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain)
throws IOException, ServletException {
// Pre-process code can go here
chain.doFilter(request, response);
// Post-process code can go here
}
public void destroy() {}
}
在这个过滤器中,你可能会检查请求的路径,或者对响应的内容类型进行判断和调整,以确保它们是JSON格式。
4.2 拦截器配置和优先级
Struts2框架的强大之处在于其拦截器机制。拦截器可以在Action执行前后执行自定义的业务逻辑。为了确保JSON插件正确处理数据,需要配置正确的拦截器及其优先级。
4.2.1 拦截器的类型和作用
Struts2提供了一系列拦截器,如 conversionError
, params
, token
, i18n
, chain
, modelDriven
, fileUpload
等。对于JSON插件来说, json
拦截器是必不可少的,它负责将Action的结果转化为JSON格式。
<interceptor-ref name="json" />
4.2.2 拦截器栈的构建与配置
拦截器栈是拦截器的集合,它们按照一定的顺序执行。通常,会有一个默认的拦截器栈,但针对特定需求,你可以构建自定义的拦截器栈。
<interceptor-stack name="jsonStack">
<interceptor-ref name="defaultStack" />
<interceptor-ref name="json" />
</interceptor-stack>
将拦截器添加到栈中时,需要考虑它们的执行顺序。默认栈已经预设了一组拦截器及其顺序,添加 json
拦截器时要确保它放在合适的位置,以避免执行时出现问题。
4.3 异常处理配置
无论多么完善的系统,都无法避免异常的发生。在Struts2中,可以通过配置异常处理器来优雅地处理和响应JSON相关的异常。
4.3.1 默认异常处理器
Struts2提供了一个默认的异常处理器 struts-default.xml
,它定义了一些默认的异常处理行为。你可以覆盖这些设置,以适应你的需求。
<package name="jsonPackage" extends="json-default">
<global-exception-mappings>
<exception-mapping result="jsonError" exception="java.lang.Exception"/>
</global-exception-mappings>
</package>
4.3.2 自定义异常处理器
在有些情况下,你可能需要一个更具体的异常处理策略,这时可以定义自己的异常处理器。例如,你可能想要捕获特定的异常并返回一个详细的错误消息。
public class CustomException extends Exception {
private String errorMessage;
public CustomException(String message, String errorMessage) {
super(message);
this.errorMessage = errorMessage;
}
public String getErrorMessage() {
return errorMessage;
}
}
然后,你可以创建一个Action来处理这个异常,并返回适当的JSON格式结果。
4.4 配置的测试和调试
配置完成后,需要进行测试和调试以确保一切运行正常。这包括验证过滤器、拦截器和异常处理器的配置是否按预期工作。
4.4.1 使用Struts2提供的测试框架
Struts2提供了一个测试框架,可以用来测试Action和拦截器。利用这个框架可以模拟HTTP请求和响应,确保配置的正确性。
public class JsonActionTest extends TestCase {
private MockStrutsTestCase test = new MockStrutsTestCase();
public void testJsonAction() throws Exception {
test宝贵的资料。.setActionForm(new MyForm());
test宝贵的资料。.actionForm.setField("value");
test宝贵的资料。.request.addParameter("param", "value");
test宝贵资料。.setForward("success");
test宝贵资料。.executeAction("jsonAction");
// Validate the results.
assertNotNull(test宝贵资料。.getResponseContent());
assertTrue(test宝贵资料。.getResponseContent().startsWith("{\"success\""));
}
}
4.4.2 日志和监控
在配置阶段,应该开启详细的日志记录,以便在出现问题时能够迅速定位。此外,监控Web服务器的运行状态和性能指标也是必要的。
通过以上步骤,我们可以确保Struts2框架中的JSON插件得到正确的配置和高效运行。接下来,我们将通过编写具体的Action类,将这些配置付诸实践。
5. 创建返回JSON响应的Action类
5.1 设计Action类结构
为了创建一个能够返回JSON响应的Action类,我们首先需要设计类的基本结构。在Struts2框架中,Action类负责封装业务逻辑,并提供数据给视图层。在返回JSON响应时,Action类通常需要以下几个要素:
- 属性:用于封装要返回的数据。
- 方法:处理业务逻辑。
- 注解或XML配置:定义如何将Action的结果转换成JSON格式。
表格5.1展示了Action类的基本组成部分及其作用。
| 组件 | 作用 | | --- | --- | | 属性 | 封装数据,供方法操作和JSON序列化使用 | | 方法 | 实现业务逻辑,返回处理结果 | | 注解或XML配置 | 指定结果类型,定义返回JSON的方式 |
5.2 使用注解实现Action类
下面我们将通过一个具体的例子来实现一个返回JSON的Action类。首先使用注解的方式定义Action类的属性和方法。
import com.opensymphony.xwork2.ActionSupport;
import com.opensymphony.xwork2.Preparable;
import com.opensymphony.xwork2.validator.annotations.Validations;
import com.fasterxml.jackson.annotation.JsonIgnoreProperties;
@JsonIgnoreProperties(ignoreUnknown = true)
public class JsonAction extends ActionSupport implements Preparable {
private static final long serialVersionUID = 1L;
private String name;
private int age;
private String email;
@Override
public void prepare() throws Exception {
// Preparing logic here...
}
@Validations(
requiredStrings = {
@RequiredStringValidator(field = "name", message = "Name is required"),
@RequiredStringValidator(field = "email", message = "Email is required")
}
)
public String execute() throws Exception {
// Business logic here...
return SUCCESS;
}
// Getters and setters for all fields
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public int getAge() {
return age;
}
public void setAge(int age) {
this.age = age;
}
public String getEmail() {
return email;
}
public void setEmail(String email) {
this.email = email;
}
}
代码分析
在上面的代码中,我们创建了一个名为 JsonAction
的类,继承自 ActionSupport
并实现了 Preparable
接口。 @JsonIgnoreProperties(ignoreUnknown = true)
注解告诉框架忽略JSON中未定义的属性,防止反序列化时发生错误。 @Validations
注解用于在执行 execute
方法前进行数据校验,其中包含了对 name
和 email
字段的非空验证。 execute
方法包含业务逻辑,并在执行成功时返回 SUCCESS
。
5.3 注解与XML配置结合使用
注解提供了一种快速和简洁的方式来配置Action,但在复杂的场景下,使用XML配置可能更灵活。下面我们展示如何结合注解和XML配置来实现同样的功能。
<action name="jsonAction" class="com.example.JsonAction">
<result name="success" type="json">
<param name="root">jsonResult</param>
<param name="excludeProperties">age</param>
</result>
</action>
代码分析
在Struts2的XML配置文件中,我们定义了一个名为 jsonAction
的Action,指定其对应的处理类为 com.example.JsonAction
。在 <result>
标签内,我们通过 type="json"
指定返回类型为JSON,并通过 <param>
标签排除 age
属性。 <param name="root">jsonResult</param>
表示返回的JSON对象的根节点名为 jsonResult
。
结合注解与XML配置,可以使得Action类的配置更加灵活,也更易于管理和维护。
5.4 实现与模型对象的交互
在实际应用中,Action类常常需要与后端的模型对象进行交互。下面我们将通过一个示例来展示如何在Action中与模型对象进行交互,并返回JSON数据。
public class UserModel {
private String username;
private String email;
// Getters and setters
}
public class JsonAction extends ActionSupport {
// Other fields, annotations, and methods remain unchanged
private UserModel userModel;
public String execute() throws Exception {
// Assume we have a service method to fetch user details
userModel = userService.getUserDetails(name);
return SUCCESS;
}
// Getters and setters for userModel
public UserModel getUserModel() {
return userModel;
}
public void setUserModel(UserModel userModel) {
this.userModel = userModel;
}
}
代码分析
在 JsonAction
类中,我们添加了一个 userModel
属性,它是一个 UserModel
对象。 execute
方法中的逻辑调用了一个服务层的 getUserDetails
方法,该方法根据用户名返回用户的详细信息。返回的 userModel
对象将会被自动序列化为JSON格式,因为我们的Action类配置了返回类型为JSON。
通过上述步骤,我们就成功创建了一个能够返回JSON响应的Action类,并与模型对象进行了交互。在实际开发中,用户可以根据具体需求调整Action类的设计,以适应不同的业务场景。
6. 使用OGNL表达式序列化属性为JSON
OGNL表达式简介
OGNL(Object-Graph Navigation Language)表达式是一种功能强大的表达式语言,它允许你通过简单的语法访问和操作数据,而不需要编写复杂的代码。OGNL在Struts2框架中扮演了重要的角色,特别是在数据的传递和展示上。OGNL可以方便地从Action类中获取数据,并通过序列化将这些数据转换成JSON格式,以满足现代Web应用中前后端分离的需求。
OGNL表达式的基本语法
OGNL表达式的基本语法通常包括以下几个部分:
-
#
符号表示OGNL表达式的开始。 - 对象属性访问,例如
#object.property
。 - 静态方法调用,例如
#class.staticMethod(arg1, arg2)
。 - 集合和数组操作,例如
#collection[index]
或#map['key']
。 - 运算符,例如
+
,-
,==
,!=
,&&
,||
等。
配置OGNL序列化为JSON
为了在Struts2中使用OGNL表达式序列化对象为JSON格式,首先需要确保已经正确配置了JSON插件。在Struts2的 struts.xml
配置文件中添加如下配置:
<package name="jsonPackage" extends="json-default">
<!-- 其他配置 -->
</package>
这段配置继承了 json-default
包,该包提供了默认的JSON支持。接下来,需要确保OGNL库被包含在项目中,通常这个库会在引入Struts2 JSON插件时一并添加。
序列化对象属性为JSON
在Action类中,可以使用OGNL表达式来序列化对象的属性为JSON格式。假设我们有一个 User
对象,它有两个属性: username
和 age
。在Action方法中,我们可以这样序列化:
public class UserAction extends ActionSupport {
private User user;
public String execute() {
// 假设已经设置了user对象的属性
return SUCCESS;
}
// Getter和Setter方法
public User getUser() {
return user;
}
public void setUser(User user) {
this.user = user;
}
}
接下来,我们可以在 struts.xml
配置文件中设置OGNL表达式:
<action name="getUserJson" class="com.example.UserAction">
<result name="success" type="json">
<param name="root">user</param>
<param name="includeProperties">username, age</param>
</result>
</action>
在这个配置中, getUserJson
动作被定义为返回JSON格式的响应。 root
参数指定了OGNL表达式的根对象,而 includeProperties
参数指定了需要序列化的属性。
处理复杂的序列化需求
在处理复杂对象时,可能需要自定义OGNL的序列化行为。例如,当需要忽略某些属性,或者需要对特定属性进行特殊的格式化时,可以使用OGNL的 @ognl.OgnlContextAccessor
注解来编写自定义的序列化逻辑。这种情况下,可以通过扩展JSON插件提供的拦截器来实现。
示例代码演示
下面是一个完整的示例,演示了如何在Struts2中使用OGNL表达式序列化对象为JSON格式:
package com.example;
import com.opensymphony.xwork2.ActionSupport;
import com.opensymphony.xwork2.interceptor.annotations.InputConfig;
import com.opensymphony.xwork2.validator.annotations.RequiredStringValidator;
public class User {
private String username;
private int age;
// Getter和Setter方法
// ...
}
public class UserAction extends ActionSupport {
private User user = new User();
public String execute() {
// 示例:手动设置User对象的属性
user.setUsername("JohnDoe");
user.setAge(30);
return SUCCESS;
}
// Getter和Setter方法
public User getUser() {
return user;
}
public void setUser(User user) {
this.user = user;
}
}
在 struts.xml
配置文件中,可以这样配置:
<struts>
<package name="default" extends="json-default">
<action name="getUserJson" class="com.example.UserAction">
<result name="success" type="json">
<param name="root">user</param>
<param name="includeProperties">username, age</param>
</result>
</action>
</package>
</struts>
通过上述步骤和代码示例,我们展示了如何在Struts2框架中使用OGNL表达式来序列化对象属性为JSON格式。OGNL的灵活性和强大功能,结合Struts2 JSON插件的支持,为开发者提供了强大的数据处理能力。需要注意的是,在实际开发中,还需要考虑安全性问题,比如避免潜在的XSS攻击等。这通常需要对OGNL表达式进行严格的控制,确保它只在安全的上下文中使用。
简介:Struts2是一个用于构建企业级Java Web应用的框架,能够通过JSON插件高效地在服务器端和客户端之间交换数据。通过示例项目"Struts2Json example",展示了如何集成JSON插件到Struts2框架中,并通过配置和Action类的设计返回JSON格式的响应。文章详细说明了如何在Struts2配置文件中添加JSON插件依赖,创建返回JSON响应的Action类,以及在客户端使用JavaScript库解析JSON数据。