背景
运行在tomcat容器里的web服务,在响应头信息里,一般都会包含响应状态码,例如:
Status Code: 200 OK
在tomcat 8.5以后,该响应码去掉了状态描述,变成了这样:
Status Code: 200
最近在跟银联的业务往来时,银联要求我们接收到通知后,返回接收结果,并以响应状态码来判断是否解析。这里的状态码就包括状态描述“OK”。
解决
现有系统基于Spring boot 2.3.3.RELEASE,默认tomcat版本为9.x。
- 首先将tomcat版本将为8.5.58,修改pom.xml文件,指定tomcat版本
<properties>
<tomcat.version>8.5.58</tomcat.version>
</properties>
重启应用。发现报错:
***************************
APPLICATION FAILED TO START
***************************
Description:
An attempt was made to call a method that does not exist. The attempt was made from the following location:
org.springframework.boot.web.embedded.tomcat.TomcatServletWebServerFactory.getWebServer(TomcatServletWebServerFactory.java:175)
The following method did not exist:
org.apache.tomcat.util.modeler.Registry.disableRegistry()V
The method's class, org.apache.tomcat.util.modeler.Registry, is available from the following locations:
jar:file:/Users/admin/org/apache/tomcat/embed/tomcat-embed-core/8.5.58/tomcat-embed-core-8.5.58.jar!/org/apache/tomcat/util/modeler/Registry.class
The class hierarchy was loaded from the following locations:
org.apache.tomcat.util.modeler.Registry: file:/Users/admin/org/apache/tomcat/embed/tomcat-embed-core/8.5.58/tomcat-embed-core-8.5.58.jar
Action:
Correct the classpath of your application so that it contains a single, compatible version of org.apache.tomcat.util.modeler.Registry
Process finished with exit code 1
报错原因就是Spring boot 2.3.3.RELEASE不支持tomcat 8.5,
- 第二步,将Spring boot 版本降低到 2.1.17. RELEASE,或者其他支持tomcat8.5的版本。
- 根据tomcat官方文档描述,在8.5 - 9.0之间的版本中,在“Connector”配置中支持“ sendReasonPhrase”配置参数,可以将状态描述正常返回。
sendReasonPhrase
Set this attribute to true if you wish to have a reason phrase in the response. The default value is false.
Note: This option is deprecated and will be removed in Tomcat 9. The reason phrase will not be sent.
3.1 修改conf/server.xml文件,适用于外置tomcat
<Connector port="8080" protocol="org.apache.coyote.ajp.AjpAprProtocol" redirectPort="8443" sendReasonPhrase="true" />
3.2 Spring boot代码配置,适用于内置tomcat
@Bean
public ConfigurableServletWebServerFactory webServerFactory() {
TomcatServletWebServerFactory factory = new TomcatServletWebServerFactory();
factory.addConnectorCustomizers(
connector -> connector.setAttribute("sendReasonPhrase", "true"));
return factory;
}
参考链接:
https://bz.apache.org/bugzilla/show_bug.cgi?id=60362
https://tomcat.apache.org/tomcat-8.5-doc/config/http.html
https://stackoverflow.com/questions/40034949/add-reason-phrase-back-in-spring-boot-1-4-x