日期:2014-05-16  浏览次数:20374 次

解决struts2-json-plugin中GZIP压缩中文乱码问题

??? 当使用struts2的struts2-json-plugin输出接送数据时,如果配置enableGZIP为true,发现竟然有中文乱码问题。查看源代码,果然有一小小问题,所以干脆动手自己修改吧。

?1.首先在struts.xml中加入下面的代码:

<!-- 修正struts2-json-plugin-2.1.8.1中enableGZIP为true时中文乱码问题 -->
	<package name="json-guofeng" extends="json-default">
        <result-types>
            <result-type name="json" class="com.guofeng.ux.jsonplugin.GfJSONResult"/>
        </result-types>
    </package>

?2.GfJSONResult:

public class GfJSONResult extends JSONResult{
	
	/**
	 * @author $Author: GuoFeng $
	 * @date $Date:Sep 28, 2010 3:39:33 PM $
	 * 修正struts2-json-plugin-2.1.8.1中enableGZIP为true时中文乱码问题
	 */
	private static final long serialVersionUID = -997525907667125535L;
	private int statusCode;
	private int errorCode;
	private boolean prefix;
	private String contentType;
	
	@Override
	protected void writeToResponse(HttpServletResponse response, String json,
			boolean gzip) throws IOException {
		GfJSONUtil.writeJSONToResponse(new SerializationParams(response, getEncoding(), isWrapWithComments(),
                json, false, gzip, isNoCache(), statusCode, errorCode, prefix, contentType, getWrapPrefix(),
                getWrapSuffix()));
	}

	public void setStatusCode(int statusCode) {
		this.statusCode = statusCode;
	}

	public void setErrorCode(int errorCode) {
		this.errorCode = errorCode;
	}

	public void setPrefix(boolean prefix) {
		this.prefix = prefix;
	}

	public void setContentType(String contentType) {
		this.contentType = contentType;
	}
}

?

3.GfJSONUtil代码:

public class GfJSONUtil {
	private static final Logger LOG = LoggerFactory.getLogger(MyJSONUtil.class);

	public static void writeJSONToResponse(
			SerializationParams serializationParams) throws IOException {
		StringBuilder stringBuilder = new StringBuilder();
		if (StringUtils.isNotBlank(serializationParams.getSerializedJSON()))
			stringBuilder.append(serializationParams.getSerializedJSON());

		if (StringUtils.isNotBlank(serializationParams.getWrapPrefix()))
			stringBuilder.insert(0, serializationParams.getWrapPrefix());
		else if (serializationParams.isWrapWithComments()) {
			stringBuilder.insert(0, "/* ");
			stringBuilder.append(" */");
		} else if (serializationParams.isPrefix())
			stringBuilder.insert(0, "{}&& ");

		if (StringUtils.isNotBlank(serializationParams.getWrapSuffix()))
			stringBuilder.append(serializationParams.getWrapSuffix());

		String json = stringBuilder.toString();

		if (LOG.isDebugEnabled()) {
			LOG.debug("[JSON]" + json);
		}

		HttpServletResponse response = serializationParams.getResponse();

		// status or error code
		if (serializationParams.getStatusCode() > 0)
			response.setStatus(serializationParams.getStatusCode());
		else if (serializationParams.getErrorCode() > 0)
			response.sendError(serializationParams.getErrorCode());

		// content type
		if (serializationParams.isSmd())
			response.setContentType("application/json-rpc;charset="
					+ serializationParams.getEncoding());
		else
			response.setContentType(serializationParams.getContentType()
					+ ";charset=" + serializationParams.getEncoding());

		if (serializationParams.isNoCache()) {
			response.setHeader("Cache-Control", "no-cache");
			response.setHeader("Expires", "0");
			response.setHeader("Pragma", "No-cache");
		}

		if (serializationParams.isGzip()) {
			response.addHeader("Content-Encoding", "gzip");
			GZIPOutputStream out = null;
			InputStream in = null;
			try {
				out = new GZIPOutputStream(response.getOutputStream());
				/**
				 * @author $Author: GuoFeng $ 修正编码问题
				 * @date $Date:Sep 28, 2010 3:40:17 PM $
				 */
				in = new ByteArrayInputStream(json.getBytes(serializationParams
						.getEncoding()));
				byte[] buf = new byte[1024];
				int len;
				while ((len = in.read(buf)) > 0) {
					out.write(buf, 0, len);
				}