2 Punkte von GN⁺ 2025-09-12 | 1 Kommentare | Auf WhatsApp teilen
  • Die Paketinstallation von Bun arbeitet im Vergleich zu bestehenden Paketmanagern extrem schnell
  • Der Schlüssel zur schnellen Installation liegt in einem systemprogrammatischen Ansatz und der Minimierung von Systemaufrufen
  • Leistungssteigerungen werden durch detaillierte Strategien wie native Implementierung auf Basis von Zig, die Nutzung von Binärcaches und OS-spezifische Optimierungen erzielt
  • Auch bei der Entpackung von Tarballs und dem Kopieren von Dateien kommen Hochleistungsverfahren zum Einsatz, die Hardware-Eigenschaften ausnutzen
  • Durch Optimierung von Datenstrukturen wie Abhängigkeitsgraphen und Lockfiles werden CPU-Cache-Effizienz und Speicherzugänglichkeit verbessert

Warum Bun Install schnell ist

  • bun install von Bun bietet im Durchschnitt eine 7-fach schnellere Paketinstallation als npm, 4-fach schneller als pnpm und 17-fach schneller als yarn
  • Das liegt nicht nur an Benchmarks, sondern daran, dass das Problem der Paketinstallation aus der Perspektive der Systemprogrammierung statt aus der von JavaScript angegangen wurde
  • Auf mehreren Ebenen werden Leistungsoptimierungen konsequent umgesetzt, darunter die Minimierung von Systemaufrufen, binäres Caching von Manifesten, optimierte Tarball-Extraktion und natives Dateikopieren des Betriebssystems

Grenzen von Node.js und der Architektur von Paketmanagern

  • Seit der Veröffentlichung von Node.js im Jahr 2009 hat sich das asynchrone IO-Modell auf Basis von Event Loop und Threadpool auch auf Paketmanager übertragen
  • Damals war diese Strategie mit asynchronem IO und hoher Frequenz an Systemaufrufen aufgrund der Hardwaregrenzen (langsame Festplatten, langsame Netzwerke) sinnvoll
  • In modernen Systemen sind jedoch NVMe-SSDs, schnelle Netzwerke und leistungsstarke CPUs verbreitet, und der eigentliche Flaschenhals ist nicht IO, sondern der Overhead von Systemaufrufen

Die Kosten von Systemaufrufen und Moduswechseln

  • Wenn ein Programm eine Aufgabe wie das Lesen einer Datei anfordert, muss es von User Mode in den Kernel Mode wechseln, was teure CPU-Zyklen verbraucht (1000–1500 cycles)
  • Paketinstallationen erfordern grundsätzlich zehntausende bis hunderttausende Systemaufrufe, sodass allein die Kosten dieser Umschaltungen bereits mehrere Sekunden CPU-Zeit verbrauchen können
  • Bei der Installation von React und seinen Abhängigkeiten verwendet npm zum Beispiel rund 1 Million, yarn 4 Millionen, pnpm 500.000 und bun 160.000 Systemaufrufe

Unterschiede zwischen bestehenden Paketmanagern und dem Ansatz von Bun

  • npm, pnpm und yarn basieren alle auf Node.js, wodurch JavaScript durch mehrere Abstraktionsschichten ausgeführt werden muss (libuv, Event Loop, Threadpool, Vermittlung von Systemaufrufen)
  • Dabei summieren sich Argumentkonvertierung, Workerpool-Warteschlangen, Verzweigung von Event-Loop-Aufgaben und futex-Systemaufrufe zur Locksynchronisation, sodass am Ende die Verwaltung der Systemaufrufe sogar langsamer wird als das IO selbst
  • Paketmanager, die mit Node.js gebaut sind, können aufgrund dieser strukturellen Grenzen kaum eine tatsächlich native Leistung erreichen

