Warum 11ty: sechs Jahre statisch — und warum ich auch als Build Awesome dabeibleibe

Vom eigenen PHP-CMS über WordPress zu Eleventy: warum 11ty seit 2020 meine Homepage und diese Knowledge Base baut — Sicherheit, A11y, Performance, SEO und GEO, plus eine ehrliche Einordnung des Build-Awesome-Rebrands.

von ·

Am 5. Juni 2020 habe ich in einem leeren Verzeichnis git init getippt. Zwei Tage später stand die erste package.json, und darin genau eine Zeile, die alles Weitere entschieden hat:

"devDependencies": {
  "@11ty/eleventy": "^0.11.0"
}

Diese Zeile ist heute sechs Jahre alt. Das Repository dahinter hat inzwischen 683 Commits, der letzte ist vom 21. August 2026, und es baut immer noch www.jpkc.com. Kein Rewrite, kein Framework-Wechsel, keine Migration. In einem Ökosystem, in dem Build-Tools schneller durchrotieren als meine Kaffeemaschine entkalkt wird, ist das die eigentliche Nachricht.

Ich schreibe diesen Artikel aus zwei Gründen. Erstens, weil ich immer wieder gefragt werde, warum ich mich als jemand, der seit über 25 Jahren Websites baut, ausgerechnet für einen statischen Generator entschieden habe — und dann auch noch für diesen. Zweitens, weil sich bei 11ty gerade etwas verändert: Das Projekt heißt künftig Build Awesome. Das hat in der Community für Diskussionen gesorgt, und ich finde, ein Artikel, der 11ty feiert, muss diesen Teil ehrlich mitverhandeln statt ihn wegzulassen.

Vorweg: Ich bin Fan. Das merkst du diesem Text an, und das soll es auch. Aber Fan sein heißt nicht, die Schwachstellen zu verschweigen — und eine davon ist ernst genug, dass sie hier einen eigenen Abschnitt bekommt.

Der Weg hierher: HTML, ein eigenes CMS, WordPress

Meine ersten Seiten waren reines HTML und CSS. Von Hand, Datei für Datei, mit allem Charme und aller Mühsal, die dazugehören. Irgendwann wurde mir das Kopieren gleicher Kopf- und Fußbereiche zu dumm, und ich habe getan, was Entwickler in dieser Situation eben tun: Ich habe mir mein eigenes CMS geschrieben. JPKCMS, in PHP. Es hat funktioniert, es hat mir sehr viel beigebracht, und es hatte genau den Nachteil, den jedes selbstgebaute CMS hat — ich war der einzige Mensch auf der Welt, der es warten konnte.

Danach kam WordPress. Aus den nachvollziehbaren Gründen: fertig, erweiterbar, dokumentiert, eine riesige Community. Dazwischen habe ich immer wieder Alternativen evaluiert — Drupal, Contao, Backdrop CMS, auch Hugo. Alle nur lokal, keine davon ist je online gegangen. Es waren ehrliche Tests, keine Show: Ich wollte wissen, ob es etwas gibt, das besser passt.

Was mich am Ende von WordPress weggetrieben hat, war kein einzelner Auslöser, sondern vier, die alle in dieselbe Richtung zeigten:

Der Wartungsaufwand. Meine Seite ändert sich inhaltlich in Wochen, nicht in Stunden. Trotzdem hat sie mich in einem Rhythmus beschäftigt, der zu einer Redaktion mit täglichen Beiträgen gepasst hätte: Core-Updates, Plugin-Updates, Theme-Updates, danach jedes Mal nachsehen, ob noch alles steht. Das Verhältnis von Pflege zu Inhalt stimmte nicht mehr.

Die Kontrolle über das Markup. Ich lege Wert auf semantisches HTML und auf Barrierefreiheit, die diesen Namen verdient. In einem Theme-System bist du dabei ständig am Gegensteuern: Ein Plugin bringt eigenes Markup mit, ein Widget setzt Überschriftenebenen, wie es will, ein Builder verschachtelt <div>s um Inhalte, die eigentlich eine Liste sind. Ich wollte nicht mehr korrigieren, was ein System für mich entscheidet. Ich wollte entscheiden.

Die Performance. Eine Seite, die zur Auslieferung PHP startet, eine Datenbank befragt, ein Theme rendert und ein halbes Dutzend Plugins mitlädt, hat gegen eine fertige HTML-Datei keine Chance — nicht bei der Time to First Byte, nicht beim LCP, nicht bei der Stabilität unter Last. Ich habe lange optimiert, gecacht und Plugins ausgemistet. Am Ende habe ich das Offensichtliche akzeptiert: Der schnellste Weg, HTML auszuliefern, ist, HTML auszuliefern.

