Ich lese das Buch "Learning TypeScript" von Remo Jansen. In einem Abschnitt beschreibt der Autor, wie ein sehr einfaches Proof-of-Concept-MVC-Framework erstellt wird, einschließlich der Erstellung der Model
Klasse, und sagt Folgendes:
Ein Modell muss mit der URL des Webdienstes versehen sein, den es verwendet. Wir werden einen Klassendekorateur namens ModelSettings verwenden, um die URL des zu konsumierenden Dienstes festzulegen. Wir könnten die Service-URL über ihren Konstruktor einfügen, aber es wird als schlechte Praxis angesehen, Daten (im Gegensatz zu einem Verhalten) über einen Klassenkonstruktor einzufügen .
Ich verstehe diesen letzten Satz nicht. Insbesondere verstehe ich nicht, was es bedeutet, "Daten zu injizieren". Es scheint mir, dass in fast allen Einführungen in JavaScript-Klassen anhand stark vereinfachter Beispiele Daten über ihre Parameter in den Konstruktor eingeführt ("injiziert"?) Werden. Zum Beispiel:
class Person {
constructor(name) {
this.name = name;
}
}
Ich denke sicherlich an name
Daten, nicht an Verhalten, und es ist allgemein in dieser Art von Beispiel als Konstruktorparameter enthalten, und es wird nie erwähnt, dass dies eine schlechte Praxis ist. Ich gehe daher davon aus, dass ich etwas im obigen Zitat falsch verstehe, entweder was mit "Daten" oder "Einspritzen" oder etwas anderem gemeint ist.
Ihre Antworten könnten Erklärungen enthalten, wann, wo, wie und warum Dekoratoren in JavaScript / TypeScript verwendet werden, da ich stark vermute, dass das Konzept eng mit dem von mir gesuchten Verständnis verbunden ist. Noch wichtiger ist jedoch, dass ich allgemeiner verstehen möchte, was unter dem Einfügen von Daten über einen Klassenkonstruktor zu verstehen ist und warum dies schlecht ist.
Um dem obigen Zitat mehr Kontext zu geben, ist dies die Situation: Es Model
wird eine Klasse erstellt, die in diesem Beispiel zum Erstellen von Börsenmodellen verwendet wird, eines für NASDAQ und eines für NYSE. Jedes Modell benötigt den Pfad des Webdienstes oder der statischen Datendatei, die die Rohdaten bereitstellen. Das Buch besagt, dass für diese Informationen ein Dekorateur anstelle eines Konstruktorparameters verwendet werden sollte, was zu Folgendem führt:
@ModelSettings("./data/nasdaq.json")
class NasdaqModel extends Model implements IModel {
constructor(metiator : IMediator) {
super(metiator);
}
...
}
Ich habe nur nicht verstanden, warum ich die Service-URL über den Dekorator hinzufügen sollte, anstatt nur als Parameter für den Konstruktor, z
constructor(metiator : IMediator, serviceUrl : string) {...
quelle
Antworten:
Ich werde dem Autor den Vorteil des Zweifels geben, und vielleicht ist das bei Typescript so, aber ansonsten ist dies in anderen Umgebungen eine völlig unbegründete Behauptung, die nicht ernst genommen werden sollte.
Auf den ersten Blick kann ich mir eine Vielzahl von Situationen vorstellen, in denen die Übergabe von Daten über den Konstruktor gut ist, einige davon neutral, aber keine schlecht.
Wenn eine bestimmte Klasse von einem bestimmten Datenelement abhängt, um in einem gültigen Zustand zu sein und ordnungsgemäß ausgeführt zu werden, ist es durchaus sinnvoll, diese Daten im Konstruktor anzufordern. Eine Klasse, die eine serielle Schnittstelle darstellt, könnte den Portnamen annehmen, ein Dateiobjekt könnte den Dateinamen erfordern, eine Zeichenfläche, deren Auflösung erforderlich ist usw. Wenn Sie die Daten nicht im Konstruktor übergeben, ist es möglich, dass sich das Objekt in einem ungültigen Zustand befindet muss beobachtet und überprüft werden. Andernfalls können Sie nur bei der Objektinstanziierung prüfen und anschließend davon ausgehen, dass sie größtenteils funktioniert. Die Autoren behaupten, dass diese vorteilhafte Situation unmöglich ist.
Darüber hinaus macht die Entscheidung, die Weitergabe von Daten in einem Konstruktor zu verbieten, praktisch alle unveränderlichen Objekte unmöglich. Unveränderliche Objekte haben in vielen Situationen eine Vielzahl von Vorteilen, und all diese werden mit den Richtlinien des Autors verworfen.
Selbst wenn veränderbare Objekte das sind, was Sie wollen, wie ist diese schlechte Praxis:
zugunsten:
Hält der Autor das erste wirklich für eine schlechte Praxis und ich sollte immer mit Option 2 gehen? Ich denke, das ist verrücktes Gerede.
Da ich das Buch nicht habe und es auch dann nicht lesen würde, wenn ich es tun würde, würde ich diese Aussage und so ziemlich jede allgemeine Aussage an dieser Stelle mit einem erheblichen Misstrauen betrachten.
quelle
Ich denke, es hängt vom Kontext ab, welche Art von Modell hier diskutiert wird. Ich habe Remos Buch nicht, aber ich denke, dass das Modell eine Art Servicemodell ist, das die Daten von einem Remote-Webdienst abrufen muss. Wenn dies der Fall ist, ist es als Webdienstmodell besser, alle erforderlichen Daten als Argumente in den Methoden des Webdienstes zu übergeben, wodurch der Dienst zustandslos wird.
Ein zustandsloser Dienst hat mehrere Vorteile. Beispielsweise muss jeder, der einen Dienstmethodenaufruf liest, nicht nachschlagen, wenn der Dienst erstellt wird, um die Details des aufgerufenen Dienstes herauszufinden. Alle Details werden in den Argumenten angezeigt, die im Methodenaufruf verwendet werden (mit Ausnahme der Remote-URL).
quelle
Einfach raten.
Wenn ich "Injektionsverhalten, nicht Daten" höre, würde ich darüber nachdenken, anstatt dies zu tun:
(Entschuldigung für das Beispiel im Pseudocode):
Um dies zu tun:
Auf diese Weise können Sie das Verhalten des Rauschens immer ändern, es zufällig machen, abhängig von einer inneren Variablen ...
Ich denke, es geht nur um die Regel "Verbund gegenüber Vererbung bevorzugen". Das ist eine großartige Regel, muss ich sagen.
Dies bedeutet NICHT, dass Sie den Namen nicht in das Objekt "Person" "einfügen" können, da es sich bei diesem Namen offensichtlich um reine Geschäftsdaten handelt. Aber in dem Beispiel , das Sie geben, den Web - Service, ist die URL etwas , das Sie brauchen , um etwas zu erzeugen , irgendwie , dass ein Dienst verbindet. Das ist irgendwie ein Verhalten: Wenn Sie die URL einfügen, fügen Sie die 'Daten' ein, die zum Erstellen eines 'Verhaltens' erforderlich sind. In diesem Fall ist es besser, das Verhalten nach außen zu verschieben und einsatzbereit zu injizieren: Injizieren Sie stattdessen eine URL-Injektion eine verwendbare Verbindung oder ein verwendbarer Verbindungsaufbau.
quelle