Bun: eine native Installations-Engine in Zig

  • Bun ruft in der Sprache Zig Systemaufrufe direkt auf und lässt damit sowohl die JavaScript-Engine als auch sämtliche Abstraktionsschichten aus
  • Beim Lesen einer Datei wird zum Beispiel direkt aus Zig-Code der Systemaufruf openat() ausgeführt und die Daten sofort zurückgegeben
  • Dadurch kann das Lesen von zehntausenden Dateien ohne separaten Threadpool, Event Loop oder Datenkonvertierung extrem schnell ablaufen
  • In Benchmarks kann Bun 146.057 package.json-Dateien pro Sekunde lesen; Node.js ist mit rund 60.000 mehr als doppelt so langsam

Optimierung von Abhängigkeitsverwaltung und DNS

  • Beim Ausführen von bun install stößt Bun parallel zur Analyse der Abhängigkeiten asynchron DNS-Prefetching an
  • Auf macOS wird dafür zum Beispiel Apples inoffizielle asynchrone DNS-API (getaddrinfo_async_start()) verwendet, was die gleichzeitige Ausführung von Netzwerkaufgaben ohne blockierende Threads ermöglicht
  • Bestehende Paketmanager basieren auf dem libuv-Threadpool, wodurch intern faktisch blockierender Code läuft und Ressourcen verschwendet werden

Binäres Caching von Paketmanifesten

  • npm und andere cachen Manifeste als JSON, Bun hingegen parst sie einmal und speichert das Ergebnis anschließend als Binärformat (.npm-Datei)
  • Dadurch werden String-Duplikate und Parsing-Overhead minimiert; im Arbeitsspeicher ist der direkte Zugriff über Offset-Berechnungen möglich (keine neuen Objekte, kein erneutes Parsing, keine Garbage Collection nötig)
  • Mit ETag- und If-None-Match-Headern werden nur Änderungen geprüft, sodass die Aktualität ohne unnötiges Parsen von Daten verifiziert werden kann
  • In Benchmarks ist eine Installation aus dem Bun-Cache sogar schneller als eine frische Installation mit npm

Performance bei der Verarbeitung von Tarballs

  • Herkömmliche Paketmanager empfangen Tarballs als Stream, wodurch bei unzureichendem Pufferspeicher fortlaufend Reallokationen, Kopien und Größenanpassungen auftreten
  • Bun empfängt zuerst den gesamten Tarball und entpackt ihn dann; über die letzten 4 Bytes von gzip wird die unkomprimierte Größe vorab bestimmt, sodass nur ein einziges Mal Speicher allokiert werden muss
  • Mit libdeflate und ähnlichen Bibliotheken wird schnelles Entpacken ermöglicht und sowohl unnötige Kopien als auch Größenanpassungen vollständig vermieden

Abhängigkeitsgraphen und Optimierung von Datenstrukturen

  • Bestehende Paketmanager erzeugen Abhängigkeitsbäume auf Basis von JavaScript-Objekten und Pointern, was zu zufälliger Verteilung im Speicher und häufigen CPU-Cache-Misses führt (Problem des Pointer Chasing)
  • Bun verwendet das Muster Structure of Arrays (SoA) und speichert alle Pakete, Strings und Abhängigkeiten in großen zusammenhängenden Speicherblöcken
    • Durch den Zugriff auf Basis von Offsets und Längen kann die CPU mehrere Pakete gleichzeitig in Cache-Line-Einheiten lesen (cachefreundliche Struktur)
    • Auch das Lockfile wird statt als JSON/YAML passend zum SoA-Muster so gespeichert, dass String-Deduplizierung und sequenzieller Speicherzugriff leicht möglich sind
  • Das Binärformat des Lockfiles (bun.lockb) wurde ebenfalls experimentell eingeführt, wegen der schlechteren Zusammenarbeit über Git jedoch durch ein besser lesbares Plain-Format ersetzt

OS-spezifische Optimierung beim Kopieren von Dateien

