使用HttpServletResponseWrapper加密接口返回值及中文亂碼解決方案
在開發對外API接口時,數據加密至關重要。本文探討在Filter中使用HttpServletResponseWrapper加密接口返回值時,如何有效避免中文亂碼問題。 核心問題在于如何正確獲取響應數據并進行加密處理。
以下代碼片段展示了常見的錯誤嘗試:使用CharArrayWriter緩存響應內容,并在flushBuffer方法中進行加密。然而,flushBuffer可能不會被執行,導致加密失敗。 嘗試在FilterChain.doFilter之后獲取數據,則可能出現中文亂碼。
HttpServletResponse response = (HttpServletResponse) servletResponse; EncryptResponseWrapper encryptResponseWrapper = new EncryptResponseWrapper(response); encryptResponseWrapper.setCharacterEncoding("UTF-8"); filterChain.doFilter(servletRequest, encryptResponseWrapper);
關鍵在于EncryptResponseWrapper的實現。改進后的代碼如下:
package com.wondersgroup.wdls.js.wapper; import com.wondersgroup.wdls.js.web.utils.DESUtils; import javax.servlet.*; import javax.servlet.http.HttpServletResponse; import javax.servlet.http.HttpServletResponseWrapper; import java.io.*; public class EncryptResponseWrapper extends HttpServletResponseWrapper { private CharArrayWriter charArrayWriter = null; private PrintWriter writer = null; private ServletOutputStream out = null; public EncryptResponseWrapper(HttpServletResponse response) throws IOException { super(response); charArrayWriter = new CharArrayWriter(); out = new WrapperOutputStream(charArrayWriter); // 關鍵修改:顯式指定UTF-8編碼 writer = new PrintWriter(new OutputStreamWriter(new WrapperOutputStream(charArrayWriter), "UTF-8")); } @Override public PrintWriter getWriter() throws IOException { return writer; } @Override public ServletOutputStream getOutputStream() throws IOException { return out; } public CharArrayWriter getCharArrayWriter() { return charArrayWriter; } @Override public void flushBuffer() throws IOException { if (out != null) { out.flush(); } if (writer != null) { writer.flush(); } } @Override public void reset() { charArrayWriter.reset(); } public String getResponseData() throws IOException { flushBuffer(); return charArrayWriter.toString(); } private class WrapperOutputStream extends ServletOutputStream { private CharArrayWriter charArrayWriter = null; public WrapperOutputStream(CharArrayWriter charArrayWriter) { this.charArrayWriter = charArrayWriter; } @Override public void write(int b) throws IOException { charArrayWriter.write(b); } @Override public boolean isReady() { return false; } @Override public void setWriteListener(WriteListener listener) { } } }
解決中文亂碼的關鍵在于: 在創建PrintWriter時,通過new OutputStreamWriter(…, “UTF-8”)顯式指定UTF-8編碼。這確保了寫入CharArrayWriter的數據使用正確的編碼,避免了后續讀取時出現亂碼,從而保證了加密操作的正確性和數據的完整性。
? 版權聲明
文章版權歸作者所有,未經允許請勿轉載。
THE END