Die Sicherheit. Jede WordPress-Installation ist ein permanent laufendes, öffentlich erreichbares PHP-Programm mit Datenbank und Adminbereich. Das ist kein Vorwurf an WordPress, das ist einfach die Bauform. Und diese Bauform bedeutet: Angriffsfläche, jederzeit, für jeden, der sie sucht — und es suchen sie viele, automatisiert, rund um die Uhr.

Im Juni 2020 habe ich den Schnitt gemacht. Eleventy 0.11.0 war zu dem Zeitpunkt vier Wochen alt.

Was 11ty eigentlich ist

Eleventy ist ein statischer Website-Generator in JavaScript. Du gibst ihm ein Verzeichnis mit Templates, Markdown-Dateien und Daten, er macht daraus fertiges HTML. Das war's im Kern — und diese Beschränkung ist der Punkt.

Was 11ty von den meisten Alternativen unterscheidet, steht so ähnlich auf der eigenen Startseite und ist der Grund, warum ich geblieben bin:

„Eleventy offers full control over your project's output. We don't inject our own markup into your pages."

Das ist keine Marketingfloskel, sondern eine überprüfbare Eigenschaft. Was in deinem Template steht, steht am Ende im HTML. Kein Wrapper-<div>, keine generierten Klassennamen, keine Runtime, kein Hydration-Bundle. Die Startseite formuliert das an anderer Stelle noch deutlicher: „zero client-side JavaScript by default across the board". Jedes Byte JavaScript, das bei meinen Besuchern ankommt, habe ich selbst dorthin gelegt und kann es auch selbst wieder entfernen.

Dazu kommen drei Eigenschaften, die im Alltag mehr wiegen, als sie klingen. 11ty ist zero-config, funktioniert also ohne Konfigurationsdatei, lässt sich aber tief konfigurieren, wenn du es brauchst. Es arbeitet mit deiner Verzeichnisstruktur, statt dir ein app/ oder pages/ vorzuschreiben. Und es erlaubt schrittweise Einführung — du kannst einzelne Templates umstellen und den Rest liegen lassen. Genau das hat mir 2020 den Umstieg überhaupt erst schmackhaft gemacht.

Nicht ganz unwichtig, weil es heute selten geworden ist: 11ty sammelt keine Telemetrie. „We don't have or use telemetry nor require you to opt-out of data collection", steht auf der Startseite. Ein Build-Tool, das nicht nach Hause telefoniert, sollte der Normalfall sein. Es ist es nicht.

Kurze Geschichte: von Omaha in die halbe Welt

11ty stammt von Zach Leatherman (öffnet in neuem Tab), einem Webentwickler aus Omaha, Nebraska. Die Idee war denkbar unglamourös: Jekyll fand er gut, aber Jekyll ist in Ruby geschrieben — er wollte dasselbe in JavaScript. Die erste Version, 0.1.0, erschien im Dezember 2017. Den Namen verdankt das Projekt einer Familiengeschichte: Seine Großmutter erzählte, wie er als Kind die Zahl elf falsch aussprach. „Eleventy". Daher auch das Kürzel 11ty und der Zirkus aus Uhrzeit-, Blitz-, Ballon- und Opossum-Emoji, den das Projekt bis heute im Wappen führt.

Die Versionsgeschichte, direkt aus der npm-Registry:

Version Veröffentlicht Bedeutung
0.1.0 Dezember 2017 erste Version
0.11.0 10.05.2020 die Version, mit der ich angefangen habe
1.0.0 08.01.2022 erstes stabiles Major-Release
2.0.0 08.02.2023
3.0.0 01.10.2024 Umstellung auf ESM
3.1.0 13.05.2025 „11 % schneller und 22 % kleiner"
3.1.6 02.06.2026 aktuelles Stable
4.0.0-alpha.10 01.07.2026 Canary

Zwischendurch, 2022, gab es einen Google Open Source Peer Bonus Award (öffnet in neuem Tab). Zach Leatherman selbst hat über die Jahre bei Filament Group, Netlify und CloudCannon gearbeitet, die NEJS CONF und NebraskaJS mitgetragen und nach eigener Zählung 89 Vorträge in neun Ländern gehalten — unter anderem im Weißen Haus. Heute ist er „builder for the web at Font Awesome".

Und damit sind wir beim Teil, der Erklärung braucht.

Build Awesome: was wirklich passiert ist

Am 12. September 2024 hat Font Awesome bekanntgegeben (öffnet in neuem Tab), dass Eleventy und sein Erfinder zum Unternehmen stoßen. „Eleventy and its creator, Zach Leatherman, are joining Font Awesome!" Aus einem Projekt, das lange nebenher lief, wurde eine bezahlte Vollzeitaufgabe.

