JavaWeb乱码---Spring后端乱码问题
1.场景:
使用Apache的HttpClient+Spring控制器,来探究Java后端Http请求中容易出现的乱码。关于Apache的HttpClient发送请求可以查看我的Apache-HttpClient请求
心法:乱码解决,从根入手。
2.Post请求
2.1 HttpClient发送请求时乱码
【JavaWeb乱码---Spring后端乱码问题】HttpClient发送post请求有两种方式:请求参数key-value键值对 或 请求参数为字符串。
这个步骤是Http请求源头,我们首先要保证源头处中文被显式设置为指定编码 eg:UTF-8
1>请求参数是key-value键值对
HttpEntity request= new UrlEncodedFormEntity(params, "UTF-8");
2>请求参数为字符串
StringEntity stringEntity = new StringEntity(requestBody, "UTF-8");
2.2 Spring控制器获取请求时乱码
Spring一般会在web.xml设置一个CharacterEncodingFilter过滤器,处理获取过程中文乱码问题,代码如下:
encodingFilter
org.springframework.web.filter.CharacterEncodingFilter
encodingUTF-8
forceEncodingtrue
encodingFilter
/*
后来了解CharacterEncodingFilter本质作用:
request.setCharacterEncoding("UTF-8");
response.setCharacterEncoding("UTF-8");
1>获取key-value键值对请求参数
使用上述web.xml中CharacterEncodingFilter编码配置。
2>获取字符串请求参数:以流的方式获取,且显式设置UTF-8编码
public String getReqeustData(HttpServletRequest request) {
String data = https://www.it610.com/article/null;
try {
BufferedReader br = new BufferedReader(new InputStreamReader(request.getInputStream(),"utf-8"));
String line = null;
StringBuilder sb = new StringBuilder();
while ((line = br.readLine()) != null) {
sb.append(line);
}
data = https://www.it610.com/article/sb.toString();
if (StringUtils.isEmpty(data)) {
return null;
}} catch (Exception e) {
logger.error("read Inputstream for httpReqeust error", e);
}
return data;
}
2.3 Spring控制器响应时乱码
Spring控制器有两种常见方式,对请求进行响应:
1>使用 HttpServletResponse response响应
为了避免中文乱码,要么配置上述web.xml中CharacterEncodingFilter配置编码; 要么response显式设置响应编码。两者必须有一个,否则响应信息中文会乱码。
response.setCharacterEncoding("UTF-8");
2>使用@ResponseBody标签响应
@ResponseBody会将内容或对象作为 HTTP 响应正文返回,使用@ResponseBody将会跳过视图处理部分,而是调用适合的HttpMessageConverter,将返回值写入输出流。如果返回String,则使用StringHttpMessageConverter,但这个convert使用的是字符集是ISO-8859-1,而且是final的。响应乱码的万恶之源啊!
部分源码如下:
public class StringHttpMessageConverter extends AbstractHttpMessageConverter {public static final Charset DEFAULT_CHARSET = Charset.forName("ISO-8859-1");
}
解决方案有两种:
方法一:对于需要返回字符串的方法添加注解: produces = "application/json; charset=UTF-8"。但是这个方法,需要在每个需要的方法都加上此注解,比较麻烦,所以就有了下面的方法二和三。
@RequestMapping(value = "https://www.it610.com/testStringParams", produces = "application/json;
charset=UTF-8")
@ResponseBody
public String testStringReqParams(HttpServletRequest request){String stringReqParams = getReqeustData(request);
return stringReqParams;
}//end method
方法二:
在mvc配置文件中,修改StringHttpMessageConverter使用字符集
方法三:
在mvc配置文件中,使用MappingJackson2HttpMessageConverter转换字符串
text/html;
charset=UTF-8
application/json;
charset=UTF-8
2.4 HttpClient接收响应时乱码
显式设置接收信息编码格式:
String result = EntityUtils.toString(entity, "UTF-8");
3.Get请求 3.1 获取Get请求查询参数时乱码
可以去设置URIEncoding="utf-8"
3.2 Tomcat7和Tomcat8之于乱码
可是有时候你会发现,同样的项目,A本地解析get查询参数中文正常,但是B本地解析中文乱码。这个是由于Tomcat8和Tomcat7,对URIEncoding默认编码是不一样的:Tomcat8默认是UTF-8,而Tomcat7是ISO-8895-1。详见Tomcat7和Tomcat8编码
个人总结,助人助己。
推荐阅读
- javaweb|基于Servlet+jsp+mysql开发javaWeb学生成绩管理系统
- SpringMVC返回的ResponseEntity出现乱码及解决
- Maven|Maven test命令 中文乱码
- 最新JavaWebIDEA2020教程及资料
- JavaWeb|JavaWeb学习——CSS
- JavaWeb|JavaWeb学习——用户注册(14)
- arcgis属性表出现中文乱码问题解决
- intellij-idea|JavaWeb: IntelliJ IDEA集成开发环境下开发第一个servlet程序(JDBC)Tomcat
- HTML1
- Maven|Maven 控制台乱码问题