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

Apache POI生成Excel时K8s环境JVM崩溃问题求助

问题描述

我开发的Web应用使用Apache POI实现数据写入Excel并提供下载功能,在Linux虚拟机上运行正常,但部署到K8s环境后,每次触发下载请求都会导致JVM崩溃。

关键崩溃信息

JVM崩溃日志核心片段

# A fatal error has been detected by the Java Runtime Environment:
#
#  SIGSEGV (0xb) at pc=0x00007f808e739294, pid=1, tid=0x00007f7fe52a4700
#
# JRE version: Java(TM) SE Runtime Environment (8.0_241-b07) (build 1.8.0_241-b07)
# Java VM: Java HotSpot(TM) 64-Bit Server VM (25.241-b07 mixed mode linux-amd64 compressed oops)
# Problematic frame:
# C  [libc.so.6+0x10b294]  __clock_gettime+0x24
#
# The crash happened outside the Java Virtual Machine in native code.

Java调用栈关键路径

org.apache.poi.ss.util.SheetUtil.getDefaultCharWidth(Workbook)
org.apache.poi.xssf.streaming.AutoSizeColumnTracker.<init>(Sheet)
org.apache.poi.xssf.streaming.SXSSFSheet.<init>(SXSSFWorkbook, XSSFSheet)

运行环境

操作系统:Alpine Linux v3.13
libc版本:glibc 2.30

解决方案

从崩溃路径看,问题是POI自动计算列宽时触发了Java字体管理的本地代码崩溃,结合Alpine环境的特性,可按以下方案解决:

  • 禁用自动列宽计算:
    替换POI自动计算列宽的逻辑,手动设置固定列宽,避免触发字体相关的本地调用:

    // 示例:设置第0列宽度为15个字符(POI中列宽单位为1/256字符宽度)
    sheet.setColumnWidth(0, 256 * 15);
    
  • 启用Java无头模式:
    在JVM启动参数中添加-Djava.awt.headless=true,让Java在无图形环境下运行,跳过X11字体管理器的初始化,避免触发崩溃的本地代码路径。

  • 更换基础镜像:
    Alpine Linux默认使用musl libc,与Oracle JDK兼容性较差,换成基于Debian/Ubuntu的OpenJDK镜像(如openjdk:8-jdk-slim),这类镜像使用glibc,能更好适配Oracle JDK的本地调用。

  • 在Alpine镜像中补充依赖:
    如果必须使用Alpine,安装字体配置工具和基础字体,确保Java能正常加载字体:

    apk add --no-cache fontconfig ttf-dejavu
    

    同时在JVM参数中指定字体路径:

    -Dsun.font.fontpath=/usr/share/fonts/TTF
    

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.25 15:24:18