Am 3. März 2026 folgte der nächste Schritt: „Eleventy is now Build Awesome" (öffnet in neuem Tab). Das Projekt zieht unter das „Awesome"-Dach von Font Awesome, so wie zuvor schon Shoelace zu Web Awesome wurde. Kernaussagen: „Eleventy v4 will be Build Awesome v4" und „Build Awesome Pro will not be required to use Build Awesome (Eleventy)." Der Open-Source-Kern bleibt MIT-lizenziert und kostenlos; „Pro" ist ein separater, kommerzieller Website-Builder darüber.

Dazu lief ein Kickstarter. Und über den kursieren bis heute falsche Darstellungen, deshalb hier die belegte Chronologie:

Datum Was passiert ist
03.03.2026 Rebrand-Ankündigung, Kickstarter startet
~04.03.2026 Finanzierungsziel an einem Tag erreicht
06.03.2026 Kampagne wird pausiert
28.04.2026 Kampagne startet neu
13.05.2026 zusätzliche Sponsoring-Stufen
29.05.2026 Abschluss bei 313 % finanziert

Der Grund für die Pause war banal und bitter zugleich. Font Awesome schrieb dazu (öffnet in neuem Tab): „Most of our announcements never landed. We won't get into details, but let's just say Gmail had other ideas. Our launch emails reached maybe 5-10% of the people they were supposed to." Kickstarter-Kampagnen leben von den ersten 48 Stunden — und die verpufften, weil die Ankündigungsmails im Spam landeten. Also: abbrechen, E-Mail-Infrastruktur reparieren, neu starten. Der Neustart hat funktioniert, die Kampagne endete deutlich über Ziel.

Der Umbenennung ist das nicht in die Quere gekommen, auch wenn das gelegentlich behauptet wird. Nachprüfbar: Das GitHub-Repository liegt heute unter 11ty/buildawesome (öffnet in neuem Tab), und seit dem 16. Juni 2026 existiert das npm-Paket @awesome.me/buildawesome — MIT-lizenziert, mit 4.0.0-alpha.10 als Alpha-Kanal. @11ty/eleventy funktioniert daneben unverändert weiter.

Die Kritik — und warum sie mich nicht umstimmt

Die Reaktionen waren teilweise heftig. Der meistdiskutierte Beitrag, „The End of Eleventy" (öffnet in neuem Tab) vom 4. März 2026, argumentiert, dass ein visueller Website-Builder an der eigentlichen Zielgruppe vorbeigeht: Wer sich für statische Seiten interessiere, ziehe eine lokale Entwicklungsumgebung und ein Terminal jeder Klickoberfläche vor. Der Rebrand fühle sich „corporate, pro-capitalist" an und mache aus einem der letzten handwerklichen Hobbys eine Ware. Andere störten sich schlicht daran, dass die Ankündigung den Namen Eleventy kaum noch nannte — ein Kommunikationsfehler, den Font Awesome im Pause-Beitrag selbst einräumt: „One thing we want to be clearer about in the relaunch…"

Ich verstehe das Unbehagen. Ein Projekt, das dir jahrelang gehört hat, bekommt plötzlich einen Produktnamen — das fühlt sich an wie ein Umzug, den jemand anders für dich beschlossen hat. Und wer schon erlebt hat, wie Open Source nach einer Übernahme langsam ausgetrocknet wurde, hat allen Grund, misstrauisch zu sein.

Trotzdem bleibe ich entspannt, und zwar aus drei Gründen.

Erstens: Die Zusage ist explizit und unmissverständlich. „Build Awesome (née Eleventy) will always be free and open source. Always." Das steht in einem offiziellen Beitrag, nicht in einem Forumskommentar.

Zweitens: Die Lizenz ist MIT, und das gilt auch für den neuen Paketnamen. MIT lässt sich für bereits veröffentlichten Code nicht rückwirkend zurücknehmen. Falls es je schiefgehen sollte, ist ein Fork keine Drohgebärde, sondern ein Werkzeug, das jederzeit greifbar ist.

Drittens, und das wiegt für mich am schwersten: Ich habe die Alternative gesehen. Ein Open-Source-Projekt, das ausschließlich in der Freizeit einer einzelnen Person entsteht, ist kein Erfolgsmodell — es ist ein Risiko mit angenehmer Oberfläche. Wenn diese Person die Lust verliert, krank wird oder das Leben dazwischenkommt, steht dein Fundament still. Eine Finanzierung, die Vollzeitarbeit an einem MIT-lizenzierten Kern bezahlt, ist mir lieber als romantischer Ehrenamts-Verschleiß. Dass mir der Name „Build Awesome" weniger gefällt als „Eleventy", ändert daran nichts. Namen sind Geschmack. Wartung ist Substanz.

