Saubere Architektur für das Frontend



Das moderne Web ist kompliziert. Die Anzahl der Frameworks und das Tempo ihrer Entwicklung lassen den Entwickler galoppieren. Jemand benutzt neue, jemand liest Modebücher. Aber manchmal vertiefen sich das Lesen und die Energie in Architektur, OOP, TDD, DDD usw. Erwartungen nicht erfüllen. Und manchmal sind die Bücher verwirrend! Und selbst das Schlimmste ist, dass sie den FAC unglaublich erhöhen!

Ich werde es wagen, auf einfache Weise die Hauptidee der reinen Architektur in Bezug auf das Frontend darzulegen. Ich hoffe, dass dies für Menschen nützlich ist, die dieses Buch lesen möchten, und für diejenigen, die bereits gelesen haben, aber das im wirklichen Leben erworbene Wissen nicht nutzen. Und für diejenigen, die daran interessiert sind, wie ich das Frontend hierher gezogen habe.

Motivation


Das erste Mal, dass ich die FAQ lese, dauert ungefähr anderthalb Jahre, bevor ich einen Artikel auf Anraten eines der leitenden Entwickler schreibe. Davor war ich sehr beeindruckt von den kurzen Auszügen aus Pure Code, die für JavaScript angepasst wurden ( https://github.com/ryanmcdermott/clean-code-javascript ). Ich habe diesen Tab sechs Monate lang offen gehalten, um die Best Practices in meiner Arbeit anzuwenden. Außerdem sind meine ersten Versuche, den ursprünglichen Clean Code zu lesen, fehlgeschlagen. Vielleicht, weil es zu sehr an den Merkmalen von Front-End-Projekten festhält oder weil das Lesen durch langfristige Praxis verstärkt werden sollte. Trotzdem ist die Tscheka eine praktische Anleitung, die Sie nehmen und sofort auf die schriftliche Funktion anwenden können (ich empfehle dringend, sie zuerst zu lesen, wenn Sie nicht vertraut sind).

Mit TA wird es jedoch immer komplizierter - hier finden Sie eine Reihe von Grundsätzen, Gesetzen und Tipps für den Aufbau des gesamten Programms. Es gibt keine Besonderheiten, die Sie sofort in die Komponente aufnehmen und zayuzat können. Dieses Buch soll die Art und Weise, wie Sie Software schreiben, ändern und Ihnen mentale Werkzeuge und Metriken geben. Es ist ein Fehler zu bedenken, dass der ChA nur für Architekten nützlich ist, und ich werde versuchen, dies anhand eines an das Front-End angepassten Beispiels zu vermitteln.

Geschäftslogik und Frontend




Wenn es um ChA geht, zeichnen viele Menschen Kreise in ihrer Fantasie (siehe Abbildung unter der Überschrift), Projekte von gigantischer Größe, unglaublich komplexe Geschäftslogik und eine Reihe von Fragen - was für ein Papa soll YuzKeysy sein? Die Idee der Anwendbarkeit der Prinzipien von ChA auf die Schaffung einer Akkordeonkomponente ist verwirrend. Die Probleme, die bei der Entwicklung moderner Schnittstellen auftreten, erfordern jedoch eine ernsthafte Einstellung. Moderne Schnittstellen sind komplex und oft schmerzhaft. Lassen Sie uns zunächst herausfinden, was am Frontend am wichtigsten ist.

Jeder weiß seit langem, dass Sie die Geschäftslogik von einer Präsentation trennen und die SOLID-Prinzipien einhalten müssen. Onkel Bob im CHA wird Ihnen dies ausführlich erzählen. Aber was ist Geschäftslogik? R. Martin bietet verschiedene Definitionen und Unterkategorien an, von denen eine ungefähr klingt Damit:
Geschäftslogik (Geschäftsregeln) sind Regeln, die Unternehmen auch ohne Automatisierung Geld bringen.
Im Allgemeinen ist Geschäftslogik etwas sehr Wichtiges. (Ich höre Backender kichern, wenn sie von vorne von Geschäftslogik hören). Aber ich schlage vor, dass sich die Spitzenreiter etwas entspannen und sich daran erinnern, was an unserer Front sehr wichtig sein kann. Und egal wie seltsam es klingt, das Wichtigste auf der Vorderseite ist die Benutzeroberfläche. Der erste Schritt zum Verständnis der AA war für mich die Erkenntnis, dass sich die Schnittstellenlogik in der Mitte des vorderen Kreises befinden sollte! (Abb. unter der Überschrift).

Ich verstehe, dass dies eine unbegründete Aussage ist, und man kann stark damit argumentieren. Aber denken wir daran, was sich an der Front oft und schmerzhaft ändert. Ich weiß nichts über dich, aber ich werde am häufigsten gebeten, das Verhalten interaktiver Elemente zu ändern - Akkordeons, Formen, Knöpfe. Es ist erwähnenswert, dass sich Layout (Design) viel seltener ändert als das Verhalten der Benutzeroberfläche. Änderungen und Akteure ( Initiatoren von Änderungen ) werden insbesondere in der PA erörtert .

Böser Schimmel


Lassen Sie uns nicht viel für die Terminologie stören. Wir geben ein Beispiel und klären ein wenig, was ich die Schnittstellenlogik nenne.

Es gibt einige Eingaben mit Validierung und bedingter Zuordnung. Sie können nur ein Feld ausfüllen, und das Formular ist gültig, es werden jedoch optionale Eingaben angezeigt. (Achten Sie darauf, dass es uns egal ist, welche Art von Daten vorhanden sind. Hauptsache Interaktivität)





Ich hoffe die Logik ist klar. Und die Implementierung wirft zunächst keine Fragen auf. Sie schieben dieses Ding in eine Komponente Ihres Frameworks und verwenden es mutig in anderen Formen als integralen und unabhängigen Bestandteil. Irgendwo müssen Sie Flags übergeben, um die Validierung geringfügig zu ändern, irgendwo ein kleines Layout, irgendwo die Funktionen zum Herstellen einer Verbindung mit dem übergeordneten Formular. Im Allgemeinen Code auf dünnem Eis. Und einmal erhalten Sie eine Aufgabe in dieser Form (und verwenden sie) und frieren für ein paar Tage ein, obwohl es 15 Minuten zu sein scheint. Verdammt der Manager, Formen und langweilige langweilige Aufgaben.

Wo ist der Fehler? Es scheint, dass Sie mehr als einen Tag gearbeitet haben, die Zusammensetzung der Komponenten sehr gut durchdacht, verschiedene Hockeys ausprobiert, Vorlagen durch Requisiten übertragen, mit dem Framework zum Erstellen von Formularen beschworen und sogar versucht haben, SOLID beim Schreiben dieser Komponenten zu folgen.

Hinweis: Komponenten in ChA! == Komponenten in React / Angular und Co.

Tatsache ist jedoch, dass Sie vergessen haben, die Logik hervorzuheben. Beruhige dich ein bisschen, gehe zurück zur Aufgabe und spiele Simulation.

Zu einfache Aufgabe


Die NA betont, dass Architektur für große Projekte von entscheidender Bedeutung ist. Dies negiert jedoch nicht die Nützlichkeit der ChA-Ansätze für kleine Aufgaben. Es scheint uns, dass die Aufgabe zu einfach ist, um über die Architektur irgendeiner Form zu sprechen. Und wie kann man einen Weg bestimmen, um Änderungen vorzunehmen, wenn nicht durch Architektur? Wenn Sie die Grenzen und Komponenten der interaktiven Oberfläche nicht definieren, wird dies noch verwirrender. Denken Sie daran, mit welchen Gedanken Sie die Aufgabe übernehmen, die Form bei Ihrer Arbeit zu ändern.

Aber kommen wir zur Sache. Was ist das für ein Formular? Wir versuchen zu modellieren und Gedanken mit einem Pseudocode auszudrücken.

ContactFormGroup
  +getValue()
  +isValid()

Meiner Meinung nach besteht unsere gesamte Aufgabe für die Außenwelt darin, ein Objekt mit zwei Methoden zu erstellen. Es klingt einfach - so wie es ist. Wir beschreiben weiterhin, was wir sehen und was uns interessiert.

ContactFormGroup
  emailFormGroup
  phoneFormGroup
  getValue()
    => [emailFormGroup.getValue(), phoneFormGroup.getValue()]
  isValid()
    => emailFormGroup.isValid() || phoneFormGroup.isValid()

Wahrscheinlich lohnt es sich, explizit auf das Auftreten kleinerer Eingaben hinzuweisen. Wenn ein Manager Sie auffordert, das Formular schnell zum 10. Mal zu bearbeiten, sieht in seinem Kopf alles einfach aus - genau wie bei diesem Pseudocode.

EmailFormGroup
  getValue()
  isValid()
  isSecondaryEmailVisible()
    => isValid() && !!getValue()

Können wir einen Ort für seltsame Anforderungen finden ...

PhoneFormGroup
  getValue()
  isValid()
  isSecondaryPhoneVisible()
    => isValid() && today !== ‘sunday’

Eine der Implementierungen unseres Formulars auf Angular könnte so aussehen.

ContactFormGroup-Implementierung (Angular)
export class ContactFormGroup {
    emailFormGroup = new EmailFormGroup();
    phoneFormGroup = new PhoneFormGroup();

    changes: Observable<unknown> = merge(this.emailFormGroup.changes, this.phoneFormGroup.changes);

    constructor() {}

    isValid(): boolean {
        return this.emailFormGroup.isValid() || this.phoneFormGroup.isValid();
    }

    getValue() {
        return {
            emails: this.emailFormGroup.getValue(),
            phones: this.phoneFormGroup.getValue(),
        };
    }
}

export class EmailFormGroup {
    emailControl = new FormControl();
    secondaryEmailControl = new FormControl();

    changes: Observable<unknown> = merge(
        this.emailControl.valueChanges,
        this.secondaryEmailControl.valueChanges,
    );

    isValid(): boolean {
        return this.emailControl.valid && !!this.emailControl.value;
    }

    getValue() {
        return {
            primary: this.emailControl.value,
            secondary: this.secondaryEmailControl.value,
        };
    }

    isSecondaryEmailVisible(): boolean {
        return this.isValid();
    }
}


Somit erhalten wir drei Schnittstellen (oder Klassen, die nicht wichtig sind). Sie sollten diese Klassen an prominenter Stelle in einer separaten Datei ablegen, damit Sie die beweglichen Teile der Benutzeroberfläche verstehen, indem Sie sie einfach untersuchen. Wir haben die problematische Logik identifiziert, gezogen und hervorgehoben. Jetzt steuern wir das Verhalten des Formulars und kombinieren die Implementierung einzelner Teile von ContactFormGroup. Und die Anforderungen für verschiedene Anwendungsfälle können leicht als separate Objekte dargestellt werden.

Dies scheint eine Standardimplementierung des MVC-Musters zu sein und nichts weiter. Aber ich würde elementare Dinge, die in der Praxis überhaupt nicht respektiert werden, nicht ablehnen. Der Punkt ist nicht, dass wir einen Code aus der Ansicht gezogen haben. Der Punkt ist, dass wir den wichtigen Teil, der Änderungen unterworfen ist, hervorgehoben und sein Verhalten beschrieben haben, damit es einfach wird.

Gesamt


ChA informiert uns über die Gesetze zum Schreiben von Software. Es gibt Metriken, anhand derer wir wichtige Teile von kleineren unterscheiden und Abhängigkeiten zwischen diesen Teilen korrekt steuern können. Beschreibt die Vorteile von OOP und Ansätze zur Lösung von Problemen durch Modellierung.

Wenn Sie die Qualität Ihrer Programme verbessern, sie flexibel gestalten, OOP in Ihrer Arbeit verwenden, lernen möchten, wie Sie die Abhängigkeiten in Ihrem Projekt verwalten, im Code über die Lösung des Problems und nicht über die Details Ihrer Bibliothek sprechen, empfehle ich dringend, Clean Architecture zu lesen. Die Tipps und Prinzipien aus diesem Buch sind für jeden Stapel und jedes Paradigma relevant. Haben Sie keine Angst vor Experimenten mit Ihren Aufgaben. Viel Glück

PS Über State Management


Ein sehr großes Hindernis für das Verständnis von NA kann die Verpflichtung gegenüber einer staatlichen Verwaltungsbibliothek sein. Bibliotheken wie redux / mobx lösen gleichzeitig die Aufgabe, Komponenten über Änderungen zu informieren. Und für einige Entwickler ist eine Front ohne Staatsmanager etwas Undenkbares. Ich glaube, dass die Prinzipien von ChA mit und ohne den Einsatz eines Staatsmanagers angewendet werden können. Wenn Sie sich jedoch auf die staatliche Verwaltungsbibliothek konzentrieren, verlieren Sie unweigerlich einen Teil der Flexibilität. Wenn Sie in Bezug auf ChA und OOP denken, verschwindet das Konzept der staatlichen Verwaltung im Allgemeinen. Die einfachste Implementierung ohne staatliche Verwaltung finden Sie hier habr.com/de/post/491684

PPS


Ehrlich gesagt habe ich meinem Freund die Lösung für eine ähnliche Schnittstellenaufgabe gezeigt - er hat es nicht geschätzt und alles für Reaktions-Hooks neu geschrieben. Es scheint mir, dass die Ablehnung in größerem Maße auf die Tatsache zurückzuführen ist, dass OOP in realen Projekten praktisch nicht verwendet wird und die meisten jungen Front-End-Entwickler nicht die geringste Erfahrung mit OOP-Lösungen haben. Bei Interviews fragen sie manchmal nach SOLID, aber oft nur, um Kandidaten auszusondern. Darüber hinaus können die Entwicklungsböen im Bereich PLO in einigen Teams durch eine Überprüfung unterdrückt werden. Und es ist oft einfacher für Leute, eine neue Bibliothek zu sortieren, als ein langweiliges Buch zu lesen oder ihr Recht zu verteidigen, Logik aus einer Komponente herauszunehmen. Bitte unterstützen Sie OOP-Aktivisten :)

All Articles