macOS

  • Verwendung von clonefile: Ein Verzeichnis wird als Ganzes per Copy-on-Write mit einem einzigen Systemaufruf dupliziert
  • Dadurch wird die doppelte Nutzung von Speicherplatz auf dem Datenträger minimiert und die Installationsgeschwindigkeit maximiert
  • Falls clonefile fehlschlägt, erfolgt ein stufenweiser Fallback über per-directory cloning zu copyfile

Linux

  • Zuerst wird ein Hardlink versucht: Es wird keine neue Datei erzeugt, sondern nur eine neue Referenz auf die bestehende Datei angelegt (ohne Verschiebung von Datenträgerdaten)
  • Wenn Hardlinks nicht möglich sind, wird auf Btrfs/XFS per ioctl_ficlone Copy-on-Write verwendet
  • Danach folgen als Fallback copy_file_range, sendfile und zuletzt normales copyfile

Gesamtfazit

  • Bun überschreitet durch Minimierung von Systemaufrufen, binäre Strukturen, OS-Optimierung und verbesserte Datenstrukturen die traditionellen Leistungsgrenzen von Paketmanagern
  • Dadurch werden neben extrem schnellen Installationen auch Speicher- und CPU-Effizienz verbessert
  • Im Vergleich zu bestehenden Node.js-basierten Managern kann es ohne Austausch der Laufzeit direkt in Projekten eingesetzt werden (Kompatibilität bleibt erhalten)
  • In realen großen Codebasen verkürzt es Installationsvorgänge, die früher mehrere Minuten dauerten, auf wenige Millisekunden bis einige Sekunden
  • Als gelungenes Beispiel für maßgeschneiderte Optimierung auf System-, Hardware- und OS-Ebene hat es hohen Forschungs- und Referenzwert