Was ich tatsächlich beobachte statt nur zu glauben: ob der Open-Source-Kern weiter Releases bekommt, ob die Dokumentation gepflegt bleibt, und ob Pro-Funktionen dem freien Kern etwas wegnehmen. Der bisherige Befund spricht dagegen, und zwar mit Daten von nach dem Rebrand: Das freie @11ty/eleventy hat am 2. Juni 2026 die 3.1.6 bekommen, die Version-4-Alphas kamen am 18. Juni und am 1. Juli. Das Projekt liefert also genau in den Monaten, in denen die Kritiker den Ausverkauf befürchtet haben.

Warum 11ty für meine Projekte die richtige Wahl ist

Jetzt zum eigentlichen Thema. Sechs Gründe, warum ich diese Entscheidung nicht bereut habe.

Sicherheit: das, was nicht läuft, kann nicht angegriffen werden

Meine Seite besteht aus HTML, CSS und ein wenig JavaScript. Auf dem Server läuft zur Auslieferung kein Code. Keine PHP-Runtime, keine Datenbank, kein Adminbereich, keine Session, kein Login-Formular, kein Upload-Verzeichnis mit Schreibrechten. Die klassischen Angriffswege einer dynamischen Website — SQL-Injection, Remote Code Execution, kompromittierte Plugins, geratene Admin-Passwörter — laufen ins Leere, weil es nichts gibt, in das sie hineinlaufen könnten.

Das ist kein Härtungstrick, sondern eine Eigenschaft der Bauform, und deshalb bleibt sie auch bestehen, wenn ich einen Monat lang nicht hinschaue. Kein Sicherheitsupdate, das am Freitagabend eingespielt werden muss, weil in irgendeiner Erweiterung eine Lücke aufgetaucht ist, die seit Jahren stillschweigend mitläuft.

Die ehrliche Kehrseite: Node.js und npm

Und jetzt der Teil, den ein Fan-Artikel gerne weglässt — ich nicht, weil er wichtig ist.

Die Angriffsfläche verschwindet nämlich nicht. Sie verschiebt sich. Weg von der Laufzeit, hin zur Build-Zeit. In der Sekunde, in der ich npm ci ausführe, holt sich mein Rechner dutzende bis hunderte fremde Pakete und darf im Standardverhalten beliebigen Code daraus ausführen — über Install-Hooks, noch bevor ich irgendetwas davon benutze. Das ist der Vektor, über den event-stream, ua-parser-js und die ganze Reihe der npm-Vorfälle funktioniert haben.

Wer behauptet, eine statische Seite sei „automatisch sicher", hat diese Verschiebung nicht verstanden. Der gefährliche Moment ist nicht der Seitenaufruf, sondern der Build.

Das ist beherrschbar, und ich habe mein komplettes Gegen-Setup in einem eigenen Artikel aufgeschrieben: Sicheres Arbeiten mit Node.js und npm. Die Kurzfassung, so wie sie in allen meinen Projekten läuft — auch in dem, das diese Seite hier baut:

  • Socket Firewall (sfw) vor jedem npm-Aufruf. Bekannte Schadpakete werden geblockt, bevor sie auf die Platte kommen — und damit bevor ein Install-Hook überhaupt starten könnte.
  • ignore-scripts=true in der .npmrc. Install-Hooks laufen grundsätzlich nicht.
  • save-exact=true und exakt gepinnte Versionen ohne ^ oder ~. Kein Build zieht ungefragt eine neue Version.
  • npm ci statt npm install als Standard. Reproduzierbar aus dem Lockfile.
  • "private": true in der package.json, alle Abhängigkeiten als devDependencies.

