You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Shell脚本终端可运行,Kotlin调用无法启动MapTiler服务器

问题排查:Kotlin调用MapTiler启动脚本卡住的原因与解决方法

核心原因

通过Java/Kotlin的Runtime.exec()或kscript的runCommand()调用长期运行的进程(如MapTiler服务器)时,子进程的标准输出(stdout)和标准错误(stderr)会被系统缓冲区缓存。当缓冲区被填满后,子进程会暂停执行,等待父进程读取缓冲区内容,最终导致出现CPU占用为0的阻塞状态。而直接在终端运行脚本时,终端会实时消费这些输出,不会触发缓冲区阻塞。

验证依据

  • 执行ls/date等输出量极小的命令时正常,因为输出不会填满缓冲区
  • 手动终止bash进程后,Kotlin应用抛出异常,说明父进程一直等待子进程退出,但子进程实际因缓冲区阻塞无法继续运行

解决方案

方案1:修改脚本,重定向输出

在setup_server.sh中把输出重定向到文件或/dev/null,避免缓冲区堆积:

#! /bin/sh
./maptiler-server --workDir "./" --adminPassword "abcdefg" > server.log 2>&1

若不需要保留日志,可直接丢弃输出:

#! /bin/sh
./maptiler-server --workDir "./" --adminPassword "abcdefg" > /dev/null 2>&1

方案2:在Kotlin代码中主动处理子进程输出

通过单独线程读取子进程的stdout和stderr,避免缓冲区阻塞:

class ScriptExecutor {
    companion object{
        @JvmStatic
        fun execute(s: String){
            try {
                // 简化命令,去掉冗余的sh嵌套
                val cmd = arrayOf("/bin/sh", "./maptiler-server-macos/setup_server.sh")
                val process = Runtime.getRuntime().exec(cmd)
                
                // 启动线程读取标准输出
                Thread {
                    process.inputStream.bufferedReader().useLines { lines ->
                        lines.forEach { println(it) }
                    }
                }.start()
                
                // 启动线程读取标准错误
                Thread {
                    process.errorStream.bufferedReader().useLines { lines ->
                        lines.forEach { System.err.println(it) }
                    }
                }.start()
                
                // 若无需等待服务器启动完成,可注释下面的代码
                // process.waitFor()
            }catch (e: Exception){
                e.printStackTrace()
            }
        }
    }
}

额外优化:简化调用命令

原命令/bin/sh -c sh ./xxx.sh存在冗余嵌套,直接使用/bin/sh ./maptiler-server-macos/setup_server.sh即可;也可以给脚本添加可执行权限(chmod +x setup_server.sh),之后直接调用./maptiler-server-macos/setup_server.sh。

内容的提问来源于stack exchange,提问作者Chicovara

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.15 15:22:16