Tomcat 容器启动问题
前提
- Spring Boot 版本 2.0.3.RELEASE
- druid-spring-boot-starter 版本 1.1.9
- mysql-connector-java 版本 5.1.46
- MySQL 数据库版本 5.7
- Tomcat 版本 7.0.67(最终升级了版本到 Tomcat 8)
- JDK 版本 1.7(最终升级到1.8)
问题: 测试、生产配置文件属性不同步,生产环境很多属性未配置,导致错误注入。
解决: 将所有注入的 API 地址同步。
问题: 启动时 Dubbo 报错,找不到服务。
解决: 提供者所在机器 Dubbo 端口未开放,开放对应端口即可。
问题: Tomcat 无法启动,每次启动报不同的错误。
解决: JDK版本升级到 1.8→Tomcat 版本升级到 7.0.92
问题: java.lang.NoClassDefFoundError: javax/el/ELManager
解决:参考
问题:
配置:
1 | # MySQL数据源配置 |
异常信息:
1 | Caused by: java.sql.SQLException: connect error, url jdbc\:mysql\://rds.xxx.com\:3306/xxx?useUnicode\=true&characterEncoding\=UTF-8&zeroDateTimeBehavior\=convertToNull, driverClass com.mysql.jdbc.Driver |
解决: 异常信息里非常明确的提及是数据库连接 url 的问题,在 Spring Boot 的 yml 配置文件中,格式为:property: value
属性名称加「:」之后有一个空格,项目之前的配置文件中 MySQL 数据库的连接地址转义过,这里直接复制过来使用,是行不通的,将转义字符「\」去掉即可。
Tomcat 重启之后异常
问题:
异常信息:
1 | org.apache.catalina.session.StandardManager doLoad |
解决: 删除 ${catalina.home}/work/Catalina/localhost/${APP-NAME}/SESSION.ser
即可
问题: Dubbo 报错
报错信息:
1 | 2018-12-15 20:26:52,387 [DubboSaveRegistryCache-thread-1] WARN [com.alibaba.dubbo.registry.zookeeper.ZookeeperRegistry] - [DUBBO] Failed to save registry store file, cause: Can not lock the registry cache file /root/.dubbo/dubbo-registry-10.11.12.13.cache, ignore and retry later, maybe multi java process use the file, please config: dubbo.registry.file=xxx.properties, dubbo version: 2.5.3, current host: 10.20.30.40 |
Dubbo 会使用文件缓存注册中心地址列表及服务提供者列表,默认路径在 /${user.home}/.dubbo/dubbo-registry-10.20.30.40.cache
,应用重启时将基于此文件恢复,一台服务器有多个应用使用这个文件恢复时,会出现这个警告。
解决: 可以在每个项目 Dubbo 配置文件中的 dubbo:registry
标签中的 file 指定不同的文件路径。 官方文档 参考地址
问题: Tomcat 容器无日志输出
logback-spring.xml配置:1
2
3
4
5
6
7
8
9
10...
<!-- 测试环境+开发环境. -->
<springProfile name="test,dev">
<logger name="com.xxx.im" level="INFO"/>
</springProfile>
<!-- 生产环境 -->
<springProfile name="prod">
<logger name="com.xxx.im" level="ERROR"/>
</springProfile>
...
解决: 生产环境日志输出级别过高,INFO
级别的无法输出,将 ERROR
改为 INFO
即可。
转战华为云之后🙂
RabbitMQ 连接
Spring Boot 版本
2.0.3.RELEASE
问题: RabbitMQ 直接使用 yaml 配置如下:
1 | spring: |
项目启动时报错信息:
1 | ... |
解决: 从异常日志中可以很明显的看到,是 Connection closed
,解决思路如下:
初步判断当前机器无法连通 RabbitMQ 所在机器,使用
ping rabbitmq.xxx.com
命令可以 ping 通 RabbitMQ 所在机器,并且telnet rabbitmq.xxx.com 5672
也是可以连通的,排除此原因;确认
username、password
准确性,发现 RabbitMQ 是新装的,使用命令查看其用户:1
2
3[root@rabbit ~]# rabbitmqctl list_users
Listing users ...
admin [administrator]发现并没有
user
这个用户,创建用户:1
2[root@rabbit ~]# rabbitmqctl add_user user password123456
Creating user "user" ...设置为管理员:
1
2[root@rabbit ~]# rabbitmqctl set_user_tags user administrator
Setting tags for user "user" to [administrator] ...此时,使用该用户登录 RabbitMQ WEB 端管理页面后查看该用户信息:
点击Set permission
配置权限,重启项目后问题解决。
Tomcat 问题
问题: 启动 Tomcat 容器报错信息如下:
1 | org.apache.tomcat.jni.Error: 70023: This function has not been implemented on this platform |
解决: 修改 $TOMCAT_HOME/conf/server.xml
中的 <Listener className="org.apache.catalina.core.AprLifecycleListener" SSLEngine="off" />
即可解决。
Tomcat 问题
问题: 启动 Tomcat 容器报错信息如下:
1 | org.apache.tomcat.jni.Error: 70023: This function has not been implemented on this platform |
解决: 修改 $TOMCAT_HOME/conf/server.xml
中的 <Listener className="org.apache.catalina.core.AprLifecycleListener" SSLEngine="off" />
即可解决。
线上问题处理
问题:
MongoDB 版本:TokuMX 2.0.2 | MongoDB 2.4
spring-data-mongodb 版本:1.4.1.RELEASE
spring-data-commons 版本:1.7.2.RELEASE
1 | java.lang.IllegalArgumentException: You have to provide at least one property to sort by! |
解决: 异常信息很明确,未提供排序的属性,检查代码,异常代码片段如下:
1 | ... |
很明显,排序属性集合 sortStrList
中有可能没有任何属性,再查看 org.springframework.data.domain.Sort
中的构造方法:
1 | public Sort(Sort.Direction direction, String... properties) { |
可以看出,sortStrList
完全无需转换为数组,但这不是主要原因,从下面的构造方法中可以看出,传入的 List 集合不可为空对象并且必须集合大小必须大于 0,所以解决方案可以有多种,只需控制 sortStrList
集合不为空且 size 大于 0,或者根据判断查询不加排序条件也可以解决。
问题:
1 | org.springframework.data.mongodb.UncategorizedMongoDbException: Lock not granted. Try restarting the transaction.; nested exception is com.mongodb.MongoExcep |
解决: 手动配置的 MongoDB 事务问题,尚未彻底解决。
问题:
Spring 整合 MongoDB配置文件:
1
2
3
4
5
6
7
8
9
10
11 > <bean id="mongoOptions" class="com.mongodb.MongoOptions">
> ...
> <!-- 连接超时时间(毫秒),默认为4000 -->
> <property name="connectTimeout" value="4000" />
> <!-- socket读写时超时时间(毫秒),默认为0,不超时 -->
> <property name="socketTimeout" value="0" />
> <!-- 是socket连接在防火墙上保持活动的特性,默认为false -->
> <property name="socketKeepAlive" value="true" />
> ...
> </bean>
>
1 | org.springframework.dao.DataAccessResourceFailureException: can't say something; nested exception is com.mongodb.MongoException$Network: can't say something |
解决: 异常最后很明确的提示了 connect timed out
连接超时的问题,我们可以将 connectTimeout
连接超时属性适当扩大,如果是提示 read timed out
,原因是在进行数据操作时过长时间没有返回结果,此时要修改 socketTimeout
属性了。