背景
一直都没更新操作系统的版本,心血来潮更新了 MacOS 的 14(Sonoma)
macOS
Sonoma - Apple (中国大陆)
然后发现单测竟然跑不通了,但是 push 上去的代码 CI
依然可以通过,所以当时基本就确定是版本升级带来的兼容性问题了
看了下日志,是嵌入的 Redis 运行不起来
1 2 3 4 5 java.lang.RuntimeException: Can't start redis server. Check logs for details. Redis process log: at redis.embedded.AbstractRedisInstance.awaitRedisServerReady(AbstractRedisInstance.java:70) at redis.embedded.AbstractRedisInstance.start(AbstractRedisInstance.java:42) at redis.embedded.RedisServer.start(RedisServer.java:9)
这里嵌入的 Redis 是用来 mock 单测内的 Redis 服务端的
使用的开源 kstyrc/embedded-redis:
Redis embedded server for Java integration testing (github.com)
排查
检查端口占用
当然第一时间检查端口占用,这种代码内嵌的服务经常会出现关闭失败的情况,导致主线程已经结束了实际服务还在运行,导致端口占用;当然从异常栈信息来看并不是端口占用导致的
debug
异常信息上表示 Check logs for details
事实上也没有日志可以查看,只能 debug 进行查看了
具体位置在
org.apache.commons.io.IOUtils.AbstractRedisInstance.start()
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 @Override public synchronized void start () throws EmbeddedRedisException { if (active) { throw new EmbeddedRedisException ("This redis server instance is already running..." ); } try { redisProcess = createRedisProcessBuilder().start(); logErrors(); awaitRedisServerReady(); active = true ; } catch (IOException e) { throw new EmbeddedRedisException ("Failed to start Redis instance" , e); } }
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 private void awaitRedisServerReady () throws IOException { BufferedReader reader = new BufferedReader (new InputStreamReader (redisProcess.getInputStream())); try { String outputLine; do { outputLine = reader.readLine(); if (outputLine == null ) { throw new RuntimeException ("Can't start redis server. Check logs for details." ); } } while (!outputLine.matches(redisReadyPattern())); } finally { IOUtils.closeQuietly(reader); } }
但是 debug 也没发现哪里有日志
事实上还找到了一个 issue 来询问这个问题
"Can't
start redis server. Check logs for details" - which logs???? · Issue #51
· kstyrc/embedded-redis (github.com)
看下方的评论很多人都是因为 Windows 的不兼容导致
对应的 issue
只能继续找 issue,看看有没有解决方案,还真找到了一样的问题
Unable
to run on macOS Sonoma · Issue #135 · kstyrc/embedded-redis
(github.com)
有老哥 fork 后解决了不兼容问题
codemonstur/embedded-redis:
Redis embedded server (github.com)
解决
因为是本地单测环境问题,所以引用开源的风险也不大
其次因为之前的这个依赖在 parent 包内管理,很难快速进行版本升级
所以决定 fork 代码后修改坐标,在本地打一个相同坐标的包进行覆盖
1 2 3 4 5 <dependency > <groupId > com.github.kstyrc</groupId > <artifactId > embedded-redis</artifactId > <version > 0.6</version > </dependency >
总结
真 · 跑起来就不要再动了
不要轻易更新版本 : (