02Blog

Die fehlende Dokumentation

Notizen zu dem, was wir beim Bauen lernen. Fast alles kommt aus einem konkreten Problem, das uns mehr gekostet hat als gedacht.

Alle
  1. ProductoLa web de un pintor solo tiene que hacer una cosa: que le llamenHice la web y la app de trabajo de Mamu, un pintor de Valencia, en cuatro días sueltos. Lo que más mejoró la web fue borrar las páginas de precios y de por qué elegirnos.
  2. IACómo construimos Zenbu, un buscador de anime que busca por lo que cuentasCatorce mil animes, un vector por serie y un LLM que reordena al final. Lo que más nos costó no fue la búsqueda semántica: fueron las secuelas con sinopsis de una línea.
  3. ArchitekturIch habe viermal den Auth-Anbieter gewechseltVier gemanagte Anbieter in anderthalb Jahren, und bei allen dasselbe Ziel: eigene Middleware. Was bei jedem Übergang kaputtgeht und worauf ich heute achte, bevor ich eine Zeile Auth schreibe.
  4. BetriebStripe hat mir den Build fünfmal zerlegt und steht jetzt im KalenderDie API-Version von Stripe hochzuziehen ist kein Vorfall. Es ist wiederkehrende Wartung mit ziemlich vorhersehbaren Kollateralschäden, und man sollte sie einplanen.
  5. ProduktCredits, Guthaben, AusgabenlimitsIn fünf Produkten habe ich die nutzungsbasierte Abrechnung gleich gebaut: Ich fange mit Credits an und lande bei Guthaben in Cent und Limits pro Schlüssel. Ich weiß inzwischen, auf welcher Stufe man anfangen sollte.
  6. DatenbankenWarum ich RLS in Postgres beide Male entfernt habe, die ich es benutzt habeRow Level Security wirkt wie die richtige Standardpraxis. Mit Drizzle, Server Actions und eigener Auth lebt die Berechtigungslogik schon woanders, und beide zu pflegen tut weh.
  7. UrteilskraftIch fange nie bei null an: was ich immer mitnehme und was ich immer wegschneideZehn Projekte auf demselben Boilerplate. Der erste Commit jedes einzelnen ähnelt dem letzten des vorherigen mehr als einem neuen Projekt, und der zweite Commit löscht fast immer etwas.
  8. UrteilskraftDas Erste, was ich aus jedem Template entferne, ist StripeIch starte fast jedes Projekt damit, Checkout, Portal und Webhook zu löschen. Das ist keine Schusseligkeit: Es trennt die Infrastruktur, die ich immer brauchen werde, von der, die noch nicht dran ist.
  9. ArchitekturDerselbe Concurrency-Bug ist mir in drei verschiedenen Projekten begegnetEin Zähler, der unter Last hochzählt, verliert Inkremente, und einer, der abzieht, kann dasselbe zweimal berechnen. Wenn der Zähler Geld ist, ist das kein Detail, das man später behebt.
  10. KIJedes neue Modell macht mir etwas anderes kaputtSechs Modellmigrationen in anderthalb Jahren. Keine davon war der Austausch eines Strings, auch wenn alle so anfingen.
  11. DatenbankenIch habe dasselbe Vertragsmodell mehr als zehnmal neu geschriebenEin kompliziertes Domänenmodell gelingt nicht beim ersten Versuch. Man nähert sich ihm an, indem man es mit den echten Daten vor Augen neu schreibt, und dazu gehört, Entscheidungen zurückzunehmen, die richtig aussahen.
  12. DatenbankenMeine ersten Datenschemata überleben fast nie den ersten MonatDas Schema von Tag 1 ist eine Hypothese über eine Domäne, die du noch nicht verstehst. Das anzunehmen verändert, wie du es schreibst und wie weh es tut, es zu ändern.
  13. SicherheitWarum ich Gastzugänge mit Session-Token mache und nicht mit CodesEin sechsstelliger Code sieht aus wie der einfache Weg, jemanden ohne Konto reinzulassen. Das ist er auch, bis du ihn widerrufen musst und merkst, dass du nicht weißt, wen du gerade rauswirfst.
  14. BetriebWarum "läuft lokal" mir nichts mehr sagtDie Unterschiede zwischen deiner Maschine und der Produktion sind kein Pech: Es sind vier konkrete Kategorien, die immer scheitern und die ein grüner Build nicht sehen kann.
  15. TechnikDer Test, der grün war und logSechs SCRIPT ERROR in einem Test, der ALLE TESTS OK ausgab und mit Code 0 endete. Wie man merkt, dass ein Grün falsch ist, und was ich jetzt mache, bevor ich einem traue.
  16. PerformanceAdmin-Listen fallen als Erstes umDas interne Panel wird ohne Limits geschrieben, weil es am Anfang vier Zeilen hat. Genau dort fliegt alles auseinander, wenn das Produkt wächst.
  17. SicherheitWas ich gelernt habe, als ich meinen eigenen Code wie fremden auditiert habeEine leere ACL, die den ganzen Korpus zurückgab, eine CSS-Injection ohne eine einzige Zeile JavaScript und ein API-Key, der nach der Kündigung seines Besitzers weiter galt. Alles an einem Tag, alles in Code, den ich geschrieben hatte.
  18. ArchitekturWarum ich in Apps, die es nicht brauchen, einen Login verlangeOhne Identität gibt es kein Kontingent, kein Ausgabenlimit und keine Möglichkeit, jemanden zu stoppen, der es übertreibt. Die Reibung der Registrierung ist billig im Vergleich zu dem, was es kostet, sie nicht zu haben.
  19. UrteilskraftWas am Ende immer passiert, wenn ich etwas von Hand anfangeIch habe viermal Editoren von Hand gebaut. Drei davon wurden mit einer Bibliothek neu geschrieben. Der vierte hielt keine zwei Tage.
  20. FrontendWann sich ein globaler Store seinen Platz verdientGlobaler State rechtfertigt sich nicht durch Bequemlichkeit. Er rechtfertigt sich, wenn eine Zwischenkomponente Props bekommt, die sie nicht benutzt, nur um sie nach unten weiterzureichen.
  21. UrteilskraftFünf Migrationen von ESLint zu Biome: die Entscheidung ist längst gefallenWenn du dieselbe Migration in fünf Projekten machst, ohne nachzudenken, ist es keine Vorliebe mehr, sondern Urteilskraft. Was dabei kaputtgeht und was verloren geht.
  22. UrteilskraftDokumentieren vor dem Programmieren: meine Regel für Integrationen, die ich nicht kontrolliereBei einer Integration mit einer fremden API fassen die ersten vier Commits keinen Code an. Das Dokument vorher zu schreiben zwingt dazu, die Grenzen zu messen, die dir später in Produktion um die Ohren fliegen.