A GraphCompose-generated banner showing the engine's own architecture: DSL to document model to layout engine to LayoutGraph, feeding PDF and PPTX backends

One Document Language, Many Formats: Separating the Layout Engine from PDFBox and Apache POI

In an earlier post about GraphCompose I described how I borrowed ideas from unrelated corners of software development and tried to apply them to document generation: a declarative DSL, a separate layout pass, snapshot tests, and a bit of ECS thinking. Back then GraphCompose mostly looked like a PDF engine. That was fair. The only real backend was PDF, PDFBox did the work underneath, and support for other formats lived somewhere between the roadmap and the classic developer promise of yes, I’ll definitely get to that later. But I never set out to build another library that can only produce PDF. The original idea was different: ...

3 August 2026 · 15 min · Artem Demchyshyn
One document description resolving into a layout graph, then into a PDF page and an editable slide deck

GraphCompose 2.1: One Document, Two Real Outputs

My girlfriend is a senior marketing researcher, and last year she started building presentations with AI tools. The first result was usually fine. The layout was there, the content was placed, the slides looked finished. Then she needed to fix a typo. Not restructure the deck — fix one word. And because the tool owned the whole artifact, the only way to change one word was to ask for the whole deck again. It would fix the typo and move a box. Or rewrite a sentence that was already correct. Or quietly break a slide that had been fine. A thirty-second correction became a negotiation with a generator. ...

26 July 2026 · 9 min · Artem Demchyshyn
A GraphCompose-rendered benchmark table comparing render time and peak heap across GraphCompose, iText 9, and JasperReports

I Just Wanted to Make a CV in Java. I Ended Up Building a Document Engine.

It started with a very simple and very innocent idea. I wanted to create my own CV in pure Java. No big framework. No fancy designer tool. No “let’s overengineer everything before I even have one page.” Just Java and PDFBox. And at first I thought: okay, how hard can it be? Famous last words. The classic PDF loop Very quickly I found myself inside the loop every developer who has touched PDFBox or iText knows by heart: ...

5 July 2026 · 14 min · Artem Demchyshyn
A long Markdown file on the left, a PDF with a clickable bookmark outline on the right

A Big Markdown File Should Become a PDF You Can Navigate

Update (July 2026). The first version of this post told one story — headings become a PDF bookmark outline. That’s still the heart of it, but the library grew a whole navigation layer since, and it just shipped to Maven Central as io.github.demchaav:graph-compose-markdown:0.3.0. So here’s the fuller picture: the outline, plus working [text](#heading) jumps, an auto-generated [TOC], a page-numbered book-style contents, and bidirectional footnotes — all the same idea applied five times. ...

4 July 2026 · 9 min · Artem Demchyshyn
GraphCompose 1.8 banner with native gradient bar charts, rendered by the engine itself

GraphCompose 1.8: Documents That Can Draw

For most of its life, GraphCompose could lay out text and structure very well, and draw very little. It produced invoices, reports, CVs, and proposals — documents that are mostly typography, spacing, and tables. That was the point. But real business documents are not only words. They have a revenue chart, a sparkline next to a KPI, a logo, a divider shape, a coloured panel with a soft gradient. Up to now, every one of those meant rasterizing an image somewhere else and pasting it in. ...

19 June 2026 · 7 min · Artem Demchyshyn
Pipeline diagram: backend data flows through a document engine and a tested layout into business documents

Document Generation Is Backend Infrastructure

Most backend systems eventually need to produce documents: invoices, reports, offers, letters, CVs, certificates, export packs. The business treats those documents as serious output. They are sent to customers, attached to applications, used by operations teams, and archived for compliance. The code that produces them often does not get the same respect. This is the companion to What Drove Me to Build GraphCompose — that post was the personal story of how GraphCompose started. This one is about a claim I now believe after living inside that code: document generation is backend infrastructure, and it pays off when you build it like infrastructure instead of like a one-off script. ...

15 June 2026 · 4 min · Artem Demchyshyn
A developer connecting layout fragments into finished document pages

What Drove Me to Build GraphCompose

It started with a simple idea: I wanted to create my own CV in pure Java. No big framework. No designer tool. No attempt to overengineer everything before I even had one page. Just Java, PDFBox, and the confidence every developer has right before a supposedly small task becomes a real project. At first I thought: how hard can it be? Very quickly I found myself inside the classic PDF generation loop: ...

14 June 2026 · 9 min · Artem Demchyshyn
A developer looking at layered document layout plans

Lessons from Building a Java PDF Engine

Building a PDF engine in Java is a useful way to meet a lot of hidden complexity at once. Text measurement, pagination, styling, rendering order, reusable components, API design, testing, and performance all become visible very quickly. This is not a tutorial about drawing text into a PDF. It is a reflection on what I learned while building the layout engine behind GraphCompose: the hard part is rarely one isolated algorithm. The hard part is making many small rules work together until the final document feels reliable. ...

14 June 2026 · 7 min · Artem Demchyshyn