I'm using Java 11 Corretto + Spring Boot with Apache POI but I'm facing issues when using on AWS Lambda. Works fine if I run as "normal" API but fails when running servless in a AWS lambda.
try (ByteArrayOutputStream out = new ByteArrayOutputStream(); SXSSFWorkbook workbook = new SXSSFWorkbook(1000)) {
SXSSFSheet sheet = workbook.createSheet("test"); //error here!!
} ...
Caused by: java.lang.Error: Probable fatal error: No physical fonts found. at java.desktop/sun.font.SunFontManager.lambda$getDefaultPhysicalFont$0(Unknown Source) at java.base/java.util.Optional.orElseThrow(Unknown Source) at java.desktop/sun.font.SunFontManager.getDefaultPhysicalFont(Unknown Source) at java.desktop/sun.font.CompositeFont.doDeferredInitialisation(Unknown Source) at java.desktop/sun.font.CompositeFont.getSlotFont(Unknown Source) at java.desktop/sun.font.CompositeGlyphMapper.initMapper(Unknown Source) at java.desktop/sun.font.CompositeGlyphMapper.(Unknown Source) at java.desktop/sun.font.CompositeFont.getMapper(Unknown Source) at java.desktop/sun.font.CompositeFont.canDisplay(Unknown Source) at java.desktop/java.awt.Font.canDisplayUpTo(Unknown Source) at java.desktop/java.awt.font.TextLayout.singleFont(Unknown Source) at java.desktop/java.awt.font.TextLayout.(Unknown Source) at org.apache.poi.ss.util.SheetUtil.getDefaultCharWidth(SheetUtil.java:285) at org.apache.poi.xssf.streaming.AutoSizeColumnTracker.(AutoSizeColumnTracker.java:117) at org.apache.poi.xssf.streaming.SXSSFSheet.(SXSSFSheet.java:84) at org.apache.poi.xssf.streaming.SXSSFWorkbook.createAndRegisterSXSSFSheet(SXSSFWorkbook.java:705) at org.apache.poi.xssf.streaming.SXSSFWorkbook.createSheet(SXSSFWorkbook.java:724)
I tried to create a fix to the fonts but I have no idea how to proceed
@PostConstruct
public void loadFonts() {
URL configURL = getClass().getClassLoader().getResource("fontconfig.properties");
String path = configURL != null ? configURL.getPath() : null;
Properties props = System.getProperties();
LOGGER.info("Loading font config file: {}", path);
props.put("sun.awt.fontconfig", path);
String[] fonts;
try {
GraphicsEnvironment.getLocalGraphicsEnvironment().getAvailableFontFamilyNames();
} catch (Throwable ex) {
LOGGER.warn("Reloading Fonts");
}
try {
fonts = GraphicsEnvironment.getLocalGraphicsEnvironment().getAvailableFontFamilyNames();
for (String font : fonts) {
LOGGER.info("Available Font: {}", font);
}
} catch (Throwable ex) {
LOGGER.error("Could not load Fonts");
}
}
Config file:
version=1
sequence.allfonts=default
When running on AWS Lambda it outputs some fonts to the logs so I don't understand why I get that error:
2022-05-31 16:00:14 INFO Starting Lambda Container Handler 2022-05-31 16:00:18 INFO Loading font config file: /var/task/fontconfig.properties 2022-05-31 16:00:18 INFO Available Font: Dialog 2022-05-31 16:00:18 INFO Available Font: DialogInput 2022-05-31 16:00:18 INFO Available Font: Monospaced 2022-05-31 16:00:18 INFO Available Font: SansSerif 2022-05-31 16:00:18 INFO Available Font: Serif
Any idea how to add physical fonts and why can't the POI use the available fonts that output to the logs?
EDIT: I also tried to run as headless but I get the same error:
`props.setProperty("java.awt.headless", "true");`