Jenkins控制台日志保存截断问题排查求助
以下是针对你遇到的ByteArrayOutputStream方式保存日志被截断问题的排查方向:
- 检查
writeLogTo()方法的实际写入量
Jenkins的LogText.writeLogTo()方法本身可能存在输出限制,并非ByteArrayOutputStream扩容失败。可以通过打印方法返回值确认实际写入的字节数:
ByteArrayOutputStream stream = new ByteArrayOutputStream() long bytesWritten = currentBuild.rawBuild.getLogText().writeLogTo(0, stream) println "实际写入字节数: ${bytesWritten}" writeFile file: "archive/${jobName}-log.txt", text: stream.toString("UTF-8")
如果返回的bytesWritten远小于3.5MB,说明是writeLogTo()方法内部终止了写入,和流的扩容无关。部分Jenkins版本为避免内存过载,会限制该方法的输出长度。
排查安全沙箱限制
若你的Pipeline在安全沙箱中运行,currentBuild.rawBuild属于未授权的内部API调用,沙箱可能拦截部分日志写入操作。而curl调用的是Jenkins公开的HTTP接口,不受沙箱对Groovy代码的限制。可以尝试在非沙箱环境下测试原代码,验证是否能完整写入日志。确认字符编码是否正确
stream.toString()默认使用平台编码,若Jenkins日志采用UTF-8编码,编码转换错误可能导致日志看起来被截断。建议指定编码后写入文件:
writeFile file: "archive/${jobName}-log.txt", text: stream.toString("UTF-8")
同时对比生成文件的编码与Jenkins日志的实际编码,排除编码问题导致的误判。
检查JVM内存限制
虽然ByteArrayOutputStream支持动态扩容,但Jenkins的JVM堆内存不足时,扩容操作可能抛出OutOfMemoryError,导致写入提前终止。查看Jenkins的JVM日志,确认是否存在内存相关异常;同时检查JVM堆内存设置,确保有足够空间容纳3.5MB的日志数据。日志存储机制差异
Jenkins的日志可能采用分段存储,getLogText()仅能获取加载到内存的部分日志,而完整日志存储在磁盘中。curl调用的consoleText接口会直接读取磁盘上的完整日志文件,因此能获取完整内容。这种情况下,writeLogTo()只能写入内存缓存的部分日志,无法获取完整内容。
内容的提问来源于stack exchange,提问作者anechkayf

