‫-: In diesem Video erstellen wir
‫eine spezielle Art von Middleware namens Param-Middleware.
‫Param-Middleware ist also Middleware, die nur für bestimmte Parameter
‫ausgeführt wird, also im Grunde,
‫wenn wir einen bestimmten Parameter in unserer URL haben.
‫In unserem Beispiel hier ist der
‫einzige Parameter, den wir möglicherweise in unserer Routen-URL haben, die ID, oder?
‫Und so können wir Middleware schreiben,
‫die nur läuft, wenn diese ID in der
‫URL vorhanden ist. Okay, ich zeige Ihnen, wie es geht.
‫Es ist eigentlich ganz einfach, also auf
‫unserem Router und dann auf der param-Methode, okay.
‫Also geben wir hier zuerst den Parameter an,
‫nach dem wir eigentlich suchen wollen, also
‫im Grunde den Parameter,
‫für den diese Middleware laufen soll, und er heißt
‫id, und dann natürlich unsere eigentliche Middleware-Funktion.
‫Und wie üblich haben wir Zugriff auf das
‫Request- und das Response-Objekt,
‫und dann spürt eine Middleware-Funktion
‫auch die nächste Funktion auf, oder?
‫In einer Parameter-Middleware-Funktion
‫erhalten wir nun tatsächlich Zugriff auf ein viertes
‫Argument, und dieses ist der Wert des fraglichen Parameters.
‫Daher nennen wir das normalerweise val, was für Wert steht.
‫Und jetzt können wir es einfach
‫in die Konsole
‫einloggen, nur um zu sehen, ob das tatsächlich funktioniert. Sagen wir
‫also, Tour-ID ist und dann ID, richtig?
‫Als nächstes müssen wir auch als nächstes anrufen, oder?
‫Denn sonst bleibt der Request-Response-Zyklus
‫in dieser Middleware-Funktion
‫hängen und kann nicht zur
‫nächsten Middleware im Stack übergehen, oder?
‫Das werden diese Routen hier unten sein.
‫In Ordnung, also speichern wir es und sehen Sie es sich jetzt an.
‫Und wir möchten, dass es
‫nicht für alle Benutzer gilt, sondern für eine Tour, oder?
‫Lassen Sie mich
‫Ihnen zuerst zeigen, was passiert, wenn wir keine ID haben, okay, und
‫jetzt sehen wir in unserer Konsole kein Log-Down.
‫Aber wenn ich jetzt die gleiche Anfrage auf
‫dieser Route schicke, wo wir die ID haben, mal sehen, was dann passiert.
‫Oh, es sagt mir, dass id nicht definiert
‫ist, und tatsächlich ist es nicht id, also war das ein dummer Fehler.
‫Es ist also Wertsache, oder?
‫Denken Sie also daran, wie ich sagte, dass
‫dieser Wertparameter tatsächlich
‫den Wert des id-Parameters enthält, und den
‫müssen wir dann natürlich hier verwenden,
‫um auf diese ID zuzugreifen.
‫Versuchen wir es noch einmal, und jetzt
‫haben wir tatsächlich die Tour-ID ist zwei, oder?
‫Das Protokoll kam also direkt von dieser Funktion hier.
‫Was ich Ihnen
‫jetzt auch zeigen möchte, ist, dass
‫diese Middleware-Funktion für keine der Benutzerrouten ausgeführt wird.
‫Nehmen wir an, wir rufen einen Benutzer mit einer bestimmten ID
‫an, also kopieren wir diese
‫hierher, erstellen eine neue Anfrage mit einer ID und lassen
‫sie mich auch speichern.
‫Also Benutzer holen und an Benutzer speichern, und wenn ich es hier sende, erhalten
‫wir natürlich unsere Standardantwort, dass
‫diese Route nicht definiert ist, aber Sie sehen
‫auch, dass wir kein Protokoll wie zuvor hatten.
‫Und das liegt natürlich daran, dass diese Middleware-Funktion
‫nur in unserem Tourrouter spezifiziert ist.
‫Bei dieser Art von lokaler Minianwendung ist
‫das also wieder die Analogie, die ich gerne mache.
‫Im Grunde ist jeder
‫Router eine Art Mini-Unteranwendung, eine für jede Ressource.
‫Da diese Middleware nur auf diesem Router angegeben ist,
‫ist sie natürlich
‫nur ein Teil des Middleware-Stack,
‫wenn wir uns tatsächlich in dieser Unteranwendung befinden.
‫Macht Sinn?
‫Nehmen wir also an, wir haben eine eingehende Anfrage zu Touren/ID.
‫Also durchläuft diese Anfrage dann all diese Middleware, also
‫zuerst diese Middleware, dann diese, dann diese
‫Middleware, dann diese, also alle sind Teil des
‫Middleware-Stack und dann trifft sie schließlich
‫auf diese Middleware und da dies so
‫ist tatsächlich die Route,
‫wird es dann in die tourRouter-Middleware gelangen.
‫Okay, und von dort geht es dann direkt in diese
‫Middleware, und dann wird dieser Code ausgeführt.
‫Und das nur, weil es eine ID in der Route hat.
‫Wenn nicht, dann wird dies einfach ignoriert
‫und direkt zur nächsten
‫Middleware im Stack verschoben, also hier unten, oder?
‫Cool, so funktioniert die Param-Middleware; aber im Moment
‫ist es nicht wirklich nützlich.
‫Aber wir können es hier
‫tatsächlich für einen sehr praktischen Anwendungsfall verwenden.
‫Gehen wir also zu unseren Handlerfunktionen hier und
‫Sie sehen, dass wir in allen Handlerfunktionen,
‫die die ID tatsächlich verwenden, überprüfen, ob die ID gültig ist.
‫Also machen wir es hier in Get Tour, und wir
‫machen es auch in Update Tour, also hier und in Delete Tour.
‫Alle diese drei Funktionen haben also diesen sehr ähnlichen Code,
‫bei dem sie prüfen, ob die
‫ID gültig ist, und wenn nicht, senden sie diese ungültige ID-Antwort zurück.
‫Wir haben also all diesen Code
‫an derselben Stelle und wie Sie bereits wissen,
‫ist es keine gute Vorgehensweise, Code zu wiederholen.
‫Daher können wir hier das Konzept der
‫Param-Middleware verwenden; und führen Sie diese Prüfung hier in
‫einer externen Middleware durch, die
‫ausgeführt wird, bevor die Anforderung diese Handlerfunktionen erreicht.
‫Lassen Sie uns also den Code
‫von hier kopieren oder tatsächlich ausschneiden und eine
‫neue Middleware-Funktion namens checkID erstellen, die ich natürlich auch exportieren muss.
‫Also checkID und wir haben Zugriff, Anfrage, Antwort, Weiter und noch
‫einmal. Denken Sie daran, dass es sich um eine
‫Param-Middleware handelt und das vierte Argument der
‫Wert des Parameters ist.
‫Okay, fügen Sie es hier ein und vergessen
‫Sie dann nicht, am Ende der Middleware als nächstes anzurufen, in Ordnung?
‫Und was auch sehr wichtig
‫ist, ist, dass wir diese Rückgabeanweisung hier
‫haben, denn wenn wir diese Rückgabe hier
‫nicht hätten, dann würde Express diese Antwort zurücksenden, aber
‫den Code in
‫dieser Funktion weiterhin ausführen.
‫Und so wird es nach
‫dem Senden der Antwort immer noch diese nächste Funktion
‫treffen und es würde zur nächsten Middleware übergehen
‫und dann eine weitere Antwort an den Client senden.
‫Aber das ist wirklich nicht
‫erlaubt, also denken Sie daran, dass wir diesen Fehler tatsächlich schon
‫einmal hatten, als er uns sagte, dass
‫wir keine Header senden dürfen, nachdem die Antwort bereits gesendet wurde.
‫Und das ist die
‫Art von Fehler, auf die wir stoßen
‫würden, wenn wir diese return-Anweisung nicht hätten, okay.
‫Stellen Sie also noch einmal sicher, dass die Funktion nach dem
‫Senden dieser Antwort zurückkehrt, damit sie beendet
‫wird und diese nie als nächstes aufgerufen wird.
‫Vergiss das also nie, aber wir
‫werden das natürlich im
‫weiteren Verlauf des Kurses mehrmals machen
‫und du wirst dich an diese Art von Muster gewöhnen.
‫Lassen Sie uns also diesen wiederholten Code aus all diesen
‫anderen Funktionen entfernen, damit
‫wir ihn hier wieder haben, und ja.
‫Ich möchte diesen Code auch hier,
‫um sicherzustellen, dass die Funktion
‫tatsächlich ausgeführt wird, und in Ordnung, also können wir ihn jetzt
‫hier loswerden und durch unsere neu erstellte Controller-Funktion ersetzen.
‫Also tourController,
‫checkID, also lass uns
‫das jetzt und gut noch einmal überprüfen, nur
‫um sicherzustellen, dass es
‫nicht dort läuft, wo wir keine ID haben, also haben wir hier
‫kein Log, also funktioniert alles noch auf dieser Seite.
‫Und jetzt erhalten Sie eine Tour mit einer
‫regulären ID, also einer gültigen ID, und mal sehen.
‫Nun, wir erhalten die Tour-ID als log,
‫und das heißt, wenn
‫sie tatsächlich unsere checkID-Middleware ausgeführt hat, richtig?
‫Und wenn wir jetzt
‫eine ungültige ID versuchen, erhalten wir
‫unsere Meldung "Ungültige ID", den 404-Fehlercode und natürlich unsere Tour-ID.
‫Machen wir das gleiche mit dem Patch,
‫wir haben hier schon eine
‫ungültige ID und so läuft es auch auf diesem.
‫Also perfekt, oder?
‫Wir haben also nicht mehr den checkID-Code im
‫Update-Handler, den wir gerade aufgerufen haben, aber unsere ID
‫wird immer noch überprüft,
‫weil wir diese Middleware haben, also hier.
‫Wir haben diese Middleware im
‫Stack, bevor sie tatsächlich auf das Update tourController trifft.
‫Diese Middleware ist jetzt also Teil unserer Pipeline, wie
‫Sie sich das vorstellen können. Jetzt
‫könnten Sie argumentieren, dass wir einfach
‫eine einfache Funktion erstellen könnten,
‫die auch nach der ID suchen könnte,
‫und ich rufe diese Funktion in jeder dieser Tourfunktionen auf
‫und rufe dann auf es in jedem dieser relevanten Tour-Controller;
‫aber das würde
‫der Express-Philosophie wirklich widersprechen, wo wir immer mit dem
‫Middleware-Stack arbeiten sollten, also mit dieser Pipeline
‫so viel wie möglich, okay, und diese Funktionen hier müssen sich
‫also überhaupt nicht um die Validierung kümmern.
‫Jede dieser Funktionen hat nur einen Zweck, nämlich zu tun,
‫was sie sagen, also ruft diese
‫nur die Tour ab, diese
‫erstellt nur eine Tour, diese aktualisiert nur und diese löscht
‫nur, sie prüft nicht, sie tut es über
‫all das muss man sich keine Sorgen machen.
‫Und wenn wir hier nun
‫auch noch abhängig von der ID einen weiteren Controller hinzufügen
‫würden, dann würde das automatisch auch prüfen, ob
‫die ID ungültig ist, ohne dass wir weitere Schritte unternehmen müssen.
‫Dies wird also automatisch nach der ID
‫suchen und das ist wirklich praktisch und auch,
‫wie Express-Apps funktionieren sollten, großartig.
‫Wir haben also ein weiteres Tool in unserer Express-Toolbox, mit
‫dem wir jetzt unsere Express-Anwendungen schreiben können.