概述
将多个springcloud项目整合成一个单体的springboot工程,前端也换了架构,由于前端新架构没有将所有特殊字符比方[]中括号进行转义,开发整合过程中偶尔出现带中括号参数的请求报错400的问题,请求未到程序代码,后端Tomcat里就报错:
The valid characters are defined in RFC 7230 and RFC 3986问题
报错日志:
09-Apr-2019 14:55:11.427 信息 [http-nio-8089-exec-8] org.apache.coyote.http11.Http11Processor.service Error parsing HTTP request header
Note: further occurrences of HTTP header parsing errors will be logged at DEBUG level.
java.lang.IllegalArgumentException: Invalid character found in the request target. The valid characters are defined in RFC 7230 and RFC 3986
at org.apache.coyote.http11.Http11InputBuffer.parseRequestLine(Http11InputBuffer.java:479)
at org.apache.coyote.http11.Http11Processor.service(Http11Processor.java:684)
at org.apache.coyote.AbstractProcessorLight.process(AbstractProcessorLight.java:66)
at org.apache.coyote.AbstractProtocol$ConnectionHandler.process(AbstractProtocol.java:806)
at org.apache.tomcat.util.net.NioEndpoint$SocketProcessor.doRun(NioEndpoint.java:1498)
at org.apache.tomcat.util.net.SocketProcessorBase.run(SocketProcessorBase.java:49)
at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1142)
at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:617)
at org.apache.tomcat.util.threads.TaskThread$WrappingRunnable.run(TaskThread.java:61)
at java.lang.Thread.run(Thread.java:748)
排查发现是tomcat高版本的规范限制导致的:本工程springboot2.3集成的tomcat9版本的,中括号这种字符前端get请求必须转义。
tomcat8.0以上版本遵从RFC规范添加了对Url的特殊字符的限制,url中只允许包含英文字母(a-zA-Z)、数字(0-9)、-_.~四个特殊字符以及保留字符( ! * ’ ( ) ; : @ & = + $ , / ? # [ ] ) (26*2+10+4+18=84)这84个字符,请求中出现了{}大括号或者[],所以tomcat报错。
设置RelaxedQueryChars允许此字符(建议),设置requestTargetAllows选项(Tomcat 8.5中不推荐)。也可以降级为旧版本之一(不推荐-安全性)。
根据https://tomcat.apache.org/tomcat-9.0-doc/config/systemprops.html tomcat配置说明,requestTargetAllowis 设置允许不受欢迎字符。
实践验证一种方法设置松弛的QueryChars属性:
/**
* 解决异常信息:
* java.lang.IllegalArgumentException:
* Invalid character found in the request target. The valid characters are defined in RFC 7230 and RFC 3986
* @return
*/
@Bean
public ConfigurableServletWebServerFactory webServerFactory() {
TomcatServletWebServerFactory factory = new TomcatServletWebServerFactory();
factory.addConnectorCustomizers(new TomcatConnectorCustomizer() {
@Override
public void customize(Connector connector) {
connector.setProperty("relaxedQueryChars", "|{}[]");
}
});
return factory;
}
问题解决。
但是另一个分支不存在该问题,比对排查可能是笔者清理调整最终版分支架构导致的,最终发现跟pom依赖里的顺序有关,
最开始添加了一个底层log组件,该组件的pom里引入了spring-boot-starter-web,spring-boot-starter-web中引入了spring-boot-starter-tomcat,由此导致以上问题。
本架构本来没有使用tomcat,使用了undertow,undertow性能好一些:
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
<exclusions>
<exclusion>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-tomcat</artifactId>
</exclusion>
</exclusions>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-undertow</artifactId>
</dependency>
Spring Boot内嵌容器支持Tomcat、Jetty、Undertow。
关于Undertow等分析对比参考:
Tomcat vs. Jetty vs. Undertow: Comparison of Spring Boot Embedded Servlet Containers: https://examples.javacodegeeks.com/enterprise-java/spring/tomcat-vs-jetty-vs-undertow-comparison-of-spring-boot-embedded-servlet-containers/
Spring Boot 容器选择 Undertow 而不是 Tomcat: https://www.cnblogs.com/duanxz/p/9337022.html
备注:
另一种类似异常参考:https://blog.csdn.net/baiHoo_chen/article/details/85221852
Invalid character found in method name. HTTP method names must be token
原因:
产生这个问题的原因是页面表单提交了大量的数据,而这些数据量可能超过了Tomcat 定义的Header头内容,那么很好解决了,只要设置一下Tomcat的maxHttpHeaderSize
解决问题如下:
server:
address: 0.0.0.0
port: 8080
max-http-header-size: 10240000
tomcat:
max-http-header-size: 10240000
max-http-post-size: 10240000
最后
以上就是野性火车为你收集整理的记录springboot架构下The valid characters are defined in RFC 7230 and RFC 3986问题排查解决The valid characters are defined in RFC 7230 and RFC 3986问题的全部内容,希望文章能够帮你解决记录springboot架构下The valid characters are defined in RFC 7230 and RFC 3986问题排查解决The valid characters are defined in RFC 7230 and RFC 3986问题所遇到的程序开发问题。
如果觉得靠谱客网站的内容还不错,欢迎将靠谱客网站推荐给程序员好友。
发表评论 取消回复