欢迎访问 生活随笔!

生活随笔

当前位置: 首页 > 编程资源 > 编程问答 >内容正文

编程问答

RestTemplate--解决中文乱码

发布时间:2025/7/14 编程问答 43 豆豆
生活随笔 收集整理的这篇文章主要介绍了 RestTemplate--解决中文乱码 小编觉得挺不错的,现在分享给大家,帮大家做个参考.

【原文链接】:https://blog.tecchen.xyz ,博文同步发布到博客园。
由于精力有限,对文章的更新可能不能及时同步,请点击上面的原文链接访问最新内容。
欢迎访问我的个人网站:https://www.tecchen.xyz 。

在开发扇贝-每日一句时,使用RestTemplate请求扇贝接口,并保存返回的数据。原本正常的代码,经过架构升级后,请求接口时,会返回乱码数据。经过直接访问接口等形式,最终确认是RestTemplate这个bean有问题。
对RestTemplate的声明也比较简单,通过对apache的httpclient进行封装,返回bean实例。代码如下:

@Bean RestTemplate restTemplate() {return new RestTemplate(httpRequestFactory()); }

通过断点debug发现以String格式接收数据时,底层采用的是StringHttpMessageConverter来处理请求。查看RestTemplate的构造方法如下:

public RestTemplate() {this.messageConverters = new ArrayList();this.errorHandler = new DefaultResponseErrorHandler();this.uriTemplateHandler = new DefaultUriBuilderFactory();this.headersExtractor = new RestTemplate.HeadersExtractor();this.messageConverters.add(new ByteArrayHttpMessageConverter());this.messageConverters.add(new StringHttpMessageConverter());this.messageConverters.add(new ResourceHttpMessageConverter(false));this.messageConverters.add(new SourceHttpMessageConverter());this.messageConverters.add(new AllEncompassingFormHttpMessageConverter());if (romePresent) {this.messageConverters.add(new AtomFeedHttpMessageConverter());this.messageConverters.add(new RssChannelHttpMessageConverter());}if (jackson2XmlPresent) {this.messageConverters.add(new MappingJackson2XmlHttpMessageConverter());} else if (jaxb2Present) {this.messageConverters.add(new Jaxb2RootElementHttpMessageConverter());}if (jackson2Present) {this.messageConverters.add(new MappingJackson2HttpMessageConverter());} else if (gsonPresent) {this.messageConverters.add(new GsonHttpMessageConverter());} else if (jsonbPresent) {this.messageConverters.add(new JsonbHttpMessageConverter());}if (jackson2SmilePresent) {this.messageConverters.add(new MappingJackson2SmileHttpMessageConverter());}if (jackson2CborPresent) {this.messageConverters.add(new MappingJackson2CborHttpMessageConverter());} }

其中的StringHttpMessageConverter构造方法使用了默认字符集:ISO-8859-1。

public class StringHttpMessageConverter extends AbstractHttpMessageConverter<String> {public static final Charset DEFAULT_CHARSET;……public StringHttpMessageConverter() {this(DEFAULT_CHARSET);}……static {DEFAULT_CHARSET = StandardCharsets.ISO_8859_1;} }

private final List<HttpMessageConverter<?>> messageConverters
根据RestTemplate的构造方法的源码得知所有的HttpMessageConverter都是放在final List<HttpMessageConverter<?>> messageConverters这个常量集合中。虽然集合不可修改,但是可以对其中的元素StringHttpMessageConverter进行修改。
解决方案思路都是将ISO-8859-1的StringHttpMessageConverter替换为UTF-8的StringHttpMessageConverter。

  • 示例代码一
restTemplate.getMessageConverters().set(1, new StringHttpMessageConverter(StandardCharsets.UTF_8));
  • 示例代码二
for (HttpMessageConverter<?> httpMessageConverter : restTemplate.getMessageConverters()) {if (httpMessageConverter instanceof StringHttpMessageConverter) {((StringHttpMessageConverter) httpMessageConverter).setDefaultCharset(Charset.forName("UTF-8"));} }
  • 示例代码三
// stream .findFirst(); 也是可以的 Optional<HttpMessageConverter<?>> converter = restTemplate.getMessageConverters().stream().filter(c -> c instanceof StringHttpMessageConverter).findAny(); if(converter.isPresent()) {((StringHttpMessageConverter) converter.get()).setDefaultCharset(Charset.forName("UTF-8")); }

转载于:https://www.cnblogs.com/Candies/p/10398584.html

总结

以上是生活随笔为你收集整理的RestTemplate--解决中文乱码的全部内容,希望文章能够帮你解决所遇到的问题。

如果觉得生活随笔网站内容还不错,欢迎将生活随笔推荐给好友。