response contentType值的问题

response contentType值的问题response,contentType,UTF-8,ISO-8859-1

大家好,又见面了,我是你们的朋友全栈君。

关于 reponse 返回类型 contentType 是 application/json;charset=ISO-8859-1 现象的阐述

现象发生描述:

在 Interceptor 的 preHandle 方法对 response 设置 contentType和charset

response.setContentType(MediaType.APPLICATION_JSON_VALUE);
response.setCharacterEncoding("UTF-8");

之后,发现了浏览器F12页面中的请求结果的 responseHeader 中 contentType 属性始终是 application/json;charset=ISO-8859-1 ,并不符合预期结果,最终结果的应该是 application/json;charset=UTF-8 才是理想的啊。

排查:

经过对上述代码代码以及上下文代码进行debug,最终通过源码逻辑获得到了编码始终不对的原因。

原因:

产生问题时的代码:

PrintWriter writer = response.getWriter();
response.setContentType(MediaType.APPLICATION_JSON_VALUE);
response.setCharacterEncoding("UTF-8");

处理之后的代码:

response.setContentType(MediaType.APPLICATION_JSON_VALUE);
response.setCharacterEncoding("UTF-8");
PrintWriter writer = response.getWriter();

对比代码可以看到,没错!就是 response.getWriter(); 这句代码的执行顺序导致的,它是在设置类型和编码之前还是之后!

那为什么先调用 response.getWriter(); 就会导致设置的编码类型不成功呢?来看源码:

org.apache.catalina.connector.Response#getWriter:

    @Override
    public PrintWriter getWriter()
        throws IOException { 
   

        if (usingOutputStream) { 
   
            throw new IllegalStateException
                (sm.getString("coyoteResponse.getWriter.ise"));
        }
				// 看这个if,这个是问题产生的核心内容
        if (ENFORCE_ENCODING_IN_GET_WRITER) { 
   
            /* * If the response's character encoding has not been specified as * described in <code>getCharacterEncoding</code> (i.e., the method * just returns the default value <code>ISO-8859-1</code>), * <code>getWriter</code> updates it to <code>ISO-8859-1</code> * (with the effect that a subsequent call to getContentType() will * include a charset=ISO-8859-1 component which will also be * reflected in the Content-Type response header, thereby satisfying * the Servlet spec requirement that containers must communicate the * character encoding used for the servlet response's writer to the * client). */
            setCharacterEncoding(getCharacterEncoding());
        }

        usingWriter = true;
        outputBuffer.checkConverter();
        if (writer == null) { 
   
            writer = new CoyoteWriter(outputBuffer);
        }
        return writer;
    }

首先看注释,注释中就描述了“如果未制定response的编码,就默认为ISO-8859-1”。

并且会执行 usingWriter = true; 语句,记住这句,一会就用到了。

其次看代码 setCharacterEncoding(getCharacterEncoding()); 内容:

org.apache.catalina.connector.Response#getCharacterEncoding:
在这里插入图片描述

org.apache.catalina.connector.Response#setCharacterEncoding:
在这里插入图片描述

版权声明:本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 举报,一经查实,本站将立刻删除。

发布者:全栈程序员-站长,转载请注明出处:https://javaforall.net/161577.html原文链接:https://javaforall.net

赞 (0)
全栈程序员-站长的头像全栈程序员-站长

相关推荐

  • 常用shell命令_使用shell命令

    常用shell命令_使用shell命令1、目录信息查看命令ls  Shell下文件浏览命令为ls,格式如下:ls[选项][路径]  ls命令主要用于显示指定目录下的内容,列出指定目录下包含的所有的文件以及子目录,它的主要参数有:  -a显示所有的文件以及子目录,包括以“.”开头的隐藏文件。  -l显示文件的详细信息,比如文件的形态、权限、所有者、大小等信息。  -t将文件按照创建时间排序列出。  -A和-a一样,但是不列出“.”(当前目录)和“…”(父目录)。  -R递归列出所有文件,包括子目录中的

    2022年11月3日
  • Enterprise Library5.0 配置Log时差问题

    Enterprise Library5.0 配置Log时差问题最近使用EnterpriseLibrary5.0配置Log日志时候出现的默认时间与本地系统时间不一致。默认时间为格里尼治时间,在一个log中出现两个时间会让人迷惑,这个事件到底是什么时候发生的呢?经过小弟我一上午多次尝试后,总算是解决了这个问题。解决方法:在LogMessageFormatters->Template->将Timestamp:{timestamp}{newline}

    2022年10月20日
  • Nginx修改默认端口80

    Nginx修改默认端口80前言    安装流程请参考我的文章–Windows下安装Nginx。    博客地址:https://blog.csdn.net/zengwende/article/details/86610692修改步骤1、打开Nginx的配置文件nginx.conf2、修改默认端口的值即可(nginx默认的端口为80) …

    2022年9月8日
  • 腾讯云免费SSL证书配置

    腾讯云免费SSL证书配置基于ngnix的https配置1.证书上传1)申请证书请参照官方文档,然后把已经颁发下来的证书下载下来。2)解压文件,然后把ngnix文件夹下的1_xxx.com_bundle.crt和2_xxx.com.key上传到服务器的nginx配置文件目录(上传到同一目录),如:/usr/loc…

    2022年9月3日
  • 退出多个activity的方法

    退出多个activity的方法

    2022年2月21日
  • VBS 代码合集(慎用,好玩)

    VBS 代码合集(慎用,好玩)玩玩就好啦记得关注哦一、你打开好友的聊天对话框,然后记下在你QQ里好友的昵称,把下面代码里的xx替换一下,就可以自定义发送QQ信息到好友的次数(代码里的数字10改一下即可).xx.vbs=>=—————————————————————————OnErrorResumeNextDimwsh,yesetwsh=createobject(“wscript.shell”)fori=1

    2022年6月5日

发表回复

您的邮箱地址不会被公开。 必填项已用 * 标注

关注全栈程序员社区公众号