Erfreulich ist, dass das 11ty-Projekt hier selbst vorangeht. Im Dezember 2025 hat Zach Leatherman beschrieben (öffnet in neuem Tab), wie das gesamte @11ty/*-Ökosystem auf Trusted Publishers umgestellt wurde: „we are now npm Access Token-free!" Damit gibt es keine langlebigen Zugangstoken mehr, die jemand stehlen könnte — der Klassiker bei gekaperten Maintainer-Konten. Begründet wird das ausdrücklich mit der Lage im Ökosystem: „As we harden our release practices in the wake of numerous recent vulnerabilities in npm packages amongst high profile authors…"

Dazu kommt konsequente Abhängigkeits-Diät. 2025 hat das Projekt die Dependency-Zahl des Kerns um 28 % und das Gewicht um 22 % gesenkt, von 187 auf 134 Pakete und von 27 MB auf 21 MB. Die aktuelle 3.1.6 hat 33 direkte Abhängigkeiten. Bei den Version-4-Alphas geht die Kurve weiter nach unten. Jede Abhängigkeit, die nicht da ist, kann auch nicht kompromittiert werden — das ist die einzige Supply-Chain-Maßnahme mit hundertprozentiger Wirksamkeit.

Barrierefreiheit: Kontrolle ist die halbe Miete

Barrierefreiheit ist bei mir kein nachgelagerter Prüfpunkt, sondern Teil der Bauweise — spätestens seit dem BFSG ist sie das auch rechtlich für viele. Und hier zahlt sich „we don't inject our own markup into your pages" jeden Tag aus.

Wenn eine Landmark falsch gesetzt ist, ist das meine Entscheidung gewesen, und ich kann sie in einer Zeile korrigieren. Wenn die Überschriftenhierarchie springt, liegt das an meinem Template, nicht an einem Plugin. Wenn ein Fokus-Style unsichtbar ist, hat kein fremdes Stylesheet ihn weggeräumt. Ich habe in den WordPress-Jahren mehr Zeit damit verbracht, fremdes Markup zu reparieren, als eigenes zu schreiben — und Reparatur ist bei Barrierefreiheit immer die schlechtere Ausgangslage als Konstruktion. Wie ich die Struktur konkret aufbaue, steht in HTML-Landmarks in der Praxis.

Für diese These gibt es auch außerhalb meiner Projekte einen guten Zeugen. Eric Bailey, der A11Y Project (öffnet in neuem Tab) läuft auf 11ty, hat es so beschrieben:

„a11yproject.com launched with version 1.0.0 of Eleventy. […] It's been a little under three years and I haven't had to make any adjustments to its dependencies, and it can still install and run from a cold start with no complications."

Dass ausgerechnet das bekannteste Barrierefreiheits-Projekt des Webs mit diesem Generator baut, halte ich nicht für einen Zufall.

Performance: die Ausgangslage ist unschlagbar

Bei Core Web Vitals gewinnst du die meisten Punkte, bevor du optimierst — durch die Architektur. Eine statische HTML-Datei vom Apache hat keine Datenbankabfrage, kein Template-Rendering zur Laufzeit, keine PHP-Initialisierung. Die Time to First Byte ist eine Frage von Dateisystem und Netzwerk, sonst nichts. Und weil im Standard kein Framework-JavaScript mitkommt, gibt es auch keinen Hydration-Schritt, der den INP nach unten zieht, und keine nachträglich einfliegenden Komponenten, die den CLS ruinieren.

Das heißt nicht, dass Performance geschenkt ist. Bilder, Schriften und die eigenen Skripte muss ich weiterhin im Griff haben, und genau darum geht es in Core Web Vitals & Performance. Der Unterschied ist die Startposition: Ich optimiere von einem sehr guten Wert aus nach oben, statt einen schlechten mit Caching-Schichten zu übertünchen.

Auf der Build-Seite bin ich dir einen ehrlichen Wert schuldig, weil an dieser Stelle gerne geflunkert wird. Ein vollständiger Production-Build dieser Knowledge Base erzeugt Stand heute 1.936 Dateien — 963 HTML-Seiten, dazu 962 Markdown-Spiegel (die 404 hat keinen) sowie Feeds, Sitemap und llms.txt. Er dauert auf meiner Maschine je nach Auslastung knapp drei bis dreieinhalb Minuten — zwei Durchläufe beim Schreiben dieses Artikels brauchten 176 und 209 Sekunden. Damit gewinne ich keinen Blumentopf, und ich schreibe es trotzdem hin, weil „blitzschnell" in solchen Artikeln zu oft heißt „nicht nachgemessen".

Interessanter ist, wohin die Zeit geht — denn 11ty sagt es dir von sich aus. Der eingebaute Benchmark weist den größten Einzelposten meiner eigenen Konfiguration zu: rund 35 Sekunden, etwa 19 % der Gesamtzeit, für einen Transform, der jeden externen Link mit target="_blank", rel="noopener", einer Markierungsklasse und einem versteckten „öffnet in neuem Tab"-Hinweis versieht. Das ist meine Entscheidung, nicht die des Generators. Genau das schätze ich daran: Ich sehe schwarz auf weiß, was mich was kostet, und kann jederzeit abwägen, ob mir eine Funktion ihre Sekunden wert ist. Für den Fall, dass es eng wird, bringt 11ty außerdem inkrementelle Builds mit — die habe ich hier bislang schlicht nicht gebraucht.

SEO und GEO: crawlbar ist der halbe Sieg

Für Suchmaschinen ist eine vorgerenderte Seite der freundlichste Fall, den es gibt. Der komplette Inhalt steht im ausgelieferten HTML — kein Rendering-Budget, keine JavaScript-Ausführung, kein Zwei-Wellen-Indexing, bei dem der eigentliche Text erst in der zweiten Runde ankommt. Strukturierte Daten, Canonicals, hreflang, Sitemap: alles zur Build-Zeit erzeugt, überall identisch, ohne Plugin, das sich in die Quere kommt. Der technische Unterbau dazu steht in Technical SEO: Das Fundament.

Bei GEO, der Optimierung für generative KI-Systeme, wird der Vorteil noch größer, und das ist der Grund, warum diese Seite überhaupt existiert. Weil ich die volle Kontrolle über den Build habe, kann ich zusätzliche Ausgabeformate erzeugen, die kein CMS-Plugin für mich vorgesehen hätte. Jede Seite hier gibt es deshalb zusätzlich als reines Markdown: /db/blog/warum-11ty/ liegt auch unter /db/blog/warum-11ty.md, mit dem unveränderten Original-Markdown statt einer HTML-Rückübersetzung. Dazu ein llms.txt als Index über alle Inhalte und ein <link rel="alternate" type="text/markdown"> im <head>, damit Systeme das rauschfreie Format überhaupt finden.

Genau das ist mit 11ty ein überschaubarer Aufwand: ein Pagination-Template, ein Filter, fertig. In einem System, das mir das Markup abnimmt, wäre es entweder ein Plugin-Projekt oder unmöglich. Was das inhaltlich bedeutet, steht in GEO: Sichtbarkeit in KI-Antworten und Schreiben für KI.

Kosten und Aufwand: das Argument, das niemand vorträgt

Der Kostenvorteil einer statischen Seite wird meist mit dem Hosting begründet. Das stimmt auch — fertige Dateien brauchen keine PHP-Prozesse, keinen Datenbankserver, keine Skalierung nach Last, und sie lassen sich auf praktisch jedem Webspace ausliefern. Aber der größere Posten ist ein anderer, und er taucht in keiner Rechnung auf: meine Zeit.

Kein monatliches Update-Fenster. Kein Nachziehen von Plugins, die nach einem Core-Update nicht mehr wollen. Kein nächtlicher Anruf, weil eine Lücke aktiv ausgenutzt wird. Keine Backup-Strategie für eine Datenbank — das Repository ist das Backup, und der Build ist jederzeit reproduzierbar. Rechne die Stunden zusammen, die eine gepflegte CMS-Installation über sechs Jahre kostet, und du hast den eigentlichen Betrag. Bei mir ist er in diesen sechs Jahren gegen null gegangen.

Stabilität: das unterschätzte Feature

Für mich der stärkste Punkt, und der, den ich erst mit den Jahren richtig schätzen gelernt habe. Das Projekt formuliert ihn selbst am besten:

„Eleventy is stable. We've shipped 226 releases going back to the first version in December 2017 and only three of those releases have had Eleventy-specific changes requiring developer changes."

226 Releases, drei davon mit Anpassungsbedarf. Ich habe das an meinem eigenen Repository gegengeprüft, und das Ergebnis ist erfreulich langweilig:

  • 12.04.2022, Sprung auf 1.0.0 — der Versions-Commit steht in der Historie zwischen Favicon- und Logo-Änderungen desselben Tages. Kein Nachspiel.
  • 28.02.2023, Sprung auf 2.0.0 — der Versions-Commit und ein node_modules-Update, beide am selben Tag. Die Commits der Folgetage betreffen Barrierefreiheit, nicht die Migration.
  • 22.10.2024, Sprung auf 3.0.0 — die ESM-Umstellung, der größte Bruch der Projektgeschichte. Bei mir: drei Commits, alle an einem einzigen Tag.

In sechs Jahren gab es keinen Punkt, an dem ich vor der Wahl stand, entweder alles neu zu schreiben oder auf einer toten Version sitzen zu bleiben. Wer die letzten Jahre im JavaScript-Ökosystem verbracht hat, weiß, wie außergewöhnlich das ist.

Flexibilität und Erweiterbarkeit

11ty bringt out of the box HTML, Markdown, JavaScript, Liquid, Nunjucks, Handlebars, Mustache und EJS mit; über Plugins kommen WebC, Haml, Pug, TypeScript, JSX, MDX und Sass dazu. Entscheidend ist nicht die Länge der Liste, sondern dieser Satz aus der Dokumentation:

„Eleventy's super power is that it is built on an extensible architecture that can work with one or more template languages in the same project."

Du musst dich nicht entscheiden. In diesem Projekt schreibe ich Inhalte in Markdown, Layouts in Nunjucks, Generatoren für die Markdown-Spiegel ebenfalls in Nunjucks und die Build-Logik in reinem JavaScript. Alles im selben Projekt, ohne Brücke.

Dazu die Haltung zum Format, die ich für unterschätzt halte: „We don't want to hold your content hostage with a custom format." Meine Inhalte sind Markdown-Dateien mit YAML-Frontmatter. Wenn ich 11ty morgen verlassen wollte, nähme ich das Verzeichnis mit und wäre fertig. Das ist keine theoretische Freiheit — es ist der Grund, warum ich den Umstieg 2020 überhaupt gewagt habe.

Erweitert wird in JavaScript, nicht in einer Template-Sprache mit angeflanschter Logik. Ein eigener Filter ist eine Funktion:

// config/filters.js — der tatsächliche Filter aus diesem Projekt
eleventyConfig.addFilter("mdUrl", function (url) {
  if (!url) return url;
  const trimmed = url.endsWith("/") ? url.slice(0, -1) : url;
  return (trimmed === "" ? "/index" : trimmed) + ".md";
});

Genau so entstehen hier die Markdown-Spiegel, die Tag-Suche und die zweisprachige Navigation. Nichts davon ist ein Plugin, das jemand für mich vorgesehen hätte — es sind fünf Zeilen JavaScript in einer Datei, die ich vollständig verstehe.

Der pathPrefix ist ein schönes Beispiel dafür, wie weit diese Konfigurierbarkeit reicht. Diese Knowledge Base liegt nicht auf einer eigenen Domain, sondern als Unterordner unter https://www.jpkc.com/db/. Dafür brauche ich genau eine Zeile:

// eleventy.config.js — gekürzt
return {
  pathPrefix: "/db/",
  dir: { input: "src", output: "_site", includes: "_includes", data: "_data" },
};

Der eingebaute HTML-Base-Plugin schreibt danach alle internen Links und Assets im Output automatisch um. Ich schreibe in meinen Templates weiterhin /assets/css/main.css, ausgeliefert wird /db/assets/css/main.css. Ein Unterordner-Deployment, das in anderen Systemen ein Nachmittag voller Überraschungen ist, ist hier eine Konfigurationszeile.

Plattformunabhängigkeit: der Node-Bonus

11ty läuft überall, wo Node.js läuft — offiziell ab Version 18. Das ist praktisch jedes System, das für Entwicklung in Frage kommt: Linux, macOS, Windows, WSL, ein Container, ein CI-Runner, ein Raspberry Pi.

Für mich ist das kein abstraktes Argument. Ich entwickle unter WSL2 auf Windows, dieses Blog hier baut zusätzlich auf einem GitHub-Actions-Runner unter Linux, und ausgeliefert wird auf einen Apache-Webspace. Sehr verschiedene Umgebungen, und der Build verhält sich in allen identisch, weil er nichts voraussetzt außer Node und dem Lockfile. Kein Compiler-Toolchain-Abenteuer, keine plattformspezifischen Binaries, die auf dem CI-Runner fehlen — bis auf eine Handvoll nativer Pakete wie sharp oder pagefind, die ihre Binaries sauber über optionalDependencies mitbringen.

Der Vergleich mit Hugo ist hier ehrlicherweise ein Unentschieden: Ein einzelnes Go-Binary ist beim Deployment noch anspruchsloser. Der Unterschied ist, was du beim Erweitern in der Hand hast. Bei Hugo schreibst du Go-Templates. Bei 11ty schreibst du JavaScript — dieselbe Sprache, in der ich ohnehin denke, mit einem Ökosystem, in dem es für jede Aufgabe schon eine Bibliothek gibt. Für mich hat genau das den Ausschlag gegeben, zusammen mit der Freiheit bei den Template-Sprachen.

Automatisiertes Deployment

Ein Build, der reproduzierbar aus einem Repository fällt, lässt sich automatisieren — und das ist der zweite große Gewinn nach der Sicherheit.

Bei mir laufen beide Varianten parallel, und ich finde die Gegenüberstellung lehrreich. www.jpkc.com übertrage ich weiterhin manuell: bauen, _site/ hochladen, fertig. Das klingt altmodisch, ist aber bei einer Seite, die sich selten ändert, vollkommen ausreichend — und es hat einen Vorzug, den ich nicht unterschätze: Zwischen meinem Commit und der Live-Seite steht eine bewusste Entscheidung.

Diese Knowledge Base dagegen wird über einen GitHub-Actions-Workflow gebaut und ausgeliefert. Bei 1.936 erzeugten Dateien pro Durchlauf und mehreren Änderungen pro Woche will ich das nicht mehr von Hand machen — und die drei Minuten Build-Zeit verbringt lieber ein Runner als ich. Was so ein Workflow leistet, ist immer dasselbe Muster:

  1. Checkout des Repositories.
  2. Node in der festgelegten Version bereitstellen.
  3. npm ci — reproduzierbar aus dem Lockfile, nicht npm install.
  4. Build ausführen, inklusive CSS, JS-Bundle und Suchindex.
  5. Das Ergebnis auf das Ziel übertragen.

Der Punkt, auf den es mir dabei ankommt: Auch die CI ist eine Maschine, auf der fremde Pakete installiert werden. Alles, was ich lokal an Härtung mache, gehört genauso in den Workflow — npm ci, gepinnte Versionen, keine Install-Hooks. Ein Deploy-Workflow, der ungeprüft aus der Registry zieht, ist kein Fortschritt, sondern nur ein schnellerer Weg zum selben Problem. Wie ich Workflows dieser Art aufsetze, habe ich am Beispiel eines WordPress-Plugins in Eigene WordPress-Plugins per GitHub Actions ausliefern beschrieben.

Wo 11ty nicht die Antwort ist

Ein Fan, der keine Grenzen benennt, ist ein schlechter Ratgeber. Es gibt drei Fälle, in denen ich abraten würde.

Redaktionelle Teams ohne Terminal. 11ty setzt Git, eine Kommandozeile und einen Editor voraus. Für Kolleginnen und Kollegen, die einen Beitrag schreiben und auf „Veröffentlichen" klicken wollen, ist das die falsche Bauform. Es gibt Git-basierte Redaktionsoberflächen, und Build Awesome Pro zielt genau auf diese Lücke — aber im Standard ist 11ty ein Werkzeug für Menschen, die mit Dateien arbeiten. Wenn dein Team das nicht will, nimm ein CMS und sei damit glücklich.

Wirklich dynamische Funktionen. Ein Login-Bereich, ein Warenkorb, personalisierte Inhalte, ein Forum: All das braucht Code zur Laufzeit. Das lässt sich um eine statische Seite herum bauen, über externe Dienste oder ein separates Backend, aber dann sitzt die Komplexität eben dort. Wenn der dynamische Teil das Herz deines Projekts ist, baust du am Ende zwei Systeme statt eines.

Sehr große Seitenzahlen. Bei Zehntausenden von Seiten wird der Build-Durchlauf zum Thema. 11ty hat dafür inkrementelle Builds und einen Cache, und in meiner Größenordnung merke ich davon nichts — aber im sechsstelligen Bereich gehört das ehrlich geprüft, bevor du dich festlegst.

Und der vierte Punkt, den ich oben schon ausgeführt habe: Die Node-Abhängigkeit bringt die npm-Angriffsfläche zur Build-Zeit mit. Beherrschbar, aber nicht wegzudiskutieren.

Fazit

Sechs Jahre, ein Generator, zwei Websites, kein Rewrite. Wenn ich den Nutzen von 11ty auf einen Satz eindampfen müsste, wäre es dieser: Es nimmt mir die Arbeit ab, die ich nicht machen will, und lässt mir die Kontrolle über alles, was mir wichtig ist.

Das Bauen von HTML aus Templates und Markdown übernimmt es. Semantik, Barrierefreiheit, Performance-Budget, Struktur, Ausgabeformate — das bleibt bei mir. Genau in dieser Aufteilung liegt der Unterschied zu einem CMS, das mir Arbeit abnimmt, indem es Entscheidungen für mich trifft, die ich lieber selbst getroffen hätte.

Ob das Werkzeug in einem Jahr Eleventy oder Build Awesome heißt, ist mir dabei ehrlich gesagt gleichgültig. Was zählt, ist die MIT-Lizenz, ein Kern, der weiter gepflegt wird, und Inhalte in einem Format, das ich jederzeit mitnehmen kann. Diese drei Dinge stehen, und sie stehen heute besser da als in den Jahren, in denen das Projekt von der Freizeit einer einzelnen Person abhing.

Falls du gerade vor derselben Frage stehst wie ich 2020: Es ist ein Nachmittag, um es auszuprobieren. Ein Verzeichnis, eine Markdown-Datei, npx @11ty/eleventy --serve. Mehr braucht es nicht, um zu sehen, ob es zu dir passt.

Weiterlesen