1 Kommentare

 
GN⁺ 2025-09-12
Hacker-News-Kommentare
  • Ich habe versucht, die Behauptung zu überprüfen, dass mein M4 Max MacBook im Jahr 2009 unter die Top 50 der TOP500-Supercomputer gefallen wäre
    Um 2009 in die TOP500 zu kommen, brauchte man mehr als 75 TFlop/s Leistung
    Der M4 Max erreicht bei FP32 18,4 TFlop/s, aber die TOP500 verwendet FP64 (LINPACK)
    Basierend auf M2-Benchmarks liegt FP64 bei etwa einem Viertel von FP32, also wären grob 9 TFlop/s zu erwarten
    Damit würde er es nicht in die TOP500 von 2009 schaffen
    Siehe TOP500-Liste von 2009

    • Wenn jede Verbindung gleichzeitig mehrere I/O-Operationen ausführt, muss man mit Tausenden von Verbindungen multiplizieren
      Ich habe gehört, dass Server ungefähr 95 % der Gesamtzeit auf I/O warten, aber das gilt in Wirklichkeit pro Thread, nicht für den gesamten Server
      In der Praxis liegt die CPU-Auslastung eines echten Servers oft bei 70–80 %; darüber wird die Tail Latency schnell deutlich schlechter
      Wenn bei Volllast nur 5 % CPU genutzt werden, deutet das auf zu wenig parallele Prozesse oder Speicherprobleme hin
      Technisch ist das ein kleines Detail, aber solche Fehler können die Glaubwürdigkeit des Posts mindern, gesagt aus Sicht eines Bun-Fans

    • Diese Schlussfolgerung wirkt irgendwie wie eine Halluzination aus einem LLM
      Besonders der Schlussteil liest sich so, als wäre er von einem LLM erzeugt worden
      "Ich habe verstanden, dass die benchmarkten Package-Manager nicht falsch waren, sondern Lösungen, die zu ihrer Zeit passten"
      "Es wird betont, dass Buns Ansatz weniger revolutionär ist, sondern eher das Ergebnis eines nüchternen Blicks auf die Ursachen heutiger Geschwindigkeitsprobleme"
      "Dass die Paketinstallation 25-mal schneller wurde, ist keine Magie, sondern eine natürliche Folge davon, Tools für moderne Hardware zu bauen"

  • Obwohl das Thema komplex ist, war es sehr angenehm, wie leicht verständlich und einfach es erklärt wurde
    Es beeindruckt mich, dass es immer noch leidenschaftliche Menschen gibt, die den Status quo aufbrechen und sich an schwierige Aufgaben wagen
    Dass Computerhardware jeden Monat besser wird, Software aber immer langsamer, fühlt sich unnatürlich an
    Ich wünschte, mehr Leute würden effizienter programmieren

    • Ich wusste nicht, dass bun in Zig geschrieben ist
      Zig ist eine ziemlich neue Sprache, daher ist es interessant zu sehen, wie sie in der Praxis ernsthaft eingesetzt wird
  • Ich habe bun zum ersten Mal ausprobiert und war sehr beeindruckt
    Dank eingebautem Server und SQLite muss man nur bun installieren, was die Entwicklung viel bequemer macht
    Ich nutze normalerweise nur vanilla js und mochte das Node-Ökosystem ohnehin nie besonders, deshalb denke ich, ich hätte bun früher ausprobieren sollen

    • Ich habe Bun mehrfach ausprobiert und die Nutzung war jedes Mal sehr zufriedenstellend
      Es fühlte sich besser an als Node
      Aber ich bin immer auf ein entscheidendes Problem gestoßen und am Ende wieder zu Node zurückgekehrt
      Zuerst war das crypto-Modul nicht mit Nodejs kompatibel, was inzwischen behoben ist, und danach lief Playwright unter Bun nicht

    • Inzwischen unterstützt auch Node einen eingebauten Server und SQLite
      Wenn man mehr Funktionen braucht, ist Hono ebenfalls eine gute Alternative

  • Ich habe den Teil im Artikel nicht ganz verstanden, in dem die Hardlinks von Linux und clonefile von MacOS als gleichwertig beschrieben werden
    Bei Hardlinks würde doch eine Änderung an einer Kopie unerwartet die Dateien aller Projekte verändern, oder?

  • Obwohl die Erklärung technisch ziemlich komplex ist, bin ich beeindruckt, wie lesbar und unterhaltsam sie geschrieben ist

    • Lydia ist sehr gut darin, komplexe Konzepte einfach zu vermitteln
      Ich habe die meisten ihrer Arbeiten und Videos gesehen, und man merkt, wie gründlich sie sich vorbereitet
      Wenn du Zeit hast, kann ich ihre Artikel und YouTube-Inhalte sehr empfehlen
      In letzter Zeit scheint sie vermutlich wegen ihres aktuellen Jobs weniger aktiv zu sein
  • Im Abschnitt Binary Manifest Caching scheint die Benchmark-Zeit für "npm (cached)" zu fehlen
    Es gibt nur bun, bun (cached) und npm, und auch die zusammenfassenden Statistiken scheinen nicht ganz zu stimmen

  • Mir gefällt der Stil dieses Beitrags sehr
    Der Text ließe sich gut als Beispiel dafür weiterverwenden, wie wichtig io_uring ist
    Ich frage mich, ob Zigs aktuelles io-Update in v0.15 der Performance von Bun zusätzliche Vorteile bringen könnte

  • Ich warte seit über einem Jahr auf bun
    Ich dachte, 2025 würde das Jahr werden, in dem bun wirklich im Mainstream ankommt, aber überraschenderweise ist es immer noch nicht so populär
    Unter den Top-100.000-Repositories auf GitHub werden für neue Repos im Jahr 2025 npm 35-mal und pnpm 11-mal häufiger verwendet
    Auch Deno ist nicht so populär, wie ich erwartet hätte
    Ich frage mich, woran das liegt
    Ist es vielleicht, weil die Kompatibilität bei einer Runtime schwieriger hinzubekommen ist als bei einem Package-Manager?
    Mich würden die Meinungen von Leuten interessieren, die bun ausprobiert, aber nicht übernommen haben
    Zugehörige Statistik
    Zugehöriger HN-Kommentar

    • Ich wollte sowohl Bun als auch Deno mögen und habe beide mehrfach ausprobiert, bin aber jedes Mal auf einen entscheidenden Fehler gestoßen und konnte sie deshalb nicht weiter nutzen
      Das größte Problem, das ich zuletzt mit Bun hatte, war ein Issue, bei dem Streams vorzeitig geschlossen wurden
      Passender Issue-Link
      Bei Deno bin ich auf ein Memory-Leak-Problem gestoßen
      Passender Issue-Link
      Am Ende glaube ich, dass das Node-Ökosystem die Vorteile von Bun und Deno zuerst übernehmen wird

    • Bun ist ein neuer Herausforderer, finanziert durch frisches Venture-Capital, der mit einem etablierten Open-Source-Mainstream-Produkt (Node) konkurriert
      Es gibt Lock-in-Anreize, und letztlich unterscheidet es sich nicht grundlegend von Node
      Die strategischen Stärken sind nicht klar ausgeprägt, und es bietet nichts wirklich Neues, das mit Node nicht möglich wäre
      Ich habe es nie in ernsthaften Einsätzen gesehen, nur in eher lockeren Anwendungsfällen

    • Wenn man sich den Issue-Tracker ansieht, scheint es häufig zu Abstürzen zu kommen, vielleicht weil die Sprache Zig ziemlich unsicher ist
      Ich bleibe deshalb bei Node

    • Mich interessieren die Meinungen anderer ebenfalls
      Meiner Ansicht nach ist Node als Projekt reif, demokratisch und stark von der Community getragen
      Es hat sogar die io.js-Fork-Krise gut überstanden
      bun und deno wirken dagegen beide wie Projekte mit VC-Finanzierung und nicht wie demokratisch community-getriebene Vorhaben

    • Ich bin ein großer Fan von Bun
      Ich nutze Bun für möglichst viele Projekte und schreibe auch allerlei One-off-Skripte in Bun/TS
      Es gibt aber ein paar seltene, jedoch beunruhigende Probleme, weshalb ich mich mit dem Einsatz in Produktion noch schwertue
      Zum Beispiel gab es den Fall, dass ein einfacher Express-Webserver in Docker hängenblieb, wenn er mit bun gestartet wurde
      Wenn ich nur auf node umgestellt habe, lief alles normal
      Vor einem Jahr gab es auch bei der Kombination Bun + Prisma ein Memory Leak, durch das der Server abstürzte; ich nehme an, dass das inzwischen behoben ist
      Trotzdem mag ich Bun so sehr, dass es mir insgesamt trotz dieser Nachteile Entwicklungszeit spart
      Der Komfort bei Transpiling, Modulen, Workspaces und Ähnlichem ist enorm
      Ich kann gut verstehen, dass es noch nicht so verbreitet ist wie npm

  • Es hat großen Spaß gemacht, diesen Text zu lesen
    Er zeigt sehr gut, wie wichtig Informatikprinzipien in der Softwareentwicklung in der Praxis wirklich sind
    Big O, zeitliche/räumliche Lokalität, algorithmische Komplexität, User-/Kernel-Space, Dateisysteme, Copy-on-Write und so weiter
    Bei der Entwicklung solcher Low-Level-Packages wird praktisch alles angewendet, was man in einem CS-Studium lernt

    • Das ist eigentlich eher Software Engineering (SE) als Computer Science (CS)
      CS untersucht Berechnung und Theorie wie Programmiersprachen, Algorithmen, Kryptografie oder Machine Learning
      SE wendet Ingenieurprinzipien an, um skalierbare und zuverlässige Software zu bauen
  • Ich verstehe nicht ganz, warum es vorteilhaft sein soll, erst das gesamte Archiv zu lesen und dann mit dem Entpacken zu beginnen
    Ich würde vermuten, dass es eher von Vorteil ist, schon vor Abschluss des Downloads mit dem Entpacken anzufangen, selbst wenn dafür mehr Speicher-Rekopien nötig sind