Über Stilwartung

Avatar of Sarah Drasner
Sarah Drasner am

DigitalOcean bietet Cloud-Produkte für jede Phase Ihrer Reise. Starten Sie mit 200 $ kostenlosem Guthaben!

Ich sprach neulich mit einem brillanten Ingenieurfreund, der erwähnte, dass er nie etwas von Grund auf neu bauen könne. Seine gesamte Karriere bestand darin, den (oft ziemlich schlechten) Code anderer Leute zu warten.

In einer perfekten Welt würden wir alle Code von Grund auf neu schreiben, er würde perfekt funktionieren und wir würden ihn in eine Wolke packen, damit ihn niemand mehr ansieht.

Wir wissen alle, dass es so nicht läuft. Code muss gepflegt werden.

Kyle Simpson beginnt oft seine Vorträge mit der Aussage, dass wir nur 30 % unserer Zeit mit dem Schreiben von Code verbringen und 70 % unserer Zeit mit dessen Pflege. Ein guter Kollege und Programmierer zu sein, bedeutet nicht nur, ein geschickter Problemlöser zu sein, sondern auch lesbar zu sein. Große Entwickler erstellen Code mit Blick auf die Wartung.

Ich scherze oft, dass ich keinen Code-Ninja einstellen möchte. Ninjas kommen mitten in der Nacht und hinterlassen ein blutiges Chaos.

Ich möchte einen Code-Hausmeister. Jemanden, der durch die Gänge des Codes geht, Teile reinigt, vernachlässigte Bereiche abstaubt, andere auf Hochglanz poliert und unnötige Stücke wegwirft. Diese sanftere, genauere Analogie bevorzuge ich. Das ist die Person, die Sie in Ihrem Team haben wollen. Das ist die Person, die Sie in Ihren Code-Reviews haben wollen.

Ein großes Dankeschön an JD Cantrell, der ein großartiger Code-Hausmeister und Code-Reviewer ist.

Denken wir über Code-Pflege aus der Perspektive zweier verschiedener Programmierparadigmen nach

In der Programmierung gibt es viele Werkzeuge und Verfahren, um dasselbe Ziel zu erreichen. Es gibt keine richtige Antwort. Hier ist eine prägnante Definition von Michael Feather von zwei sehr beliebten Programmierparadigmen

Objektorientierte Programmierung macht Code verständlich, indem sie bewegliche Teile kapselt...

Funktionale Programmierung macht Code verständlich, indem sie bewegliche Teile minimiert.

Betrachten wir beide im Hinblick auf nicht nur Verständlichkeit, sondern auch Wartung.

Funktionale Programmierung

Ich habe selbst den Wert der Verwendung eines funktionalen Ansatzes in Front-End-JavaScript erfahren. Wenn wir Code schreiben, wollen wir manchmal davon ausgehen, dass er für immer so verwendet wird, wie wir es beabsichtigt haben, aber die meisten von uns tun das schon lange genug, um anzuerkennen, dass dies nicht immer der Fall ist.

Funktionale Programmierung beinhaltet, ist aber nicht beschränkt auf:

  • Sie ist deklarativ – wir schreiben auf eine Weise, die wiederverwendet werden kann, und sagen dem Computer nicht genau, was er bei jedem Schritt tun soll. Dies hat einige Ähnlichkeiten mit Abstraktion.
  • Sie ist rein – wir verändern oder modifizieren nichts außerhalb des Geltungsbereichs der Funktion, und aus diesem Grund...
  • Sie ist unveränderlich – Sie geraten nicht in eine Situation, in der Sie dieselbe Eingabe mehrmals mit unterschiedlichen Ergebnissen versehen.

Ich glaube, funktionale Programmierung kann aufgrund der fehlenden Nebeneffekte äußerst nützlich für die Wartung sein. Das ist riesig. Das verhindert, dass unser Code brüchig wird. Leute denken manchmal, das größte Problem seien Fehler in unserem Code. Ich würde argumentieren, dass der schlimmste Code nicht der ist, der Fehler verursacht und fehlschlägt. Diesen können wir mit methodischer Isolierung nachverfolgen. Der schlimmste Code ist Code, der sich auf unvorhersehbare Weise leise und überall verhält. Sie rennen durch die Codebasis und spielen Whack-a-Mole, und manchmal ist es schwierig, den Schuldigen zu finden. Ein funktionaler Programmierstil geht dieses Problem präventiv an, da er von Grund auf darauf ausgelegt ist, dies zu verhindern (so gut wie möglich).

Hier sind einige Ressourcen, wenn Sie tiefer in funktionale Programmierung eintauchen möchten

So sehr ich funktionale Programmierung liebe, bitte beachten Sie, dass es immer noch Probleme mit der Wartung geben kann. Wenn einige Dinge dieselbe reine Funktion verwenden und Sie diese Funktion im Laufe der Zeit für eine ihrer Anwendungen anpassen, können Probleme auftreten, bei denen Sie auch andere Dinge ändern, die versteckte Abhängigkeiten sind. Gute Dokumentation ist hier sehr hilfreich.

