深夜奋战:解决 nohup java -jar xxx.jar 启动失败的曲折之路

背景

昨晚十点多,刚过完情人节的我回到家正在舒服的泡脚。突然,运维联系的一条消息让我心提到嗓子眼:你的 Java 应用无法启动,并附上一张截图,图中提示Error: unable to access jarfile xxx.jar

时间紧迫,心情焦急,我不得不熬夜排查问题,直到凌晨十二点才终于解决。以下是这段“惊心动魄”的排查过程,记录了我从迷茫到豁然开朗的心路历程。


1. 初遇问题:深夜的警报

1.1 问题的出现

晚上十点,运维像往常一样执行上线,使用 nohup java -jar xxx.jar & 启动应用,准备测试一下功能。然而,命令行无情地抛出了一行错误:Error: unable to access jarfile xxx.jar

我的心一下子提到了嗓子眼——本来准备美美的睡一觉了,时间紧迫,要赶紧解决,不然就扣绩效了,问题出在哪儿呢?

1.2 初步检查

我深吸一口气,告诉自己冷静下来,开始一步步排查:

  • 文件是否存在
    ls -l xxx.jar,文件明明就在那里,权限也没问题。
  • Java 环境
    java -version,JDK 8,版本正常。
  • 文件权限
    chmod 755 xxx.jar,权限也给了,为什么还是不行?

2. 深入排查:迷雾中的探索

2.1 检查 JAR 文件

既然文件存在,权限也没问题,难道是 JAR 文件损坏了?我试着用 jar -tf xxx.jar 查看文件内容,发现里面的文件列表正常,META-INF/MANIFEST.MF 也完好无损。

接着我用md5sum xxx.jar查看文件md5值,发现服务器上的文件md5值和本地的不一致!

挖了个渠!问题就要解决了吗?于是重新传了一份jar文件确保md5值一样,以为万事大吉了,结果运维使用vim xxx.jar的方式修改了jar包里配置文件的数据库连接,然后保存,这md5肯定不一样啊,不出意外,执行启动命令还是同样的错!以为发现了新大陆呢…

然后我想到了不修改jar文件内容,通过在启动命令修改参数。这样确保jar文件和预发环境一致,于是重新上传jar文件然后通过nohup java -Dxxx=yyy -Dmmm=nnn -jar xxx.jar & 的方式启动,还是同样的错!崩溃…

2.2 检查资源文件

突然想到,应用依赖了一些外部配置文件。会不会是路径问题?我打开代码,检查资源文件的加载逻辑,发现确实是通过相对路径加载的。于是,我试着将配置文件放到 JAR 文件同级目录下,但问题依旧。

2.3 尝试直接运行

为了进一步缩小问题范围,我直接运行:
java -jar xxx.jar
结果依然是 unable to access jarfile xxx.jar。这让我更加困惑——明明文件就在那里,为什么就是不行呢?


3. 转机:绝对路径的启示

3.1 灵光一现

就在我几乎要放弃的时候,突然想到:会不会是路径的问题?我之前一直在 JAR 文件所在目录下执行命令,使用的是相对路径 ./xxx.jar。于是,我试着改用绝对路径:
java -jar /path/to/xxx.jar
奇迹出现了——应用成功启动了!

3.2 恍然大悟

原来,问题出在当前工作目录上。当我在 JAR 文件所在目录下执行命令时,应用程序内部可能基于当前工作目录加载资源文件,而相对路径的解析导致了路径错误。改用绝对路径后,路径问题迎刃而解。


4. 根本原因:相对路径的陷阱

  • 当前工作目录的影响
    应用程序在运行时依赖当前工作目录加载资源文件,而相对路径的解析受当前工作目录影响。
  • 路径配置问题
    应用程序未正确处理相对路径,导致资源文件无法加载。

5. 解决方案:绝对路径的力量

5.1 使用绝对路径

在启动命令中使用绝对路径:
nohup java -jar /path/to/xxx.jar > output.log 2>&1 &

5.2 明确指定资源文件路径

如果应用程序依赖外部资源文件,使用绝对路径或明确指定路径:
java -jar xxx.jar --spring.config.location=/path/to/application.properties

5.3 修改应用程序代码

在代码中确保资源文件的路径是绝对路径,或基于 JAR 文件的位置动态计算路径。


6. 预防措施:避免重蹈覆辙

  • 避免直接修改 JAR 文件
    如果需要修改 JAR 文件内容,建议解压、修改、重新打包。
  • 使用外部配置文件
    将配置文件放在 JAR 文件外部,通过命令行参数或环境变量指定路径。
  • 统一路径管理
    在应用程序中统一管理资源文件路径,避免硬编码。

7. 总结:深夜的收获

  • 问题原因
    相对路径导致资源文件加载失败。
  • 解决方法
    使用绝对路径启动 JAR 文件,或明确指定资源文件路径。
  • 经验教训
    在 Linux 系统中,尽量使用绝对路径启动应用程序,避免因当前工作目录变化导致的路径问题。

8. 示例命令

8.1 使用绝对路径启动

nohup java -jar /path/to/xxx.jar > output.log 2>&1 &

8.2 指定外部配置文件

java -jar xxx.jar --spring.config.location=/path/to/application.properties

8.3 设置环境变量

export SPRING_DATASOURCE_URL=jdbc:mysql://localhost:3306/mydb
export SPRING_DATASOURCE_USERNAME=root
export SPRING_DATASOURCE_PASSWORD=123456

java -jar xxx.jar


希望这篇笔记对你有帮助!如果有其他问题,欢迎随时交流!

原文始发于微信公众号(BiggerBoy):深夜奋战:解决 nohup java -jar xxx.jar 启动失败的曲折之路

版权声明:本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 举报,一经查实,本站将立刻删除。

文章由极客之音整理,本文链接:https://www.bmabk.com/index.php/post/315620.html

(0)
小半的头像小半

相关推荐

发表回复

登录后才能评论
极客之音——专业性很强的中文编程技术网站,欢迎收藏到浏览器,订阅我们!