编译为jar包后项目失效,Java调用bat文件启动游戏服务器异常问题
问题根因排查
打包后运行无反应
你代码中硬编码了本地开发路径C:\\Users\\User\\IdeaProjects,IDEA本地运行时路径匹配自然可以正常执行,当你把jar包部署到服务器后,服务器不存在这个路径,无法找到对应的run.bat文件,所以没有任何执行效果。
另外还要确认打包jar时是否正确指定了主类BatRunner,以及是否把依赖的plexus-utils包打入了jar包(如果没有做fatjar打包,单独的jar包缺少依赖类也会运行失败)。执行命令后进程卡住
CommandLineUtils.executeCommandLine是同步阻塞方法,会等待启动的子进程完全退出后才会返回结果。你启动的是游戏服务器进程,这类进程默认会持续运行不会主动退出,所以代码会永远卡在这一行不会往下执行,导致大量闲置Java进程残留。
同时你的代码存在逻辑顺序错误:System.exit(0)写在了返回码判断逻辑之前,就算调用正常返回,也会直接退出进程,永远不会执行后面的返回码打印逻辑。
解决方案
这里推荐改用JDK自带的ProcessBuilder实现需求,不需要引入第三方依赖,可控性更高,修改后代码如下:
import java.io.File; import java.io.IOException; public class BatRunner { public static void main(String[] args) { // 优先读取启动参数传入的bat路径,没有就默认读取当前jar所在目录的run.bat String batPath = args.length > 0 ? args[0] : System.getProperty("user.dir") + File.separator + "run.bat"; File batFile = new File(batPath); if (!batFile.exists()) { System.err.println("找不到指定的bat文件:" + batPath); System.exit(1); } try { ProcessBuilder pb = new ProcessBuilder("cmd.exe", "/c", batFile.getAbsolutePath()); // 工作目录设置为bat文件所在目录,避免相对路径报错 pb.directory(batFile.getParentFile()); // 把服务器的输出和错误流继承到当前进程,也可以改成输出到日志文件 pb.inheritIO(); // 启动进程,不需要等待服务器退出,直接执行后续逻辑 pb.start(); System.out.println("服务器启动成功"); // 启动完成后直接退出当前Java进程,不会残留 System.exit(0); } catch (IOException e) { e.printStackTrace(); System.exit(2); } } }
使用说明
- 打包jar时确保指定主类为
BatRunner,使用上面的原生API不需要额外依赖,普通打包即可正常运行。 - 部署时可以把jar和run.bat放在同一个目录,直接执行
java -jar 你的jar包名.jar即可启动;如果bat文件在其他路径,执行java -jar 你的jar包名.jar "bat文件的绝对路径"即可。
内容的提问来源于stack exchange,提问作者Tobi
相关产品推荐
相关产品推荐