Objektorientierte Programmierung

Im Gegensatz dazu ist die objektorientierte Programmierung eher wie das Befolgen der Schritte eines Rezepts. Sie verwendet Objekte, die Daten enthalten können oder auch nicht, und Methoden, die tendenziell prozedural sind. Typischerweise haben Objekte eine Vorstellung von sich selbst (z. B. „this“ in JavaScript). Objektorientierung konzentriert sich nicht auf Reinheit, sondern neigt dazu, Kapselung zu verwenden, um sicherzustellen, dass nichts in den äußeren Geltungsbereich austritt.

Im besten Fall denken objektorientierte Ansätze tendenziell über die höchste Ordnung von etwas nach, dann reduzieren sie sich auf jede Art von Instanz, die Sie haben können, und zerlegen, was in jedem Fall zu tun ist. Wenn Sie es sich wie das Linsche System der Klassifizierung von Tieren vorstellen und wie wir Morphologietbäume erstellen würden (wer würde das nicht? :)) Sie würden damit beginnen zu fragen, ob es warmblütig ist? Dann, hat es Fell? Dann hat es eine Schnauze? usw. Ich verhunze hier wirklich die Biologie, aber es ist ein Beispiel.

Im schlimmsten Fall erfährt objektorientierte Programmierung viel berechtigte Kritik, weil man manchmal nicht klar beschreibt, was man zu beschreiben glaubt. Sie können sich das so vorstellen: Sie denken, etwas sei eine Banane, aber es ist wirklich ein Pfirsich, weil Ihnen nur gesagt wurde, dass Sie eine Frucht haben. Wir haben bereits kurz darüber gesprochen, wie solche Codes ein Albtraum für die Wartung sein können, also ist das zwar nicht immer der Fall, aber es kann sicherlich vorkommen.

Ein anwendbares Beispiel in CSS

Mit beiden funktionalen und objektorientierten Ansätzen im Hinterkopf betrachten wir, wie sich das auf CSS und das Konzept von Autorenschaft versus Wartung auswirkt. CSS wird deklarativ und rein geschrieben. Sie können einen CSS-Block nicht mit einem anderen CSS-Block verändern.

Ich denke, viele Leute würden erwarten, dass ein rein funktionaler Ansatz für CSS am besten wäre. Sie könnten das mit der Pflege von CSS so rein wie möglich assoziieren, woher Ideen wie CSS Modules stammen. Das Konzept ist, dass, wenn Sie die Stile für das Ding, das Sie ändern, dort einkapseln, wo Sie sie brauchen. Sie beschäftigen sich nur mit dieser Instanz. Keine Nebeneffekte. Ich stimme dem nicht zu. Sie vermeiden auf diese Weise einige Dinge.

  • Sie vermeiden Konflikte. Hier bekommt die objektorientierte Programmierung manchmal einen schlechten Ruf.
  • Sie vermeiden Benennung. Das Benennen ist schwierig. Sie können das Benennen mit diesem Ansatz vermeiden.
  • Sie vermeiden den Umgang mit der Kaskade. Darauf werde ich gleich eingehen.

Für andere Arten der (Nicht-CSS-)Programmierung halten wir Dinge rein und vermeiden globale Geltungsbereiche und sind damit im Reinen! Das muss also überall gelten, richtig?

Hier müssen wir zum Thema das richtige Werkzeug für den Job kommen. Wenn wir Wartung über Schreiben betrachten, hier glänzen andere Ansätze

  • Unternehmen, ob groß oder klein, führen mindestens alle 1-2 Jahre Redesigns durch. Wenn Ihre Codebasis groß ist, mit vielen Leuten, und Sie die Zeilenhöhe überall von 1,1rem auf 1,2rem ändern müssen, müssen Sie dann in jedes Modul zurückgehen und diesen Wert ändern? Ein globales oder ein erweitertes Objekt wird hier außergewöhnlich nützlich.
  • Die Kaskade kann helfen, wenn Sie sie verstehen und organisieren. Das ist dasselbe wie jedes hochentwickelte Softwaredesign. Sie können sich ansehen, was Sie bauen, und verantwortungsvolle Entscheidungen über Ihren Build und Ihr Design treffen. Sie entscheiden, was auf der obersten Ebene liegen kann und von anderen, kleineren Teilen geerbt werden muss. Dies vermeidet Spaghetti-Code in CSS und hält Ihren Code DRY.
  • CSS ist Design. Gutes Design ist von Natur aus erfolgreich, wenn es kohäsiv ist. Eine CSS-Codebasis, die sich an der Design-Infrastruktur ausrichtet, auf der sie aufbaut, ermöglicht saubereren Code mit dem zusätzlichen Vorteil einer besseren Zusammenarbeit. CSS kann auch für Designer selbsterklärend sein: „Moment, wir haben noch einen tertiären Button? Warum?“ Lecks in kohäsiven UI/UX kündigen sich in diesem Modell gut an.
  • Das Benennen kann bei der Dokumentation helfen. Dieser Punkt ist etwas kniffliger und ich bin mir nicht sicher, ob er ganz notwendig ist, aber erwähnenswert. Ob Sie BEM, SMACSS/OOCSS oder Atomic mögen, gut gemachtes Benennen kann Ihnen tatsächlich gute Informationen darüber geben, wo eine Klasse verwendet wird und warum.

