‫Dozent: Und nun, um dieses Projekt abzuschließen,
‫lassen Sie uns diese Stripe-Integration mit Webhooks abschließen.
‫Denken wir daran, wie unsere Stripe-Integration
‫jetzt tatsächlich funktioniert.
‫Wir haben diesen Checkout-Session-Endpunkt,
‫der von unserem Front-End aufgerufen wird.
‫Dies ruft dann die Funktion getCheckoutSession auf, also
‫im Grunde diese
‫hier, die mit all diesen Informationen hier eine
‫Checkout-Sitzung auf dem Server erstellt und
‫sie dann an den Client zurücksendet.
‫Nachdem die Zahlungsabwicklung von Stripe erfolgreich
‫durchgeführt wurde, leiten Sie den
‫Benutzer dann zu dieser Erfolgs-URL weiter, also dieser, die
‫wir erstellt haben.
‫Denken Sie daran, dass wir dieser URL die Tour-ID, die
‫Benutzer-ID und auch den Preis hinzugefügt haben.
‫Wir haben das gemacht, damit unsere Anwendung, sobald diese URL
‫hier aufgerufen wird, ein neues Buchungsdokument in
‫unserer Datenbank erstellt.
‫Wie hat das funktioniert?
‫In der my-tours-Route haben wir dafür eine Middleware.
‫Denken Sie daran, hier in den viewRoutes, in
‫my-tours, haben wir dieses createBookingCheckout.
‫Diese Funktion hier, die im Wesentlichen aus der Abfrage die Tour,
‫den Benutzer und den Preis nimmt und
‫mit diesen Daten einen Eintrag in der Datenbank erstellt.
‫Grundsätzlich setzen wir diese Daten immer dann
‫in die URL ein, wenn Stripe eine Zahlung erfolgreich verarbeitet.
‫Und dann holt diese Middleware-Funktion, die wir hier
‫haben, die Daten ab und erstellt anhand dieser Daten eine neue Buchung
‫in unserem System.
‫Und danach leiten wir hier im Grunde
‫auf die ursprüngliche URL ohne den Abfragestring um.
‫Das Problem dabei war, dass es nicht wirklich sicher ist.
‫Also, jeder, der diese URL-Struktur kennt, also
‫die hier oben, welche Tour, Benutzer und Preis im Abfragestring,
‫kann im Grunde eine Buchung in unserem System
‫erstellen, ohne tatsächlich zu bezahlen.
‫Wir müssen also nur diese URL mit einigen
‫Daten öffnen
‫und von dort aus automatisch eine Buchung
‫erstellen, ohne den Stripe-Prozess zu durchlaufen.
‫Denken Sie daran, wie ich damals sagte, dass wir dies
‫mit Hilfe von sogenannten Webhooks beheben würden.
‫Also, das machen wir jetzt.
‫Denn dafür
‫brauchen wir tatsächlich unsere Website, um bereitgestellt zu werden.
‫An diesem Punkt ist das jetzt tatsächlich der Fall.
‫Und jetzt können wir diese Webhooks implementieren.
‫Gehen wir dafür zu unserem Stripe-Dashboard.
‫Und das habe ich hier eigentlich schon geöffnet.
‫Gehen Sie dann hier zu Entwicklern, wählen Sie Webhooks aus und
‫fügen Sie hier einen neuen Endpunkt hinzu.
‫Was ist nun dieser Endpunkt hier und dieser Webhook?
‫Grundsätzlich werden wir hier eine URL angeben,
‫an die Stripe automatisch eine POST-Anfrage sendet, wenn eine Checkout-Sitzung
‫erfolgreich abgeschlossen wurde, also im Grunde immer
‫dann, wenn eine Zahlung erfolgreich war.
‫Mit dieser POST-Anfrage sendet Stripe dann die ursprünglichen Sitzungsdaten zurück,
‫die wir im ersten Schritt erstellt haben, als
‫wir diese Checkout-Sitzung erstellt haben.
‫Aus diesem Grund mussten wir unsere Website
‫eigentlich hier bereitstellen, da wir jetzt diese reale
‫URL hier angeben müssen.
‫Lassen Sie uns das von
‫hier aus aufnehmen und dann im Grunde unsere Route hier hinzufügen.
‫Ich werde dies einen Webhook-Checkout nennen.
‫Es ist nicht in der API und nicht in den Buchungen enthalten.
‫Sie werden gleich sehen, warum das so ist.
‫Auch hier wird Stripe bei
‫erfolgreicher Zahlung automatisch die
‫ursprünglichen Sitzungsdaten an diese URL senden.
‫Jetzt müssen wir auch noch das Ereignis auswählen.
‫Und Sie sehen, es gibt Tonnen von Ereignissen, die wir hier gebrauchen könnten.
‫Die von uns verwendete ist checkout_session_completed.
‫Fügen Sie das hinzu.
‫Jetzt müssen Sie hier noch einmal Ihr Passwort eingeben.
‫Und dann geht es los.
‫Dieser Webhook hat dann auch hier ein Geheimnis.
‫Diese benötigen wir dann auch gleich, wenn
‫wir hier tatsächlich unsere Route für diese URL erstellen.
‫Genau das werden wir als nächstes tun.
‫Grundsätzlich brauchen wir in
‫unserem System natürlich jetzt hier eine Route dafür, damit
‫wir, wenn Stripe die Daten dann an unsere Anwendung postet, dann
‫auch tatsächlich etwas damit anfangen können.
‫Lassen Sie uns hierher zurückkehren und unsere Anwendung öffnen.
‫Wir werden diese Route hier tatsächlich hinzufügen.
‫Auch hier erkläre ich Ihnen gleich warum.
‫Also App. post
‫und standard route und dann brauchen
‫wir natürlich eine Handlerfunktion dafür.
‫Lass es uns schnell hier in unserem bookingController erstellen.
‫Ich nenne das Export. webhookCheckout.
‫Jetzt muss ich diesen Controller in die App importieren. js.
‫Machen wir das eigentlich gleich hier nach dem
‫bookingRouter, also dieser und dieser, Controller
‫und hier auch Controller.
‫Gut.
‫Hier unten ist das bookingController. webhookCheckout.
‫Warum definieren wir eigentlich diesen Webhook-Checkout hier
‫in der App. js anstatt dies
‫beispielsweise im bookingRouter zu tun.
‫Der Grund dafür ist, dass in dieser Handler-Funktion, wenn wir
‫den Körper von Stripe erhalten, die Stripe-Funktion, die
‫wir dann verwenden werden, um
‫den Körper tatsächlich zu lesen, diesen Körper in einer rohen Form benötigt,
‫also im Grunde als String und nicht als JSON.
‫Auch hier müssen wir in dieser
‫Route den Körper, der mit der Anfrage kommt, nicht
‫in JSON sein, sonst funktioniert dies überhaupt nicht.
‫Die Sache ist nun, dass, sobald eine Anfrage
‫diese Middleware hier trifft, der Body geparst und
‫in JSON konvertiert wird.
‫Es wird dann auf Anfrage gestellt. body als einfaches JSON-Objekt.
‫Auch damit würde dieser Routenhandler hier
‫dann nicht funktionieren.
‫Aus diesem Grund müssen wir diese Route hier einfügen,
‫bevor wir den Body-Parser aufrufen.
‫Jetzt müssen wir noch den Körper tatsächlich parsen,
‫aber in einem sogenannten Rohformat.
‫Als ich dieses Video aufnahm, konnten wir es nicht
‫mit Express out of the box machen.
‫Und so laden wir in diesem Video den Body-Parser von npm herunter und
‫verwenden ihn, wie ich ihn im Video zeige.
‫Allerdings hat Express etwa fünf Tage nach der
‫Aufnahme dieses Videos auch den Rohparser zu Express hinzugefügt.
‫Jetzt können wir Express verwenden. raw statt den Body-Parser oder
‫die Middleware von npm installieren zu müssen.
‫Auch in diesem Video werde ich jetzt den Body-Parser installieren, aber das
‫ist nicht unbedingt erforderlich.
‫Sie können einfach Express verwenden. roh statt.
‫Npm Body-Parser
‫installieren.
‫Das klingt wahrscheinlich alles ein wenig konzentriert, und
‫ich verstehe das vollkommen, aber
‫genau so funktioniert die Stripe-Dokumentation und zwingt uns dazu,
‫es wirklich zu tun.
‫Kehren wir hier zu unserer Route zurück.
‫Auf dieser Route müssen wir den Körper in einem Rohformat haben.
‫Das können wir hier als Middleware zwischen der Route und dem
‫finalen Handler hinzufügen.
‫Hier sagen wir bodyParser. raw,
‫und wir müssen hier auch
‫den Typ sehr schnell als application/json angeben.
‫Wir haben dieses Body-Parsing jetzt als Rohkörper hier in
‫diesem Middleware-Stack hinzugefügt.
‫All dies wird wirklich zusammenkommen,
‫sobald wir mit der Implementierung dieser Funktion beginnen.
‫Lass uns das jetzt machen,
‫also gleich hier.
‫Aber bevor wir das tatsächlich
‫tun, lassen Sie uns den gesamten Code loswerden, den
‫wir geschrieben haben, damit er sofort funktioniert.
‫Im Grunde brauchen wir diese
‫Middleware-Funktion nicht mehr.
‫Auch hier in den
‫viewRoutes brauchen wir es hier auch nicht mehr.
‫Und schließlich setzen wir im
‫bookingController auch unsere URL wieder auf normal zurück.
‫Ich werde dies alles hier lassen, damit
‫Sie es als Referenz behalten können.
‫Aber jetzt sollte die Erfolgs-URL eigentlich nur diese sein.
‫Grundsätzlich möchten wir nach erfolgreicher
‫Buchung noch auf my-tours zurückkommen, aber
‫ohne all diese Abfrageparameter,
‫denn nun ist es nicht mehr diese Funktion
‫hier, die sich um die Erstellung der
‫Buchung kümmert, sondern diese Funktion
‫hier, die von natürlich derjenige,
‫der aufgerufen wird, sobald Stripe unseren Webhook anruft.
‫Lassen Sie uns dies nun implementieren.
‫Das erste, was wir
‫tun müssen, ist, diese Stripe-Signatur aus unseren Headern zu entfernen,
‫also signieren und dann anfordern. Header
‫und dann von dort Stripe-Signatur.
‫Wenn Stripe unseren Webhook aufruft, fügt es
‫dieser Anforderung grundsätzlich einen Header
‫hinzu, der eine spezielle Signatur für unseren Webhook enthält.
‫Wenn Sie denken, dass Sie einfach blindlings
‫dem folgen, was ich
‫hier tue, nun, (lacht), genau das habe
‫ich auch aus den Stripe-Dokumentationen gemacht.
‫Auch hier funktioniert Stripe wirklich so, und
‫wir können nichts dagegen tun.
‫Wie auch immer, als nächstes
‫erstellen wir ein Stripe-Ereignis, sodass const-Ereignis gleich Stripe ist.
‫Dafür müssen wir natürlich die Stripe-Bibliothek installieren, die
‫wir hier oben haben.
‫Also Streifen. Webhooks. constructEvent.
‫Hier kommt nun endlich dieser Körper ins Spiel, also
‫fordern Sie ihn an. Karosserie.
‫Und denken Sie daran, dass dieser Körper
‫hier in der Rohform vorliegen muss,
‫also im Grunde als String verfügbar ist.
‫Aus diesem Grund stellen wir diese Route noch
‫einmal vor alle unsere
‫anderen Routen und insbesondere, bevor der Body-Parser seine Aufgabe
‫erfüllen konnte, unseren Körper in ein JSON-Objekt zu konvertieren.
‫Dann brauchen wir neben diesem Body für das Event eine Signatur, also im
‫Grunde die Signatur, die zusammen
‫mit dem Header gesendet wurde, und schließlich unser Webhook-Geheimnis.
‫Holen wir uns das von hier, kopieren Sie es.
‫Da es ein Geheimnis ist, sollten wir es wie
‫immer hier zu
‫unserer Konfigurationsdatei hinzufügen, also STRIPE_WEBHOOK_SECRET.
‫Und später natürlich nicht vergessen, dies
‫auch zu unserer Heroku-Konfiguration hinzuzufügen.
‫Lass uns das jetzt benutzen.
‫Prozess hinzufügen. env.
‫Ich hätte das gleich hier
‫kopieren sollen.
‫Sie sehen, all dies dient dazu, den Prozess
‫super, super sicher zu machen.
‫Wir brauchen all diese Daten wie
‫die Signatur und auch das Geheimnis, um die Daten, die
‫in den Körper kommen, grundsätzlich
‫zu validieren, damit sie niemand wirklich manipulieren kann.
‫Nun kann es bei der Erstellung
‫dieses Ereignisses zu
‫Fehlern kommen, beispielsweise wenn die Signatur
‫falsch ist oder das Geheimnis falsch ist.
‫Also packen wir dies in einen Try-Catch-Block.
‫Okay.
‫Natürlich brauchen wir jetzt den Haken.
‫Falls ein
‫Fehler auftritt, möchten wir einen Fehler an
‫Stripe zurücksenden, also sende res zurück. status 400 und dann einfach send
‫webhook error verwenden und
‫dann den Fehler einfach hinzufügen. Botschaft.
‫Es ist also Stripe, der diese Antwort hier erhält,
‫weil es wiederum Stripe ist, der tatsächlich die URL aufruft,
‫also unseren Webhook, der dann diese Funktion aufruft.
‫Jetzt müssen wir dieses Ereignis natürlich auch hier außerhalb
‫des Try-Catch-Blocks deklarieren, da wir
‫es sonst dort unten nicht verwenden können.
‫Also, let event und dann hier unten neu zuweisen, denn denken
‫Sie daran, dass die ES6 const
‫und let block-Scope sind.
‫Daher wäre diese Variable außerhalb dieses Blocks
‫nicht verfügbar.
‫Lassen Sie uns dieses Ereignis nun tatsächlich verwenden.
‫Als erstes müssen wir testen, ob dies wirklich die Veranstaltung ist, die
‫wir wollen.
‫So können wir Event machen. type ist gleich
‫checkout. Sitzung. Komplett.
‫Denken Sie daran, dass dies in
‫unserem Stripe-Dashboard genau der Typ ist, den wir hier definiert haben.
‫Das ist also der Ereignistyp.
‫Jetzt prüfen wir, ob das wirklich das
‫Ereignis ist, das wir hier empfangen, nur um 100% sicher zu sein.
‫Wenn ja, möchten wir die Veranstaltung dann tatsächlich nutzen, um unsere
‫Buchung in unserer Datenbank zu erstellen.
‫Lassen Sie uns das in einer separaten
‫Funktion tun und nicht in diesem ganzen Durcheinander.
‫Dafür erstelle ich eine Funktion.
‫Lassen Sie mich
‫ihm genau denselben Namen geben, also createBookingCheckout.
‫Eigentlich ein schöner Name, aber jetzt
‫kann es keine Middleware sein, sondern
‫nur eine normale Funktion.
‫Diese Funktion übernimmt die Sitzungsdaten.
‫Und denken Sie daran, dass die Sitzungsdaten genau diese Sitzung sind, die
‫wir hier zuerst erstellt haben.
‫Wenn dies das richtige Ereignis ist,
‫rufen wir diese Funktion tatsächlich auf,
‫also createBookingCheckout mit der Sitzung, die sich im
‫Ereignis befindet. Daten. Objekt.
‫Und dann
‫lassen Sie uns zum Schluss einfach eine Antwort an Stripe zurücksenden.
‫Also, Status 200 und
‫dann nehmen wir an, dass ein
‫JSON-Empfang auf "true" gesetzt wird.
‫Macht Sinn?
‫Auch hier wird all dieser
‫Code ausgeführt, wenn eine Zahlung erfolgreich war.
‫Stripe ruft dann unseren Webhook auf, die URL,
‫die diese Funktion aufruft.
‫Diese Funktion erhält also einen Hauptteil der Anfrage
‫und erstellt dann zusammen mit der Signatur und/oder dem Webhook-Geheimnis
‫ein Ereignis, das die Sitzung enthält.
‫Und dann können wir mit diesen
‫Sitzungsdaten unsere neue Buchung in der Datenbank erstellen.
‫Das wird also dem, was wir hier
‫zuvor hatten, ziemlich ähnlich sein.
‫Wir werden diese Codezeile hier also wieder benötigen.
‫Dies wird also auch eine asynchrone Funktion sein.
‫Und das ist genau das gleiche.
‫Jetzt brauchen wir
‫hier natürlich Zugriff auf die Tour, den Benutzer und den Preis.
‫Aber diese Daten werden noch einmal in dieser Sitzung gespeichert.
‫Beginnen wir also mit der Tour.
‫Und erinnern Sie sich, wie ich
‫hier oben, als wir
‫diese Handler-Funktion zum ersten Mal erstellten, dieses client_reference_id-Feld
‫angegeben und die tourId hinzugefügt habe.
‫Erinnere dich daran?
‫Ich tat das, weil ich
‫zu diesem Zeitpunkt schon wusste, dass wir diese Tour ID etwas später brauchen würden.
‫Jetzt ist es an der Zeit, dass wir die
‫Tour-ID tatsächlich benötigen, um diese neue Buchung erstellen zu können.
‫Und so ist jetzt
‫die Tour-ID, die wir brauchen, die Referenz-ID des Sitzungspunkt-Clients.
‫Also, lass uns das kopieren und sagen
‫Session.
‫Und natürlich müssen wir hier Tour sagen.
‫Das ist also die Tour-ID.
‫Als nächstes benötigen wir die Benutzer-ID.
‫Jetzt sind die Informationen, die wir in
‫unserer Sitzung über den Benutzer haben, die E-Mail des Benutzers.
‫Was wir jetzt also
‫tun müssen, ist im Grunde die ID des Benutzers zu erhalten.
‫Dafür fragen wir per E-Mail ab.
‫Kein Problem, denn auch die E-Mail ist einzigartig.
‫Auf dieser Grundlage können wir dann die eindeutige ID finden.
‫Der const-Benutzer wird also erwartet.
‫Und ich denke, wir haben den Benutzer bereits hier.
‫Nein?
‫Nein, das tue ich tatsächlich nicht.
‫Also machen wir das hier einfach.
‫Und Benutzer auch hier.
‫Okay.
‫Also, Benutzer. findOne und fragen dann per E-Mail ab,
‫die sich im Sitzungspunkt befindet, und ich glaube, das ist
‫die E-Mail des Kunden oder so.
‫Es ist customer_email.
‫Okay.
‫Aber das wird dann das gesamte Dokument zurückgeben, aber
‫wir wollen eigentlich die ID.
‫Lassen Sie uns das alles hier in Klammern
‫setzen und dann die ID dort aufrufen oder die ID tatsächlich lesen.
‫Das war's.
‫Und schließlich der Preis.
‫Wo wird der Preis gespeichert?
‫Nun, es ist hier in line_items.
‫Das ist ein Array, also bei Element
‫null, und dann der Betrag geteilt durch 100.
‫Also haben wir es hier mit 100 multipliziert, um Cent zu
‫bekommen, aber jetzt wollen wir es natürlich in Dollar zurück.
‫Also müssen wir das im Grunde wieder aufteilen.
‫Und so, Sitzung. line_items und dann
‫die Punktmenge des ersten Elements, wenn ich richtig liege.
‫Ja.
‫Also Betrag geteilt durch 100.
‫Das sollte es eigentlich sein.
‫Lassen Sie uns nun unsere Änderungen in das
‫Repo übertragen und an Stripe übertragen.
‫Also, git natürlich alles hinzufügen
‫und dann git commit
‫message Verbesserte Stripe-Implementierung
‫und dann git push heroku master.
‫Dies wird wiederum einige Zeit in Anspruch nehmen.
‫Wir sehen uns, wenn das erledigt ist.
‫Gut.
‫Vergessen Sie jetzt nicht, diese neue Umgebungsvariable zu setzen.
‫Also, das ist heroku config Doppelpunktsatz, und dann
‫einfach von hier kopieren.
‫Okay.
‫Das startet dann die Anwendung neu.
‫Und das ist es.
‫Also, lassen Sie uns jetzt wirklich weitermachen und es testen.
‫Gut.
‫Wir sind immer noch hier in unserer Bewerbung.
‫Mal sehen, welche Touren Laura schon gebucht hat.
‫Sie hat den Waldwanderer.
‫Diese Buchung wurde noch mit der alten Methode durchgeführt.
‫Aber diese alte Methode funktioniert jetzt nicht mehr.
‫Wenn wir jetzt noch eine Buchung machen
‫und es funktioniert, nun, dann
‫bedeutet das natürlich, dass unsere neue Implementierung funktioniert.
‫Lass uns das hier testen.
‫Wie immer 4242.
‫Jetzt warten wir es ab.
‫Nun, das lief anscheinend nicht so gut, denn
‫sonst müsste unsere zweite neue Tour schon
‫in unseren Buchungen stehen.
‫Sehen wir uns hier in unserem Dashboard an.
‫Wenn wir das
‫jetzt nachladen, dann sehen wir tatsächlich, dass es eine gelungene Veranstaltung war.
‫Das ist also das Ereignis, das wir gerade erstellt
‫haben und das diesen Körper hierher geschickt und
‫dann diese Antwort erhalten hat.
‫Dieser auf true gesetzte Empfang ist also
‫genau das, was wir hier in unserem Code gemacht haben,
‫also hier.
‫Das ist also die Antwort, die
‫wir gesendet haben, und die Leiche, die wir bekamen, waren all diese Daten.
‫Und so können wir hier die Session
‫mit dem Preis, mit der E-Mail, mit der Tour sehen.
‫Und deshalb bin ich mir nicht sicher, warum es nicht funktioniert hat.
‫Also, lass uns das hier schnell neu laden.
‫Unsere Stripe-Implementierung sollte also eigentlich korrekt sein, aber aus
‫irgendeinem Grund wurde unsere neue Buchung nicht erstellt.
‫Lassen Sie uns das auch hier in Compass überprüfen.
‫Und tatsächlich ist es nicht da.
‫Kehren wir also zu unserem Code hier zurück.
‫Oh, und ein Fehler, den ich sofort sehe, ist hier.
‫Es sollte also so abgeschlossen werden.
‫Das ist also ein dummer Fehler.
‫Mal sehen, ob hier oben
‫in createBookingCheckout möglicherweise ein weiterer Fehler auftritt.
‫Hier haben
‫wir line_items.
‫Mal sehen ob das stimmt.
‫Und ja, es scheint zu sein.
‫Das können wir auch hier in unserem Stripe noch einmal bestätigen.
‫Eigentlich heißt es hier display_items.
‫Das ist seltsam.
‫Zur Sicherheit nennen wir es hier in unserem
‫Code hier auch display_items.
‫Eine andere Sache, die mir jetzt
‫aufgefallen ist, als ich hier noch
‫einmal nachgesehen habe, ist, dass wir dieses Bild immer noch in diesen
‫anderen Naturen festcodiert haben. dev.
‫Lassen Sie uns das nun tatsächlich beheben, denn zu diesem Zeitpunkt
‫ist unsere Website natürlich bereits live und bereitgestellt.
‫Und so können wir das im Grunde durch das
‫gleiche ersetzen, das wir hier haben.
‫Daher verwenden wir diesen Teil hier oft.
‫Es ist also an der Zeit, das hier wieder zu verwenden.
‫Ja.
‫Versuchen wir, dies erneut bereitzustellen.
‫Also, git alles wieder hinzufügen.
‫Und nennen wir
‫das hier einfach Verbesserte Stripe-Implementierung zwei.
‫Und dann schiebe es wieder zu Heroku.
‫Okay.
‫Versuchen wir das noch einmal.
‫Gehen wir hierher zurück.
‫Versuchen wir jetzt erneut, bei Park Camper zu buchen.
‫Gut.
‫Sie sollten das Bild hier auf der linken Seite sehen.
‫Das heißt, auch unsere neue Bildintegration
‫hat einwandfrei funktioniert.
‫Jetzt wird es bearbeitet.
‫Ach jetzt ist es da.
‫Groß.
‫Das ist schön.
‫Jetzt haben wir wirklich eine
‫sichere und viel professionellere Stripe-Implementierung in
‫unserer Anwendung.
‫Das ist großartig.
‫Natürlich, wenn Sie hier
‫nachladen, dann sollten Sie dieses neue Ereignis hier sehen,
‫also diesen neuen Aufruf zu unserem
‫Webhook, der natürlich wieder erfolgreich war.
‫Das ist einfach großartig.
‫Jetzt möchte ich nur noch eine letzte Sache machen,
‫nämlich dem Benutzer im Grunde ein Feedback in Form einer
‫dieser grünen Nachrichten zu geben, die wir
‫beispielsweise auch beim Login verwenden.
‫Im Moment gibt unsere Anwendung
‫kein wirkliches Feedback, wenn eine neue Tour gebucht wurde.
‫Das möchte ich nun ändern.
‫Dies ist jedoch nicht wirklich einfach,
‫da diese Nachrichten
‫tatsächlich von JavaScript angezeigt werden.
‫In den anderen Fällen haben wir also einen HTTP-Aufruf an unsere API durchgeführt.
‫Und als das erledigt war, haben wir JavaScript verwendet, um
‫irgendeine Art von Nachricht anzuzeigen.
‫Aber jetzt machen wir es nicht so.
‫Die Nachricht sollte also schon beim Laden der Seite
‫irgendwo im HTML-Code stehen,
‫damit unser JavaScript diese Nachricht aus dem
‫HTML-Code aufgreifen und dort oben in einem dieser Banner
‫schön darstellen kann.
‫Daher setze ich diese Warnungen wieder
‫in HTML ein, indem ich eine data-Eigenschaft verwende.
‫Beginnen wir damit, diese Funktion direkt in unserer
‫Hauptvorlage zu implementieren.
‫Das ist hier in Ansichten, Basis.
‫Ich werde diese Warnmeldung tatsächlich direkt
‫in das body-Element einfügen.
‫Hier haben wir eine Datenalert-Eigenschaft, die eigentlich
‫nur gesetzt werden sollte,
‫wenn die Alert-Variable hier verfügbar ist.
‫Verwenden wir also ES6, also eine Vorlagenzeichenfolge, und sagen
‫wir, wenn es eine Warnung gibt, verwenden
‫wir hier "alert" und andernfalls eine leere Zeichenfolge.
‫Daher ist diese Warnung hier die Warnmeldung,
‫die JavaScript dann aufnimmt und auf der Seite anzeigt.
‫Wie landet diese Warnmeldung nun eigentlich als
‫Warnvariable hier in unserem Template?
‫Nun, ich habe eine Lösung entwickelt, die wiederverwendbar ist, sodass
‫wir sie in unserer gesamten Anwendung verwenden können.
‫Das heißt, wir fügen in der Abfragezeichenfolge
‫ein Warnschlüsselwort hinzu und dann
‫haben wir eine Middleware,
‫die dieses Schlüsselwort aus der URL nimmt und
‫dann entsprechend dem dort eingegebenen Schlüsselwort eine
‫ganze Warnmeldung als Antwort ausgibt . Einheimische.
‫Denken Sie also daran, dass alles, was auf Antwort steht. locals steht dann
‫als Variable in allen unseren Templates zur Verfügung.
‫Also, wir haben das tatsächlich schon früher
‫in unserem AuthController verwendet, glaube ich.
‫Ganz schnell, lass mich dir das zeigen.
‫Genau hier sagten wir Antwort. lokal. Benutzer und legen
‫Sie dort den aktuellen Benutzer ab.
‫Dann haben wir automatisch in allen
‫Vorlagen Zugriff auf diese Benutzervariable.
‫Also, lasst uns jetzt implementieren, was ich gerade
‫gesagt habe und mit der URL beginnen.
‫Was ich hier tun werde, ist, diese Abfragezeichenfolge hier
‫der Erfolgs-URL hinzuzufügen.
‫Hier werde ich gleich Buchung aufmerksam machen.
‫Jetzt könnte ich in allen anderen URLs auch noch einen Alert hinzufügen und
‫dann natürlich mit einem anderen Keyword hier.
‫Und das werden wir hier wirklich nur für diese Buchung tun.
‫Aber auch hier habe ich eine Art wiederverwendbare Lösung geschaffen.
‫Wie auch immer, jetzt brauchen wir in unseren Routen im Grunde eine
‫Middleware, die für alle Anfragen läuft.
‫Und es ist diese Middleware, die die
‫Warnung aus der Abfragezeichenfolge aufnimmt und eine Warnmeldung in
‫unsere Antwort einfügt. Einheimische.
‫Also Router.
‫verwenden Sie viewController. Warnungen.
‫Dies ist also eine Middleware-Funktion,
‫die im Wesentlichen für jede einzelne Anfrage ausgeführt wird, die in
‫diesen Router eingeht, also
‫im Wesentlichen für alle Anfragen an unsere Website.
‫Lassen Sie uns nun diese Middleware in
‫unserem viewsController erstellen.
‫Also Exporte. Benachrichtigungsanforderung,
‫Antwort und weiter.
‫Die Warnung
‫ist also eine Anfrage. Anfrage. Alarm.
‫Also verwenden wir diese Strukturierung hier einfach noch einmal.
‫Und dann sagen wir, wenn Alert gleich Buchung ist, also den
‫Alert, den wir hier in die Abfragezeichenfolge einfügen, dann
‫sagen wir
‫in diesem Fall Antwort. Einheimische. Eine Benachrichtigung wird angezeigt,
‫dass
‫Ihre Buchung erfolgreich
‫war. Bitte überprüfen
‫Sie Ihre E-Mail, um eine Bestätigung zu erhalten.
‫Und wir sollten auch noch einen anderen
‫Satz hinzufügen, und zwar diesen, wenn Ihre Buchung dies nicht tut, wählen Sie
‫diesen aus, wird hier nicht sofort angezeigt, bitte kommen Sie
‫später wieder.
‫Und der
‫letzte Teil liegt daran, dass Stripe in
‫seiner Dokumentation sehr genau sagt, dass der Webhook manchmal
‫kurz nach dem Aufruf der Erfolgs-URL aufgerufen wird.
‫In diesem Fall würde diese Erfolgs-URL dann
‫alle aktuellen Touren anzeigen, aber erst danach
‫würde der Webhook
‫aufgerufen und die Tour in unserer Datenbank erstellt.
‫Daher wird die neue Buchung nicht sofort auf
‫der Seite Meine Buchungen angezeigt.
‫Aber natürlich hat in diesem Fall noch alles gut funktioniert.
‫Also lade ich einfach neu, aber später werden wir dieses Problem beheben.
‫Jetzt müssen wir nur noch die nächste Middleware aufrufen.
‫Und das ist es tatsächlich.
‫Auch hier haben wir dies hier nur für Warnungen gleich der
‫Buchung getan, aber wir konnten dies jetzt
‫überall auf unserer Website verwenden, indem wir verschiedene
‫Warnungsschlüsselwörter und Abfragezeichenfolgen festlegen.
‫Damit setzen wir diese Nachricht hier auf res. Einheimische. Alarm.
‫Auch hier wird unsere Basisvorlage dies
‫aufnehmen und hier in dieser Datenwarnungseigenschaft anzeigen.
‫Und so müssen Sie jetzt nur noch zu unserem Index gehen. js und lesen Sie die
‫Warnung von hier aus und zeigen Sie sie dann an.
‫Und so sollte das ziemlich einfach sein.
‫Hier in der Öffentlichkeit machen wir es im Index tatsächlich richtig.
‫Und das erste ist, dass wir die Alerts-Funktion tatsächlich
‫importieren müssen.
‫Das ist keine App.
‫Es ist hier im Index.
‫Okay.
‫Und dann hier unten, lesen wir im Grunde diese Warnung.
‫Also, const alertMessage, sagen wir, ist ein
‫Dokument. querySelector, dann
‫das body-Element, Punkt-Dataset. Alarm.
‫Und so, natürlich nur, wenn es
‫eine Warnung gibt, dann zeigen Sie
‫die Warnung
‫mit Erfolg und die Warnmeldung an.
‫Und jetzt möchte ich diese kleine
‫ShowAlert-Funktion hier ein wenig ändern, weil wir jetzt
‫tatsächlich viel Text haben.
‫Und die Standardzeit, in der die Warnung angezeigt
‫wird, würde nicht ausreichen, um den gesamten Text tatsächlich zu lesen.
‫Sie sehen hier also, dass die Warnung nach
‫fünf Sekunden ausgeblendet wird.
‫Lassen Sie uns dem Benutzer tatsächlich
‫erlauben, die Anzahl der Sekunden anzugeben, die die Warnung angezeigt wird.
‫Wir werden dies standardmäßig mit fünf Sekunden tun.
‫Hier machen wir dann einfach die Zeit mal 1.000, um es
‫in Millisekunden umzurechnen.
‫So funktionieren alle Funktionen überall mit
‫fünf Sekunden.
‫Machen wir es tatsächlich sieben Sekunden,
‫wenn wir nichts angeben.
‫Aber wenn wir wollen, können wir diese sieben dann überschreiben.
‫Und so werde ich das jetzt
‫hier machen und es tatsächlich 20 Sekunden auf den Bildschirm bringen.
‫Gut.
‫Ich denke, das sollte es sein.
‫Ich hoffe, das war sinnvoll.
‫Lassen Sie uns nun ganz schnell unser Bundle zusammenstellen.
‫Das ist npm run build und tippe dann auf Autocomplete.
‫Das dauert auch ein bisschen.
‫Aber jetzt ist es geschafft.
‫Lassen Sie es uns jetzt ein letztes Mal bereitstellen, in
‫der Hoffnung, dass es tatsächlich funktioniert.
‫Also, git commit.
‫Also, Stripe-Nachrichten.
‫Und ein letztes Mal, git push heroku master.
‫Lassen Sie es uns jetzt testen, indem wir hier eine weitere Tour kaufen.
‫Holen wir uns diesmal den City Wanderer.
‫Oh, ich sehe gerade, dass hier bereits eine Nachricht steht.
‫Das ist nicht gut.
‫Und Sie sehen, dass es nach 20 Sekunden verschwunden ist.
‫Es sieht so aus, als
‫ob diese Warnungsklasse jetzt standardmäßig immer hier platziert wird.
‫(lacht)
‫Ja.
‫Das liegt daran, dass es hier alertMessage und nicht
‫nur alert sein sollte.
‫Aber egal, testen wir jetzt einfach, ob die Meldung
‫bei der Buchung der Tour tatsächlich stimmt.
‫Okay.
‫Jetzt warten wir es ab.
‫Auf geht's.
‫Tatsächlich ist da unsere Botschaft.
‫So schön.
‫Auch unsere Tour zeigt sich hier.
‫Und Sie sehen, dass es wirklich lange hier bleibt.
‫Das funktioniert also auch.
‫Lass uns nur ganz schnell...
‫Und zuerst müssen wir das Bundle hier tatsächlich neu erstellen.
‫Dann können wir alles
‫zu unserem Staging-Bereich hinzufügen, Fehlerkorrektur für Nachrichtenwarnungen.
‫Das sind
‫also schon einige (lacht) wirklich professionell klingende Botschaften.
‫Jetzt noch ein letzter Stoß zu Heroku.
‫Wenn wir nun unsere Seite laden, sollten
‫wir keine Warnmeldung sehen.
‫Und tatsächlich, jetzt ist alles sauber.
‫Und so kann ich jetzt sagen, dass dieses
‫Projekt zumindest vorerst wirklich abgeschlossen ist.
‫Nochmals tolle Arbeit, herzlichen Glückwunsch und gut gemacht,
‫dass Sie wahrscheinlich einer der wenigen Leute sind, die es tatsächlich
‫bis zum Ende des Projekts schaffen und
‫diese schöne Website und auch API wirklich aufbauen, die Sie
‫jetzt in Ihr Portfolio aufnehmen können und der
‫Welt zeigen.