时隔1年半后,再次在csdn的blog中发表日志,sohu的blog也用着不爽。
最近在用webwork+ext在做东西,发现webwork2.2.7版本虽然支持JSON,但存在bug,他默认是不支持设置返回json的charset的,所以需要自己修改一下webwork的源文件中的JSONResult文件。具体修改如下(红色部分):
/*
* Copyright (c) 2002-2007 by OpenSymphony
* All rights reserved.
*/
package com.opensymphony.webwork.dispatcher.json;
import com.opensymphony.webwork.ServletActionContext;
import com.opensymphony.webwork.WebWorkException;
import com.opensymphony.xwork.ActionContext;
import com.opensymphony.xwork.ActionInvocation;
import com.opensymphony.xwork.Result;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import javax.servlet.http.HttpServletResponse;
import java.io.OutputStream;
public class JSONResult implements Result {
private static final Log LOG = LogFactory.getLog(JSONResult.class);
private String jsonObjectProperty = "jsonObject";
private String contentType = "application/json";
private String charset = "utf-8";
/**
* Returns the property which will be used to lookup {@link JSONObject} in WebWork's ValueStack. Default to
* 'jsonObject'.
*
* @return String
*/
public String getJSONObjectProperty() {
return jsonObjectProperty;
}
/**
* Set the property which will be used to lookup {@link JSONObject} in WebWork's ValueStack. Default to
* 'jsonObject'.
*
* @param jsonObject
*/
public void setJSONObjectProperty(String jsonObject) {
this.jsonObjectProperty = jsonObject;
}
/**
* Returns the content-type header to be used. Default to 'application/json'.
*
* @return String
*/
public String getContentType() {
return contentType;
}
/**
* Set the content-type header to be used. Default to 'application/json'.
*
* @param contentType
*/
public void setContentType(String contentType) {
this.contentType = contentType;
}
/**
* Writes the string representation of {@link JSONObject} defined through {@link #getJSONObjectProperty()}
* to {@link javax.servlet.http.HttpServletResponse}'s outputstream.
*
* @param invocation
* @throws Exception
*/
public void execute(ActionInvocation invocation) throws Exception {
if (LOG.isDebugEnabled()) {
LOG.debug("executing JSONResult");
}
JSONObject jsonObject = getJSONObject(invocation);
if (jsonObject != null) {
String json = jsonObject.toString();
HttpServletResponse response = getServletResponse(invocation);
response.setContentType(getContentType());
byte[] bs = json.getBytes(charset);
response.setContentLength(bs.length);
OutputStream os = response.getOutputStream();
os.write(bs);
os.flush();
if (LOG.isDebugEnabled()) {
LOG.debug("written ["+json+"] to HttpServletResponse outputstream");
}
}
}
/**
* Attempt to look up a {@link com.opensymphony.webwork.dispatcher.json.JSONObject} instance through the property
* ({@link #getJSONObjectProperty()}) by looking up the property in WebWork's ValueStack. It shall be found if there's
* accessor method for the property in WebWork's action itself.
*
* Returns null if one cannot be found.
*
* We could override this method to return the desired JSONObject when writing testcases.
*
* @param invocation
* @return {@link JSONObject} or null if one cannot be found
*/
protected JSONObject getJSONObject(ActionInvocation invocation) throws JSONException {
ActionContext actionContext = invocation.getInvocationContext();
Object obj = actionContext.getValueStack().findValue(jsonObjectProperty);
if (obj == null) {
LOG.error("property ["+ jsonObjectProperty +"] returns null, expecting JSONObject", new WebWorkException());
return null;
}
if (! JSONObject.class.isInstance(obj)) {
LOG.error("property ["+ jsonObjectProperty +"] is ["+obj+"] especting an instance of JSONObject", new WebWorkException());
return null;
}
return (JSONObject) obj;
}
/**
* Returns a {@link javax.servlet.http.HttpServletResponse} by looking it up through WebWork's ActionContext Map.
*
* We could override this method to return the desired Mock HttpServletResponse when writing testcases.
*
* @param invocation
* @return {@link javax.servlet.http.HttpServletResponse}
*/
protected HttpServletResponse getServletResponse(ActionInvocation invocation) {
return (HttpServletResponse) invocation.getInvocationContext().getContextMap().get(ServletActionContext.HTTP_RESPONSE);
}
public String getCharset() {
return charset;
}
public void setCharset(String charset) {
this.charset = charset;
}
}