Die Paradigmen teilen sich Eigenschaften

Wie Sie vielleicht vermuten, sehe ich zwar Wert in anderen Paradigmen, meine Präferenz ist jedoch ein funktionaler Stil. Vor diesem Hintergrund fragen Sie sich vielleicht, warum ich einen objektorientierten Ansatz für CSS wertschätzen würde.

Trotz seines Namens teilt OOCSS Eigenschaften mit der funktionalen Programmierung. Um OOCSS korrekt und wie beabsichtigt zu verwenden, erstellen Sie hauptsächlich Mixins, die ähnlich wie Funktionen mit Parametern (oft mit Standardwerten) in Ihrem System ausgedrückt werden. Sie sind rein und können für mehrere Anwendungen verwendet werden.

Es verwendet immer noch objektorientierte Ansätze. Mit einer sehr intelligenten Architektur, die antizipiert, wie sich Dinge gegenseitig beeinflussen könnten, und sorgfältig überlegt, was vererbt werden sollte. Angesichts der Tatsache, dass CSS im Grunde eine Gruppe von Objekten ist, ergibt dies in einem CSS-Kontext tendenziell mehr Sinn als in anderen Sprachen.

Letztes Jahr habe ich ein Team geleitet, um ein riesiges Front-End-Komponentensystem komplett zu refaktorisieren. Es verwendete eine OOCSS-Architektur. Ich habe selbst den Nutzen dieses Modells gesehen. Designer konnten mich bitten, etwas zu ändern, und wir konnten es schnell auf der ganzen Website aktualisieren sehen. Sie konnten sogar ihre Meinung ändern, ohne zu viel Aufwand. Eine Last-Minute-Anfrage von oben hat unsere Veröffentlichung nicht verzögert. Ich sage definitiv nicht, dass es keine schmerzhaften Punkte gab – aber es war überraschend reibungslos für seine Größenordnung. Das hat dazu geführt, dass ich die Art und Weise, wie ich CSS für andere Anwendungen schreibe, mit ganz neuen Augen betrachte.

Zukunftsorientiert

Leute neigen dazu, diese Dinge gegeneinander auszuspielen

  • CSS
  • Styling via JavaScript

Ich würde argumentieren, dass Sie auf beide Arten wartungsfreundlich sein oder einen Wartungsalbtraum schaffen können.

Sie können Dinge wie Zeilenhöhen, Schriftarten und Verhaltensweisen absolut verantwortungsvoll in Aphrodite, React-CXS oder CSS Modules handhaben. Ich mag einige dieser Ansätze sehr. Sie können Vererbung handhaben und für einen DRY-eren und wartungsfreundlicheren Ansatz erweitert werden.

Aber auch wenn Sie es können, habe ich persönlich nicht genügend Beispiele von Projekten gesehen, die es tun. (Ich würde gerne Beispiele sehen!)

Meistens sehe ich, dass Leute eine Variable oder zwei für die Markenfarbe herausnehmen und nichts weiter. Ein paar Variablen machen keine verantwortungsvolle Systemarchitektur aus. Ich denke, wir können hier mehr tun, wenn wir über unseren Code nicht in Bezug auf das nachdenken, was leichter zu schreiben ist, sondern was leichter zu ändern ist. Oder besser noch, in Bezug auf das, was für andere leichter zu ändern ist.

Bitte kümmern Sie sich auch um gute Dokumentation! Mit beiden Programmierparadigmen müssen Sie alle Ihre Abhängigkeiten kennen, bevor Sie sie anpassen. Großartige Dokumentation bedeutet auch, dass Sie zielgerichteter in Ihren Entscheidungen sind. Es gibt weniger "Ach ja"-Momente, wenn Sie anderen erklären müssen, was ein Ding ist und wo es verwendet wird.

Die Probleme, die ich in diesem Artikel behandle, sind Probleme der Zusammenarbeit und des Maßstabs. Nicht jedes Unternehmen, jede Website oder sogar jede Webanwendung beschäftigt sich mit diesen Dingen. Dies ist ein Meinungsartikel, der auf Erfahrung beruht. Unterschiedliche Dinge funktionieren für unterschiedliche Projekte.

Meine Hoffnung für diesen Artikel ist es, Entwickler zu ermutigen, vorausschauend zu denken. Wir stecken alle zusammen drin, und das Beste, was wir tun können, ist, voneinander zu lernen. Wenn Sie mir völlig widersprechen, ist das völlig in Ordnung. Meine Hoffnung ist, dass Sie auch dadurch, dass Sie eine Haltung einnehmen, eine Richtung festigen, in die Sie sich mit Wartung als Kernkonzept bewegen.