首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
您现在的位置: 程式碼之家 >> 編程語言 >  >> 網頁程式設計 >> JSP 程式設計 >> 關於JSP

JSP 中文亂碼徹底解決:兩大經典方案(工具方法 vs Filter 過濾器)

     編輯:關於JSP

    亂碼根因

    瀏覽器發送請求參數預設以 ISO-8859-1 編碼;伺服器若以 GBK/UTF-8 解碼即產生亂碼。解決核心:統一雙端編碼或正確轉碼。

    方案一:工具類轉碼法(適用舊專案快速修補)

    在 JSP 頁面或共用檔定義靜態方法:

    <%!
        public static String toChinese(String str) {
            if (str == null) return null;
            try {
                byte[] bytes = str.getBytes("ISO-8859-1");
                return new String(bytes, "GBK"); // 或 UTF-8
            } catch (Exception e) { return str; }
        }
    %>
    
    <%-- 使用 --%>
    String name = toChinese(request.getParameter("name"));
    

    缺點:每個取參數處皆需呼叫、易遺漏、POST/GET 需分開處理、效能稍差。

    方案二:Filter 統一編碼(推薦、一勞永逸)

    實作 javax.servlet.Filter,在 doFilter 早期設定請求編碼,並包裝 HttpServletRequest 覆寫 getParameter* 方法自動轉碼。

    完整 Filter 實作

    package filters;
    
    import java.io.IOException;
    import javax.servlet.*;
    
    public class EncodingFilter implements Filter {
        private String encoding = "UTF-8";
        private boolean ignore = true;
    
        public void init(FilterConfig config) {
            String e = config.getInitParameter("encoding");
            if (e != null) encoding = e;
            String ig = config.getInitParameter("ignore");
            if (ig != null) ignore = Boolean.parseBoolean(ig);
        }
    
        public void doFilter(ServletRequest req, ServletResponse res, FilterChain chain)
                throws IOException, ServletException {
            HttpServletRequest request = (HttpServletRequest) req;
            // POST 請求直接設定編碼
            if ("POST".equalsIgnoreCase(request.getMethod())) {
                if (ignore || request.getCharacterEncoding() == null) {
                    request.setCharacterEncoding(encoding);
                }
            } else {
                // GET 請求需包裝 Request 覆寫 getParameter
                request = new RequestWrapper(request, encoding);
            }
            chain.doFilter(request, res);
        }
    
        public void destroy() {}
    }
    
    // 包裝類
    class RequestWrapper extends HttpServletRequestWrapper {
        private String encoding;
        public RequestWrapper(HttpServletRequest request, String encoding) {
            super(request); this.encoding = encoding;
        }
        private String decode(String s) {
            try { return new String(s.getBytes("ISO-8859-1"), encoding); }
            catch (Exception e) { return s; }
        }
        @Override public String getParameter(String name) { return decode(super.getParameter(name)); }
        @Override public String[] getParameterValues(String name) {
            String[] vals = super.getParameterValues(name);
            if (vals != null) for (int i=0;i

    web.xml 註冊

    <filter>
        <filter-name>EncodingFilter</filter-name>
        <filter-class>filters.EncodingFilter</filter-class>
        <init-param><param-name>encoding</param-name><param-value>UTF-8</param-value></init-param>
        <init-param><param-name>ignore</param-name><param-value>true</param-value></init-param>
    </filter>
    <filter-mapping>
        <filter-name>EncodingFilter</filter-name>
        <url-pattern>/*</url-pattern>
    </filter-mapping>
    

    進階:Tomcat 8+ 內建支援

    server.xml 的 <Connector> 加入:

    <Connector port="8080" protocol="HTTP/1.1"
               URIEncoding="UTF-8" useBodyEncodingForURI="true" />
    

    即可解決 GET 參數編碼,POST 仍需 request.setCharacterEncoding("UTF-8") 或 Filter。

    最佳實踐總結

    1. 新專案:全站 UTF-8 + EncodingFilter + Tomcat URIEncoding="UTF-8"。
    2. 舊專案:優先加 Filter,逐步統一頁面編碼為 UTF-8。
    3. 資料庫連線 URL 附帶 characterEncoding=utf8(MySQL)或對應設定。
    4. 前端 JS 統一用 encodeURIComponent() 送參數。
    1. 上一篇文章:
    2. 下一篇文章:
    Copyright © 程式碼之家 All Rights Reserved