在使用struts 2处理ajax请求并返回json数据时,开发者常会遇到json解析错误或ajax请求进入错误回调函数的问题。这通常源于对struts 2 json插件工作原理的误解。
最初的尝试可能是在Action中手动获取HttpServletResponse的Writer,然后将JSON字符串直接写入响应流,同时在struts.xml中配置result type="json"。例如:
初始Action代码片段(错误示范):
public class PropertyTesting extends ActionSupport {
public String execute() {
JSONObject obj = new JSONObject();
obj.put("Name", "PersonName");
obj.put("ID", "PersonID");
try {
ServletActionContext.getResponse().getWriter().write(obj.toJSONString());
} catch (IOException e) {
e.printStackTrace();
}
return SUCCESS;
}
}对应的Struts.xml配置:
这种做法的问题在于:当struts.xml中配置了
要正确地从Struts 2 Action返回JSON数据给AJAX请求,关键在于让Struts 2 JSON插件接管JSON的序列化过程。这意味着Action类不应该手动写入响应流,而是应该将需要转换为JSON的数据封装为Action的属性,并通过公共的Getter方法暴露出来。JSON插件会自动检测这些属性并将其序列化。
核心思想:
以下是基于上述原则修正后的Action类和相关配置:
import java.util.HashMap;
import java.util.Map;
import com.opensymphony.xwork2.ActionSupport;
public class PropertyTesting extends ActionSupport {
// 定义一个Map属性,用于存储需要序列化的数据
private Map jsonData;
// 提供公共的
Getter方法,JSON插件会通过此方法获取数据
// 注意:方法名通常是 "get" + 属性名首字母大写
public Map getJsonData() {
return jsonData;
}
@Override
public String execute() {
// 在execute方法中初始化并填充Map
jsonData = new HashMap<>();
jsonData.put("Name", "PersonName");
jsonData.put("ID", "PersonID");
// 返回SUCCESS,让Struts 2的JSON结果类型处理响应
return SUCCESS;
}
} 说明:
前端AJAX代码保持不变,因为它已经正确地设置了dataType:"json",期望接收JSON数据。
<%@ page language="java" contentType="text/html; charset=UTF-8"
pageEncoding="UTF-8"%>
<%@ taglib uri="/struts-tags" prefix="s"%>
Property Testing
Struts配置也保持不变,因为json-default包和result type="json"是正确使用JSON插件的基础。
重要提示:
通过遵循这些指导原则,你将能够更高效、更稳定地在Struts 2应用中处理AJAX JSON响应。