Das ultimative Ruby on Rails-Tutorial für Fortgeschrittene: Erstellen wir eine vollständige App!

Es gibt viele Online-Tutorials, die zeigen, wie Sie Ihre erste App erstellen. Dieses Tutorial geht noch einen Schritt weiter und erklärt Zeile für Zeile, wie eine komplexere Ruby On Rails-Anwendung erstellt wird.

Während des gesamten Tutorials werde ich nach und nach neue Techniken und Konzepte einführen. Die Idee ist, dass Sie mit jedem neuen Abschnitt etwas Neues lernen sollten.

Die folgenden Themen werden in diesem Handbuch behandelt:

  • Ruby On Rails Grundlagen
  • Refactoring: Helfer, Teilbemerkungen, Anliegen, Gestaltungsmuster
  • Prüfung: TDD / BDD (RSpec & Capybara), Fabriken (Factory Girl)
  • Aktionskabel
  • Aktiver Job
  • CSS, Bootstrap, JavaScript, jQuery

Worum geht es in der App?

Es wird eine Plattform sein, auf der Sie Gleichgesinnte suchen und treffen können.

Hauptfunktionen der App:

  • Authentifizierung (mit Devise)
  • Möglichkeit, Beiträge zu veröffentlichen und sie zu durchsuchen und zu kategorisieren
  • Instant Messaging (Popup-Fenster und ein separater Messenger) mit der Möglichkeit, private und Gruppengespräche zu führen.
  • Möglichkeit, Benutzer zu Kontakten hinzuzufügen
  • Echtzeit-Benachrichtigungen

Sie können sehen, wie die vollständige Bewerbung aussehen wird.

Den vollständigen Quellcode des Projekts finden Sie auf GitHub.

Inhaltsverzeichnis

  1. Einführung und Einrichtung
    Voraussetzungen
    Konfiguration
    Erstelle eine neue App
  2. Layout
    Startseite
    Bootstrap
    Navigationsleiste
    Stylesheets
  3. Beiträge
    Authentifizierung
    Helfer
    Testen
    Hauptfutter
    Einzelne Post
    Spezifische Branchen
    Service-Objekte
    Erstellen Sie einen neuen Beitrag
  4. Instant Messaging
    Private Unterhaltung
    Kontakte
    Gruppengespräch
    Bote
  5. Benachrichtigungen
    Kontaktanfragen
    Gespräche

Voraussetzungen

Ich werde versuchen, jede Codezeile zu erklären und zu erklären, wie ich auf die Lösungen gekommen bin. Ich denke, es ist durchaus möglich, dass ein absoluter Anfänger diesen Leitfaden vervollständigt. Beachten Sie jedoch, dass dieses Tutorial einige Themen behandelt, die über die Grundlagen hinausgehen.

Wenn Sie also ein absoluter Anfänger sind, wird es schwieriger, da Ihre Lernkurve ziemlich steil wird. Ich werde Links zu Ressourcen bereitstellen, über die Sie zusätzliche Informationen zu jedem neuen Konzept erhalten können, das wir berühren.

Idealerweise ist es am besten, wenn Sie sich der Grundlagen von:

  • HTML, CSS, Bootstrap, JavaScript, jQuery
  • Ruby, Ruby On Rails
  • Git

Konfiguration

Ich gehe davon aus, dass Sie bereits Ihre grundlegende Ruby On Rails-Entwicklungsumgebung eingerichtet haben. Wenn nicht, überprüfen Sie RailsInstaller.

Ich hatte für eine Weile auf Windows 10 entwickelt. Anfangs war es okay, aber nach einiger Zeit hatte ich es satt, mystische Hindernisse zu überwinden, die von Windows verursacht wurden. Ich musste immer wieder Hack-Methoden finden, um meine Anwendungen zum Laufen zu bringen. Mir ist klar geworden, dass es meine Zeit nicht wert ist. Die Überwindung dieser Hindernisse brachte mir keine wertvollen Fähigkeiten oder Kenntnisse ein. Ich habe nur meine Zeit damit verbracht, das Windows 10-Setup aufzuzeichnen.

Also wechselte ich stattdessen zu einer virtuellen Maschine. Ich entschied mich für Vagrant, um eine Entwicklungsumgebung zu erstellen, und PuTTY, um eine Verbindung zu einer virtuellen Maschine herzustellen. Wenn Sie Vagrant auch verwenden möchten, ist dies das Tutorial, das ich nützlich fand.

Erstelle eine neue App

Wir werden PostgreSQL als unsere Datenbank verwenden. Es ist eine beliebte Wahl unter Ruby On Rails-Community. Wenn Sie noch keine Rails-Apps mit PostgreSQL erstellt haben, können Sie dieses Tutorial lesen.

Wenn Sie mit PostgreSQL vertraut sind, navigieren Sie zu einem Verzeichnis, in dem Sie Ihre Projekte aufbewahren, und öffnen Sie eine Befehlszeile.

Um eine neue App zu generieren, führe diese Zeile aus:

schiebt neues Kollaborationsfeld --database = postgresql

Collabfield, so werden unsere Anwendungen genannt. Standardmäßig verwendet Rails SQlite3. Da wir jedoch PostgreSQL als Datenbank verwenden möchten, müssen wir Folgendes hinzufügen:

--database = postgresql

Jetzt sollten wir erfolgreich eine neue Anwendung generiert haben.

Navigieren Sie zu einem neu erstellten Verzeichnis, indem Sie den folgenden Befehl ausführen:

cd collabfield

Und jetzt können wir unsere App ausführen, indem wir Folgendes eingeben:

Schienen s

Wir haben gerade unsere App gestartet. Jetzt sollten wir sehen können, was wir bisher erreicht haben. Öffnen Sie einen Browser und rufen Sie http: // localhost: 3000 auf. Wenn alles gut gegangen ist, sollten Sie die Rails-Signatur-Willkommensseite sehen.

Layout

Zeit zum Code. Wo sollen wir anfangen? Nun, wir können beginnen, wo immer wir wollen. Wenn ich eine neue Website erstelle, erstelle ich gerne eine Art grundlegende visuelle Struktur und erst dann alles andere. Lass uns genau das tun.

Startseite

Wenn wir zu http: // localhost: 3000 gehen, sehen wir die Rails-Begrüßungsseite. Wir werden diese Standardseite durch unsere eigene Homepage ersetzen. Dazu generieren Sie einen neuen Controller namens Pages. Wenn Sie mit Rails-Controllern nicht vertraut sind, sollten Sie den Action Controller durchgehen, um eine Vorstellung davon zu bekommen, was der Rails-Controller ist. Führen Sie diese Zeile in Ihrer Eingabeaufforderung aus, um einen neuen Controller zu generieren.

Schienen g Controller-Seiten

Dieser Schienengenerator sollte einige Dateien für uns erstellt haben. Die Ausgabe in der Eingabeaufforderung sollte ungefähr so ​​aussehen:

Wir werden diesen PagesController verwenden, um unsere speziellen und statischen Seiten zu verwalten. Öffnen Sie nun das Collabfield-Projekt in einem Texteditor. Ich verwende Sublime Text, aber Sie können alles verwenden, was Sie wollen.

Öffnen Sie eine Datei pages_controller.rb

app / controller / pages_controller.rb

Hier definieren wir unsere Homepage. Natürlich können wir die Homepage auch auf andere Weise und in einem anderen Controller definieren. Aber normalerweise definiere ich die Homepage gerne im PagesController.

Wenn wir pages_controller.rb öffnen, sehen wir Folgendes:

Es handelt sich um eine leere Klasse mit dem Namen PagesController, die von der ApplicationController-Klasse erbt. Sie finden den Quellcode dieser Klasse in app / controller / application_controller.rb.

Alle unsere Controller, die wir erstellen, werden von der ApplicationController-Klasse erben. Das bedeutet, dass alle in dieser Klasse definierten Methoden für alle unsere Controller verfügbar sind.

Wir definieren eine öffentliche Methode namens index, damit sie als Aktion aufgerufen werden kann:

Wie Sie vielleicht im Action Controller gelesen haben, bestimmt das Routing, welcher Controller und seine öffentliche Methode (Aktion) aufgerufen werden sollen. Definieren wir eine Route. Wenn wir also unsere Stammseite der Website öffnen, weiß Rails, welcher Controller und welche Aktion aufgerufen werden müssen. Öffnen Sie eine routes.rb-Datei in app / config / routes.rb.

Wenn Sie nicht wissen, was Rails-Routen sind, ist dies der perfekte Zeitpunkt, um sich mit dem Rails-Routing vertraut zu machen.

Füge diese Zeile ein:

root auf: 'pages # index'

Ihre routes.rb-Datei sollte folgendermaßen aussehen:

Das Hash-Symbol # in Ruby repräsentiert eine Methode. Wie Sie sich erinnern, ist eine Aktion nur eine öffentliche Methode. Daher heißt es in pages # index: "Rufen Sie den PagesController und seinen öffentlichen Methodenindex (Aktionsindex) auf."

Wenn wir zu unserem Stammpfad http: // localhost: 3000 gehen, wird die Indexaktion aufgerufen. Wir haben jedoch noch keine Vorlagen zum Rendern. Erstellen wir also eine neue Vorlage für unsere Indexaktion. Gehen Sie zu app / views / pages und erstellen Sie eine index.html.erb-Datei in diesem Verzeichnis. In diese Datei können wir unseren regulären HTML + Embedded Ruby Code schreiben. Schreiben Sie einfach etwas in die Datei, damit wir die gerenderte Vorlage im Browser sehen können.

Startseite

Wenn wir nun zu http: // localhost: 3000 gehen, sollten wir so etwas anstelle der standardmäßigen Rails-Informationsseite sehen.

Jetzt haben wir einen sehr grundlegenden Ausgangspunkt. Wir können anfangen, neue Dinge auf unserer Website einzuführen. Ich denke, es ist Zeit, unser erstes Commit zu erstellen.

Führen Sie in Ihrer Eingabeaufforderung Folgendes aus:

Git Status

Und Sie sollten so etwas sehen:

Wenn Sie nicht bereits wissen, wird beim Generieren einer neuen Anwendung ein neues lokales Git-Repository initialisiert.

Fügen Sie alle aktuellen Änderungen hinzu, indem Sie Folgendes ausführen:

git add -A

Führen Sie dann alle Änderungen aus, indem Sie Folgendes ausführen:

git commit -m "PagesController generieren. Homepage initialisieren"

Wenn wir dies ausgeführt haben:

Git Status

Wir würden sehen, dass nichts festgeschrieben werden muss, da wir gerade alle Änderungen erfolgreich festgeschrieben haben.

Bootstrap

Für die Navigationsleiste und das responsive Grid-System wird die Bootstrap-Bibliothek verwendet. Um diese Bibliothek nutzen zu können, müssen wir die installieren
Bootstrap-Sass Juwel. Öffne das Gemfile in deinem Editor.

Collabfield / Gemfile

Fügen Sie der Gemfile einen Bootstrap-Sass-Edelstein hinzu. Wie aus der Dokumentation hervorgeht, müssen Sie sicherstellen, dass auch Sass-Rails Gem vorhanden sind.

...
Edelstein 'bootstrap-sass', '~> 3.3.6'
Edelstein 'Sass-Rails', '> = 3.2'
...

Speichern Sie die Datei und führen Sie diese aus, um neu hinzugefügte Edelsteine ​​zu installieren:

Bundle installieren

Wenn Sie die Anwendung noch ausführen, starten Sie den Rails-Server neu, um sicherzustellen, dass neue Gems verfügbar sind. Um den Server neu zu starten, fahren Sie ihn einfach herunter, indem Sie Strg + C drücken, und führen Sie den Befehl rail s erneut aus, um den Server zu starten.

Wechseln Sie zu Assets, um die Datei application.css zu öffnen:

app / assets / stylesheets / application.css

Fügen Sie unter dem gesamten kommentierten Text Folgendes hinzu:

...
@import "bootstrap-sprockets";
@import "bootstrap";

Ändern Sie nun den Namen von application.css in application.scss. Dies ist erforderlich, um die Bootstrap-Bibliothek in Rails zu verwenden. Außerdem können wir Sass-Funktionen verwenden.

Wir möchten die Reihenfolge steuern, in der alle .scss-Dateien gerendert werden, da wir in Zukunft möglicherweise einige Sass-Variablen erstellen möchten. Wir möchten sicherstellen, dass unsere Variablen definiert werden, bevor wir sie verwenden.

Entfernen Sie dazu diese beiden Zeilen aus der Datei application.scss:

* = require_self
* = require_tree.

Wir sind fast in der Lage, die Bootstrap-Bibliothek zu verwenden. Es gibt noch eine Sache, die wir tun müssen. Wie in den bootstrap-sass-Dokumenten angegeben, ist Bootstrap-JavaScript von der jQuery-Bibliothek abhängig. Um jQuery mit Rails zu verwenden, müssen Sie jquery-rails gem hinzufügen.

Juwel 'jquery-Rails'

Lauf…

Bundle installieren

… Und starten Sie den Server neu.

Im letzten Schritt müssen Bootstrap und jQuery in der JavaScript-Datei der Anwendung vorhanden sein. Gehen Sie zu application.js

app / assets / javascripts / application.js

Fügen Sie dann die folgenden Zeilen in die Datei ein:

// = Benötige JQuery
// = Bootstrap-Ritzel benötigen

Übernehmen Sie die Änderungen:

git add -A
git commit -m "Bootstrap Gem hinzufügen und konfigurieren"

Navigationsleiste

Für die Navigationsleiste wird die Navigationsleisten-Komponente von Bootstrap als Ausgangspunkt verwendet und anschließend vollständig geändert. Wir speichern unsere Navigationsleiste in einer Teilvorlage.

Wir tun dies, weil es besser ist, jede Komponente der App in separaten Dateien zu speichern. Sie können damit den Code der App viel einfacher testen und verwalten. Wir können diese Komponenten auch in anderen Teilen der App wiederverwenden, ohne den Code zu duplizieren.

Navigiere zu:

Ansichten / Layouts

Erstellen Sie eine neue Datei:

_navigation.html.erb

Für Teilstriche verwenden wir ein Unterstreichungspräfix, damit das Rails-Framework es als Teilstrich unterscheiden kann. Kopieren Sie nun die Navbar-Komponente aus den Bootstrap-Dokumenten, fügen Sie sie ein und speichern Sie die Datei. Um das Teil auf der Website zu sehen, müssen wir es irgendwo rendern. Navigieren Sie zu views / layouts / application.html.erb. Dies ist die Standarddatei, in der alles gerendert wird.

In der Datei sehen wir die folgende Methode:

<% = Ausbeute%>

Die angeforderte Vorlage wird gerendert. Um die Ruby-Syntax in der HTML-Datei zu verwenden, müssen wir sie mit <%%> umbrechen (eingebettetes Ruby ermöglicht dies). Schauen Sie sich diese StackOverflow-Antwort an, um die Unterschiede zwischen der ERB-Syntax schnell zu erkennen.

Im Abschnitt Homepage legen wir die Route fest, um die Root-URL zu erkennen. Wenn wir also eine GET-Anfrage senden, um zu einer Root-Seite zu gelangen, wird die Index-Aktion von PagesController aufgerufen. Und diese entsprechende Aktion (in diesem Fall die Indexaktion) antwortet mit einer Vorlage, die mit der yield-Methode gerendert wird. Wie Sie sich erinnern, befindet sich unsere Vorlage für eine Homepage unter app / views / pages / index.html.erb.

Da wir eine Navigationsleiste über alle Seiten haben möchten, rendern wir unsere Navigationsleiste in der Standarddatei application.html.erb. Verwenden Sie zum Rendern einer Teildatei einfach die Rendermethode und übergeben Sie den Pfad des Teils als Argument. Tun Sie dies direkt über der Yield-Methode wie folgt:

...
<% = 'Layouts / Navigation' rendern%>
<% = Ausbeute%>
...

Gehen Sie nun zu http: // localhost: 3000 und Sie sollten die Navigationsleiste sehen können.

Wie oben erwähnt, wird diese Navigationsleiste geändert. Entfernen wir zunächst alle

  • - und
    -Elemente. In Zukunft werden wir hier unsere eigenen Elemente erstellen. Die Datei _navigation.html.erb sollte jetzt so aussehen.

    Wir haben jetzt eine einfache Navigationsleiste. Es ist ein guter Zeitpunkt, um ein neues Commit zu erstellen. Führen Sie in der Eingabeaufforderung die folgenden Befehle aus:

    git add -A
    git commit -m "Hinzufügen einer grundlegenden Navigationsleiste"

    Wir sollten den Namen der Navigationsleiste von Brand in collabfield ändern. Da Brand ein Linkelement ist, sollten wir eine link_to-Methode verwenden, um Links zu generieren. Warum? Denn mit dieser Methode können wir einfach URI-Pfade generieren. Öffnen Sie eine Eingabeaufforderung und navigieren Sie zum Projektverzeichnis. Führen Sie den folgenden Befehl aus:

    Schienenwege

    Dieser Befehl gibt unsere verfügbaren Routen aus, die von der Datei routes.rbfile generiert werden. Wie wir sehen:

    Derzeit haben wir nur eine Route, die wir zuvor definiert haben. Wenn Sie sich die angegebenen Routen ansehen, sehen Sie eine Präfixspalte. Wir können diese Präfixe verwenden, um einen Pfad zu einer gewünschten Seite zu generieren. Wir müssen nur einen Präfixnamen verwenden und _path hinzufügen. Wenn wir root_path schreiben würden, würde dies einen Pfad zur Root-Seite erzeugen. Nutzen wir also die Möglichkeiten der link_to-Methode und -Routen.

    Ersetzen Sie diese Zeile:

     Marke 

    Mit dieser Zeile:

    <% = link_to 'collabfield', root_path, Klasse: 'navbar-brand'%>

    Denken Sie daran, dass Sie, wenn Sie die Funktionsweise einer bestimmten Methode nicht genau verstehen, nur Google verwenden und die Dokumentation wahrscheinlich mit einer Erklärung finden. Manchmal sind die Dokumentationen schlecht geschrieben, daher möchten Sie vielleicht ein bisschen mehr googeln und finden möglicherweise ein Blog oder eine StackOverflow-Antwort, die hilfreich sind.

    In diesem Fall übergeben wir einen String als erstes Argument, um den Wert des -Elements hinzuzufügen. Das zweite Argument wird für einen Pfad benötigt. Hier hilft uns routes, diesen zu generieren. Das dritte Argument ist optional und wird im Options-Hash gesammelt. In diesem Fall mussten wir die Klasse navbar-brand hinzufügen, damit unsere Bootstrap-Navigationsleiste funktioniert.

    Machen wir ein weiteres Commit für diese kleine Änderung. Im nächsten Abschnitt ändern wir das Design unserer App von der Navigationsleiste aus.

    git add -A
    git commit -m "Ändere den Markennamen der Navigationsleiste von Brand zu Collabfield"

    Stylesheets

    Ich möchte Ihnen vorstellen, wie ich meine Stylesheet-Dateien strukturiere. Soweit ich weiß, gibt es keine strengen Konventionen für die Strukturierung Ihrer Stylesheets in Rails. Jeder macht es etwas anders.

    So strukturiere ich normalerweise meine Dateien.

    • Basisverzeichnis - Hier verwalte ich Sass-Variablen und -Stile, die in der gesamten App verwendet werden. Beispielsweise Standardschriftgrößen und Standardelementstile.
    • Partials - Die meisten meiner Stile gehen dorthin. Ich behalte alle Stile für separate Komponenten und Seiten in diesem Verzeichnis.
    • Responsive - Hier definiere ich verschiedene Stilregeln für verschiedene Bildschirmgrößen. Beispielsweise Stile für einen Desktop-Bildschirm, einen Tablet-Bildschirm, einen Telefonbildschirm usw.

    Erstellen Sie zunächst einen neuen Repository-Zweig, indem Sie Folgendes ausführen:

    git checkout -b "styles"

    Wir haben soeben einen neuen Git-Zweig erstellt und automatisch zu ihm gewechselt. Von nun an werden wir auf diese Weise neue Änderungen am Code vornehmen.

    Der Grund dafür ist, dass wir unsere derzeit funktionsfähige Version (Hauptzweig) isolieren und einen neuen Code in die Kopie eines Projekts schreiben können, ohne Angst zu haben, etwas zu beschädigen.

    Sobald wir mit der Implementierung fertig sind, können wir nur noch Änderungen an der Master-Verzweigung zusammenführen.

    Beginnen Sie mit der Erstellung einiger Verzeichnisse:

    App / Assets / Stylesheets / Partials / Layout

    Erstellen Sie im Layoutverzeichnis eine Datei navigation.scss und fügen Sie in der Datei Folgendes hinzu:

    Mit diesen Codezeilen ändern wir die Hintergrund- und Linkfarbe der Navigationsleiste. Wie Sie vielleicht bemerkt haben, ist ein Selektor in einem anderen Deklarationsblock verschachtelt. Mit Sass können wir diese Funktionalität nutzen. ! important wird verwendet, um standardmäßige Bootstraps-Stile strikt zu überschreiben. Das Letzte, was Sie vielleicht bemerkt haben, ist, dass wir anstelle eines Farbnamens eine Sass-Variable verwenden. Der Grund dafür ist, dass wir diese Farbe in der gesamten App mehrmals verwenden werden. Definieren wir diese Variable.

    Erstellen Sie zuerst einen neuen Ordner:

    App / Assets / Stylesheets / Base

    Erstellen Sie im Basisverzeichnis eine neue Datei variables.scss. In der Datei definieren Sie eine Variable:

    $ navbarColor: # 323738;

    Wenn Sie versuchen, http: // localhost: 3000 aufzurufen, werden Sie keine Stiländerungen bemerken. Der Grund dafür ist, dass wir im Abschnitt Bootstrap diese Zeilen entfernt haben:

    * = require_self
    * = require_tree.

    von application.scss, um nicht automatisch alle Style-Dateien zu importieren.

    Das bedeutet, dass wir jetzt unsere neu erstellten Dateien in die Hauptanwendung ".scssfile" importieren müssen. Die Datei sollte jetzt so aussehen:

    Der Grund für den Import der Datei variables.scss im oberen Bereich besteht darin, sicherzustellen, dass die Variablen definiert sind, bevor wir sie verwenden.

    Fügen Sie oben in der Datei navigation.scss noch etwas CSS hinzu:

    Natürlich können Sie diesen Code am Ende der Datei einfügen, wenn Sie möchten. Persönlich bestelle und gruppiere ich CSS-Code basierend auf der Spezifität der CSS-Selektoren. Wieder macht es jeder etwas anders. Ich setze weniger spezifische Selektoren darüber und spezifischere Selektoren darunter. So gehen beispielsweise Typ-Selektoren über Klassen-Selektoren und Klassen-Selektoren über ID-Selektoren.

    Nehmen wir Änderungen vor:

    git add -A
    git commit -m "CSS zur Navigationsleiste hinzufügen"

    Wir möchten sicherstellen, dass die Navigationsleiste immer sichtbar ist, auch wenn wir nach unten scrollen. Derzeit haben wir nicht genügend Inhalte, um nach unten zu scrollen, aber wir werden es in Zukunft tun. Warum geben wir diese Funktion derzeit nicht in die Navigationsleiste ein?

    Verwenden Sie dazu die Bootstrap-Klasse navbar-fixed-top. Fügen Sie diese Klasse zum nav-Element hinzu, so dass es so aussieht:

    Außerdem möchten wir, dass das Kollaborationsfeld an der linken Seitengrenze des Bootstrap-Rastersystems liegt. Im Moment befindet es sich an der linken Seitengrenze des Ansichtsfensters, da unsere Klasse derzeit Container-Fluid ist. Um dies zu ändern, ändern Sie die Klasse in container.

    Es sollte so aussehen:

    Übernehmen Sie die Änderungen:

    git add -A
    git commit -m "
    - in _navigation.html.erb füge navbar-fixed-top class zu nav hinzu.
    - Behälter-Flüssigkeitsklasse durch Behälter ersetzen "

    Wenn Sie zu http: // localhost: 3000 wechseln, sehen Sie, dass der Homepage-Text unter der Navigationsleiste verborgen ist. Das liegt an der Navbar-Fixed-Top-Klasse. Um dieses Problem zu beheben, drücken Sie den Hauptteil nach unten, indem Sie der Datei navigation.scss Folgendes hinzufügen:

    Körper {
     Rand oben: 50px;
    }

    Zu diesem Zeitpunkt sollte die App folgendermaßen aussehen:

    Übernehmen Sie die Änderung:

    git add -A
    git commit -m "Füge 50 Pixel nach oben zum Hauptteil hinzu"

    Wie Sie sich erinnern, haben wir zuvor eine neue Filiale erstellt und zu dieser gewechselt. Es ist Zeit, zur Hauptniederlassung zurückzukehren.

    Führen Sie den Befehl aus:

    Git-Zweig

    Sie können die Liste unserer Filialen sehen. Derzeit sind wir in der Stilbranche.

    Führen Sie Folgendes aus, um zurück zum Hauptzweig zu wechseln:

    Git Checkout Master

    Führen Sie einfach Folgendes aus, um alle Änderungen, die wir im Zweig "Stile" vorgenommen haben, zusammenzuführen:

    Git-Merge-Stile

    Der Befehl hat diese beiden Zweige zusammengeführt, und jetzt können wir die Zusammenfassung der vorgenommenen Änderungen anzeigen.

    Wir brauchen keine Styles-Verzweigung mehr, daher können wir sie löschen:

    Git Branch -D Stile

    Beiträge

    Es ist fast der richtige Zeitpunkt, mit der Implementierung der Posts-Funktionalität zu beginnen. Da es unser App-Ziel ist, Nutzer mit Gleichgesinnten in Kontakt zu bringen, müssen wir sicherstellen, dass die Autoren der Posts identifiziert werden können. Um dies zu erreichen, ist ein Authentifizierungssystem erforderlich.

    Authentifizierung

    Für ein Authentifizierungssystem werden wir das Designedelstein verwenden. Wir könnten unser eigenes Authentifizierungssystem erstellen, aber das würde viel Aufwand erfordern. Wir wählen eine einfachere Route. Es ist auch eine beliebte Wahl in der Rails-Community.

    Beginnen Sie mit dem Erstellen eines neuen Zweigs:

    git checkout -b Authentifizierung

    Wie bei jedem anderen Juwel folgen wir beim Einrichten der Dokumentation. Glücklicherweise ist es sehr einfach einzurichten.

    Fügen Sie Ihrem Gemfile hinzu

    Juwel 'erfinden'

    Führen Sie dann die folgenden Befehle aus:

    Bundle installieren
    schienen erzeugen gerät: installieren

    Wahrscheinlich sehen Sie einige Anweisungen in der Eingabeaufforderung. In diesem Lernprogramm werden keine Mailer verwendet, daher ist keine weitere Konfiguration erforderlich.

    Wenn Sie noch nichts über Rails-Modelle wissen, sollten Sie sich an dieser Stelle mit ihnen vertraut machen, indem Sie die Active Record- und Active Modeldokumentation durchblättern.

    Verwenden Sie jetzt einen Gerätegenerator, um ein Benutzermodell zu erstellen.

    Schienen erzeugen Gerätebenutzer

    Initialisieren Sie eine Datenbank für die App, indem Sie Folgendes ausführen:

    Schienen db: erstellen

    Führen Sie dann diesen Befehl aus, um neue Tabellen in Ihrer Datenbank zu erstellen:

    Schienen db: migrieren

    Das ist es. Technisch ist unser Authentifizierungssystem eingerichtet. Jetzt können wir die von Devise vorgegebenen Methoden verwenden und neue Benutzer erstellen. Übernehmen Sie die Änderung:

    git add -A
    git commit -m "Hinzufügen und Konfigurieren des Devise-Gems"

    Durch die Installation von Devise Gem erhalten wir nicht nur die Back-End-Funktionalität, sondern auch Standardansichten. Wenn Sie Ihre Routen auflisten, indem Sie Folgendes ausführen:

    Schienenwege

    Sie können sehen, dass Sie jetzt eine Reihe neuer Routen haben. Denken Sie daran, wir hatten bis jetzt nur eine Wurzelroute. Wenn etwas verwirrend zu sein scheint, können Sie immer die Dokumentationen öffnen und Ihre Antworten erhalten. Vergessen Sie auch nicht, dass viele der gleichen Fragen in den Köpfen anderer Menschen auftauchen. Es besteht eine hohe Wahrscheinlichkeit, dass Sie die Antwort auch von Google finden.

    Probieren Sie einige dieser Routen aus. Gehen Sie zu localhost: 3000 / users / sign_in und Sie sollten eine Anmeldeseite sehen.

    Wenn Sie zu localhost: 3000 / users / sign_up gehen, wird auch eine Anmeldeseite angezeigt. Gottverdammt! wie Noob Noob sagt. Wenn Sie sich das Views-Verzeichnis ansehen, werden Sie feststellen, dass es kein Devise-Verzeichnis gibt, das wir ändern könnten. Um die Ansichten von Devise zu ändern, müssen Sie sie, wie in den Devise-Dokumenten angegeben, mit einem Gerätegenerator generieren. Lauf

    schienen erzeugen gedanken: ansichten

    Wenn Sie das Ansichtsverzeichnis überprüfen, wird ein generiertes Geräteverzeichnis angezeigt. Hier können wir ändern, wie die Anmelde- und Anmeldeseiten aussehen. Beginnen wir mit der Anmeldeseite, da dies in unserem Fall eine einfachere Implementierung sein wird. Auf der Registrierungsseite ist aufgrund unserer gewünschten Funktion ein zusätzlicher Aufwand erforderlich.

    Loginseite

    Navigieren Sie zu app / views / devise / sessions / new.html.erb und öffnen Sie es.

    Hier werden die Anmeldeseitenansichten gespeichert. In der Datei befindet sich nur ein Anmeldeformular. Wie Sie vielleicht bemerkt haben, wird die form_for-Methode verwendet, um dieses Formular zu generieren. Dies ist eine praktische Rails-Methode zum Generieren von Formularen. Wir werden den Stil dieses Formulars mit dem Bootstrap ändern. Ersetzen Sie den gesamten Inhalt der Datei durch:

    Hier ist nichts Besonderes los. Wir haben dieses Formular soeben in ein Bootstrap-Formular geändert, indem wir den Namen der Methode in bootstrap_form_for geändert und den Feldern Formularsteuerungsklassen hinzugefügt haben.

    Sehen Sie sich an, wie die Argumente in den Methoden gestaltet sind. Jedes Argument beginnt in einer neuen Zeile. Der Grund, warum ich das getan habe, ist, lange Codezeilen zu vermeiden. Normalerweise sollten Codezeilen nicht länger als 80 Zeichen sein, da dies die Lesbarkeit verbessert. Wir werden den Code für den Rest des Handbuchs so gestalten.

    Wenn wir localhost: 3000 / users / sign_in besuchen, wird ein Fehler angezeigt:

    undefinierte Methode 'bootstrap_form_for'

    Um Bootstrap-Formulare in Rails verwenden zu können, müssen Sie ein bootstrap_form-Gem hinzufügen. Fügen Sie dies der Gemfile hinzu

    Edelstein 'bootstrap_form'

    Dann renne:

    Bundle installieren

    In diesem Moment sollte die Anmeldeseite so aussehen:

    Änderungen übernehmen:

    git add -A
    git commit -m "Geräteansichten generieren, Anmeldeformular ändern
    und füge das bootstrap_form gem hinzu. "

    Um das Rastersystem des Bootstraps der Seite zuzuweisen, binden Sie das Anmeldeformular in den Bootstrap-Container ein.

    Die Breite des Anmeldeformulars beträgt 6 von 12 Spalten. Der Versatz beträgt 3 Spalten. Auf kleineren Geräten nimmt das Formular die gesamte Bildschirmbreite ein. So funktioniert das Bootstrap-Gitter.

    Machen wir ein weiteres Commit. Eine kleine Veränderung, was? Aber so mache ich normalerweise Commits. Ich setze eine bestimmte Änderung in einem Bereich um und lege sie dann fest. Ich denke, dass dies dazu beiträgt, Änderungen nachzuverfolgen und zu verstehen, wie sich der Code entwickelt hat.

    git add -A
    git commit -m "Anmeldeformular auf der Anmeldeseite mit einem Boostrap-Container umbrechen"

    Es wäre besser, wenn wir nur die Anmeldeseite erreichen könnten, indem wir zu / logininstead of / users / sign_in gehen. Wir müssen die Route ändern. Dazu müssen wir wissen, wo sich die Aktion befindet, die beim Aufrufen der Anmeldeseite aufgerufen wird. Gerätesteuerungen befinden sich im Edelstein selbst. Durch Lesen der Devise-Dokumentation können wir feststellen, dass sich alle Controller im Devise-Verzeichnis befinden. Nicht wirklich überrascht von der Entdeckung, um ehrlich zu sein U_U. Mit der devise_scope-Methode können wir einfach die Route ändern. Gehen Sie zur Datei routes.rb und fügen Sie hinzu

    devise_scope: user do
      get 'login', to: 'devise / sessions # new'
    Ende

    Übernehmen Sie die Änderung:

    git add -A
    git commit -m "ändere die Route von / users / sign_in nach / login"

    Lassen Sie die Anmeldeseite vorerst unverändert.

    Anmeldeseite

    Wenn wir zu localhost: 3000 / users / sign_up navigieren, wird die Standard-Anmeldeseite von Devise angezeigt. Wie oben erwähnt, ist die Anmeldeseite jedoch mit einigem Aufwand verbunden. Warum? Da wir der Benutzertabelle eine neue Spalte hinzufügen möchten, könnte ein Benutzerobjekt das Attribut: name haben.

    Wir sind dabei, einige Änderungen an der Datei schema.rb vorzunehmen. Wenn Sie derzeit mit Schemaänderungen und -migrationen nicht vertraut sind, empfehlen wir Ihnen, die Active Record Migrations-Dokumente durchzulesen.

    Zunächst müssen wir der Benutzertabelle eine zusätzliche Spalte hinzufügen. Wir könnten eine neue Migrationsdatei erstellen und eine change_table-Methode verwenden, um eine zusätzliche Spalte hinzuzufügen. Wir befinden uns jedoch noch in der Entwicklungsphase. Unsere App ist noch nicht implementiert. Wir können einfach eine neue Spalte direkt in der Migrationsdatei devise_create_users definieren und dann die Datenbank neu erstellen. Navigieren Sie zu db / migrate, öffnen Sie die Datei * CREATION_DATE * _devise_create_users.rb und fügen Sie in die Methode create_table t.string: name, null: false, default: "" ein.

    Führen Sie nun die Befehle zum Löschen und Erstellen der Datenbank sowie zum Ausführen von Migrationen aus.

    Schienen db: fallen lassen
    Schienen db: erstellen
    Schienen db: migrieren

    Wir haben der Benutzertabelle eine neue Spalte hinzugefügt und die Datei schema.rb geändert.

    Um ein zusätzliches Attribut senden zu können, damit der Devise-Controller es akzeptiert, müssen einige Änderungen auf Controller-Ebene vorgenommen werden. Wir können Änderungen an Devise-Controllern auf verschiedene Arten vornehmen. Wir können einen Generator verwenden und Controller generieren. Oder wir können eine neue Datei erstellen, den Controller und die zu ändernden Methoden angeben. Beide Wege sind gut. Wir werden das letztere verwenden.

    Navigieren Sie zu app / controller und erstellen Sie eine neue Datei registrations_controller.rb. Fügen Sie der Datei den folgenden Code hinzu:

    Dieser Code überschreibt die Methoden sign_up_params und account_update_params, um das Attribut: name zu akzeptieren. Wie Sie sehen, befinden sich diese Methoden im Devise RegistrationsController. Deshalb haben wir sie angegeben und ihre Methoden geändert. Jetzt müssen wir in unseren Routen diesen Controller angeben, damit diese Methoden überschrieben werden können. Innerhalb von routes.rb ändern

    devise_for: Benutzer

    zu

    devise_for: users,: controller => {: registrations => "registrations"}

    Übernehmen Sie die Änderungen.

    git add -A
    git commit -m "
    - Fügen Sie der Benutzertabelle die Namensspalte hinzu.
    - Fügen Sie das Namensattribut zu sign_up_params und account_update_params hinzu
      Methoden im RegistrationsController "

    Öffnen Sie die Datei new.html.erb:

    app / views / devise / registrierungen / new.html.erb

    Entfernen Sie wieder alles außer dem Formular. Konvertieren Sie das Formular in ein Bootstrap-Formular. Dieses Mal fügen wir ein zusätzliches Namensfeld hinzu.

    Übernehmen Sie die Änderung.

    git add -A
    git commit -m "
    Löschen Sie bis auf das Formular alles von der Anmeldeseite.
    Form in ein Bootstrap-Formular konvertieren. Ein zusätzliches Namensfeld hinzufügen "

    Umhüllen Sie das Formular mit einem Bootstrap-Container und fügen Sie Text hinzu.

    Übernehmen Sie die Änderung.

    git add -A
    git commit -m "
    Wickeln Sie das Anmeldeformular mit einem Bootstrap-Container ein.
    Informationstext in den Container einfügen "

    Genau wie bei der Anmeldeseite wäre es besser, wenn wir nur eine Anmeldeseite öffnen könnten, indem wir zu / signup anstatt zu users / sign_up gehen. Fügen Sie in der Datei routes.rb den folgenden Code hinzu:

    devise_scope: user do
      get 'signup', to: 'devise / registrations # new'
    Ende

    Übernehmen Sie die Änderung.

    git add -A
    git commit -m "Ändere die Route der Anmeldeseite von / users / sign_up zu / signup"

    Wenden wir einige Stiländerungen an, bevor wir fortfahren. Navigieren Sie zu app / assets / sytlesheets / partials und erstellen Sie eine neue Datei signup.scss. Fügen Sie in die Datei das folgende CSS ein:

    Außerdem haben wir keine Dateien aus dem partials-Verzeichnis in der application.scss-Datei importiert. Lass es uns gleich tun. Navigieren Sie zu application.scss und direkt über den @ import partials / layout / *. Importieren Sie alle Dateien aus dem Partialsdirectory. Application.scss sollte so aussehen

    Übernehmen Sie die Änderungen.

    git add -A
    git commit -m "
    - Erstellen Sie eine signup.scss und fügen Sie der Anmeldeseite CSS hinzu
    - Importieren Sie alle Dateien aus dem Verzeichnis partials in die Datei application.scss. "

    Fügen Sie dem gesamten Erscheinungsbild der Website einige weitere Stiländerungen hinzu. Navigieren Sie zu app / assets / stylesheets / base und erstellen Sie eine neue Datei default.scss. Fügen Sie in die Datei den folgenden CSS-Code ein:

    Hier wenden wir einige allgemeine Stiländerungen für die gesamte Website an. Die Schriftgröße ist auf 62,5% festgelegt, sodass 1 Rem-Einheit 10px darstellen kann. Wenn Sie die Rem-Einheit nicht kennen, können Sie dieses Tutorial lesen. Wir möchten keinen Beschriftungstext auf Bootstrap-Formularen sehen. Deshalb haben wir Folgendes festgelegt:

    .control-label {
      Anzeige: keine;
    }

    Möglicherweise haben Sie bemerkt, dass die Variable $ backgroundColor verwendet wird. Diese Variable ist jedoch noch nicht festgelegt. Öffnen Sie dazu die Datei variables.scss und fügen Sie Folgendes hinzu:

    $ backgroundColor: # f0f0f0;

    Die Datei default.scss wird nicht in die Datei application.scss importiert. Importieren Sie es unter Variablen. Die Datei application.scss sollte folgendermaßen aussehen:

    Übernehmen Sie die Änderungen.

    git add -A
    git commit -m "
    Fügen Sie CSS hinzu und importieren Sie CSS-Dateien in die Hauptdatei
    - Erstellen Sie eine default.scss-Datei und fügen Sie CSS hinzu
    - Definieren Sie die Variable $ backgroundColor
    - Importieren Sie die Datei default.scss in die Datei application.scss. "

    Aktualisierung der Navigationsleiste

    Im Moment haben wir drei verschiedene Seiten: Home, Login und Registrierung. Es ist eine gute Idee, sie alle miteinander zu verbinden, damit die Benutzer mühelos durch die Website navigieren können. In der Navigationsleiste werden Links zu Anmelde- und Anmeldeseiten angezeigt. Navigieren Sie zur Datei _navigation.html.erb und öffnen Sie sie.

    app / views / layouts / _navigation.html.erb

    Wir werden hier zusätzlichen Code hinzufügen. In Zukunft werden wir hier noch mehr Code hinzufügen. Dies führt zu einer Datei mit viel Code, die schwer zu verwalten und zu testen ist. Um den Umgang mit langem Code zu vereinfachen, werden wir damit beginnen, größeren Code in kleinere Teile aufzuteilen. Um dies zu erreichen, verwenden wir Teiltöne. Teilen Sie den aktuellen Code _navigation.html.erb bereits in Teilcodes auf, bevor Sie zusätzlichen Code hinzufügen.

    Lassen Sie mich Ihnen kurz vorstellen, wie unsere Navigationsleiste funktionieren wird. Wir werden zwei Hauptteile haben. Zum einen werden Elemente immer angezeigt, unabhängig von der Bildschirmgröße. Im anderen Teil der Navigationsleiste werden Elemente nur auf größeren Bildschirmen angezeigt und auf den kleineren reduziert.

    So sieht die Struktur innerhalb des .container-Elements aus:

    Im Layoutverzeichnis:

    App / Ansichten / Layouts

    Erstellen Sie ein neues Navigationsverzeichnis. Erstellen Sie in diesem Verzeichnis eine neue partielle Datei _header.html.erb.

    app / views / layouts / navigation / _header.html.erb

    Schneiden Sie aus der Datei _navigation.html.erb den gesamten Abschnitt .navbar-header aus und fügen Sie ihn in die Datei _header.html.erb ein. Erstellen Sie im Navigationsverzeichnis eine weitere Teildatei mit dem Namen _collapsible_elements.html.erb.

    app / views / layouts / navigation / _collapsible_elements.html.erb

    Schneiden Sie aus der Datei _navigation.html.erb den gesamten Abschnitt .navbar-collapse aus und fügen Sie ihn in die Datei _collapsible_elements.html.erb ein. Lassen Sie uns nun diese beiden Partials in der Datei _navigation.html.erb rendern. Die Datei sollte jetzt so aussehen.

    Wenn Sie jetzt zu http: // localhost: 3000 gehen, werden Sie keinen Unterschied bemerken. Wir haben unseren Code nur ein wenig aufgeräumt und für eine weitere Entwicklung vorbereitet.

    Wir sind bereit, einige Links zur Navigationsleiste hinzuzufügen. Navigieren Sie zur Datei _collapsible_elements.html.erb und öffnen Sie sie erneut:

    app / views / layouts / _collapsible_elements.html.erb

    Füllen Sie diese Datei mit Links und ersetzen Sie den Inhalt der Datei durch:

    Lassen Sie mich Ihnen kurz erklären, was hier vor sich geht. Erstens habe ich in der zweiten Zeile die ID des Elements in "navbar-collapsible-content" geändert. Dies ist erforderlich, um diesen Inhalt komprimierbar zu machen. Es ist eine Bootstrap-Funktionalität. Die Standard-ID war bs-example-navbar-collapse-1. Um diese Funktion auszulösen, befindet sich die Schaltfläche mit dem Attribut data-target in der Datei _header.html. Öffnen Sie views / layouts / navigation / _header.html.erb und ändern Sie das Attribut data-target in data-target = "# navbar-collapsible-content". Jetzt wird die Schaltfläche den ausblendbaren Inhalt auslösen.

    Als nächstes sehen Sie in der Datei_collapsible_elements.html.erb einige, wenn elselogic with the user_signed_in? Methode entwickeln. Hier werden verschiedene Links angezeigt, je nachdem, ob ein Benutzer angemeldet ist oder nicht. Das Verlassen der Logik, z. B. wenn andere Anweisungen in Ansichten nicht sinnvoll sind. Ansichten sollten ziemlich "dumm" sein und nur die Informationen ausspucken, ohne überhaupt zu "denken". Wir werden diese Logik später mit Helfern umgestalten.

    Das Letzte, was in der Datei beachtet werden muss, sind die CSS-Klassen pc-menu und mobile menu. Mit diesen Klassen wird gesteuert, wie Links auf verschiedenen Bildschirmgrößen angezeigt werden. Fügen wir für diese Klassen CSS hinzu. Navigieren Sie zu App / Assets / Stylesheets und erstellen Sie ein neues Verzeichnis. Erstellen Sie im Verzeichnis zwei Dateien, desktop.scss und mobile.scss. Der Zweck dieser Dateien besteht darin, unterschiedliche Konfigurationen für unterschiedliche Bildschirmgrößen zu haben. Fügen Sie in der Datei desktop.scss Folgendes hinzu:

    Fügen Sie in der Datei mobile.scss Folgendes hinzu:

    Wenn Sie mit CSS-Medienabfragen nicht vertraut sind, lesen Sie diese. Importieren Sie Dateien aus dem Antwortverzeichnis in der Datei application.scss. Importieren Sie es am Ende der Datei, sodass die Datei application.scss folgendermaßen aussehen sollte:

    Navigieren Sie zur Datei navigation.scss und öffnen Sie sie

    app / assets / stylesheets / partials / layout / navigation.scss

    und nehmen Sie einige stilistische Änderungen an der Navigationsleiste vor, indem Sie Folgendes in die Auswahl des Navigationselements einfügen:

    Fügen Sie außerhalb des nav-Elements den folgenden CSS-Code hinzu:

    In diesem Moment sollte unsere Anwendung so aussehen, wenn ein Benutzer nicht angemeldet ist:

    So, wenn ein Benutzer angemeldet ist:

    Und so, wenn die Bildschirmgröße kleiner ist:

    Übernehmen Sie die Änderungen.

    git add -A
    git commit -m "
    Aktualisieren Sie die Navigationsleiste
    - Fügen Sie in der Navigationsleiste Links zum Anmelden, Registrieren, Abmelden und Bearbeiten von Profilen hinzu
    - Teilen Sie den Code _navigation.scss in Teilbereiche auf
    - Erstellen Sie ein Responsive-Verzeichnis im Stylesheets-Verzeichnis und fügen Sie CSS hinzu.
    - Fügen Sie CSS hinzu, um den Stil der Navigationsleiste zu optimieren "

    Jetzt haben wir eine grundlegende Authentifizierungsfunktion. Es erfüllt unsere Bedürfnisse. Lassen Sie uns also den Authentifizierungszweig mit dem Hauptzweig zusammenführen.

    Git Checkout Master
    Git-Merge-Authentifizierung

    Wir können die Zusammenfassung der Änderungen wieder sehen. Der Authentifizierungszweig wird nicht mehr benötigt. Löschen Sie ihn daher.

    Git Branch -D-Authentifizierung

    Helfer

    Als wir an der Datei _collapsible_elements.html.erb arbeiteten, erwähnte ich, dass Rails-Ansichten nicht der richtige Ort für Logik sind. Wenn Sie in das App-Verzeichnis des Projekts schauen, sehen Sie dort das Verzeichnis "helpers". Wir extrahieren die Logik aus den Rails-Ansichten und fügen sie in das Hilfeverzeichnis ein.

    App / Ansichten / Seiten

    Erstellen wir unsere ersten Helfer. Erstellen Sie zunächst einen neuen Zweig und wechseln Sie zu diesem.

    Git Checkout -B Helfer

    Navigieren Sie zum Hilfeverzeichnis und erstellen Sie eine neue Datei navigation_helper.rbfile

    app / helpers / navigation_helper.rb

    In Hilfedateien werden Helfer als Module definiert. In der navigation_helper.rb definieren Sie das Modul.

    Standardmäßig lädt Rails alle Hilfedateien in alle Ansichten. Persönlich mag ich das nicht, da die Namen von Methoden aus verschiedenen Hilfedateien möglicherweise nicht übereinstimmen. Um dieses Standardverhalten zu überschreiben, öffnen Sie die Datei application.rb

    config / application.rb

    Fügen Sie innerhalb der Application-Klasse diese Konfiguration hinzu

    config.action_controller.include_all_helpers = false

    Jetzt stehen Hilfsprogramme nur für die Ansichten des entsprechenden Controllers zur Verfügung. Wenn wir also den PagesController haben, sind alle Helfer in der pages_helper.rb-Datei für alle Ansichtsdateien im pages-Verzeichnis verfügbar.

    Wir haben den NavigationController nicht, daher sind die im NavigationHelper-Modul definierten Hilfsmethoden nirgendwo verfügbar. Die Navigationsleiste ist auf der gesamten Website verfügbar. Wir können das NavigationHelper-Modul in den ApplicationHelper aufnehmen. Wenn Sie nicht mit dem Laden und Einschließen von Dateien vertraut sind, lesen Sie diesen Artikel, um eine Vorstellung davon zu bekommen, was passieren wird.

    Benötigen Sie in der Datei application_helper.rb die Datei navigation_helper.rb. Jetzt haben wir Zugriff auf den Inhalt der Datei navigation_helper.rb. Fügen Sie also das NavigationHelper-Modul mithilfe einer Include-Methode in das ApplicationHelper-Modul ein. Die application_helper.rb sollte so aussehen:

    Jetzt sind die Hilfsmethoden von NavigationHelper in der gesamten App verfügbar.

    Navigieren Sie zur Datei _collapsible_elements.html.erb und öffnen Sie sie

    app / views / layouts / navigation / _collapsible_elements.html.erb

    Wir werden den Inhalt in den if else-Anweisungen in Teilbereiche aufteilen. Erstellen Sie ein neues Verzeichnis collapsible_elements im Navigationsverzeichnis.

    app / views / layouts / navigation / zusammenklappbare_elemente

    Erstellen Sie im Verzeichnis zwei Dateien: _signed_in_links.html.erb und _non_signed_in_links.html.erb. Schneiden Sie nun den Inhalt aus den if else-Anweisungen der _collapsible_elements.html.erb-Datei aus und fügen Sie ihn in die entsprechenden Partials ein. Die Teiltöne sollten folgendermaßen aussehen:

    Fügen Sie nun in der Datei _collapsible_elements.html.erb anstelle von anderen Anweisungen die Rendermethode mit der Methode collapsible_links_partial_pathhelper als Argument hinzu. Die Datei sollte so aussehen

    collapsible_links_partial_path ist die Methode, die wir im NavigationHelper definieren werden. Öffnen Sie navigation_helper.rb

    app / helpers / navigation_helper.rb

    und definieren Sie die Methode innerhalb des Moduls. Die Datei navigation_helper.rb sollte folgendermaßen aussehen:

    Die definierte Methode ist ziemlich einfach. Wenn ein Benutzer angemeldet ist, geben Sie den Pfad eines entsprechenden Teils zurück. Wenn ein Benutzer nicht angemeldet ist, geben Sie den Pfad eines anderen Teils zurück.

    Wir haben unsere erste Hilfsmethode erstellt und die Logik aus den Ansichten in eine Hilfsmethode extrahiert. Wir werden dies für den Rest des Handbuchs tun, wenn wir in einer Ansichtsdatei auf Logik stoßen. Auf diese Weise machen wir uns selbst einen Gefallen, und das Testen und Verwalten der App wird viel einfacher.

    Die App sollte gleich aussehen und funktionieren.

    Übernehmen Sie die Änderungen.

    git add -A
    git commit -m "Konfiguriere und erstelle Helfer
    - Ändern Sie include_all_helpers config in false
    - Teilen Sie den Inhalt der Datei _collapsible_elements.html.erb in
      Partials und extrahieren Sie die Logik aus der Datei in Partials "

    Führen Sie den Helferzweig mit dem Master zusammen

    Git Checkout Master
    git merge helpershttps: //gist.github.com/domagude/419bba70cb97e27f4ea04fe37820194a#file-rails_helper-rb

    Testen

    Zu diesem Zeitpunkt verfügt die Anwendung über einige Funktionen. Obwohl es noch nicht viele Funktionen gibt, müssen wir bereits einige Zeit damit verbringen, die App manuell zu testen, um sicherzustellen, dass alles funktioniert. Stellen Sie sich vor, die Anwendung hätte 20-mal mehr Funktionen als jetzt. Was für eine Enttäuschung wäre es zu überprüfen, ob alles funktioniert, jedes Mal, wenn wir Codeänderungen vorgenommen haben. Um diese Frustration und die stundenlangen manuellen Tests zu vermeiden, implementieren wir automatisierte Tests.

    Gestatten Sie mir, Ihnen vor dem Eintauchen in das Schreiben von Tests vorzustellen, wie und was ich teste. Lesen Sie auch den Leitfaden zum Testen von Rails-Anwendungen, um sich mit den Standard-Rails-Testtechniken vertraut zu machen.

    Was ich zum Testen benutze

    • Framework: RSpec
      Als ich mit dem Testen meiner Rails-Apps begann, verwendete ich das Standard-Minitestframework. Jetzt benutze ich RSpec. Ich glaube nicht, dass es hier eine gute oder eine schlechte Wahl gibt. Beide Frameworks sind großartig. Ich denke, es hängt von einer persönlichen Präferenz ab, welches Framework verwendet werden soll. Ich habe gehört, dass RSpec in der Rails-Community eine beliebte Wahl ist, daher habe ich beschlossen, es zu versuchen. Jetzt benutze ich es die meiste Zeit.
    • Beispieldaten: factory_girl
      Auch hier habe ich zunächst die Standard-Rails-Way-Fixtures ausprobiert, um Beispieldaten hinzuzufügen. Ich habe festgestellt, dass dies ein anderer Fall ist als beim Testen von Frameworks. Welcher Testrahmen zu wählen ist, ist wahrscheinlich eine persönliche Präferenz. Meiner Meinung nach ist dies bei Beispieldaten nicht der Fall. Anfangs waren die Spiele in Ordnung. Ich habe jedoch festgestellt, dass die Steuerung von Beispieldaten mit Fixtures schwierig wird, nachdem Apps größer geworden sind. Vielleicht habe ich es falsch benutzt. Aber mit Fabriken war sofort alles schön und friedlich. Egal, ob eine App kleiner oder größer ist - der Aufwand zum Festlegen von Beispieldaten ist derselbe.
    • Abnahmetests: Capybara
      Standardmäßig verwendet Capybara den rack_test-Treiber. Dieser Treiber unterstützt leider kein JavaScript. Anstelle des Standard-Capybara-Treibers habe ich Poltergeist verwendet. Es unterstützt JavaScript und war in meinem Fall der am einfachsten einzurichtende Treiber.

    Was ich teste

    Ich teste alle Logik, die von mir geschrieben wurde. Es könnte sein:

    • Helfer
    • Modelle
    • Arbeitsplätze
    • Designmuster
    • Jede andere von mir geschriebene Logik

    Neben der Logik verpacke ich meine App mit Akzeptanztests mit Capybara, um sicherzustellen, dass alle Funktionen der App ordnungsgemäß funktionieren, indem ich die Interaktion eines Benutzers simuliere. Um meine Simulationstests zu unterstützen, stelle ich mithilfe von Anforderungstests sicher, dass alle Anforderungen die richtigen Antworten zurückgeben.

    Das teste ich in meinen persönlichen Apps, weil es meine Anforderungen voll erfüllt. Offensichtlich können Teststandards von Person zu Person und von Unternehmen zu Unternehmen unterschiedlich sein.

    Controller, Ansichten und Edelsteine ​​wurden nicht erwähnt, warum? Wie viele Rails-Entwickler sagen, sollten Controller und Views keine Logik enthalten. Und ich stimme ihnen zu. In diesem Fall gibt es dann nicht viel zu testen. Meiner Meinung nach sind Benutzersimulationstests für Views und Controller ausreichend und effizient. Und Edelsteine ​​werden bereits von ihren Machern getestet. Ich denke also, dass Simulationstests ausreichen, um sicherzustellen, dass Edelsteine ​​auch richtig funktionieren.

    Wie ich teste

    Natürlich versuche ich, wann immer möglich, den TDD-Ansatz zu verwenden. Schreiben Sie zuerst einen Test und implementieren Sie dann den Code. In diesem Fall wird der Entwicklungsfluss flüssiger. Manchmal sind Sie sich jedoch nicht sicher, wie das fertige Feature aussehen wird und welche Art von Ausgabe zu erwarten ist. Möglicherweise experimentieren Sie mit dem Code oder probieren einfach andere Implementierungslösungen aus. In diesen Fällen funktioniert der Ansatz "Erst testen" und "Später implementieren" nicht wirklich.

    Vor (manchmal nach, wie oben besprochen) jeder von mir geschriebenen Logik schreibe ich einen isolierten Test für sie und einen Komponententest. Um sicherzustellen, dass jede Funktion einer App funktioniert, schreibe ich Akzeptanztests (Benutzersimulation) mit Capybara.

    Richten Sie eine Testumgebung ein

    Bevor wir unsere ersten Tests schreiben, müssen wir die Testumgebung konfigurieren.

    Öffne das Gemfile und füge diese Gems der Testgruppe hinzu

    Edelstein 'Rspec-Rails', '~> 3.6'
    Juwel 'factory_girl_rails'
    Juwel 'Rails-Controller-Test'
    Edelstein "kopflos"
    Edelstein "Capybara"
    Juwel 'Poltergeist'
    Edelstein 'database_cleaner'

    Wie oben erläutert, ist rspec gem ein Testframework, factory_girl dient zum Hinzufügen von Beispieldaten, capybara dient zum Simulieren der Interaktion eines Benutzers mit der App, und der Poltergeist-Treiber bietet JavaScript-Unterstützung für Ihre Tests.

    Sie können einen anderen Treiber verwenden, der JavaScript unterstützt, wenn die Einrichtung für Sie einfacher ist. Wenn Sie sich für Poltergeist Gem entscheiden, muss PhantomJS installiert sein. Um PhantomJS zu installieren, lesen Sie die Poltergeist-Dokumentation.

    Für die Unterstützung von Headless-Treibern ist Headless Gem erforderlich. Poltergeist ist ein kopfloser Fahrer. Deshalb brauchen wir dieses Juwel. Rails-Controller-Testing Gem wird benötigt, wenn wir Anfragen und Antworten mit den Anfragespezifikationen testen. Dazu später mehr.

    database_cleaner ist erforderlich, um die Testdatenbank nach Tests zu bereinigen, bei denen JavaScript ausgeführt wurde. Normalerweise bereinigt sich die Testdatenbank nach jedem Test von selbst. Wenn Sie jedoch Features testen, die über JavaScript verfügen, bereinigt sich die Datenbank nicht automatisch. Möglicherweise ändert sich dies in der Zukunft. Gegenwärtig wird die Testdatenbank jedoch nicht automatisch bereinigt, nachdem Tests mit JavaScript ausgeführt wurden. Aus diesem Grund müssen wir unsere Testumgebung manuell konfigurieren, um die Testdatenbank auch nach jedem JavaScript-Test zu bereinigen. Wir werden gleich konfigurieren, wann der Edelstein "database_cleaner" ausgeführt werden soll.

    Wenn nun der Zweck dieser Edelsteine ​​erläutert ist, können Sie sie installieren, indem Sie Folgendes ausführen:

    Bundle installieren

    Führen Sie Folgendes aus, um das Spezifikationsverzeichnis für das RSpec-Framework zu initialisieren:

    Schienen erzeugen rspec: install

    Im Allgemeinen bedeutet spec einen einzelnen Test im RSpec-Framework. Wenn wir unsere Spezifikationen ausführen, bedeutet dies, dass wir unsere Tests ausführen.

    Wenn Sie sich das App-Verzeichnis ansehen, werden Sie ein neues Verzeichnis mit dem Namen spec bemerken. Hier werden wir Tests schreiben. Möglicherweise haben Sie auch ein Verzeichnis namens test bemerkt. Hier werden Tests gespeichert, wenn Sie eine Standardtestkonfiguration verwenden. Wir werden dieses Verzeichnis überhaupt nicht verwenden. Sie können es einfach aus dem Projekt c (x_X) entfernen. B.

    Wie oben erwähnt, müssen wir den database_cleaner für die Tests einrichten, die JavaScript enthalten. Öffnen Sie die Datei rails_helper.rb

    spec / rails_helper.rb

    Ändern Sie diese Zeile

    config.use_transactional_fixtures = true

    zu

    config.use_transactional_fixtures = false

    und füge unten den folgenden Code hinzu:

    Ich habe diesen Codeausschnitt aus diesem Tutorial genommen.

    Als letztes müssen wir einige Konfigurationen hinzufügen. Fügen Sie in den Konfigurationen der Datei "rails_helper.rb" die folgenden Zeilen hinzu

    Lassen Sie uns den Code ein wenig aufschlüsseln.

    Wenn Sie Methoden benötigen, laden wir Dateien aus den neu hinzugefügten Edelsteinen, sodass wir deren Methoden unten verwenden können.

    config.include Devise :: Test :: IntegrationHelpers, geben Sie Folgendes ein:: feature

    Diese Konfiguration ermöglicht es uns, Methoden innerhalb von Capybara-Tests zu entwickeln. Wie bin ich auf diese Linie gekommen? Es wurde in den Devise-Dokumenten bereitgestellt.

    config.include FactoryGirl :: Syntax :: Methods

    Diese Konfiguration ermöglicht die Verwendung der Methoden von factory_girl gem. Auch diese Konfiguration habe ich in der Dokumentation des Edelsteins gefunden.

    Capybara.javascript_driver =: Poltergeist
    Capybara.server =: puma

    Diese beiden Konfigurationen sind erforderlich, um JavaScript mit Capybara testen zu können. Lesen Sie immer zuerst die Dokumentation, wenn Sie etwas implementieren möchten, von dem Sie nicht wissen, wie es geht.

    Der Grund, warum ich Ihnen die meisten Test-Juwelen und -Konfigurationen auf einmal und nicht nach und nach vorstellte, sobald wir auf ein bestimmtes Problem stoßen, ist, Ihnen ein klares Bild davon zu geben, was ich zum Testen verwende. Jetzt können Sie jederzeit zu diesem Abschnitt zurückkehren und die meisten Konfigurationen an einem Ort überprüfen. Anstatt von einem Ort zum anderen zu springen und Edelsteine ​​mit Konfigurationen wie Puzzleteilen zusammenzusetzen.

    Lassen Sie uns die Änderungen vornehmen und uns endlich die Hände mit Tests schmutzig machen.

    git add -A
    git commit -m "
    Richten Sie die Testumgebung ein
    - Testverzeichnis entfernen
    - Hinzufügen und Konfigurieren von rspec-Rails, factory_girl_rails,
      Rails-Controller-Test, Headless, Capybara, Poltergeist,
      database_cleaner gems "

    Hilfsspezifikationen

    Zu jeder Art von Spezifikationen (Tests) finden Sie allgemeine Informationen, indem Sie die rspec-Dokumente und ihre Juwelendokumente lesen. Beide sind ziemlich ähnlich, aber Sie können einige Unterschiede zwischen einander finden.

    Erstellen Sie und wechseln Sie zu einem neuen Zweig:

    git checkout -b specs

    Bisher haben wir nur eine Hilfsmethode erstellt. Lass es uns testen.

    Navigieren Sie zum angegebenen Verzeichnis, und erstellen Sie ein neues Verzeichnis mit dem Namen "helpers".

    spec / helfer

    Erstellen Sie im Verzeichnis eine neue Datei navigation_helper_spec.rb

    spec / helpers / navigation_helper_spec.rb

    Schreiben Sie in die Datei den folgenden Code:

    Mit 'Rails_Helper' erhalten wir Zugriff auf alle Testkonfigurationen und -methoden. : type =>: helper behandelt unsere Tests als Hilfsspezifikationen und stellt uns spezifische Methoden zur Verfügung.

    So sollte die Datei navigation_helper_spec.rb aussehen, wenn die Methode collapsible_links_partial_path getestet wird.

    Lesen Sie die grundlegenden Strukturdokumente, um mehr über den Kontext und den Kontext zu erfahren. Hier testen wir zwei Fälle - wenn ein Benutzer angemeldet ist und wenn ein Benutzer nicht angemeldet ist. In jedem Kontext von angemeldeten und nicht angemeldeten Benutzern haben wir Hooks vor. Innerhalb des entsprechenden Kontexts werden diese Hooks (Methoden) vor jedem unserer Tests ausgeführt. In unserem Fall führen wir vor jedem Test die Stub-Methode aus, damit der user_signed_in? Gibt den Wert zurück, den wir ihm mitteilen.

    Und schließlich überprüfen wir mit der expect-Methode, ob beim Aufruf der collapsible_links_partial_path-Methode ein erwarteter Rückgabewert vorliegt.

    Um alle Tests auszuführen, führen Sie einfach Folgendes aus:

    rspec spec

    Führen Sie Folgendes aus, um speziell die Datei navigation_helper_spec.rb auszuführen:

    rspec spec / helpers / navigation_helper_spec.rb

    Wenn die Tests bestanden wurden, sollte die Ausgabe folgendermaßen aussehen:

    Übernehmen Sie die Änderungen.

    git add -A
    git commit -m "Spezifikationen zur collapsible_links_partial_path-Methode von NavigationHelper hinzufügen"

    Fabriken

    Als Nächstes benötigen wir einige Beispieldaten, um unsere Tests durchzuführen. Mit factory_girl gem können wir sehr einfach Beispieldaten hinzufügen, wann immer wir sie benötigen. Außerdem bietet es eine gute Qualität der Dokumente, so dass das Gesamterlebnis ziemlich angenehm ist. Das einzige Objekt, das wir bisher mit unserer App erstellen können, ist der Benutzer. Erstellen Sie zum Definieren der Benutzerfactory ein Factory-Verzeichnis im Verzeichnis spec.

    spezifikationen / fabriken

    Erstellen Sie im Factory-Verzeichnis eine neue Datei users.rb und fügen Sie den folgenden Code hinzu:

    Jetzt können wir innerhalb unserer Spezifikationen problemlos neue Benutzer in der Testdatenbank erstellen, wann immer wir sie benötigen, und zwar mithilfe der Methoden von factory_girl gem. Eine umfassende Anleitung zum Definieren und Verwenden von Fabriken finden Sie in den Dokumenten von factory_girlgem.

    Unsere definierte Fabrik, Benutzer, ist ziemlich einfach. Wir haben die Werte definiert, die Benutzerobjekte haben werden. Auch wir haben die Sequenzmethode verwendet. Wenn Sie Dokumente lesen, können Sie feststellen, dass mit jedem zusätzlichen Benutzerdatensatz der Wert n um eins erhöht wird. Das heißt Der Name des ersten erstellten Benutzers lautet test0, der des zweiten test1 usw.

    Übernehmen Sie die Änderungen.

    git add -A
    git commit -m "Benutzerfactory hinzufügen"

    Feature-Spezifikationen

    In den Funktionsspezifikationen schreiben wir Code, der die Interaktion eines Benutzers mit einer App simuliert. Die Leistungsmerkmale werden vom Edelstein Capybara unterstützt.

    Die gute Nachricht ist, dass wir alles vorbereitet haben, um unsere ersten Funktionsspezifikationen zu schreiben. Wir werden die Anmelde-, Abmelde- und Anmeldefunktionen testen.

    Erstellen Sie im Verzeichnis spec ein neues Verzeichnis mit dem Namen features.

    spec / features

    Erstellen Sie im Features-Verzeichnis ein anderes Verzeichnis mit dem Namen user.

    spec / features / benutzer

    Erstellen Sie im Benutzerverzeichnis eine neue Datei mit dem Namen login_spec.rb

    spec / features / user / login_spec.rb

    So sieht der Login-Test aus:

    Mit diesem Code simulieren wir einen Besuch auf der Anmeldeseite, beginnend von der Homepage. Dann füllen wir das Formular aus und senden es ab. Abschließend prüfen wir, ob in der Navigationsleiste das Element # user-settings vorhanden ist, das nur für angemeldete Benutzer verfügbar ist.

    Funktion und Szenario sind Teil der Capybara-Syntax. Das Merkmal ist dasselbe wie der Kontext / die Beschreibung und das Szenario ist dasselbe wie es. Weitere Informationen finden Sie in den Capybara-Dokumenten unter Verwenden von Capybara mit Rspec.

    Mit let method können wir gespeicherte Methoden schreiben, die wir für alle Spezifikationen im Kontext verwenden können. Die Methode wurde definiert.

    Hier verwenden wir auch unsere erstellte Benutzerfactory und die Erstellungsmethode, die mit dem Juwel factory_girl geliefert wird.

    Mit js: true können Funktionen getestet werden, die JavaScript beinhalten.

    Um festzustellen, ob ein Test bestanden wurde, führen Sie wie immer eine bestimmte Datei aus. In diesem Fall ist es die Datei login_spec.rb:

    rspec spec / features / user / login_spec.rb

    Übernehmen Sie die Änderungen.

    git add -A
    git commit -m "Anmeldeinformationen hinzufügen"

    Jetzt können wir die Abmeldefunktion testen. Erstellen Sie im Benutzerverzeichnis eine neue Datei mit dem Namen logout_spec.rb

    spec / features / user / logout_spec.rb

    Der implementierte Test sollte folgendermaßen aussehen:

    Der Code simuliert, wie ein Benutzer auf die Abmeldeschaltfläche klickt und erwartet, dass nicht angemeldete Benutzerlinks in der Navigationsleiste angezeigt werden.

    Die Methode sign_in ist eine der Hilfsmethoden von Devise. Wir haben diese Hilfsmethoden zuvor in die Datei rails_helper.rb aufgenommen.

    Führen Sie die Datei aus, um festzustellen, ob der Test bestanden wurde.

    Übernehmen Sie die Änderungen.

    git add -A
    git commit -m "Abmeldefeatures hinzufügen"

    Die letzte Funktion, die wir haben, ist die Möglichkeit, ein neues Konto zu eröffnen. Lass es uns testen. Erstellen Sie im Benutzerverzeichnis eine neue Datei mit dem Namen sign_up_spec.rb. So sollte die Datei mit dem darin enthaltenen Test aussehen:

    Wir simulieren einen Benutzer, der zur Anmeldeseite navigiert, das Formular ausfüllt, das Formular absendet und schließlich das # user-settings-Element erwartet, das nur für angemeldete Benutzer verfügbar ist.

    Hier verwenden wir die Build-Methode von Devise, anstatt zu erstellen. Auf diese Weise erstellen wir ein neues Objekt, ohne es in der Datenbank zu speichern.

    Wir können die gesamte Testsuite ausführen und prüfen, ob alle Tests erfolgreich verlaufen sind.

    rspec spec

    Übernehmen Sie die Änderungen.

    git add -A
    git commit -m "Anmeldefeatures hinzufügen"

    Wir sind mit unseren ersten Tests fertig. Lassen Sie uns also den Specs-Zweig mit dem Master zusammenführen.

    Git Checkout Master
    git merge specs

    Specs Branch wird nicht mehr benötigt. Löschen Sie es q__o.

    Git Branch -D specs

    Hauptfutter

    Auf der Startseite erstellen wir einen Beitragsfeed. In diesem Feed werden alle Arten von Posts im Kartenformat angezeigt.

    Beginnen Sie mit dem Erstellen eines neuen Zweigs:

    git checkout -b main_feed

    Generieren Sie ein neues Modell mit dem Namen Post.

    Schienen g Modellpfosten

    Dann benötigen wir ein Kategoriemodell, um die Beiträge zu kategorisieren:

    Schienen g Modellkategorie

    Erstellen wir nun einige Verknüpfungen zwischen Benutzer-, Kategorie- und Postmodellen.

    Jeder Beitrag wird einer Kategorie und ihrem Autor (Benutzer) zugeordnet. Öffnen Sie die Modelldateien und fügen Sie die Verknüpfungen hinzu.

    Klasse Post 
    Klasse User 
    class Kategorie 

    Das abhängige Argument:: destroy besagt, dass beim Löschen eines Benutzers auch alle vom Benutzer erstellten Posts gelöscht werden.

    Jetzt definieren wir Datenspalten und -zuordnungen in den Migrationsdateien.

    Führen Sie nun die Migrationsdateien aus:

    Schienen db: migrieren

    Übernehmen Sie die Änderungen:

    git add -A
    git commit -m "
    - Generieren Sie Post- und Category-Modelle.
    - Erstellen Sie Verknüpfungen zwischen Benutzer-, Post- und Kategoriemodellen.
    - Erstellen Sie Kategorien und Beiträge Datenbanktabellen. "

    Technische Daten

    Wir können die neu erstellten Modelle testen. Später benötigen wir Beispieldaten für die Tests. Da ein Beitrag zu einer Kategorie gehört, benötigen wir auch Beispieldaten für Kategorien, um die Assoziationen einzurichten.

    Erstellen Sie eine Kategorie-Factory im Factory-Verzeichnis.

    spec / factories / categories.rb

    Erstellen Sie eine Post-Factory im Factory-Verzeichnis

    spec / factories / posts.rb

    Wie Sie sehen, ist es sehr einfach, einen Verband für Fabriken zu gründen. Um Benutzer- und Kategoriezuordnungen für die Postfactory einzurichten, mussten wir lediglich die Namen der Fabriken in die Postfactory schreiben.

    Übernehmen Sie die Änderungen.

    git add -A
    git commit -m "Post- und Kategoriefabriken hinzufügen"

    Im Moment werden wir nur die Assoziationen testen, da dies das einzige ist, was wir bisher in den Modellen geschrieben haben.

    Öffnen Sie die Datei post_spec.rb

    spec / models / post_spec.rb

    Fügen Sie Spezifikationen für die Assoziationen hinzu, sodass die Datei folgendermaßen aussehen sollte:

    Wir verwenden die description_class-Methode, um die Klasse des aktuellen Kontexts abzurufen. Das ist in diesem Fall im Grunde dasselbe wie das Schreiben von Post. Dann verwenden wir die reflect_on_association-Methode, um zu überprüfen, ob eine korrekte Zuordnung zurückgegeben wird.

    Machen Sie dasselbe für andere Modelle.

    Übernehmen Sie die Änderungen.

    git add -A
    git commit -m "Spezifikationen für Benutzer-, Kategorie- und Postmodel-Assoziationen hinzufügen"

    Layout der Startseite

    Derzeit enthält die Homepage nichts, nur den Dummy-Text "Homepage". Es ist Zeit, das Layout mit dem Bootstrap zu erstellen. Öffnen Sie die Ansichtsdatei views / pages / index.html.erb der Homepage und ersetzen Sie den Inhalt der Datei durch den folgenden Code, um das Layout der Seite zu erstellen:

    Fügen Sie nun CSS hinzu, um den Stil und das Reaktionsverhalten der Elemente zu definieren.

    Erstellen Sie im Verzeichnis stylesheets / partials eine neue Datei home_page.scss

    Assets / Stylesheets / Partials / home_page.scss

    Fügen Sie der Datei das folgende CSS hinzu:

    Fügen Sie in der Medienabfrage der Datei "max-width: 767px" Folgendes hinzu:

    Jetzt sollte die Startseite auf größeren Bildschirmen so aussehen

    und so auf den kleineren Bildschirmen

    Übernehmen Sie die Änderungen.

    git add -A
    git commit -m "
    - Fügen Sie das Bootstrap-Layout zur Startseite hinzu
    - Fügen Sie CSS hinzu, um die stilistischen und reaktionsschnellen Designänderungen des Homepage-Layouts vorzunehmen. "

    Saat

    Um Beiträge auf der Homepage anzuzeigen, müssen sie zunächst in der Datenbank vorhanden sein. Das manuelle Erstellen von Daten ist langweilig und zeitaufwändig. Um diesen Prozess zu automatisieren, verwenden wir Seeds. Öffnen Sie die Datei seeds.rb.

    db / seeds.rb

    Fügen Sie den folgenden Code hinzu:

    Wie Sie sehen, erstellen wir die Methoden seed_users, seed_categories und seed_posts, um Benutzer-, Kategorie- und Beitragsdatensätze in der Entwicklungsdatenbank zu erstellen. Auch der Faker Gem wird verwendet, um Dummy-Text zu generieren. Füge faker gem zu deinem Gemfile hinzu

    Edelstein "Fälscher"

    und

    Bundle installieren

    Führen Sie einen Befehl aus, um Daten mithilfe der Datei seeds.rb zu setzen

    Schienen db: seed

    Übernehmen Sie die Änderungen.

    git add -A
    git commit -m "
    - Fake Gem hinzufügen
    - Erstellen Sie in der Datei seeds.rb Methoden zum Generieren
      Benutzer-, Kategorie- und Beitragsdatensätze in der Entwicklungsdatenbank "

    Beiträge rendern

    Zum Rendern der Posts benötigen wir ein Posts-Verzeichnis in den Ansichten.

    Generieren Sie einen neuen Controller mit dem Namen Posts, damit automatisch auch in den Ansichten ein Postverzeichnis erstellt wird.

    Schienen g Controller-Pfosten

    Da in unserer App der PagesController für die Startseite verantwortlich ist, müssen wir Daten in der Indexaktion der Datei pages_controller.rb abfragen. Rufen Sie innerhalb der Indexaktion einige Datensätze aus der Tabelle posts ab. Ordnen Sie die abgerufenen Datensätze einer Instanzvariablen zu, damit die abgerufenen Objekte in den Ansichten der Homepage verfügbar sind.

    • Wenn Sie mit Ruby-Variablen nicht vertraut sind, lesen Sie diese Anleitung.
    • Wenn Sie nicht mit dem Abrufen von Datensätzen aus der Datenbank in Rails vertraut sind, lesen Sie das Handbuch Active Record Query Interface.

    Die Indexaktion sollte jetzt ungefähr so ​​aussehen:

    Navigieren Sie zur Homepage-Vorlage

    views / pages / index.html.erb

    und innerhalb des .main-content-Elements add

    <% = @posts% rendern>

    Dadurch werden alle Posts gerendert, die innerhalb der Indexaktion abgerufen wurden. Da Post-Objekte zur Post-Klasse gehören, versucht Rails automatisch, die Teilvorlage _post.html.erb zu rendern, die sich befindet

    views / posts / _post.html.erb

    Wir haben diese Teildatei noch nicht erstellt. Erstellen Sie sie also und fügen Sie den folgenden Code hinzu:

    Ich habe hier eine Bootstrap-Kartenkomponente verwendet, um den gewünschten Stil zu erzielen. Dann habe ich nur den Inhalt und den Pfad des Posts im Element gespeichert. Außerdem habe ich einen Link hinzugefügt, der zum vollständigen Beitrag führt.

    Bisher haben wir keine Routen für Posts definiert. Wir brauchen sie jetzt, also lasst sie uns deklarieren. Öffnen Sie die Datei routes.rb und fügen Sie den folgenden Code in die Routen ein:

    Hier habe ich eine Ressourcenmethode zum Deklarieren von Routen für das Anzeigen, Bearbeiten, Erstellen, Aktualisieren und Zerstören von Aktionen verwendet. Anschließend habe ich einige benutzerdefinierte Sammlungsrouten für den Zugriff auf Seiten mit mehreren Post-Instanzen angegeben. Diese Seiten werden für separate Zweige reserviert. Sie werden später erstellt.

    Starten Sie den Server neu und rufen Sie http: // localhost: 3000 auf. Sie sollten gerenderte Beiträge auf dem Bildschirm sehen. Die Anwendung sollte ungefähr so ​​aussehen:

    Übernehmen Sie die Änderungen.

    git add -A
    git commit -m "Beiträge auf der Homepage anzeigen
    - Generiere Posts Controller und erstelle eine Indexaktion.
      Rufen Sie innerhalb der Indexaktion Post-Datensätze ab
    - Routen für Posts angeben
    - Erstellen Sie einen Teil der Datei _post.html.erb im Verzeichnis posts
    - Beiträge im Hauptinhalt der Homepage rendern "

    Erstellen Sie eine neue scss-Datei im partials-Verzeichnis, um Beiträge zu formatieren:

    Assets / Stylesheets / Partials / posts.scss

    Fügen Sie in die Datei das folgende CSS ein:

    Die Homepage sollte ungefähr so ​​aussehen:

    Übernehmen Sie die Änderung.

    git add -A
    git commit -m "Erstellt eine posts.scss-Datei und fügt ihr CSS hinzu"

    Stylen mit JavaScript

    Derzeit ist das Design der Website ziemlich langweilig. Um einen Kontrast zu schaffen, werden wir die Pfosten ausmalen. Anstatt sie nur mit CSS einzufärben, sollten Sie sie jedes Mal mit anderen Farbmustern einfärben, wenn ein Benutzer die Website aktualisiert. Dazu verwenden wir JavaScript. Es ist wahrscheinlich eine dumme Idee, aber es macht Spaß, c (o_u)?

    Navigieren Sie zum Javascripts-Verzeichnis in Ihren Assets und erstellen Sie ein neues Verzeichnis mit dem Namen posts. Erstellen Sie im Verzeichnis eine neue Datei mit dem Namen style.js. Wenn Sie möchten, können Sie auch standardmäßig generierte .coffee-Dateien im javascripts-Verzeichnis löschen. In diesem Lernprogramm wird kein CoffeeScript verwendet.

    assets / javascripts / posts / style.js

    Fügen Sie in der Datei style.js den folgenden Code hinzu.

    Mit diesem Code setzen wir zufällig einen von zwei Stilmodi, wenn ein Browser durch Hinzufügen von Attributen zu Beiträgen aktualisiert wird. Ein Stil hat nur farbige Ränder, ein anderer Stil hat einfarbige Pfosten. Bei jedem Seitenwechsel und jeder Aktualisierung des Browsers werden die Posts auch nach dem Zufallsprinzip neu eingefärbt. In der Funktion randomColorSet () sehen Sie vordefinierte Farbschemata.

    Für Posts auf bestimmten Seiten werden zukünftig Ereignishandler für mouseenter und mouseleave benötigt. Der Stil der Posts wird sich von dem der Posts auf der Homepage unterscheiden. Wenn Sie mit der Maus über einen Beitrag fahren, ändert sich die Farbe des unteren Rahmens geringfügig. Sie werden es später sehen.

    Übernehmen Sie die Änderungen.

    git add -A
    git commit -m "Erstelle eine style.js-Datei und füge js hinzu, um den Style der Posts zu erstellen"

    Ergänzen Sie das Design durch CSS. Öffnen Sie die Datei posts.scss

    Assets / Stylesheets / Partials / posts.scss

    und füge folgendes CSS hinzu:

    Fügen Sie auch in der Datei mobile.scss den folgenden Code hinzu, um zu große Textprobleme auf kleineren Bildschirmen zu beheben:

    Die Homepage sollte jetzt ungefähr so ​​aussehen:

    Übernehmen Sie die Änderungen

    git add -A
    git commit -m "Fügt CSS zu Beiträgen auf der Homepage hinzu
    - CSS zur posts.scss-Datei hinzufügen
    - Fügen Sie CSS zur Datei mobile.scss hinzu, um zu große Textprobleme auf kleineren Bildschirmen zu beheben. "

    Modales Fenster

    Ich möchte in der Lage sein, auf einen Beitrag zu klicken und dessen vollständigen Inhalt anzuzeigen, ohne zu einer anderen Seite zu wechseln. Um diese Funktionalität zu erreichen, verwende ich die modale Komponente eines Bootstraps.

    Erstellen Sie im Verzeichnis posts eine neue Teildatei _modal.html.erb

    views / posts / _modal.html.erb

    und fügen Sie den folgenden Code hinzu:

    Dies ist nur eine geringfügig geänderte Bootstrap-Komponente, um diese spezielle Aufgabe zu erfüllen.

    Rendern Sie diesen Teil oben in der Homepage-Vorlage.

    Damit dieses modale Fenster funktioniert, müssen wir JavaScript hinzufügen. Erstellen Sie im Verzeichnis posts eine neue Datei modal.js

    assets / javascripts / posts / modal.js

    Fügen Sie in der Datei den folgenden Code hinzu:

    Mit diesem Code speichern wir einfach die Daten des ausgewählten Posts in Variablen und füllen die Elemente des Modalfensters mit diesen Daten. Schließlich machen wir mit der letzten Codezeile das modale Fenster sichtbar.

    Fügen Sie CSS hinzu, um das Erscheinungsbild des Modalfensters zu verbessern. Führen Sie jedoch vor dem Hinzufügen von CSS eine schnelle Verwaltungsaufgabe im Stylesheets-Verzeichnis aus.

    Erstellen Sie im Verzeichnis partials ein neues Verzeichnis namens posts

    Assets / Stylesheets / Partials / Posts

    Erstellen Sie im Verzeichnis posts eine neue Datei home_page.scss. Schneiden Sie den gesamten Code aus der Datei posts.scss aus und fügen Sie ihn in die Datei home_page.scss ein. Löschen Sie die posts.scss-Datei. Wir tun dies für ein besseres CSS-Code-Management. Es ist klarer, wenn es nur wenige kleinere CSS-Dateien mit einem unterscheidbaren Zweck gibt, als eine große Datei, in der alles zusammengefügt ist.

    Erstellen Sie auch im Verzeichnis posts eine neue Datei modal.scss und fügen Sie das folgende CSS hinzu:

    Wenn wir nun auf den Beitrag klicken, sollte die Anwendung folgendermaßen aussehen:

    Übernehmen Sie die Änderungen.

    git add -A
    git commit -m "Füge ein Popup-Fenster hinzu, um den Inhalt eines vollständigen Beitrags anzuzeigen
    - Fügen Sie die modale Komponente von bootstrap hinzu, um den gesamten Inhalt des Posts anzuzeigen
    - Rendern Sie das Modal in der Homepage-Vorlage
    - Fügen Sie js hinzu, um das Modal mit dem Inhalt des Posts zu füllen und anzuzeigen
    - CSS hinzufügen, um das Modal zu stylen "

    Führen Sie auch den Zweig main_feed mit dem Master zusammen

    Git Checkout Master
    git merge main_feed

    Beseitigen Sie den main_feed-Zweig

    Git-Zweig -D main_feed

    Einzelne Post

    Wechseln Sie zu einem neuen Zweig

    git checkout -b single_post

    Zeige einen einzelnen Beitrag

    Wenn Sie versuchen, auf die Schaltfläche Ich bin interessiert zu klicken, wird eine Fehlermeldung angezeigt. Wir haben weder eine show.html.erb-Vorlage noch eine entsprechende Controller-Aktion erstellt. Durch Klicken auf die Schaltfläche möchte ich auf die Seite eines ausgewählten Posts weitergeleitet werden.

    Erstellen Sie im PostsController eine Show-Aktion und fragen Sie dann ein bestimmtes Post-Objekt in einer Instanzvariablen ab und speichern Sie es:

    Ich bin interessiert, Button leitet zu einem ausgewählten Beitrag weiter. Es hat ein href-Attribut mit einem Pfad zu einem Beitrag. Durch das Senden einer GET-Anforderung zum Abrufen eines Posts ruft Rails die Aktion show auf. Während der Show-Aktion haben wir Zugriff auf den ID-Parameter, da wir durch Senden einer GET-Anfrage zum Abrufen eines bestimmten Posts dessen ID angegeben haben. Das heißt Wenn Sie zu einem / posts / 1-Pfad gehen, senden Sie eine Anfrage, um einen Beitrag mit der ID 1 zu erhalten.

    Erstellen Sie eine show.html.erb-Vorlage im posts-Verzeichnis

    views / posts / show.html.erb

    Fügen Sie in die Datei den folgenden Code ein:

    Erstellen Sie eine show.scss-Datei im posts-Verzeichnis und fügen Sie CSS hinzu, um das Erscheinungsbild der Seite zu gestalten:

    Hier habe ich die Höhe der Seite auf 100 Vh-50 Pixel festgelegt, sodass der Inhalt der Seite die Höhe des gesamten Ansichtsfensters ist. Dadurch kann der Container über die gesamte Höhe des Browsers weiß gefärbt werden, unabhängig davon, ob sich genügend Inhalt im Element befindet oder nicht. Die vh-Eigenschaft bedeutet die Höhe des Ansichtsfensters. Ein Wert von 100 vh bedeutet, dass das Element um 100% der Höhe des Ansichtsfensters gedehnt ist. 100vh-50px ist erforderlich, um die Höhe der Navigationsleiste zu subtrahieren. Andernfalls würde der Container um 50px überdehnt.

    Wenn Sie jetzt auf die Schaltfläche Ich bin interessiert klicken, werden Sie zu einer Seite weitergeleitet, die ungefähr so ​​aussieht:

    Wir werden der Vorlage show.html.erb später zusätzliche Funktionen hinzufügen. Übernehmen Sie nun die Änderungen.

    git add -A
    git commit -m "Erstellt eine Showvorlage für Beiträge
    - Fügen Sie eine Show-Aktion hinzu und fragen Sie einen Beitrag zu einer Instanzvariablen ab
    - Erstelle eine show.scss Datei und füge CSS hinzu "

    Technische Daten

    Anstatt manuell zu überprüfen, ob diese Funktionalität, die modale Darstellung des Fensters und die Umleitung zu einem ausgewählten Beitrag, funktioniert, sollten Sie alles mit Spezifikationen versehen. Wir werden Capybara verwenden, um die Interaktion eines Benutzers mit der App zu simulieren.

    Erstellen Sie im Features-Verzeichnis ein neues Verzeichnis mit dem Namen posts

    spec / features / posts

    Erstellen Sie im neuen Verzeichnis eine neue Datei visit_single_post_spec.rb

    spec / features / posts / visit_single_post_spec.rb

    Und fügen Sie eine Feature-Spezifikation hinzu. Die Datei sieht folgendermaßen aus:

    Hier habe ich alle Schritte definiert, die ich manuell ausführen würde. Ich gehe zunächst zur Startseite, klicke auf den Beitrag, erwarte, dass das angezeigte modale Fenster angezeigt wird, klicke auf die Schaltfläche "Ich bin interessiert" und erwarte, dass ich zur Seite des Beitrags weitergeleitet werde, um deren Inhalt anzuzeigen.

    Standardmäßig geben RSpec-Matcher have_selector, have_css usw. true zurück, wenn ein Element für einen Benutzer tatsächlich sichtbar ist. Nachdem Sie auf einen Beitrag geklickt haben, erwartet Testing Framework ein sichtbares modales Fenster. Wenn es Ihnen egal ist, ob ein Benutzer ein Element sieht oder nicht, und Sie sich nur um die Präsenz eines Elements im DOM kümmern, übergeben Sie ein zusätzliches Argument mit dem Wert "visible: false".

    Versuchen Sie, den Test auszuführen

    rspec spec / features / posts / visit_single_post_spec.rb

    Übernehmen Sie die Änderungen.

    git add -A
    git commit -m "Fügen Sie eine Funktionsspezifikation hinzu, um zu testen, ob ein Benutzer zu a wechseln kann
    einzelner Beitrag von der Homepage "

    Führen Sie den Zweig single_post mit dem Master zusammen.

    Git Checkout Master
    git merge single_post
    Git Branch -D single_post

    Spezifische Branchen

    Jeder Beitrag gehört zu einer bestimmten Branche. Erstellen wir spezifische Seiten für verschiedene Branchen.

    Wechseln Sie zu einem neuen Zweig

    git checkout -b specific_branches

    Seitenmenü der Startseite

    Aktualisieren Sie zunächst das Seitenmenü der Startseite. Fügen Sie Links zu bestimmten Zweigen hinzu. Öffnen Sie die Datei index.html.erb:

    views / pages / index.html.erb

    Wir werden einige Links in das Seitenmenüelement # einfügen. Teilen Sie den Inhalt der Datei in Teilbereiche auf, da er sonst sehr schnell verrauscht.
    Schneiden Sie die Elemente # side-menu und # main-content aus und fügen Sie sie in separate Teildateien ein. Erstellen Sie innerhalb des Seitenverzeichnisses ein Indexverzeichnis und innerhalb des Verzeichnisses entsprechende Teildateien zu den Elementen. Die Dateien sollten folgendermaßen aussehen:

    Rendern Sie diese Teildateien in der Homepage-Vorlage. Die Datei sollte folgendermaßen aussehen:

    Übernehmen Sie die Änderungen.

    git add -A
    git commit -m "Inhalt der Homepage-Vorlage in Teilbereiche aufteilen"

    Fügen Sie innerhalb des Teils _side_menu.html.erb eine Liste von Links hinzu, sodass die Datei folgendermaßen aussehen sollte:

    Eine ungeordnete Liste wurde hinzugefügt. Innerhalb der Liste rendern wir einen anderen Teil mit Links. Diese Links stehen allen Benutzern zur Verfügung, unabhängig davon, ob sie angemeldet sind oder nicht. Erstellen Sie diese Teildatei und fügen Sie die Links hinzu.

    Erstellen Sie im Indexverzeichnis ein side_menu-Verzeichnis:

    views / pages / index / side_menu

    Erstellen Sie im Verzeichnis einen Teil von _no_login_required_links.html.erb mit dem folgenden Code:

    Hier haben wir einfach Links zu bestimmten Zweigen der Beiträge hinzugefügt. Wenn Sie sich fragen, wie wir Pfade haben, wie z. B. hobby_posts_path usw., schauen Sie in die routes.rbfile. Zuvor haben wir verschachtelte Sammlungsrouten in die Ressourcen eingefügt: postsdeclaration.

    Wenn Sie auf die Attribute von i elements achten, werden Sie fa-Klassen bemerken. Mit diesen Klassen deklarieren wir Font Awesome-Symbole. Wir haben diese Bibliothek noch nicht eingerichtet. Glücklicherweise ist es sehr einfach einzurichten. Fügen Sie im head-Element der Hauptdatei application.html.erb die folgende Zeile hinzu

    Das Seitenmenü sollte jetzt vorhanden sein.

    Übernehmen Sie die Änderungen.

    git add -A
    git commit -m "Links zum Seitenmenü der Homepage hinzufügen"

    Auf kleineren Bildschirmen mit einer Breite zwischen 767 und 1000 Pixel wirkt der Bootstrap-Container unangenehm und zu stark komprimiert. Dehnen Sie es also zwischen diesen Breiten. Fügen Sie in der Datei mobile.scss den folgenden Code hinzu:

    Übernehmen Sie die Änderung.

    git add -A
    git commit -m "setze .containerbreite auf 100%
    wenn die Breite des Ansichtsfensters zwischen 767px und 1000px liegt "

    Verzweigungsseite

    Wenn Sie versuchen, auf einen dieser Seitenmenü-Links zu klicken, wird eine Fehlermeldung angezeigt. Wir haben im PostsController keine Aktionen eingerichtet und keine Vorlagen dafür erstellt.

    Definieren Sie im PostsController Hobby-, Lern- und Teamaktionen.

    In jeder Aktion wird die Methode posts_for_branch aufgerufen. Diese Methode gibt abhängig vom Namen der Aktion Daten für die jeweilige Seite zurück. Definieren Sie die Methode im privaten Bereich.

    In der Instanzvariablen @categories rufen wir alle Kategorien für einen bestimmten Zweig ab. Das heißt Wenn Sie zur Seite der Hobbybranche gehen, werden alle Kategorien, die zur Hobbybranche gehören, abgerufen.

    Um Beiträge in der Instanzvariablen @posts abzurufen und zu speichern, wird die Methode get_posts verwendet und anschließend mit einer Paginate-Methode verkettet. Die Methode paginate stammt von will_paginate gem. Beginnen wir mit der Definition der Methode get_posts. Fügen Sie im privaten Bereich von PostsController Folgendes hinzu:

    Im Moment ruft die Methode get_posts nur 30 Posts ab, die für nichts spezifisch sind, sodass wir uns auf die weitere Entwicklung konzentrieren können. Wir werden in naher Zukunft auf diese Methode zurückkommen.

    Fügen Sie den Edelstein will_paginate hinzu, um die Paginierung verwenden zu können.

    Edelstein 'will_paginate', '~> 3.1.0'

    Lauf

    Bundle installieren

    Alles was wir jetzt vermissen, sind Vorlagen. Sie werden allen Zweigen ähnlich sein. Anstatt den Code in jedem dieser Zweige zu wiederholen, erstellen Sie einen Teil mit einer allgemeinen Struktur für einen Zweig. Erstellen Sie im Verzeichnis posts eine Datei _branch.html.erb.

    Zuerst sehen Sie eine page_title-Variable, die auf der Seite gedruckt wird. Wir übergeben diese Variable als Argument, wenn wir die Datei _branch.html.erb partiell machen. Als nächstes wird ein Teil von _create_new_post gerendert, um einen Link anzuzeigen, der zu einer Seite führt, auf der ein Benutzer einen neuen Beitrag erstellen kann. Erstellen Sie diese Teildatei in einem neuen Zweigverzeichnis:

    Hier verwenden wir eine create_new_post_partial_path-Hilfsmethode, um zu bestimmen, welche Teildatei gerendert werden soll. Implementieren Sie in der Datei posts_helper.rb die Methode:

    Erstellen Sie auch diese beiden entsprechenden Partials in einem neuen Verzeichnis create_new_post:

    Als Nächstes rendern wir in der Datei _branch.html.erb eine Liste von Kategorien. Erstellen Sie eine _categories.html.erb-Teildatei:

    In der Datei befindet sich die Hilfsmethode all_categories_button_partial_path, mit der bestimmt wird, welche Teildatei gerendert werden soll. Definieren Sie diese Methode in der Datei posts_helper.rb:

    Alle Kategorien werden standardmäßig ausgewählt. Wenn die Parameter [: Kategorie] leer sind, bedeutet dies, dass von einem Benutzer keine Kategorien ausgewählt wurden. Dies bedeutet, dass derzeit der Standardwert all ausgewählt ist. Erstellen Sie die entsprechenden Teildateien:

    Die send-Methode wird hier verwendet, um eine Methode mithilfe eines Strings aufzurufen. Dies ermöglicht es, flexibel zu sein und Methoden dynamisch aufzurufen. In unserem Fall generieren wir unterschiedliche Pfade, abhängig von der Aktion des aktuellen Controllers.

    Als Nächstes rendern wir in der Datei _branch.html.erb Posts und rufen die Hilfsmethode no_posts_partial_path auf. Wenn keine Beiträge gefunden werden, zeigt die Methode eine Nachricht an.

    Fügen Sie in posts_helper.rb die Hilfsmethode hinzu:

    Hier verwende ich einen ternären Operator, damit der Code etwas übersichtlicher aussieht. Wenn Beiträge vorhanden sind, möchte ich keine Nachrichten anzeigen. Da Sie der Rendermethode keine leere Zeichenfolge übergeben können, übergebe ich stattdessen einen Pfad zu einem leeren Teil, wenn ich nichts rendern möchte.

    Erstellen Sie ein freigegebenes Verzeichnis in den Ansichten und erstellen Sie dann einen leeren Teil:

    views / shared / _empty_partial.html.erb

    Erstellen Sie nun einen _no_posts.html.erb-Teil für die Nachricht im Zweigverzeichnis.

    Schließlich verwenden wir die will_paginate-Methode des Gems, um Beiträge auf mehrere Seiten aufzuteilen, wenn es viele Beiträge gibt.

    Erstellen Sie Vorlagen für Hobby-, Lern- und Teamaktionen. In ihnen rendern wir die Teildatei _branch.html.erb und übergeben bestimmte lokale Variablen.

    Wenn Sie zu einer dieser Verzweigungsseiten gehen, sehen Sie so etwas

    Auch wenn Sie nach unten scrollen, werden Sie sehen, dass wir jetzt eine Paginierung haben

    Wir haben eine Menge Arbeit geleistet, um diese Zweigstellenseiten zu erstellen. Übernehmen Sie die Änderungen

    git add -A
    git commit -m "Erstelle Brancheseiten für bestimmte Posts
    - Definieren Sie im PostsController Hobby-, Lern- und Teamaktionen.
      Definieren Sie eine posts_for_branch-Methode und rufen Sie sie in diesen Aktionen auf
    - Füge will_paginate gem hinzu
    - Erstellen Sie eine _branch.html.erb-Teildatei
    - Erstellen Sie eine _create_new_post.html.erb-Teildatei
    - Definieren Sie eine create_new_post_partial_path-Hilfsmethode
    - Erstellen Sie eine _signed_in.html.erb-Teildatei
    - Erstellen Sie eine _not_signed_in.html.erb-Teildatei
    - Erstellen Sie eine Teildatei _categories.html.erb
    - Definieren Sie eine Hilfsmethode all_categories_button_partial_path
    - Erstellen Sie eine _all_selected.html.erb-Teildatei
    - Erstellen Sie eine _all_not_selected.html.erb-Teildatei
    - Definieren Sie eine Hilfsmethode no_posts_partial_path
    - Erstellen Sie eine _no_posts.html.erb-Teildatei
    - Erstellen Sie eine Vorlagendatei hobby.html.erb
    - Erstellen Sie eine Vorlagendatei study.html.erb
    - Erstellen Sie eine Vorlagendatei team.html.erb "

    Technische Daten

    Decken Sie Hilfsmethoden mit Spezifikationen ab. Die posts_helper_spec.rb-Datei sollte folgendermaßen aussehen:

    Auch hier sind die technischen Daten recht einfach. Ich habe die Stub-Methode verwendet, um die Rückgabewerte der Methoden zu definieren. Um Parameter zu definieren, habe ich den Controller ausgewählt und einfach so definiert: controller.params [: param_name]. Und schließlich habe ich Instanzvariablen mithilfe einer Assign-Methode zugewiesen.

    Übernehmen Sie die Änderungen

    git add -A
    git commit -m "Spezifikationen für PostsHelper-Methoden hinzufügen"

    Design-Änderungen

    Auf diesen Zweigstellenseiten möchten wir unterschiedliche Beiträge gestalten. Auf der Homepage haben wir das Kartendesign. Erstellen Sie auf Zweigstellenseiten ein Listendesign, damit ein Benutzer mehr Posts sehen und diese effizienter durchsuchen kann.

    Erstellen Sie im Post-Verzeichnis ein Post-Verzeichnis mit einem _home_page.html.erbpartial darin.

    posts / post / _home_page.html.erb

    Schneiden Sie den Inhalt des Teils _post.html.erb aus und fügen Sie ihn in die Teildatei _home_page.html.erb ein. Fügen Sie in der Teildatei _post.html.erb die folgende Codezeile hinzu:

    Hier rufen wir die Hilfsmethode post_format_partial_path auf, um abhängig vom aktuellen Pfad zu entscheiden, welches Post-Design gerendert werden soll. Wenn sich ein Benutzer auf der Homepage befindet, rendern Sie das Beitragsdesign für die Homepage. Wenn sich ein Benutzer auf der Verzweigungsseite befindet, rendern Sie das Post-Design für die Verzweigungsseite. Aus diesem Grund schneiden wir den Inhalt der Datei _post.html.erb in die Datei _home_page.html.erb.

    Erstellen Sie im Post-Verzeichnis eine neue _branch_page.html.erb-Datei und fügen Sie diesen Code ein, um das Post-Design für die Zweigstellenseite zu definieren.

    Um zu entscheiden, welche Teildatei gerendert werden soll, definieren Sie die Methode post_format_partial_pathhelper in posts_helper.rb

    Die post_format_partial_path-Hilfsmethode ist auf der Homepage nicht verfügbar, da wir Posts in der Homepage-Vorlage rendern, die zu einem anderen Controller gehört. Um auf diese Methode zugreifen zu können, müssen Sie in der Vorlage der Homepage PostsHelper in ApplicationHelper einfügen

    PostsHelper einbinden

    Technische Daten

    Fügen Sie Spezifikationen für die Hilfsmethode post_format_partial_path hinzu:

    Übernehmen Sie die Änderungen

    git add -A
    git commit -m "Spezifikationen für die Hilfsmethode post_format_partial_path hinzufügen"

    CSS

    Beschreibe den Beitragsstil in Brancheseiten mit CSS. Erstellen Sie im Verzeichnis posts eine neue Stylesheet-Datei branch_page.scss:

    Fügen Sie in der Datei base / default.scss Folgendes hinzu:

    Um Stilprobleme auf kleineren Geräten zu beheben, fügen Sie in responsive / mobile.scss Folgendes hinzu:

    Nun sollten die Brancheseiten so aussehen:

    Übernehmen Sie die Änderungen.

    git add -A
    git commit -m "Beschreibe den Beitragsstil in Zweigstellen
    - Erstellen Sie eine branch_page.scss-Datei und fügen Sie CSS hinzu
    - Fügen Sie der Datei default.scss CSS hinzu
    - Fügen Sie der Datei mobile.scss CSS hinzu. "

    Suchleiste

    Wir möchten nicht nur in der Lage sein, Beiträge zu durchsuchen, sondern auch nach bestimmten zu suchen. Fügen Sie in der Teildatei _branch.html.erb über der Kategoriezeile Folgendes hinzu:

    Erstellen Sie eine _search_form.html.erb-Teildatei im Verzweigungsverzeichnis und fügen Sie den folgenden Code hinzu:

    Hier generieren wir mit der send-Methode dynamisch einen Pfad zu einer bestimmten PostsController-Aktion, abhängig von einem aktuellen Zweig. Außerdem senden wir ein zusätzliches Datenfeld für die Kategorie, wenn eine bestimmte Kategorie ausgewählt ist. Wenn ein Benutzer eine bestimmte Kategorie ausgewählt hat, werden nur Suchergebnisse dieser Kategorie zurückgegeben.

    Definieren Sie die Hilfsmethode category_field_partial_path in posts_helper.rb

    Erstellen Sie eine Teildatei _category_field.html.erb und fügen Sie den Code hinzu:

    Fügen Sie der Datei branch_page.scss CSS hinzu, um dem Suchformular einen bestimmten Stil zu verleihen:

    Das Suchformular auf Verzweigungsseiten sollte jetzt so aussehen

    Übernehmen Sie die Änderungen

    git add -A
    git commit -m "Fügt ein Suchformular in Zweigstellenseiten hinzu
    - Rendern Sie ein Suchformular in der Datei _branch.html.erb
    - Erstellen Sie eine _search_form.html.erb-Teildatei
    - Definieren Sie eine Hilfsmethode category_field_partial_path in PostsHelper
    - Erstellen Sie eine Teildatei _category_field.html.erb
    - CSS für das Suchformular in branch_page.scss hinzufügen "

    Derzeit ist unser Formular nicht wirklich funktionsfähig. Wir könnten einige Juwelen verwenden, um die Suchfunktion zu erreichen, aber unsere Daten sind nicht kompliziert, sodass wir unsere eigene einfache Suchmaschine erstellen können. Wir verwenden Gültigkeitsbereiche im Post-Modell, um die Verkettung von Abfragen und eine bedingte Logik im Controller zu ermöglichen.

    Definieren Sie zunächst Bereiche im Post-Modell. Definieren Sie zum Aufwärmen den default_scope in der post.rb-Datei. Diese ordnet die Beiträge in absteigender Reihenfolge nach dem Erstellungsdatum an. Die neuesten Beiträge befinden sich oben.

    Übernehmen Sie die Änderung

    git add -A
    git commit -m "Definiere einen default_scope für Beiträge"

    Stellen Sie sicher, dass das default_scope korrekt funktioniert, indem Sie es mit einer Spezifikation umschließen. Fügen Sie in der Datei post_spec.rb Folgendes hinzu:

    Übernehmen Sie die Änderung:

    git add -A
    git commit -m "Eine Spezifikation für den default_scope des Post-Modells hinzufügen"

    Lassen Sie uns nun die Suchleiste funktionsfähig machen. In posts_controller.rbreplace finden Sie den Inhalt der get_posts-Methode mit:

    Wie ich bereits erwähnt habe, ist Logik, genau wie in Ansichten, in Controllern kein wirklich guter Ort. Wir wollen sie sauber machen. Daher werden wir die Logik aus dieser Methode im nächsten Abschnitt extrahieren.

    Wie Sie sehen, gibt es eine bedingte Logik. Abhängig von einer Benutzeranforderung werden Daten mithilfe von Gültigkeitsbereichen unterschiedlich abgefragt.

    Definieren Sie im Post-Modell die folgenden Bereiche:

    Die joins-Methode wird verwendet, um Datensätze aus den zugeordneten Tabellen abzufragen. Die grundlegende SQL-Syntax wird auch zum Suchen von Datensätzen verwendet, die auf bereitgestellten Zeichenfolgen basieren.

    Wenn Sie nun den Server neu starten und zu einer dieser Verzweigungsseiten zurückkehren, sollte die Suchleiste funktionieren! Auch jetzt können Sie Beiträge filtern, indem Sie auf Kategorie-Schaltflächen klicken. Und auch wenn Sie eine bestimmte Kategorie auswählen, werden nur Beiträge aus dieser Kategorie abgefragt, wenn Sie das Suchformular verwenden.

    Übernehmen Sie die Änderungen

    git add -A
    git commit -m "Suchleisten- und Kategoriefilter erstellen
    in Zweigstellen funktionsfähig
    - Fügen Sie nach Kategorie, nach Branche und nach Suchbereichen im Post-Modell hinzu
    - Ändern Sie die Methode get_posts in PostsController. "

    Decken Sie diese Bereiche mit Spezifikationen ab. Fügen Sie im Kontext der Datei "post_spec.rb" Folgendes hinzu:

    Übernehmen Sie die Änderungen

    git add -A
    git commit -m "Spezifikationen für Post-Modelle hinzufügen
    by_branch, by_category und search scopes "

    Unendliche Schriftrolle

    Wenn Sie eine dieser Verzweigungsseiten aufrufen, sehen Sie unten auf der Seite die Paginierung

    Wenn Sie auf den nächsten Link klicken, werden Sie zu einer anderen Seite mit älteren Beiträgen weitergeleitet. Anstatt auf eine andere Seite mit älteren Posts umzuleiten, können wir eine unendliche Bildlauffunktion erstellen, die dem Feed von Facebook und Twitter ähnelt. Sie scrollen einfach nach unten und ohne Umleitung und Neuladen der Seite werden ältere Beiträge an das Ende der Liste angehängt. Überraschenderweise ist es sehr einfach zu erreichen. Alles was wir tun müssen, ist etwas JavaScript zu schreiben. Immer wenn ein Benutzer das Ende der Seite erreicht, wird eine AJAX-Anfrage gesendet, um Daten von der nächsten Seite abzurufen, und diese Daten werden an das Ende der Liste angehängt.

    Konfigurieren Sie zunächst die AJAX-Anforderung und ihre Bedingungen. Wenn ein Benutzer durch Scrollen nach unten einen bestimmten Schwellenwert überschreitet, wird eine AJAX-Anforderung ausgelöst. Erstellen Sie im Verzeichnis javascripts / posts eine neue Datei infinite_scroll.js und fügen Sie den Code hinzu:

    Die Variable isLoading stellt sicher, dass jeweils nur eine Anforderung gesendet wird. Wenn gerade eine Anfrage bearbeitet wird, werden andere Anfragen nicht initiiert.

    Überprüfen Sie zunächst, ob eine Paginierung vorhanden ist und ob weitere Beiträge zu rendern sind. Als nächstes erhalten Sie einen Link zur nächsten Seite, von der aus die Daten abgerufen werden. Legen Sie dann einen Schwellenwert für den Aufruf einer AJAX-Anforderung fest. In diesem Fall beträgt der Schwellenwert 60 Pixel ab dem unteren Rand des Fensters. Wenn alle Bedingungen erfolgreich erfüllt sind, laden Sie die Daten mit der Funktion getScript () von der nächsten Seite.

    Da die Funktion getScript () die JavaScript-Datei lädt, müssen wir angeben, welche Datei im PostsController gerendert werden soll. Geben Sie in der Methode posts_for_branch an, auf welche Formate geantwortet werden soll und welche Dateien gerendert werden sollen.

    Wenn der Controller versucht, mit der .js-Datei zu antworten, wird theposts_pagination_pagetemplate gerendert. Diese Teildatei hängt neu abgerufene Beiträge an die Liste an. Erstellen Sie diese Datei, um neue Beiträge anzufügen und das Paginierungselement zu aktualisieren.

    Erstellen Sie eine update_pagination_partial_path-Hilfsmethode in posts_helper.rb

    Hier wird die next_page-Methode aus dem Gem will_paginate verwendet, um zu bestimmen, ob in Zukunft weitere Posts geladen werden müssen oder nicht.

    Erstellen Sie die entsprechenden Teildateien:

    Wenn Sie eine der Verzweigungsseiten aufrufen und nach unten scrollen, sollten ältere Beiträge automatisch an die Liste angehängt werden.

    Außerdem müssen wir das Paginierungsmenü nicht mehr sehen, also verstecken Sie es mit CSS. Fügen Sie in der Datei branch_page.scss Folgendes hinzu:

    Übernehmen Sie die Änderungen

    git add -A
    git commit -m "Verwandle die Paginierung von Posts in eine unendliche Schriftrolle
    - Erstellen Sie eine infinite_scroll.js-Datei
    - Fügen Sie in der posts_for_branch-Methode von PostController das reply_to-Format hinzu
    - Definieren Sie einen update_pagination_partial_path
    - Erstellen Sie Partials _update_pagination.js.erb und _remove_pagination.js.erb
    - verstecke das .infinite-scroll Element mit CSS "

    Technische Daten

    Decken Sie die Hilfsmethode update_pagination_partial_path mit folgenden Angaben ab:

    Hier habe ich ein Test-Double verwendet, um die Instanzvariable posts und die verkettete Methode next_page zu simulieren. Hier erfahren Sie mehr über die RSpec Mocks.

    Übernehmen Sie die Änderungen:

    git add -A
    git commit -m "Füge Spezifikationen für den update_pagination_partial_path hinzu
    Hilfsmethode "

    Wir können auch Feature-Spezifikationen schreiben, um sicherzustellen, dass Beiträge erfolgreich angehängt werden, nachdem Sie nach unten gescrollt haben. Erstellen Sie eine infinite_scroll_spec.rb-Datei:

    In der Spezifikationsdatei werden alle Verzweigungsseiten abgedeckt. Wir stellen sicher, dass diese Funktionalität auf allen drei Seiten funktioniert. Die per_page ist die Methode von will_paginate gem. Hier wird das Beitragsmodell ausgewählt und die Standardanzahl der Beiträge pro Seite festgelegt.

    Die check_posts_count-Methode wird definiert, um die Codemenge der Datei zu reduzieren. Anstatt den gleichen Code in verschiedenen Spezifikationen immer wieder zu wiederholen, haben wir ihn in eine einzige Methode extrahiert. Sobald die Seite besucht wird, werden voraussichtlich 15 Beiträge angezeigt. Anschließend wird mit der execute_script-Methode JavaScript ausgeführt, wodurch die Bildlaufleiste bis zum unteren Rand des Browsers verschoben wird. Nach der Schriftrolle werden voraussichtlich weitere 15 Posts veröffentlicht. Insgesamt sollten jetzt 30 Beiträge auf der Seite sein.

    Übernehmen Sie die Änderungen:

    git add -A
    git commit -m "Feature-Spezifikationen für die Infinite-Scroll-Funktionalität von Posts hinzufügen"

    Aktualisierung der Homepage

    Derzeit sind auf der Homepage nur wenige zufällige Beiträge zu sehen. Ändern Sie die Startseite, damit wir einige Beiträge aus allen Branchen sehen können.

    Ersetzen Sie den Inhalt der Datei _main_content.html.erb durch:

    Wir haben Abschnitte mit Beiträgen für jede Branche erstellt.

    Definieren Sie Instanzvariablen in der Indexaktion von PagesController. Die Aktion sollte folgendermaßen aussehen:

    Wir haben die Hilfsmethode no_posts_partial_path von vorhin, aber wir sollten sie ein wenig modifizieren und sie wiederverwendbarer machen. Derzeit funktioniert es nur für Brancheseiten. Fügen Sie der Methode einen posts-Parameter hinzu, der jetzt so aussehen sollte:

    Hier wurde der Parameter posts hinzugefügt, die Instanzvariable wurde in eine einfache Variable geändert und der Pfad des Teils wurde ebenfalls geändert. Verschieben Sie also die Datei _no_posts.html.erbpartial von

    posts / branch / _no_posts.html.erb

    zu

    posts / shared / _no_posts.html.erb

    Übergeben Sie auch in der Datei _branch.html.erb die Instanzvariable @posts als Argument an die Methode no_posts_partial_path.

    Fügen Sie einige Stiländerungen hinzu. Fügen Sie in der Datei default.scss Folgendes hinzu:

    Und in der home_page.scss füge hinzu:

    Die Homepage sollte jetzt ähnlich aussehen

    Übernehmen Sie die Änderungen

    git add -A
    git commit -m "Beiträge aus allen Zweigen der Homepage hinzufügen
    - Ändern Sie die Datei _main_content.html.erb
    - Definieren Sie Instanzvariablen in der Indexaktion von PagesController
    - Ändern Sie die Hilfsmethode no_posts_partial_path so, dass sie wiederverwendbarer ist
    - Fügen Sie CSS hinzu, um die Homepage zu gestalten "

    Service-Objekte

    Wie ich bereits erwähnt habe, werden logische Verknüpfungen innerhalb von Controllern sehr leicht kompliziert und erfordern große Tests. Aus diesem Grund ist es eine gute Idee, irgendwo anders Logik daraus zu extrahieren. Zu diesem Zweck verwende ich Entwurfsmuster, Dienstobjekte (Dienste), um genauer zu sein.

    Im PostsController haben wir diese Methode:

    Es hat eine Menge Bedingungslogik, die ich mithilfe von Diensten entfernen möchte. Das Entwurfsmuster für Dienstobjekte (Dienste) ist nur eine grundlegende Rubinklasse. Es ist sehr einfach, wir übergeben einfach Daten, die wir verarbeiten möchten, und rufen eine definierte Methode auf, um einen gewünschten Rückgabewert zu erhalten.

    In Ruby übergeben wir Daten an die Initialisierungsmethode von Class. In anderen Sprachen wird sie als Konstruktor bezeichnet. Und dann erstellen wir innerhalb der Klasse nur eine Methode, die alle definierten Logiken handhabt. Lassen Sie uns das erstellen und sehen, wie es im Code aussieht.

    Erstellen Sie im App-Verzeichnis ein neues Services-Verzeichnis:

    App / Dienste

    Erstellen Sie im Verzeichnis eine neue Datei posts_for_branch_service.rb:

    Hier handelt es sich, wie oben beschrieben, nur um eine einfache Ruby-Klasse mit einer Initialisierungsmethode zum Akzeptieren von Parametern und einer Aufrufmethode zum Behandeln der Logik. Wir haben diese Logik aus der Methode get_posts übernommen.

    Erstellen Sie jetzt einfach ein neues Objekt dieser Klasse und rufen Sie die call-Methode in der get_posts-Methode auf. Die Methode sollte jetzt so aussehen:

    Übernehmen Sie die Änderungen:

    git add -A
    git commit -m "Erstellt ein Dienstobjekt zum Extrahieren der Logik
    von der get_posts Methode "

    Technische Daten

    Ein Glück bei Entwurfsmustern wie Diensten ist, dass es einfach ist, Komponententests dafür zu schreiben. Wir können einfach Spezifikationen für die Aufrufmethode schreiben und jede ihrer Bedingungen testen.

    Erstellen Sie im Verzeichnis spec ein neues Verzeichnis services:

    spec / services

    Erstellen Sie im Verzeichnis eine neue Datei posts_for_branch_service_spec.rb

    Oben in der Datei wird die Datei posts_for_branch_service.rb geladen und anschließend werden alle Bedingungen der Aufrufmethode getestet.

    Übernehmen Sie die Änderungen

    git add -A
    git commit -m "Spezifikationen für den PostsForBranchService hinzufügen"

    Erstellen Sie einen neuen Beitrag

    Bisher wurden Posts mit Hilfe von Samen künstlich erstellt. Fügen wir eine Benutzeroberfläche hinzu, damit ein Benutzer Beiträge erstellen kann.

    Fügen Sie in der Datei posts_controller.rb neue hinzu und erstellen Sie Aktionen.

    In der neuen Aktion definieren wir einige Instanzvariablen für das Formular, um neue Posts zu erstellen. In der Instanzvariablen @categories werden Kategorien für einen bestimmten Zweig gespeichert. Die Instanzvariable @post speichert ein Objekt eines neuen Posts. Dies wird für das Rails-Formular benötigt.

    In der @post-Instanzvariablen der Aktion "create" erstellen wir ein neues Postobjekt und füllen es mit Daten mithilfe der post_params-Methode. Definieren Sie diese Methode im privaten Bereich:

    Die Erlaubnismethode wird verwendet, um Attribute des Objekts auf die Positivliste zu setzen, sodass nur diese angegebenen Attribute übergeben werden dürfen.

    Fügen Sie außerdem oben im PostsController die folgende Zeile hinzu:

    Die before_action ist einer der Rails-Filter. Nicht angemeldete Benutzer sollen keinen Zugriff auf eine Seite erhalten, auf der sie neue Beiträge erstellen können. Vor dem Aufruf der neuen Aktion wird also die Methode redirect_if_not_signed_in aufgerufen. Wir benötigen diese Methode auch für andere Controller. Definieren Sie sie daher in der Datei application_controller.rb. Eine Methode zum Umleiten angemeldeter Benutzer wäre auch in Zukunft nützlich. Definieren Sie also beide.

    Jetzt ist die neue Vorlage erforderlich, damit ein Benutzer neue Beiträge erstellen kann. Erstellen Sie im Verzeichnis posts eine new.html.erb-Datei:

    Erstellen Sie ein neues Verzeichnis und eine _post_form.html.erb-Teildatei in:

    Die Form ist ziemlich einfach. Die Attribute der Felder werden definiert und die Methode collection_select wird verwendet, um eine der verfügbaren Kategorien auszuwählen.

    Übernehmen Sie die Änderungen

    git add -A
    git commit -m "Erstelle eine Benutzeroberfläche, um neue Beiträge zu erstellen
    - Im PostsController:
      Neue definieren und Aktionen erstellen
      Definieren Sie eine post_params-Methode
      Definieren Sie einen before_action-Filter
    - Im ApplicationController:
      Definieren Sie eine redirect_if_not_signed_in-Methode
      Definieren Sie eine redirect_if_signed_in-Methode
    - Neue Vorlage für Beiträge erstellen "

    Wir können testen, ob das Formular funktioniert, indem wir Spezifikationen schreiben. Beginnen Sie mit dem Schreiben von Anforderungsspezifikationen, um sicherzustellen, dass wir nach dem Senden bestimmter Anforderungen die richtigen Antworten erhalten. Erstellen Sie im Verzeichnis spec ein paar Verzeichnisse.

    spec / Anfragen / Beiträge

    Und eine new_spec.rb-Datei in:

    Wie in der Dokumentation erwähnt, bieten Anforderungsspezifikationen eine dünne Hülle um die Integrationstests. Wir testen also, ob wir beim Senden bestimmter Anfragen die richtigen Antworten erhalten. Die Zeile include Warden :: Test :: Helpers ist erforderlich, um die Methode login_as zu verwenden. Die Methode meldet einen Benutzer an.

    Übernehmen Sie die Änderung.

    git add -A
    git commit -m "Anforderungsspezifikationen für eine neue Beitragsvorlage hinzufügen"

    Wir können sogar weitere Anforderungsspezifikationen für die zuvor erstellten Seiten hinzufügen.

    Erstellen Sie im selben Verzeichnis eine branches_spec.rb-Datei:

    Auf diese Weise prüfen wir, ob alle Vorlagen der Verzweigungsseiten erfolgreich gerendert wurden. Auch das shared_examples wird verwendet, um den sich wiederholenden Code zu reduzieren.

    Übernehmen Sie die Änderung.

    git add -A
    git commit -m "Anforderungsspezifikationen für die Vorlagen von Posts-Zweigstellenseiten hinzufügen"

    Außerdem können wir sicherstellen, dass die Showvorlage erfolgreich gerendert wird. Erstellen Sie im selben Verzeichnis eine Datei show_spec.rb:

    Übernehmen Sie die Änderungen.

    git add -A
    git commit -m "Anforderungsspezifikationen für die Posts-Show-Vorlage hinzufügen"

    Um sicherzustellen, dass ein Benutzer einen neuen Beitrag erstellen kann, schreiben Sie Funktionsspezifikationen, um das Formular zu testen. Erstellen Sie im Verzeichnis features / posts eine neue Datei create_new_post_spec.rb

    Übernehmen Sie die Änderungen.

    git add -A
    git commit -m "Erstellen Sie eine Datei" create_new_post_spec.rb "mit Funktionsspezifikationen."

    Wenden Sie etwas Design auf die neue Vorlage an.

    In folgendem Verzeichnis:

    Assets / Stylesheets / Partials / Posts

    Erstellen Sie eine new.scss-Datei:

    Wenn Sie jetzt in einem Browser zur Vorlage wechseln, sollte ein Basisformular angezeigt werden

    Übernehmen Sie die Änderungen

    git add -A
    git commit -m "Füge CSS zu den Posts hinzu new.html.erb template"

    Schließlich möchten wir sicherstellen, dass alle Felder korrekt ausgefüllt sind. Innerhalb des Post-Modells werden wir einige Validierungen definieren. Fügen Sie dem Postmodel den folgenden Code hinzu:

    Übernehmen Sie die Änderungen.

    git add -A
    git commit -m "Validierungen zum Post-Modell hinzufügen"

    Decken Sie diese Validierungen mit Spezifikationen ab. Wechseln Sie zur Spezifikationsdatei des Post-Modells:

    spec / models / post_spec.rb

    Dann füge hinzu:

    Übernehmen Sie die Änderungen.

    git add -A
    git commit -m "Spezifikationen für die Validierungen des Post-Modells hinzufügen"

    Führen Sie den Zweig specific_branches mit dem Master zusammen

    Git Checkout -b Master
    git füge specific_branches zusammen
    git branch -D specific_branches

    Instant Messaging

    Benutzer können Beiträge veröffentlichen und die Beiträge anderer Benutzer lesen, sie können jedoch nicht miteinander kommunizieren. Wir könnten ein einfaches Briefkastensystem schaffen, das viel einfacher und schneller zu entwickeln wäre. Aber das ist eine sehr alte Art, mit jemandem zu kommunizieren. Echtzeitkommunikation ist viel aufregender zu entwickeln und komfortabel zu bedienen.

    Glücklicherweise verfügt Rails über Aktionskabel, mit denen die Implementierung von Echtzeitfunktionen relativ einfach ist. Das Kernkonzept der Aktionskabel besteht darin, dass anstelle von HTTP ein WebSockets-Protokoll verwendet wird. Das Kernkonzept von WebSockets besteht darin, eine Client-Server-Verbindung herzustellen und diese offen zu halten. Dies bedeutet, dass zum Senden und Empfangen zusätzlicher Daten keine erneuten Seitenladevorgänge erforderlich sind.

    Private Unterhaltung

    Das Ziel dieses Abschnitts ist es, eine funktionierende Funktion zu erstellen, mit der sich zwei Benutzer privat unterhalten können.

    Wechseln Sie zu einem neuen Zweig

    git checkout -B private_conversation

    Namespacing-Modelle

    Definieren Sie zunächst die erforderlichen Modelle. Wir benötigen vorerst zwei verschiedene Modelle, eines für private Gespräche und eines für private Nachrichten. Wir könnten sie PrivateConversation und PrivateMessage nennen, aber Sie können schnell auf ein kleines Problem stoßen. Während alles gut funktionieren würde, stellen Sie sich vor, wie das Verzeichnis models aussehen würde, nachdem wir immer mehr Modelle mit ähnlichen Namenspräfixen erstellt haben. Das Verzeichnis würde in kürzester Zeit kaum mehr zu verwalten sein.

    Um chaotische Strukturen in Verzeichnissen zu vermeiden, können wir eine Namespacetechnik verwenden.

    Mal sehen, wie es aussehen würde. Ein gewöhnliches Modell für private Konversationen würde PrivateConversation heißen und seine Datei würde private_conversation.rb heißen und im Verzeichnis models gespeichert

    models / private_conversation.rb

    In der Zwischenzeit würde die Version mit Namespace Private :: Conversation heißen. Die Datei würde conversation.rb heißen und sich im privaten Verzeichnis befinden

    models / private / conversation.rb

    Können Sie sehen, wie nützlich es sein könnte? Alle Dateien mit dem privaten Präfix werden im privaten Verzeichnis gespeichert, anstatt sich im Hauptmodellverzeichnis anzusammeln und das Lesen zu erschweren.

    Rails macht den Entwicklungsprozess wie gewohnt zum Vergnügen. Wir können Modelle mit Namespaces erstellen, indem wir ein Verzeichnis angeben, in das wir ein Modell einfügen möchten.

    Führen Sie den folgenden Befehl aus, um das namenspaced Private :: Conversation-Modell zu erstellen:

    Schienen g Modell privat / Gespräch

    Generieren Sie auch das Private :: Message-Modell:

    Schienen g Modell privat / Nachricht

    Wenn Sie sich das Verzeichnis models ansehen, sehen Sie eine private.rb-Datei. Dies ist erforderlich, um den Namen der Datenbanktabellen ein Präfix hinzuzufügen, damit Modelle erkannt werden können. Persönlich mag ich es nicht, diese Dateien im Modellverzeichnis zu speichern. Ich ziehe es vor, den Namen einer Tabelle in einem Modell selbst anzugeben. Um den Namen einer Tabelle in einem Modell anzugeben, müssen Sie self.table_name = verwenden und den Namen einer Tabelle als Zeichenfolge angeben. Wenn Sie wie ich die Namen von Datenbanktabellen auf diese Weise angeben, sollten die Modelle folgendermaßen aussehen:

    Die Datei private.rb im Verzeichnis models wird nicht mehr benötigt. Sie können sie löschen.

    Ein Benutzer kann viele private Unterhaltungen führen, und Unterhaltungen enthalten viele Nachrichten. Definieren Sie diese Assoziationen in den Modellen:

    Hier wird die class_name-Methode verwendet, um einen Namen eines zugeordneten Modells zu definieren. Auf diese Weise können Sie benutzerdefinierte Namen für unsere Verknüpfungen verwenden und sicherstellen, dass Modelle mit Namespaces erkannt werden. Ein weiterer Anwendungsfall der class_namemethod wäre, eine Beziehung zu sich selbst zu erstellen. Dies ist nützlich, wenn Sie die Daten desselben Modells unterscheiden möchten, indem Sie Hierarchien oder ähnliche Strukturen erstellen.

    Der foreign_key wird verwendet, um einen Namen der Assoziationsspalte in einer Datenbanktabelle anzugeben. Eine Datenspalte in einer Tabelle wird nur auf der Seite der zugehörigen Zuordnung erstellt. Um die Spalte jedoch erkennbar zu machen, müssen Sie für beide Modelle den Fremdschlüssel mit denselben Werten definieren.

    Private Gespräche werden zwischen zwei Benutzern geführt, wobei diese beiden Benutzer Absender und Empfänger sind. Wir hätten sie wie Benutzer1 und Benutzer2 benennen können. Es ist jedoch praktisch zu wissen, wer eine Konversation initiiert hat. Daher ist der Absender hier der Schöpfer einer Konversation.

    Definieren Sie Datentabellen in den Migrationsdateien:

    In der Tabelle private_conversations werden die IDs der Benutzer gespeichert. Dies ist erforderlich, damit die Zuordnungen belong_to und has_many funktionieren und natürlich eine Konversation zwischen zwei Benutzern hergestellt werden kann.

    In der Körperdatenspalte wird der Inhalt einer Nachricht gespeichert. Anstatt Indizes und ID-Spalten hinzuzufügen, um die Zuordnung zwischen zwei Modellen zu ermöglichen, haben wir hier die Referenzmethode verwendet, die die Implementierung vereinfacht hat.

    Führen Sie Migrationsdateien aus, um Tabellen in der Entwicklungsdatenbank zu erstellen

    Schienen db: migrieren

    Übernehmen Sie die Änderungen

    git add -A
    git commit -m "Erstelle Private :: Conversation- und Private :: Message-Modelle
    - Definieren Sie Assoziationen zwischen User, Private :: Conversation
      und Private :: Message-Modelle
    - Private_Conversations und Private_Messages Tabellen definieren "

    Ein privates Nicht-Echtzeit-Konversationsfenster

    Wir haben einen Ort zum Speichern von Daten für private Gespräche, aber das wars auch schon. Wo sollen wir jetzt anfangen? Wie in den vorherigen Abschnitten erwähnt, erstelle ich gerne eine grundlegende visuelle Seite eines Features und schreibe dann eine Logik, um es funktionsfähig zu machen. Ich mag diesen Ansatz, weil wenn ich ein visuelles Element habe, das ich funktionalisieren möchte, ist klarer, was ich erreichen möchte. Sobald Sie eine Benutzeroberfläche haben, ist es einfacher, ein Problem in kleinere Schritte zu unterteilen, da Sie wissen, was nach einem bestimmten Ereignis passieren soll. Es ist schwieriger, etwas zu programmieren, das es noch nicht gibt.

    Erstellen Sie einen Private :: Conversations-Controller, um die Benutzeroberfläche für private Konversationen zu erstellen. Sobald ich in der App einen Namespace erstellt habe, möchte ich konsistent bleiben und auch alle anderen verwandten Teile des Namespaces. Dies ermöglicht ein intuitiveres Verstehen und Navigieren im Quellcode.

    schienen g controller privat / gespräche

    Rails Generator ist ziemlich süß. Es wurden ein Namespace-Modell und Namespace-Ansichten erstellt. Alles ist bereit für die Entwicklung.

    Erstellen Sie eine neue Konversation

    Wir brauchen einen Weg, um ein neues Gespräch zu beginnen. In einem Fall von unserer App ist es sinnvoll, dass Sie eine Person kontaktieren möchten, die ähnliche Interessen wie Sie hat. Ein geeigneter Ort für diese Funktionalität ist die Seite eines einzelnen Posts.

    Erstellen Sie in der Vorlage posts / show.html.erb ein Formular, um eine neue Konversation zu initiieren. Unter der Zeile

    <% = @ post.content%> Folgendes hinzufügen:

    Definieren Sie die Hilfsmethode in posts_helper.rb

    Fügen Sie Spezifikationen für die Hilfsmethode hinzu:

    Erstellen Sie ein Show-Verzeichnis und die entsprechenden Teildateien:

    Definieren Sie die Hilfsmethode leave_message_partial_path in posts_helper.rb

    Fügen Sie Spezifikationen für die Methode hinzu

    Wir werden die Instanzvariable @message_has_been_sent gleich im PostsController definieren. Sie bestimmt, ob bereits eine erste Nachricht an einen Benutzer gesendet wurde oder nicht.

    Erstellen Sie Teildateien, die der Hilfsmethode leave_message_partial_path entsprechen, in einem neuen Verzeichnis contact_user

    Konfigurieren Sie nun die Show-Aktion des PostsControllers. Innerhalb der Aktion hinzufügen

    Definieren Sie im privaten Bereich des Controllers die conversation_exist? -Methode

    Die between_users-Methode fragt private Konversationen zwischen zwei Benutzern ab. Definieren Sie es als Bereich innerhalb des Private :: Conversation-Modells

    Wir müssen testen, ob der Bereich funktioniert. Definieren Sie vor dem Schreiben von Spezifikationen eine private_conversation-Factory, da wir Beispieldaten in der Testdatenbank benötigen.

    Wir sehen hier eine verschachtelte Factory. Dies ermöglicht es, eine Factory mit der Konfiguration ihrer Eltern zu erstellen und diese dann zu ändern. Da wir Nachrichten mit der private_conversation_with_messages-Factory erstellen, müssen wir auch die private_message-Factory definieren

    Jetzt haben wir alles bereit, um den Geltungsbereich between_users mit specs zu testen.

    Definieren Sie die Erstellungsaktion für den Private :: Conversations-Controller

    Hier erstellen wir eine Unterhaltung zwischen dem Autor eines Posts und einem aktuellen Benutzer. Wenn alles gut geht, erstellt die App eine Nachricht, die von einem aktuellen Benutzer geschrieben wurde, und gibt ein Feedback, indem ein entsprechender JavaScript-Teilbereich gerendert wird.

    Erstellen Sie diese Partials

    Erstellen Sie Routen für die Controller Private :: Conversations und Private :: Messages

    Derzeit sind nur wenige Aktionen erforderlich. Hier ist die einzige praktische Methode. Die Namespace-Methode ermöglicht das einfache Erstellen von Routen für Controller mit Namespace.

    Testen Sie die Leistung des gesamten .contact-user-Formulars mit den Funktionsspezifikationen

    Übernehmen Sie die Änderungen

    git add -A
    git commit -m "Fügen Sie in einem Beitrag ein Formular hinzu, um einen Benutzer zu kontaktieren
    - Definieren Sie eine contact_user_partial_path-Hilfsmethode in PostsHelper.
      Fügen Sie Spezifikationen für die Methode hinzu
    - Erstellen Sie _contact_user.html.erb- und _login_required.html.erb-Partials
    - Definieren Sie in PostsHelper eine Hilfsmethode leave_message_partial_path.
      Fügen Sie Spezifikationen für die Methode hinzu
    - Erstellen Sie _already_in_touch.html.erb und _message_form.html.erb
      Teildateien
    - Definiere ein @message_has_been_sent in PostsController's show action
    - Definieren Sie einen between_users-Bereich im Private :: Conversation-Modell
      Fügen Sie Spezifikationen für den Bereich hinzu
    - Definieren Sie die Fabriken private_conversation und private_message
    - Routen für Private :: Conversations und Private :: Messages definieren
    - Definieren Sie eine Erstellungsaktion in Private :: Conversations
    - Erstellen Sie _success.js- und _fail.js-Partials
    - Fügen Sie Feature-Spezifikationen hinzu, um das gesamte .contact-user-Formular zu testen. "

    Ändern Sie den Stil des Formulars ein wenig, indem Sie der Datei branch_page.scss CSS hinzufügen

    Wenn Sie einen einzelnen Beitrag besuchen, sollte das Formular ungefähr so ​​aussehen

    Wenn Sie eine Nachricht an den Autor eines Posts senden, verschwindet das Formular

    So sieht es aus, wenn Sie bereits mit einem Benutzer in Kontakt sind

    Übernehmen Sie die Änderungen

    git add -A
    git commit -m "CSS hinzufügen, um das .contact-user-Formular zu formatieren"

    Rendern Sie ein Konversationsfenster

    Wir haben eine Nachricht gesendet und eine neue Konversation erstellt. Das ist momentan unsere einzige Macht, wir können nichts anderes tun. Was für eine nutzlose Kraft bisher. Wir brauchen ein Gesprächsfenster, um Nachrichten zu lesen und zu schreiben.

    Speichern Sie die IDs der geöffneten Konversationen in der Sitzung. Auf diese Weise können Konversationen in der App geöffnet bleiben, bis ein Benutzer sie schließt oder die Sitzung beendet.

    Rufen Sie in der Erstellungsaktion von Private :: ConversationsController die Option add_to_conversations auf, es sei denn, bereits hinzugefügt? Methode, wenn eine Unterhaltung erfolgreich gespeichert wurde. Definieren Sie dann die Methode im privaten Bereich

    Dadurch wird die ID der Konversation in der Sitzung gespeichert. Und die Methode "already_added? Private" stellt sicher, dass die ID der Konversation noch nicht in der Sitzung hinzugefügt wird.

    Zuletzt benötigen wir einen Zugriff auf die Konversation in den Ansichten. Konvertieren Sie die Konversationsvariable in eine Instanzvariable.

    Jetzt können wir eine Vorlage für das Konversationsfenster erstellen. Erstellen Sie eine Teildatei für das Fenster

    Hier erhalten wir den Empfänger der Konversation mit der Methode private_conv_recipient. Definieren Sie die Hilfsmethode im Private :: ConversationsHelper

    Die opposition_user-Methode wird verwendet. Gehen Sie zum Private :: Conversation-Modell und definieren Sie die Methode

    Dies gibt einen entgegengesetzten Benutzer einer privaten Konversation zurück. Stellen Sie sicher, dass die Methode korrekt funktioniert, indem Sie sie mit Spezifikationen abdecken

    Erstellen Sie als Nächstes fehlende Teildateien für die Datei _conversation.html.erb

    Definieren Sie im Private :: ConversationsHelper die load_private_messageshelper-Methode

    Dies fügt einen Link zum Laden vorheriger Nachrichten hinzu. Erstellen Sie eine entsprechende Teildatei in einem neuen Verzeichnis messages_list

    Vergessen Sie nicht, sicherzustellen, dass alles in Ordnung mit der Methode ist, und schreiben Sie die Spezifikationen dafür

    Da die Fenster von Konversationen in der gesamten App gerendert werden, benötigen wir Zugriff auf die Private :: ConversationsHelperhelper-Methoden. Um innerhalb der gesamten App auf alle diese Methoden zugreifen zu können, fügen Sie ApplicationHelper hinzu

    include Private :: ConversationsHelper

    Erstellen Sie dann die letzte fehlende Teildatei für das neue Nachrichtenformular der Konversation

    Wir werden dieses Formular etwas später funktionsfähig machen.

    Erstellen wir nun eine Funktion, mit der das Konversationsfenster in der App gerendert wird, nachdem ein Benutzer eine Nachricht über einen einzelnen Beitrag gesendet hat.

    In der Datei _success.js.erb

    posts / show / contact_user / message_form / _success.js.erb

    hinzufügen

    <% = 'privat / gespräche / offen' rendern%>

    Mit dieser Teildatei wird der App ein Konversationsfenster hinzugefügt. Definieren Sie die Teildatei

    Diese Callback-Teildatei wird in mehreren Szenarien wiederverwendet. Um zu vermeiden, dass dasselbe Fenster mehrmals gerendert wird, überprüfen wir vor dem Rendern eines Fensters, ob es in der App bereits vorhanden ist. Dann erweitern wir das Fenster und fokussieren das Nachrichtenformular automatisch. Am Ende der Datei wird die Funktion positionChatWindows () aufgerufen, um sicherzustellen, dass alle Dialogfenster richtig positioniert sind. Wenn wir sie nicht positionieren würden, würden sie nur an derselben Stelle gerendert, was natürlich unbrauchbar wäre.

    Erstellen Sie nun im Assets-Verzeichnis eine Datei, die die Sichtbarkeit und Positionierung der Unterhaltungsfenster übernimmt

    Anstatt unsere eigenen Funktionen zum Setzen und Abrufen von Cookies oder einer ähnlichen Methode zum Verwalten von Daten zwischen JavaScript zu erstellen, können wir das Gon Gem verwenden. Eine ursprüngliche Verwendung dieses Edelsteins besteht darin, Daten von der Serverseite an JavaScript zu senden. Ich finde es aber auch nützlich, um JavaScript-Variablen in der gesamten App im Auge zu behalten. Installieren und konfigurieren Sie den Edelstein, indem Sie die Anweisungen lesen.

    Wir verfolgen die Breite des Ansichtsfensters mit einem Ereignis-Listener. Wenn sich eine Unterhaltung der linken Seite des Ansichtsfensters nähert, wird sie ausgeblendet. Sobald genügend freier Speicherplatz für ein ausgeblendetes Konversationsfenster vorhanden ist, zeigt die App es erneut an.

    Bei einem Seitenbesuch rufen wir die Positionierungs- und Sichtbarkeitsfunktionen auf, um sicherzustellen, dass sich alle Unterhaltungsfenster an der richtigen Position befinden.

    Wir verwenden die Panel-Komponente des Bootstraps, um die Fenster der Konversationen einfach zu erweitern und zu reduzieren. Standardmäßig werden sie reduziert und sind überhaupt nicht interaktiv. Um sie umschaltbar zu machen, erstellen Sie im Javascripts-Verzeichnis eine neue Datei toggle_window.js

    Erstellen Sie eine neue Datei conversation_window.scss

    assets / stylesheets / partials / conversation_window.scss

    Und fügen Sie CSS hinzu, um die Fenster von Konversationen zu formatieren

    Möglicherweise haben Sie bemerkt, dass einige Klassen noch nicht in einer HTML-Datei definiert wurden. Dies liegt daran, dass die zukünftigen Dateien, die wir im Ansichtsverzeichnis erstellen, gemeinsames CSS mit bereits vorhandenen HTML-Elementen haben werden. Anstatt mehrmals zu CSS-Dateien zu springen, nachdem wir ein untergeordnetes HTML-Element hinzugefügt haben, habe ich jetzt einige Klassen eingefügt, die in zukünftigen HTML-Elementen definiert sind. Denken Sie daran, Sie können immer zu Stylesheets gehen und analysieren, wie ein bestimmtes Styling funktioniert.

    Zuvor haben wir eine ID einer neu erstellten Konversation in der Sitzung gespeichert. Es ist an der Zeit, diese Vorteile zu nutzen und das Konversationsfenster geöffnet zu lassen, bis ein Benutzer es schließt oder die Sitzung beendet. Definieren Sie im ApplicationController einen Filter

    before_action: opens_conversations_windows

    und definieren Sie dann die Methode opens_conversations_windows

    Die Methode includes wird verwendet, um die Daten aus zugeordneten Datenbanktabellen einzuschließen. In naher Zukunft werden wir Nachrichten aus einer Konversation laden. Wenn wir die Methode "Includes" nicht verwenden, hätten wir mit dieser Abfrage keine Nachrichtendatensätze einer Konversation geladen. Dies würde zu einem N + 1-Abfrageproblem führen. Wenn wir keine Nachrichten mit der Abfrage laden, wird für jede Nachricht eine zusätzliche Abfrage ausgelöst. Dies würde die Leistung der App erheblich beeinträchtigen. Anstelle von 100 Abfragen für 100 Nachrichten haben wir jetzt nur eine erste Abfrage für eine beliebige Anzahl von Nachrichten.

    Fügen Sie in der Datei application.html.erb direkt unterhalb der Yield-Methode Folgendes hinzu

    Erstellen Sie ein neues Anwendungsverzeichnis und erstellen Sie darin die Teildatei _private_conversations_windows.html.erb

    Wenn wir nun durch die App blättern, sehen wir die ganze Zeit geöffnete Konversationen, egal auf welcher Seite wir uns befinden.

    Übernehmen Sie die Änderungen

    git add -A
    git commit -m "Rendert ein privates Konversationsfenster in der App
    - Fügen Sie der Sitzung geöffnete Konversationen hinzu
    - Erstellen Sie eine _conversation.html.erb-Datei in private / conversations
    - Definieren Sie eine Hilfsmethode private_conv_recipient in der
      private / conversations_helper.rb
    - Definieren Sie eine oppositionelle_user-Methode im Private :: Conversation-Modell
      und Spezifikationen hinzufügen
    - Erstellen Sie die Dateien _heading.html.erb und _messages_list.html.erb
      im privaten / gespräche / gespräch
    - Definiere eine load_private_messages in private / conversations_helper.rb
      und Spezifikationen hinzufügen
    - Erstellen Sie eine _neue_Nachricht_Form.html.erb in der
      privat / gespräche / gespräch
    - Erstellen Sie eine _open.js.erbinside private / Konversationen
    - Erstellen Sie eine position_and_visibility.js in der
      Assets / Javascripts / Unterhaltungen
    - Erstellen Sie eine conversation_window.scss in der
      Assets / Stylesheets / Partials
    - Definieren Sie eine Hilfsmethode für opens_conversations_windows in
      ApplicationController
    - Erstellen Sie eine _private_conversations_windows.html.erb in der
      Layouts / Anwendung

    Schließen Sie eine Unterhaltung

    Die Schaltfläche zum Schließen der Konversation ist noch nicht funktionsfähig. Aber wir haben alles bereit, um es so zu machen. Definieren Sie im Private :: ConversationsController eine Abschlussaktion

    Wenn Sie auf die Schaltfläche "Schließen" klicken, wird diese Aktion aufgerufen. Die Aktion löscht die ID der Konversation aus der Sitzung und antwortet dann mit einer Teildatei js, die mit dem Namen der Aktion identisch ist. Erstellen Sie die Teildatei

    Das Fenster der Konversation wird aus dem DOM entfernt und die übrigen Fenster der Konversation werden neu positioniert.

    Übernehmen Sie die Änderungen

    git add -A
    git commit -m "Funktioniert die Schaltfläche zum Schließen der Konversation
    - Definieren Sie eine Abschlussaktion im Private :: ConversationsController
    - Erstelle eine close.js.erb innerhalb der privaten / Konversationen "

    Nachrichten rendern

    Derzeit wird in der Nachrichtenliste ein Ladesymbol ohne Nachrichten angezeigt. Das liegt daran, dass wir keine Vorlagen für Nachrichten erstellt haben. Erstellen Sie im Verzeichnis views / privated ein Nachrichtenverzeichnis. Erstellen Sie im Verzeichnis eine neue Datei

    Die Hilfsmethode private_message_date_check überprüft, ob diese Nachricht am selben Tag wie eine vorherige Nachricht geschrieben wurde. Wenn nicht, wird eine zusätzliche Zeile mit einem neuen Datum ausgegeben. Definieren Sie die Hilfsmethode im Private :: MessagesHelper

    Fügen Sie im ApplicationHelper den Private :: MessagesHelper hinzu, damit wir über die App darauf zugreifen können

    include Private :: MessagesHelper

    Schreiben Sie Spezifikationen für die Methode. Erstellen Sie eine neue Datei messages_helper_spec.rb

    Erstellen Sie in einem neuen Nachrichtenverzeichnis eine _new_date.html.erb-Datei

    Anschließend haben wir in der Datei _message.html.erb die Hilfsmethoden send_or_received und seen_or_unseen gesendet. Sie geben in unterschiedlichen Fällen unterschiedliche Klassen zurück. Definieren Sie sie im Private :: MessagesHelper

    Schreiben Sie Spezifikationen für sie:

    Jetzt brauchen wir eine Komponente, um Nachrichten in die Nachrichtenliste zu laden. Diese Komponente fügt auch frühere Nachrichten am Anfang der Liste hinzu, wenn ein Benutzer einen Bildlauf durchführt, bis keine Nachrichten mehr in einer Konversation vorhanden sind. Wir werden einen unendlichen Scroll-Mechanismus für Nachrichten haben, ähnlich dem, den wir auf den Seiten der Posts haben.

    Erstellen Sie im Verzeichnis views / private / messages eine Datei _load_more_messages.js.erb:

    Die Instanzvariable @id_type bestimmt einen Typ der Konversation. In Zukunft können wir nicht nur private Gespräche führen, sondern auch Gruppen. Dies führt zu gemeinsamen Hilfsmethoden und Teildateien zwischen beiden Typen.

    Erstellen Sie im Hilfeverzeichnis ein freigegebenes Verzeichnis. Erstellen Sie eine messages_helper.rb-Datei und definieren Sie eine Hilfsmethode

    Bisher ist die Methode ziemlich dumm. Es wird nur der Pfad eines Teils zurückgegeben. Wir werden es später erläutern, wenn wir unserem Nachrichtensystem zusätzliche Funktionen hinzufügen. Derzeit haben wir keinen Zugriff auf Hilfsmethoden, die in dieser Datei oder in einer anderen Datei definiert sind. Wir müssen sie in andere Hilfedateien aufnehmen. In der
    Private :: MessagesHelper, enthält Methoden aus Shared :: MessagesHelper

    erfordern 'shared / messages_helper'
    include Shared :: MessagesHelper

    Erstellen Sie im freigegebenen Verzeichnis einige neue Verzeichnisse:

    shared / load_more_messages / window

    Dann erstelle eine _append_messages.js.erb Datei:

    Dieser Code sorgt dafür, dass frühere Nachrichten an den Anfang der Nachrichtenliste angehängt werden. Definieren Sie dann erneut eine andere, nicht so faszinierende Hilfsmethode im Private :: MessagesHelper

    Erstellen Sie die entsprechenden Verzeichnisse im Verzeichnis private / messages und erstellen Sie eine Datei _add_link_to_messages.js.erb

    Diese Datei aktualisiert den Link, der vorherige Nachrichten lädt. Nachdem frühere Nachrichten angehängt wurden, wird der Link durch einen aktualisierten Link ersetzt, um ältere frühere Nachrichten zu laden.

    Jetzt haben wir das ganze System, wie vorherige Nachrichten an den Anfang der Nachrichtenliste angehängt werden. Wenn wir jedoch versuchen, die App aufzurufen und ein Konversationsfenster zu öffnen, werden keine gerenderten Nachrichten angezeigt. Warum? Weil nichts den Link zum Laden vorheriger Nachrichten auslöst. Wenn wir zum ersten Mal ein Konversationsfenster öffnen, möchten wir die neuesten Nachrichten sehen. Wir können das Konversationsfenster so programmieren, dass, sobald es erweitert wird, der Link Mehr Nachrichten laden ausgelöst wird, um die neuesten Nachrichten zu laden. Es initiiert den ersten Zyklus des Anhängens früherer Nachrichten und des Ersetzens des Links zum Laden weiterer Nachrichten durch einen aktualisierten.

    Aktualisieren Sie in der Datei toggle_window.js die Umschaltfunktion, um genau das zu tun, was oben beschrieben wurde

    Erstellen Sie einen Ereignishandler. Wenn ein Benutzer einen Bildlauf durchführt und fast den oberen Rand der Nachrichtenliste erreicht, wird der Link zum Laden weiterer Nachrichten ausgelöst.

    Wenn auf den Link zum Laden weiterer Nachrichten geklickt wird, wird die Indexaktion von Private :: MessagesController aufgerufen. Dies ist der Pfad, den wir zum Link zum Laden vorheriger Nachrichten definiert haben. Erstellen Sie den Controller und seine Indexaktion

    Hier schließen wir Methoden aus dem Nachrichtenmodul ein. Das Modul befindet sich im Concerns-Verzeichnis. ActiveSupport :: Concern ist einer der Orte, an denen Sie Module speichern können, die Sie später in Klassen verwenden können. In unserem Fall fügen wir unserem Controller zusätzliche Methoden aus dem Modul hinzu. Die Methode get_messages stammt aus dem Modul Messages. Der Grund, warum es im Modul gespeichert wird, ist, dass wir genau diese Methode etwas später in einem anderen Controller verwenden werden. Um eine Vervielfältigung des Codes zu vermeiden, machen wir die Methode wiederverwendbarer.

    Ich habe einige Leute gesehen, die sich über das ActiveSupport :: Concern beschwert haben und vorgeschlagen haben, es überhaupt nicht zu verwenden. Ich fordere diese Leute auf, mich im Achteck zu bekämpfen. Ich mache Witze: D. Dies ist eine unabhängige Anwendung und wir können unsere App erstellen, wie es uns gefällt. Wenn Sie Bedenken nicht mögen, gibt es eine Reihe anderer Möglichkeiten, um wiederverwendbare Methoden zu erstellen.

    Erstellen Sie das Modul

    Hier benötigen wir active_support / concern und erweitern dann unser Modul mit ActiveSupport :: Concern, damit Rails weiß, dass es ein Problem ist.

    Mit der constantize-Methode erstellen wir dynamisch einen konstanten Namen, indem wir einen String-Wert eingeben. Wir nennen Modelle dynamisch. Dieselbe Methode wird für Private :: Conversation- und Group :: Conversation-Modelle verwendet.

    Nachdem die Methode get_messages alle erforderlichen Instanzvariablen festgelegt hat, antwortet die Indexaktion mit der Teildatei _load_more_messages.js.erb.

    Nachdem die Nachrichten an den Anfang der Nachrichtenliste angehängt wurden, möchten wir das Ladesymbol aus dem Konversationsfenster entfernen. Fügen Sie am Ende der Datei _load_more_messages.js.erb hinzu

    <% = render remove_link_to_messages%>

    Definieren Sie nun die Hilfsmethode remove_link_to_messages im Shared :: MessagesHelper

    Versuchen Sie, Spezifikationen für die Methode selbst zu schreiben.

    Erstellen Sie die Teildatei _remove_more_messages_link.js.erb

    In einem Fall, in dem keine vorherigen Nachrichten mehr vorhanden sind, werden der Link zu vorherigen Nachrichten und das Ladesymbol entfernt.

    Wenn Sie versuchen, einen Benutzer jetzt zu kontaktieren, wird ein Konversationsfenster mit einer von Ihnen gesendeten Nachricht angezeigt. Wir können Nachrichten über AJAX-Anfragen rendern.

    Übernehmen Sie die Änderungen.

    git add -A
    git commit -m "Nachrichten mit AJAX rendern
    - Erstellen Sie eine _message.html.erb in private / messages
    - Definieren Sie eine Hilfsmethode private_message_date_check in
      Private :: MessagesHelper und schreiben Spezifikationen dafür
    - Erstellen Sie eine _new_date.html.erb in private / messages / message
    - Definieren Sie die Hilfsmethoden sent_or_received und seen_or_unseen in
      Private :: MessagesHelper und schreiben Spezifikationen für sie
    - Erstellen Sie eine _load_more_messages.js.erb in private / messages
    - Definieren Sie eine Hilfsmethode append_previous_messages_partial_path in
      Shared :: MessagesHelper
    - Erstellen Sie eine _append_messages.js.erb innerhalb
      shared / load_more_messages / window
    - Definieren Sie einen replace_link_to_private_messages_partial_path in
      Private :: MessagesHelper
    - Erstellen Sie eine _add_link_to_messages.js.erb innerhalb
      private / messages / load_more_messages / window
    - Erstellen Sie eine toggle_window.js in javascripts / conversations
    - Erstellen Sie eine messages_infinite_scroll.js im Inneren
      Assets / Javascripts / Unterhaltungen
    - Definieren Sie eine Indexaktion im Private :: MessagesController
    - Erstellen Sie eine messages.rb in controller / concern
    - Definiere einen remove_link_to_messages in helpers / shared
    - Erstellen Sie eine _remove_more_messages_link.js.erb innerhalb
      shared / load_more_messages / window "

    Echtzeitfunktionalität mit Action Cable

    Die Fenster von Unterhaltungen sehen bereits hübsch aus. Und sie haben auch einige süße Funktionalität. Ihnen fehlt jedoch die wichtigste Funktion - die Fähigkeit, Nachrichten in Echtzeit zu senden und zu empfangen.

    Wie bereits erwähnt, können wir mit Action Cable die gewünschte Echtzeitfunktion für Unterhaltungen erzielen. Sie sollten die Dokumentation durchblättern, um sich darüber im Klaren zu sein, wie alles funktioniert.

    Als erstes sollten wir eine WebSocket-Verbindung erstellen und einen bestimmten Kanal abonnieren. Glücklicherweise sind WebSocket-Verbindungen bereits in der Standard-Rails-Konfiguration enthalten. Im Verzeichnis app / channels / application_cable sehen Sie die Dateien channel.rb und connection.rb. Die Connection-Klasse kümmert sich um die Authentifizierung, und die Channel-Klasse ist eine übergeordnete Klasse, in der die gemeinsame Logik aller Kanäle gespeichert wird.

    Die Verbindung ist standardmäßig eingestellt. Jetzt brauchen wir einen privaten Konversationskanal, um uns anzumelden. Generieren Sie einen Kanal mit Namespace

    Schienen g Kanal privat / Konversation

    Im generierten Private :: ConversationChannel sehen wir abonnierte und nicht abonnierte Methoden. Mit der abonnierten Methode stellt ein Benutzer eine Verbindung zum Kanal her. Mit der abgemeldeten Methode zerstört ein Benutzer offensichtlich die Verbindung.

    Aktualisieren Sie diese Methoden:

    Hier möchten wir, dass ein Benutzer einen eigenen eindeutigen Kanal hat. Über den Kanal empfängt und sendet ein Benutzer Daten. Da die Nutzer-IDs eindeutig sind, machen wir den Kanal eindeutig, indem wir eine Nutzer-ID hinzufügen.

    Dies ist eine serverseitige Verbindung. Jetzt müssen wir auch auf der Clientseite eine Verbindung herstellen.

    Um eine Instanz der Verbindung auf der Clientseite zu erstellen, müssen wir JavaScript schreiben. Tatsächlich hat Rails es bereits mit dem Kanalgenerator erstellt. Navigieren Sie zu "assets / javascripts / channels / private" und Rails generiert standardmäßig CoffeeScript-Dateien. Ich werde hier JavaScript verwenden. Benennen Sie die Datei in conversation.js um und ersetzen Sie den Inhalt durch:

    Starten Sie den Server neu, rufen Sie die App auf, melden Sie sich an und überprüfen Sie das Serverprotokoll.

    Wir haben die Verbindung. Der Kern der Echtzeitkommunikation ist gesetzt. Wir haben eine ständig offene Client-Server-Verbindung. Das bedeutet, dass wir Daten vom Server senden und empfangen können, ohne die Verbindung neu zu starten oder einen Browser zu aktualisieren, Mann! Eine wirklich mächtige Sache, wenn man darüber nachdenkt. Ab sofort bauen wir das Messaging-System um diese Verbindung herum auf.

    Übernehmen Sie die Änderungen.

    git add -A
    git commit -m "Erstelle einen einzigartigen privaten Konversationskanal und abonniere ihn"

    Lassen Sie uns das neue Nachrichtenformular des Konversationsfensters funktionsfähig machen. Fügen Sie am Ende der Datei assets / javascripts / channels / private / conversations.js die folgende Funktion hinzu:

    Die Funktion ruft Werte aus dem neuen Nachrichtenformular ab und übergibt sie an eine send_message-Funktion. Die send_message-Funktion ruft auf der Serverseite eine send_message-Methode auf, die sich um die Erstellung einer neuen Nachricht kümmert.

    Beachten Sie auch, dass sich der Ereignishandler auf einer Senden-Schaltfläche befindet. Im Konversationsfenster sind jedoch keine Senden-Schaltflächen sichtbar. Es ist eine Designwahl. Wir müssen das Konversationsfenster so programmieren, dass die Senden-Schaltfläche ausgelöst wird, wenn die Eingabetaste auf einer Tastatur gedrückt wird. Diese Funktion wird in Zukunft von anderen Funktionen verwendet. Erstellen Sie daher eine conversation.js-Datei im Verzeichnis assets / javascripts / conversations

    In der Datei wird ein allgemeines Verhalten für die Fenster von Konversationen beschrieben. Das erste Problem besteht darin, die Bildlaufleiste von oben fernzuhalten, damit frühere Nachrichten nicht geladen werden, wenn sie nicht benötigt werden. Die zweite Funktion stellt sicher, dass die Senden-Schaltfläche beim Klicken auf die Eingabetaste ausgelöst wird, und löscht dann den Eingabewert wieder in eine leere Zeichenfolge.

    Beginnen Sie, indem Sie die Funktion send_message im Objekt private_conversation erstellen. Fügen Sie es unterhalb der empfangenen Rückruffunktion hinzu

    Dadurch wird die send_message-Methode auf der Serverseite aufgerufen und der Nachrichtenwert übergeben. Die serverseitige Methode sollte im Private :: ConversationChannel definiert werden. Definieren Sie die Methode:

    Dadurch wird die Erstellung einer neuen Nachricht erledigt. Der Datenparameter, den wir aus dem übergebenen Argument erhalten, ist ein verschachtelter Hash. Um diese verschachtelte Komplexität in einen einzelnen Hash zu reduzieren, wird die each_with_object-Methode verwendet.

    Wenn Sie versuchen, eine neue Nachricht im Fenster einer Unterhaltung zu senden, wird tatsächlich ein neuer Nachrichtendatensatz erstellt. Es wird noch nicht sofort im Konversationsfenster angezeigt, wenn Sie die Website aktualisieren. Es würde angezeigt, aber wir haben nichts eingestellt, um neu erstellte Nachrichten an den Kanal eines privaten Gesprächs zu senden. Wir werden es gleich implementieren. Bevor wir jedoch fortfahren und Änderungen vornehmen, fassen Sie kurz die Funktionsweise des aktuellen Messagingsystems zusammen.

    1. Ein Benutzer füllt das neue Nachrichtenformular aus und sendet die Nachricht
    2. Die Ereignisbehandlungsroutine in der Datei javascripts / channels / private / conversations.js ruft die Daten eines Konversationsfensters, eine Konversations-ID und einen Nachrichtenwert ab und löst die Kanalinstanzen auf der clientseitigen Funktion send_message aus.

    3. Die send_message-Funktion auf der Clientseite ruft die send_messagemethod auf der Serverseite auf und übergibt Daten an sie

    4. Die send_message-Methode auf der Clientseite verarbeitet die bereitgestellten Daten und erstellt einen neuen Private :: Message-Datensatz

    Übernehmen Sie die Änderungen.

    git add -A
    git commit -m "Funktioniert das neue Nachrichtenformular eines privaten Unterhaltungsfensters
    - Fügen Sie eine Ereignisbehandlungsroutine in das hinzu
      javascripts / channels / private / conversation.js, um den Submit-Button auszulösen
    - Definieren Sie ein gemeinsames Verhalten zwischen Unterhaltungsfenstern im
      assets / javascripts / conversations / conversation.js
    - Definieren Sie eine send_message-Funktion auf Client- und Serverseite. "

    Senden Sie eine neue Nachricht

    Nachdem eine neue Nachricht erstellt wurde, möchten wir sie irgendwie an einen entsprechenden Kanal senden. Nun, Active Record Callbacks rüstet uns mit zahlreichen nützlichen Callback-Methoden für Modelle aus. Es gibt eine after_create_commit-Rückrufmethode, die ausgeführt wird, wenn ein neuer Modelldatensatz erstellt wird. Fügen Sie in der Datei des Private :: Message-Modells Folgendes hinzu:

    Wie Sie sehen, wird nach der Erstellung eines Datensatzes Private :: MessageBroadcastJob.perform_later aufgerufen. Und was ist das? Es handelt sich um einen Hintergrundjob, der Back-End-Vorgänge erledigt. Es erlaubt, bestimmte Operationen auszuführen, wann immer wir wollen. Es kann unmittelbar nach einem bestimmten Ereignis oder einige Zeit später nach einem Ereignis ausgeführt werden. Wenn Sie nicht mit Hintergrundjobs vertraut sind, lesen Sie die Informationen zu aktiven Jobs.

    Fügen Sie Spezifikationen für die Methode previous_message hinzu. Wenn Sie jetzt versuchen, Spezifikationen auszuführen, kommentieren Sie die after_create_commit-Methode aus. Wir haben den Private :: MessageBroadcastJob nicht definiert, daher würden derzeit Spezifikationen einen undefinierten konstanten Fehler auslösen.

    Jetzt können wir einen Hintergrundjob erstellen, der eine neu erstellte Nachricht an den Kanal eines privaten Gesprächs sendet.

    Schienen g Job privat / message_broadcast

    In der Datei sehen wir eine Perform-Methode. Wenn Sie einen Job aufrufen, wird diese Methode standardmäßig aufgerufen. Verarbeiten Sie nun innerhalb des Jobs die angegebenen Daten und senden Sie sie an die Abonnenten des Kanals.

    Hier rendern wir eine Nachricht und senden sie an die Abonnenten beider Kanäle. Außerdem übergeben wir einige zusätzliche Schlüssel-Wert-Paare, um die Nachricht korrekt anzuzeigen. Wenn wir versuchen, eine neue Nachricht zu senden, erhalten Benutzer Daten, die Nachricht wird jedoch nicht an die Nachrichtenliste angehängt. Es werden keine sichtbaren Änderungen vorgenommen.

    Wenn Daten an einen Kanal gesendet werden, wird die empfangene Rückruffunktion auf der Clientseite aufgerufen. Hier haben wir die Möglichkeit, Daten an das DOM anzuhängen. Fügen Sie in die empfangene Funktion den folgenden Code ein:

    Hier sehen wir, dass der Absender und der Empfänger etwas unterschiedlich behandelt werden.

    // Ändere den Stil des Conv-Fensters, wenn es unsichtbare Nachrichten gibt
    // füge eine zusätzliche Klasse zum Fenster der Konversation hinzu oder so

    Ich habe dies absichtlich erstellt. Wenn eine Konversation ungesehene Nachrichten enthält, können Sie das Fenster so gestalten, wie Sie möchten. Sie können die Farbe eines Fensters ändern, es blinken lassen oder was immer Sie möchten.

    Es werden auch die Funktionen findConv, ConvRendered, ConvMessagesVisibility verwendet. Diese Funktionen werden sowohl für private als auch für Gruppen-Chats verwendet.

    Erstellen Sie ein freigegebenes Verzeichnis:

    Assets / Javascripts / Kanäle / geteilt

    Erstellen Sie eine conversation.js-Datei in diesem Verzeichnis.

    Ein Messenger wird im Code ziemlich oft erwähnt und wir haben den Messenger noch nicht. Der Messenger wird ein separater Weg sein, um Gespräche zu eröffnen. Um in Zukunft viele kleine Änderungen zu vermeiden, habe ich Fälle in den Messenger aufgenommen.

    Das war's, die Echtzeitfunktionalität sollte funktionieren. Beide Benutzer, der Absender und der Empfänger, sollten neue Nachrichten im DOM empfangen und angezeigt bekommen. Wenn wir eine neue Nachricht senden, sollte diese sofort an die Nachrichtenliste angehängt werden. Aber jetzt gibt es ein kleines Problem. Wir haben nur eine Möglichkeit, ein Konversationsfenster zu rendern. Es wird nur gerendert, wenn eine Konversation erstellt wird. In Kürze werden weitere Möglichkeiten zum Rendern von Unterhaltungsfenstern hinzugefügt. Lassen Sie uns jedoch vorher noch einmal zusammenfassen, wie Daten die Abonnenten des Kanals erreichen.

    1. Nachdem ein neuer Private :: Message-Datensatz erstellt wurde, wird die after_create_commit-Methode ausgelöst, die den Hintergrundjob aufruft
    2. Private :: MessageBroadcastJob verarbeitet die angegebenen Daten und sendet sie an die Abonnenten des Kanals
    3. Auf der Clientseite wird die empfangene Rückruffunktion aufgerufen, die Daten an das DOM anfügt

    Übernehmen Sie die Änderungen.

    git add -A
    git commit -m "Sende eine neue Nachricht
    - Definieren Sie in der Private :: Message eine after_create_comit-Rückrufmethode.
    - Erstellen Sie einen Private :: MessageBroadcastJob
    - Definieren Sie eine empfangene Funktion im
      assets / javascripts / channels / privat / conversation.js
    - Erstellen Sie eine conversation.js in der
      Assets / Javascripts / Channels / Shared "

    Aktualisierung der Navigationsleiste

    In der Navigationsleiste wird eine Liste der Benutzergespräche angezeigt. Wenn eine Liste mit Konversationen geöffnet wird, möchten wir die Konversationen nach den neuesten Nachrichten sortiert sehen. Gespräche mit den neuesten Nachrichten stehen ganz oben auf der Liste. Diese Liste sollte für die gesamte Anwendung zugänglich sein. Speichern Sie also im ApplicationController die Konversationen der bestellten Benutzer in einer Instanzvariablen. Die Art und Weise, wie ich dies vorschlage, besteht darin, eine all_ordered_conversations-Methode innerhalb des Controllers zu definieren

    Fügen Sie einen before_action-Filter hinzu, damit die Instanzvariable @all_conversations überall verfügbar ist.

    before_action: all_ordered_conversations

    Erstellen Sie anschließend einen OrderConversationsService, der sich um die Abfrage und Bestellung von Gesprächen kümmert.

    Derzeit befasst sich dieser Dienst nur mit privaten Gesprächen. Dies ist die einzige Art von Gesprächen, die wir bisher entwickelt haben. In Zukunft werden Privat- und Gruppengespräche zusammengeführt und nach den neuesten Nachrichten sortiert. Die Sortiermethode wird verwendet, um ein Array von Konversationen zu sortieren. Wenn wir die Methode "includes" nicht verwenden, tritt erneut ein N + 1-Abfrageproblem auf. Denn wenn wir Konversationen sortieren, überprüfen wir die Erstellungsdaten der neuesten Nachrichten für jede Konversation und vergleichen sie. Aus diesem Grund haben wir in die Abfrage Nachrichtenaufzeichnungen aufgenommen.

    Der Operator <=> wertet aus, welcher created_at-Wert höher ist. Wenn wir benutzt haben
    a <=> b würde ein bestimmtes Array in aufsteigender Reihenfolge sortieren. Wenn Sie die Werte in umgekehrter Reihenfolge auswerten, b <=> a, wird ein Array in absteigender Reihenfolge sortiert.

    Wir haben den all_by_user-Bereich noch nicht im Private :: Conversation-Modell definiert. Öffnen Sie das Modell und definieren Sie den Bereich:

    Schreiben Sie Spezifikationen für den Service und den Umfang:

    Übernehmen Sie die Änderungen.

    git add -A
    git commit -m "
    - Erstellen Sie einen OrderConversationsService und fügen Sie Spezifikationen hinzu
    - Definieren Sie einen all_by_user-Bereich in der Private :: Conversation
      modellieren und Spezifikationen hinzufügen "

    Jetzt haben wir Zugriff auf eine Reihe von geordneten Gesprächen. Lassen Sie uns eine Liste ihrer Links rendern. Jedes Mal, wenn ein Benutzer auf einen von ihnen klickt, wird in der App ein Konversationsfenster gerendert. Wenn Sie sich erinnern, hat unsere Navigationsleiste zwei Hauptkomponenten. Innerhalb einer Komponente werden Elemente ständig angezeigt. In einer anderen Komponente werden Elemente auf kleineren Geräten ausgeblendet. In der Kopfzeile der Navigation, in der Komponenten ständig sichtbar sind, erstellen wir ein Dropdown-Menü mit Unterhaltungen. Um zu verhindern, dass eine große Ansichtsdatei vorhanden ist, teilen Sie sie wie gewohnt in mehrere kleinere auf.

    Öffnen Sie die Datei _header.html.erb der Navigation und ersetzen Sie den Inhalt durch Folgendes:

    Erstellen Sie nun ein Header-Verzeichnis mit einer darin enthaltenen Datei _toggle_button.html.erb

    Dies ist eine Umschaltfläche, die sich früher in der Datei _header.html.erb befand. Erstellen Sie eine weitere Datei im Header-Verzeichnis

    Und das ist die Home-Schaltfläche von _header.html.erb. Auch hier gibt es einen extra Link. Auf kleineren Geräten wird anstelle des Anwendungsnamens ein Symbol angezeigt.

    Schauen Sie sich die Datei _header.html.erb noch einmal an. Es gibt eine Hilfsmethode nav_header_content_partials, die ein Array der Pfade von Partials zurückgibt. Der Grund, warum wir Partials nicht einzeln rendern, liegt darin, dass sich das Array in verschiedenen Fällen unterscheidet. Im NavigationHelper definieren Sie die Methode

    Schreiben Sie Spezifikationen für die Methoden in die Datei navigation_helper_spec.rb

    Erstellen Sie nun die erforderlichen Dateien, um Dropdown-Menüs in der Navigationsleiste anzuzeigen. Erstellen Sie zunächst eine _dropdowns.html.erb-Datei

    Erstellen Sie ein Dropdown-Verzeichnis mit einer _conversations.html.erb-Datei

    Hier verwenden wir die Instanzvariable @all_conversations, die zuvor im Controller definiert wurde, und rendern Links zu offenen Konversationen. Die Links für die verschiedenen Konversationstypen unterscheiden sich. Für private und Gruppengespräche müssen zwei verschiedene Versionen von Links erstellt werden. Definieren Sie zunächst die Hilfsmethode conversation_header_partial_path im NavigationHelper

    Schreiben Sie Spezifikationen dafür:

    Natürlich haben wir noch nichts mit Gruppengesprächen gemacht. Sie müssen den Teil der Gruppenkonversation für eine Weile in den Spezifikationen auskommentieren, um Fehler zu vermeiden.

    Erstellen Sie eine Datei für die Links privater Konversationen:

    Definieren Sie die Hilfsmethode private_conv_seen_status in einem neuen Shared :: ConversationsHelper

    Fügen Sie dieses Modul dem Private :: ConversationsHelper hinzu

    include Shared :: ConversationsHelper

    Erstellen Sie in den Spezifikationen ein freigegebenes Verzeichnis mit einer Datei conversations_helper_spec.rbfile, um die Hilfsmethode private_conv_seen_status zu testen.

    Wenn Sie auf einen Link zu einer Unterhaltung klicken, wird die offene Aktion des Private :: Conversation-Controllers aufgerufen. Definieren Sie eine Route zu dieser Aktion. Fügen Sie in der Datei routes.rb einen Beitrag hinzu: open member in den namenspaced privateconversationsresources, direkt unter dem Beitrag: close.

    Vergessen Sie natürlich nicht, die Aktion selbst im Controller zu definieren:

    Nun sollte sich ein Konversationsfenster öffnen, wenn Sie auf den entsprechenden Link klicken. Die Navigationsleiste ist momentan chaotisch, wir müssen uns um ihr Design kümmern. Fügen Sie der Datei navigation.scss CSS hinzu, um die Dropdown-Menüs zu formatieren.

    Aktualisieren Sie die Medienabfrage max-width: 767px in der Datei mobile.scss

    Aktualisieren Sie die Medienabfrage "Min-Width: 767px" in desktop.scss

    Die App sieht jetzt so aus

    Dann können Sie die Konversationsliste erweitern

    Wenn Sie auf einen der Menü-Links klicken, sollte ein Konversationsfenster in der App angezeigt werden

    Wenn Sie versuchen, die Größe des Browsers zu verringern, sollten die Konversationen nacheinander ausgeblendet werden

    Beachten Sie auch, dass anstelle des Collabfield-Logos jetzt das Symbol für die Startseite angezeigt wird. Die Konversationsliste ist weiterhin auf kleineren Bildschirmen verfügbar. Wenn die Fenster von Konversationen auf kleineren Geräten ausgeblendet sind, wie werden Benutzer dann auf Mobilgeräten kommunizieren? Wir erstellen einen Messenger, der anstelle eines Konversationsfensters geöffnet wird.

    Übernehmen Sie die Änderungen

    git add -A
    git commit -m "Rendert ein Dropdown-Menü mit Unterhaltungslinks
    - Teilen Sie den Inhalt der Datei layouts / navigation / _header.html.erb in Teilbereiche auf
    - Erstellen Sie eine _toggle_button.erb.html in layouts / navigation / header
    - Erstellen Sie eine _home_button.html.erb in layouts / navigation / header
    - Definieren Sie ein nav_header_content_partials in NavigationHelper
      und schreiben Sie Spezifikationen dafür
    - Erstellen Sie eine _dropdowns.html.erb in layouts / navigation / header
    - Erstellen Sie eine _conversation.html.erb im Inneren
      Layouts / Navigation / Header / Dropdowns
    - Definieren Sie einen conversation_header_partial_path in NavigationHelper
      und schreiben Sie Spezifikationen dafür
    - Erstellen Sie eine _private.html.erb innerhalb
      Layouts / Navigation / Header / Dropdowns / Gespräche
    - Definieren Sie einen privaten_Conv_Seen_Status
      Shared :: ConversationsHelfen Sie und schreiben Sie Spezifikationen dafür
    - Definieren Sie eine offene Aktion im Private :: Conversations-Controller
    - CSS hinzufügen, um Dropdown-Menüs in der Navigationsleiste zu formatieren.
      Innerhalb von navigation.scss, mobile.scss und desktop.scss "

    Es ist eine gute Zeit, um sicherzustellen, dass alle Funktionen des Echtzeit-Messaging ordnungsgemäß funktionieren.

    Da wir dem DOM Elemente dynamisch hinzufügen, werden Elemente manchmal zu spät hinzugefügt, und Capybara geht davon aus, dass kein Element vorhanden ist, da die Wartezeit standardmäßig nur 2 Sekunden beträgt. Um diese Fehler zu vermeiden, ändern Sie die Wartezeit in der Datei rails_helper.rb zwischen 5 und 10 Sekunden.

    Erstellen Sie im Ordner spec / features / private / conversations eine Datei window_spec.rb.

    Hier habe ich keine Spezifikationen definiert, um zu testen, ob ein Empfängerbenutzer Nachrichten in Echtzeit empfängt. Versuchen Sie herauszufinden, wie Sie solche Tests selbst schreiben können.

    Übernehmen Sie die Änderungen

    git add -A
    git commit -m "Fügen Sie Spezifikationen hinzu, um die Funktionalität des Konversationsfensters zu testen."

    Wenn Sie sich in einem Konto angemeldet haben, in dem Nachrichten eingegangen sind, wird eine als unsichtbar gekennzeichnete Konversation angezeigt

    Im Moment gibt es keine Möglichkeit, Konversationen als gesehen zu markieren. Standardmäßig hat eine neue Nachricht einen unsichtbaren Wert. Programmieren Sie die App so, dass beim Öffnen oder Klicken eines Konversationsfensters dessen Nachrichten als gesehen markiert werden. Beachten Sie außerdem, dass derzeit nur hervorgehobene, unsichtbare Konversationen angezeigt werden, wenn das Dropdown-Menü erweitert wird. In Zukunft werden wir eine Benachrichtigungsfunktion erstellen, damit Benutzer wissen, dass sie neue Nachrichten erhalten haben, ohne etwas zu erweitern.

    Lassen Sie uns das erste Problem angehen. Wenn in der App bereits eine Konversation gerendert, diese jedoch ausgeblendet ist und ein Benutzer auf den Link des Dropdown-Menüs klickt, um diese Konversation zu öffnen, geschieht nichts. Das zusammengebrochene Gespräch bleibt zusammengebrochen. Wir müssen JavaScript hinzufügen. Wenn Sie also auf den Link im Dropdown-Menü klicken, sollte sich die Konversation ausdehnen und den neuen Nachrichtenbereich fokussieren.

    Öffnen Sie die folgende Datei und fügen Sie den Code aus dem Gist hinzu, um dies zu erreichen.

    assets / javascripts / conversations / toggle_window.js

    Wenn Sie auf einen Link klicken, um ein Konversationsfenster zu öffnen, unabhängig davon, ob bereits eine Konversation in der App vorhanden ist oder nicht, wird diese erweitert.

    Jetzt brauchen wir einen Eventhandler. Nachdem auf ein Konversationsfenster geklickt wurde, in dem noch keine Nachrichten angezeigt wurden, sollte der private Konversationsclient eine Rückruffunktion auslösen. Definieren Sie zunächst einen Ereignishandler auf der Seite des Clients für private Konversationen am Ende der Datei

    In diesem Codeausschnitt ist bereits ein Fall der Existenz eines Boten enthalten.

    Definieren Sie dann die Rückruffunktion in der Instanz private_conversation direkt unter der Funktion send_message

    Definieren Sie schließlich diese Methode auf der Serverseite

    Nachdem ein Benutzer auf einen Link geklickt hat, um ein Konversationsfenster zu öffnen, oder direkt auf ein Konversationsfenster geklickt hat, werden die nicht angezeigten Nachrichten als gesehen markiert.

    Übernehmen Sie die Änderungen

    git add -A
    git commit -m "Fügt die Fähigkeit hinzu, unsichtbare Nachrichten als gesehen zu markieren
    - Fügen Sie einen Ereignishandler hinzu, um die Konversationsfenster im zu erweitern
      assets / javascripts / conversations / toggle_window.js
    - Fügen Sie eine Ereignisbehandlungsroutine hinzu, um unsichtbare Nachrichten als innerhalb von angezeigt zu markieren
      assets / javascripts / channels / privat / conversation.js
    - Definiere eine set_as_seen Methode für Private :: ConversationChannel "

    Stellen Sie sicher, dass alles so funktioniert, wie wir es erwarten, indem Sie die Spezifikationen schreiben.

    Kontakte

    Um mit Menschen in Kontakt zu bleiben, die Sie in der App kennengelernt haben, müssen Sie sie zu Kontakten hinzufügen können. Diese Funktionalität fehlt uns derzeit. Das Vorhandensein einer Kontaktfunktion eröffnet viele Möglichkeiten, andere Funktionen zu erstellen, die nur Benutzer ausführen können, die als Kontakt akzeptiert werden.

    Generieren Sie ein Kontaktmodell

    Schienen g Modellkontakt

    Definieren Sie Verknüpfungen, Validierungen und Methoden zum Suchen von Kontaktdatensätzen, indem Sie die IDs der Benutzer angeben.

    Definieren Sie die Kontakttabelle

    Eine Fabrik für Kontakte wird benötigt. Definiere es:

    Schreiben Sie Spezifikationen, um das Modell zu testen

    Übernehmen Sie die Änderungen

    git add -A
    git commit -m "Ein Kontaktmodell erstellen und Spezifikationen dafür schreiben"

    In der Datei des Benutzermodells müssen wir geeignete Zuordnungen definieren und einige Methoden definieren, die bei Kontaktabfragen helfen.

    Decken Sie Assoziationen und Methoden mit Spezifikationen ab

    Übernehmen Sie die Änderungen

    git add -A
    git commit -m "Fügt dem Benutzermodell Assoziationen und Hilfsmethoden hinzu
    - Erstellen Sie eine Beziehung zwischen dem Benutzer und den Kontaktmodellen
    - Methoden helfen beim Abfragen der Kontaktdatensätze "

    Generieren Sie einen Kontakte-Controller und definieren Sie dessen Aktionen

    schienen g reglerkontakte

    Wie Sie sehen, können Benutzer einen neuen Kontaktdatensatz erstellen, seinen Status aktualisieren (einen Benutzer für ihre Kontakte akzeptieren) und einen Benutzer aus ihrer Kontaktliste entfernen. Da alle Aktionen über AJAX aufgerufen werden und keine Vorlagen als Antwort gerendert werden sollen, antworten wir mit einer Erfolgsantwort. Auf diese Weise muss Rails nicht überlegen, mit was sie reagieren soll.

    Definieren Sie die entsprechenden Routen:

    Übernehmen Sie die Änderungen.

    git add -A
    git commit -m "Erstelle einen ContactsController und definiere Routen zu seinen Aktionen"

    Aktualisierung des Fensters für private Konversationen

    Die Art und Weise, wie Benutzer Kontaktanfragen senden und annehmen können, erfolgt über das Fenster eines privaten Gesprächs. Später werden wir eine zusätzliche Möglichkeit hinzufügen, um Anfragen über das Dropdown-Menü einer Navigationsleiste anzunehmen.

    Erstellen Sie ein neues Überschriftenverzeichnis

    privat / Gespräche / Gespräch / Überschrift

    Hier behalten wir zusätzliche Optionen für das Fenster eines privaten Gesprächs. Erstellen Sie im Verzeichnis eine Datei _add_user_to_contacts.html.erb

    Rendern Sie am Ende der Datei _heading.html.erb die Option, den anderen Benutzer der Konversation zu den Kontakten hinzuzufügen:

    Definieren Sie die Hilfsmethode und zusätzliche Methoden in einem privaten Bereich

    Schreiben Sie Spezifikationen für diese Hilfsmethoden

    Die instance_eval-Methode wird zum Testen von Methoden in einem privaten Bereich verwendet.

    Da Optionen im Überschriftenelement des Konversationsfensters angezeigt werden, müssen wir sicherstellen, dass zusätzliche Optionen perfekt in die Überschrift passen. Ersetzen Sie in der Datei _heading.html.erb die Konversationsüberschrift
    Klasse mit <% = conv_heading_class (@contact)%>, um zu bestimmen, welche Klasse hinzugefügt werden soll.

    Definieren Sie die Hilfsmethode

    Schreiben Sie Spezifikationen für die Methode

    Die Optionen zum Senden oder Akzeptieren einer Kontaktanfrage werden noch nicht angezeigt. Weitere Elemente müssen hinzugefügt werden. Öffnen Sie die Datei _conversation.html.erb

    private / conversations / _conversation.html.erb

    Definieren Sie oben in der Datei eine @contact-Instanzvariable, damit sie für alle Teilbereiche zugänglich ist

    Definieren Sie die Hilfsmethode get_contact_record

    Decken Sie die Methode mit Angaben

    Bisher verwendeten wir die Methoden current_user und recipient let nur im Kontext eines privaten Bereichs. Jetzt müssen wir auf private und öffentliche Weise darauf zugreifen können. Schneiden Sie sie aus und platzieren Sie sie außerhalb des Kontexts des privaten Bereichs.

    Rendern Sie oben im Element .panel-body eine Teildatei, in der ein zusätzliches Nachrichtenfenster zum Akzeptieren oder Ablehnen einer Kontaktanfrage angezeigt wird

    Erstellen Sie die _request_status.html.erb-Datei

    Definieren Sie die benötigten Hilfsmethoden

    Schreibt Spezifikationen für die Hilfsmethoden

    Erstellen Sie das request_status-Verzeichnis und erstellen Sie dann _send_request.html.erb-, _sent_by_current_user.html.erb- und _sent_by_recipient.html.erb-Teildateien

    Übernehmen Sie die Änderungen

    git add -A
    git commit -m "Fügt eine Schaltfläche im Fenster der privaten Konversation hinzu
    Empfänger zu Kontakten hinzufügen "

    Implementieren Sie Designänderungen und kümmern Sie sich um Stilprobleme, die aufgrund zusätzlicher Elemente im Konversationsfenster auftreten. Fügen Sie der Datei conversation_window.scss CSS hinzu

    Übernehmen Sie die Änderungen

    git add -A
    git commit -m "CSS zu conversation_window.scss hinzufügen, um Optionsfelder zu formatieren"

    Wenn ein Konversationsfenster ausgeblendet ist, sollten keine Optionen angezeigt werden. Es ist praktischer, Optionen nur dann anzuzeigen, wenn ein Konversationsfenster erweitert wird. Fügen Sie dazu in der Umschaltfunktion der Datei toggle_window.js direkt unter der Variablen messages_visible Folgendes hinzu

    Jetzt sieht das reduzierte Fenster so aus, es hat keine sichtbaren Optionen

    Das erweiterte Fenster bietet die Option, einen Benutzer zu Kontakten hinzuzufügen. Es gibt auch eine Meldung, die dies vorschlägt

    Sie können eine Kontaktanfrage jetzt senden und annehmen, indem Sie auf ein Symbol in der Kopfzeile der Konversation oder auf den Link Zu Kontakten hinzufügen klicken. Derzeit gibt es keine Antwort, nachdem Sie auf diese Links und Schaltflächen geklickt haben. Wir werden etwas später ein Feedback- und Echtzeit-Benachrichtigungssystem hinzufügen. Technisch gesehen können Sie Ihren Kontakten jedoch Benutzer hinzufügen. Dies ist jedoch noch nicht besonders benutzerfreundlich.

    Nachdem Sie eine Kontaktanfrage gesendet haben, sieht die Seite des anderen Benutzers folgendermaßen aus

    Übernehmen Sie die Änderungen

    git add -A
    git commit -m "Füge JS in die toggle_window.js ein, um zusätzliche Optionen anzuzeigen und auszublenden."

    Derzeit können Benutzer privat sprechen und Einzelgespräche führen. Da es in der App um die Zusammenarbeit geht, wäre es logisch, auch Gruppengespräche zu führen.

    Beginnen Sie mit der Generierung eines neuen Modells

    Schienen g Modellgruppe / Gespräch

    Mehrere Benutzer können an einer Unterhaltung teilnehmen. Definieren Sie Assoziationen und die Datenbanktabelle

    Anhand einer Join-Tabelle wird nachverfolgt, wer zu welcher Gruppenkonversation gehört

    Generieren Sie dann ein Modell für Nachrichten

    Schienen g Modellgruppe / Meldung

    Wir speichern Benutzer-IDs, die eine Nachricht gesehen haben, in einem Array. Zum Erstellen und Verwalten von Objekten, z. B. eines Arrays, in einer Datenbankspalte wird eine Serialisierungsmethode verwendet. Ein Standardbereich, um die Anzahl der Abfragen zu minimieren, und einige Überprüfungen werden hinzugefügt.

    Die Art und Weise, wie wir Gruppengespräche aufbauen, ähnelt der von Privatgesprächen. Tatsächlich werden Styling und einige Teile zwischen beiden Arten von Gesprächen gemeinsam sein.

    Schreiben Sie Spezifikationen für die Modelle. Außerdem wird eine Factory für Gruppennachrichten benötigt

    Definieren Sie die Migrationsdateien

    Die Grundlagen des Gruppengesprächs werden festgelegt.

    Übernehmen Sie die Änderungen

    git add -A
    git commit -m "Erstelle Group :: Conversation- und Group :: Message-Modelle
    - Assoziationen definieren
    - Spezifikationen schreiben "

    Erstellen Sie eine Gruppenkonversation

    Wie bereits erwähnt, wird der Vorgang zum Erstellen der Gruppenkonversationsfunktion dem Vorgang für die private Konversation ähneln. Erstellen Sie zunächst einen Controller und eine grundlegende Benutzeroberfläche.

    Generieren Sie einen Controller mit Namespace

    schienen g controller gruppe / gespräche

    Definieren Sie im Controller eine Erstellungsaktion und add_to_conversations, die bereits hinzugefügt wurden. und create_group_conversation-Methoden in einem privaten Bereich

    Das Erstellen einer neuen Gruppenkonversation ist etwas komplexer. Daher extrahieren wir sie in ein Serviceobjekt. Dann haben wir add_to_conversations und bereits hinzugefügt? private Methoden. Wenn Sie sich erinnern, haben wir sie auch im Private :: ConversationsController, aber dieses Mal werden die IDs der Gruppenkonversationen in der Sitzung gespeichert.

    Definieren Sie nun den Group :: NewConversationService in einem neuen Gruppenverzeichnis

    Die Art und Weise, wie eine neue Gruppenkonversation erstellt wird, ist eigentlich eine private Konversation. Wir werden diese Schnittstelle in Kürze als Option im Fenster der privaten Konversation erstellen. Stellen Sie zuvor sicher, dass das Serviceobjekt ordnungsgemäß funktioniert, indem Sie es mit Spezifikationen abdecken. Erstellen Sie innerhalb der Services eine neue Verzeichnisgruppe mit einer Datei new_conversation_service_spec.rb

    Übernehmen Sie die Änderungen

    git add -A
    git commit -m "Backend zum Erstellen einer neuen Gruppenkonversation erstellen
    - Erstellen Sie einen Group :: ConversationsController
      Definieren Sie eine Erstellungsaktion und add_to_conversations.
      create_group_conversation and already_added? Private Methoden im Inneren
    - Erstelle einen Group :: NewConversationService und schreibe Spezifikationen dafür "

    Definieren Sie Routen für die Gruppenkonversation und ihre Nachrichten

    Übernehmen Sie die Änderungen

    git add -A
    git commit -m "Angaben für Group :: Conversations and Messages definieren"

    Derzeit kümmern wir uns nur um private Gespräche im ApplicationController. Es werden nur private Konversationen bestellt und nur ihre IDs sind in der App verfügbar, nachdem ein Benutzer sie geöffnet hat. Aktualisieren Sie im ApplicationController die Methode opens_conversations_windows

    Da die Bestellung von Konversationen mithilfe des OrderConversationsService erfolgt, müssen wir diesen Service aktualisieren

    Bisher hatten wir nur das Array "Private Konversationen" und haben es nach dem Erstellungsdatum der neuesten Nachrichten sortiert. Jetzt haben wir private und Gruppen-Konversations-Arrays, dann fügen wir sie zu einem Array zusammen und sortieren sie auf die gleiche Weise wie zuvor.

    Aktualisieren Sie auch die technischen Daten

    Übernehmen Sie die Änderungen

    git add -A
    git commit -m "Daten für Gruppenkonversationen in ApplicationController abrufen
    - Aktualisieren Sie die Methode opens_conversations_windows
    - Aktualisieren Sie den OrderConversationsService "

    Gleich müssen wir einige Daten von einem Controller an JavaScript übergeben. Zum Glück haben wir das Gon-Juwel bereits installiert, was uns das leicht macht. Fügen Sie im ApplicationController im privaten Bereich hinzu

    Verwenden Sie den before_action-Filter, um diese Methode aufzurufen

    before_action: set_user_data

    Übernehmen Sie die Änderungen

    git add -A
    git commit -m "Definiere eine private Methode set_user_data in ApplicationController"

    Technisch können wir jetzt eine neue Gruppenkonversation erstellen, aber die Benutzer haben keine Schnittstelle, um dies zu tun. Wie bereits erwähnt, werden sie dies in einem privaten Gespräch tun. Lassen Sie uns diese Option im Fenster der privaten Konversation erstellen.

    In der

    Ansichten / privat / Gespräche / Gespräch / Überschrift

    Verzeichnis eine neue Datei erstellen

    Eine collection_select-Methode wird verwendet, um eine Liste von Benutzern anzuzeigen. Nur Benutzer in Kontakten werden in die Liste aufgenommen. Definieren Sie die Hilfsmethode contacts_except_recipient

    Schreiben Sie Spezifikationen für die Methode

    Rendern Sie den Teil unten in der Datei _heading.html.erb

    Definieren Sie die Hilfsmethode

    Wickeln Sie es mit Angaben

    Übernehmen Sie die Änderungen.

    git add -A
    git commit -m "Eine Benutzeroberfläche für private Konversationen hinzufügen, um Gruppenkonversationen zu erstellen."

    Fügen Sie CSS hinzu, um die Komponente zu formatieren, mit der eine neue Gruppenkonversation erstellt werden kann

    Eine Auswahl von Kontakten ist standardmäßig ausgeblendet. Um die Auswahl zu öffnen, muss ein Benutzer auf die Schaltfläche klicken. Die Schaltfläche ist noch nicht interaktiv. Erstellen Sie eine options.js-Datei mit JavaScript, um die Auswahlliste umschaltbar zu machen.

    So sieht nun ein Konversationsfenster mit einem Empfänger aus, der ein Kontakt ist

    Es gibt eine Schaltfläche, die eine Liste von Kontakten öffnet, mit denen Sie eine Gruppenunterhaltung erstellen können, wenn Sie darauf klicken

    Übernehmen Sie die Änderungen.

    git add -A
    git commit -m "
    - Beschreiben Sie den Stil für die Option zum Erstellen einer Gruppenkonversation
    - Option umschaltbar machen "

    Wir haben eine Liste der geordneten Konversationen, einschließlich der Gruppenkonversationen, die im Dropdown-Menü der Navigationsleiste angezeigt werden. Wenn Sie sich erinnern, haben wir unterschiedliche Partials für verschiedene Arten von Gesprächen angegeben. Wenn die App versucht, einen Link zu rendern, um eine Gruppenkonversation zu öffnen, sucht sie nach einer anderen Datei als nach einer privaten Konversation. Die Datei wurde noch nicht erstellt.

    Erstellen Sie eine _group.html.erb-Datei

    Definieren Sie die Hilfsmethode group_conv_seen_status im Shared :: ConversationsHelper

    Schreiben Sie Spezifikationen für die Methode

    Übernehmen Sie die Änderungen.

    git add -A
    git commit -m "Erstellt einen Link in der Navigationsleiste, um eine Gruppenkonversation zu eröffnen."

    Übertragen Sie die Fenster von Gruppengesprächen in der App auf dieselbe Weise wie die privaten Gespräche. Fügen Sie in der Datei application.html.erb direkt unter den gerenderten privaten Konversationen Folgendes hinzu:

    Erstellen Sie die Teildatei, um die Fenster von Gruppenkonversationen nacheinander zu rendern:

    Übernehmen Sie die Änderung.

    git add -A
    git commit -m "Rendert die Fenster von Gruppengesprächen im
    application.html.erb "

    Wir haben einen Mechanismus, wie Gruppengespräche in der App erstellt und gerendert werden. Lassen Sie uns nun ein eigenes Konversationsfenster erstellen.

    Erstellen Sie im Verzeichnis group / conversations eine _conversation.html.erb-Datei.

    Definieren Sie die Hilfsmethode add_people_to_group_conv_list:

    Schreiben Sie Spezifikationen für den Helfer:

    Genau wie bei privaten Konversationen werden Gruppenkonversationen über die gesamte App zugänglich sein. Daher benötigen wir natürlich auch überall Zugriff auf die Group :: ConversationsHelper-Methoden. Fügen Sie dieses Modul in den ApplicationHelper ein

    include Group :: ConversationsHelper

    Übernehmen Sie die Änderungen.

    git add -A
    git commit -m "
    - Erstellen Sie eine _conversation.html.erb innerhalb der Gruppe / Konversationen
    - Definiere eine add_people_to_group_conv_list und schreibe Spezifikationen dafür "

    Erstellen Sie ein neues Konversationsverzeichnis mit einer _heading.html.erb-Datei in:

    Übernehmen Sie die Änderung.

    git add -A
    git commit -m "Erstelle eine _heading.html.erb in der
    Gruppe / Gespräche / Gespräch "

    Als nächstes haben wir _select_user.html.erb und _messages_list.html.erb Teildateien. Erstelle sie:

    Definieren Sie die Hilfsmethode load_group_messages_partial_path:

    Wickeln Sie es mit Angaben:

    Übernehmen Sie die Änderungen.

    git add -A
    git commit -m "
    - Erstellen Sie _select_user.html.erb und _messages_list.html.erb im Inneren
      Gruppe / Gespräche / Unterhaltung
    - Definieren Sie eine Hilfsmethode load_group_messages_partial_path
      und Spezifikationen dafür schreiben "

    Erstellen Sie eine _link_to_previous_messages.html.erb-Datei, um einen Link zum Laden vorheriger Nachrichten zu erhalten:

    Übernehmen Sie die Änderung.

    git add -A
    git commit -m "Erstelle eine _load_messages.html.erb in der
    group / conversations / conversation / messages_list "

    Erstellen Sie ein neues Nachrichtenformular

    Übernehmen Sie die Änderung.

    git add -A
    git commit -m "Erstelle eine _neue_Nachricht_Form.html.erb in der
    Gruppe / Gespräche / Gespräch / "

    Die Anwendung kann jetzt auch die Fenster von Gruppenkonversationen rendern.

    Sie sind jedoch noch nicht funktionsfähig. Zuerst müssen wir Nachrichten laden. Wir brauchen einen Controller für Nachrichten und Ansichten. Generieren Sie einen Nachrichten-Controller:

    Schienen g Controller-Gruppe / Nachrichten

    Beziehen Sie das Modul Nachrichten von Bedenken ein und definieren Sie eine Indexaktion:

    Übernehmen Sie die Änderungen.

    git add -A
    git commit -m "Erstelle einen Group :: MessagesController und definiere eine Indexaktion"

    Erstellen Sie eine _load_more_messages.js.erb

    Die Hilfsmethoden append_previous_messages_partial_path und remove_link_to_messages haben wir bereits definiert. Wir müssen nur die Hilfsmethode replace_link_to_group_messages_partial_path definieren

    Auch diese Methode wird, genau wie auf der privaten Seite, „intelligenter“, sobald wir den Messenger entwickelt haben.

    Erstellen Sie den _replace_link_to_messages.js.erb

    Fügen Sie auch den Group :: MessagesHelper zum ApplicationHelper hinzu

    include Group :: MessagesHelper

    Übernehmen Sie die Änderungen.

    git add -A
    git commit -m "Erstelle eine _load_more_messages.js.erb innerhalb der Gruppe / messages"

    Die einzige Möglichkeit, Gruppengespräche jetzt zu eröffnen, besteht darin, sie zu initialisieren. Offensichtlich ist dies keine aufregende Sache, denn sobald Sie die Sitzung zerstört haben, gibt es keine Möglichkeit, dasselbe Gespräch erneut zu eröffnen. Erstellen Sie eine Openaction innerhalb des Controllers.

    Erstellen Sie die partielle Datei _open.js.erb:

    Jetzt können wir Konversationen öffnen, indem wir auf die Dropdown-Menü-Links der Navigationsleiste klicken. Versuchen Sie, es mit den Funktionsspezifikationen selbst zu testen.

    Übernehmen Sie die Änderungen.

    git add -A
    git commit -m "Fügt die Fähigkeit hinzu, Gruppengespräche zu öffnen
    - Erstellen Sie eine offene Aktion im Group :: ConversationsController
    - Erstelle eine _open.js.erb innerhalb der Gruppe / Unterhaltungen "

    Die App versucht, Nachrichten zu rendern, hat jedoch keine Vorlagen für diese erstellt. Erstellen Sie eine _message.html.erb

    Definieren Sie die Hilfsmethoden group_message_date_check_partial_path, group_message_seen_by und message_content_partial_path.

    Die group_message_seen_by-Methode gibt eine Liste der Benutzer zurück, die eine Nachricht gesehen haben. Mit diesen wenigen Informationen können wir zusätzliche Funktionen erstellen, z. B. die Anzeige für Konversationsteilnehmer, die Nachrichten usw. gesehen haben. In unserem Fall verwenden wir diese Informationen jedoch, um festzustellen, ob ein aktueller Benutzer eine Nachricht gesehen hat oder nicht. Wenn nicht, wird die Nachricht als gesehen markiert, nachdem der Benutzer sie gesehen hat.

    Außerdem benötigen wir Hilfsmethoden aus dem Shared-Modul. Fügen Sie in dem Group :: MessagesHelper das Modul hinzu.

    erfordern 'shared / messages_helper'
    include Shared :: MessagesHelper

    Wrap-Helfer-Methoden mit Angaben:

    Übernehmen Sie die Änderungen.

    git add -A
    git commit -m "Erstelle eine _message.html.erb innerhalb von group / messages
    - Definiere group_message_date_check_partial_path,
      group_message_seen_by und message_content_partial_path helper
      Methoden und schreiben Spezifikationen für sie "

    Erstellen Sie Teildateien für die Nachricht:

    Übernehmen Sie die Änderungen.

    git add -A
    git commit -m "Erstelle _neues_Datum.html.erb,
    _different_user_content.html.erb und _same_user_content.html.erb
    innerhalb der Gruppe / messages / message / "

    Jetzt brauchen wir einen Mechanismus, der Nachrichten nacheinander rendert. Erstellen Sie eine _messages.html.erb-Teildatei:

    Übernehmen Sie die Änderung.

    git add -A
    git commit -m "Erstelle _messages.html.erb innerhalb von group / conversations"

    Hinzufügen eines Stils für Gruppennachrichten:

    Übernehmen Sie die Änderung.

    git add -A
    git commit -m "CSS für Gruppennachrichten in conversation_window.scss hinzufügen"

    Machen Sie die Schließen-Schaltfläche funktionsfähig, indem Sie eine Schließen-Aktion im Group :: ConversationsController definieren

    Erstellen Sie die entsprechende Vorlagendatei:

    Übernehmen Sie die Änderungen.

    git add -A
    git commit -m "Fügt die Funktionalität eines Fensters zum Schließen von Gruppenkonversationen hinzu
    - Definieren Sie eine Abschlussaktion im Group :: ConversationsController
    - Erstelle eine close.js.erb innerhalb der Gruppe / Unterhaltungen "

    In Echtzeit kommunizieren

    Genau wie bei privaten Gesprächen möchten wir in der Lage sein, Gespräche mit mehreren Benutzern in Echtzeit am selben Fenster zu führen. Der Prozess, um diese Funktion zu erreichen, wird ziemlich ähnlich sein wie bei privaten Gesprächen.

    Generieren Sie einen neuen Kanal für Gruppengespräche

    Schienen g Kanalgruppe / Konversation

    Diesmal prüfen wir vor dem Verbindungsaufbau, ob ein Benutzer zu einer Konversation gehört, mit der Methode belong_to_conversation. In privaten Gesprächen haben wir von einem eindeutigen Kanal gestreamt, indem wir die ID des aktuellen Benutzers angegeben haben. Bei Gruppengesprächen wird von der Clientseite eine ID eines Gesprächs übergeben. Mit der Methode "belong_to_conversation" überprüfen wir, ob Benutzer keine Manipulationen vorgenommen und keine Verbindung zu einem Kanal hergestellt haben, zu dem sie nicht gehören.

    Übernehmen Sie die Änderung

    git add -A
    git commit -m "Eine Gruppe erstellen :: ConversationChannel"

    Erstellen Sie die Group :: MessageBroadcastJob

    Schienen g job group / message_broadcast

    Übernehmen Sie die Änderung.

    git add -A
    git commit -m "Eine Gruppe erstellen :: MessageBrodcastJob"

    Das letzte fehlende Puzzleteil - die Client-Seite:

    Im Wesentlichen ist es der .js-Datei der privaten Konversation sehr ähnlich. Das Layout des Codes ist etwas anders. Der Hauptunterschied besteht in der Möglichkeit, die ID der Konversation an einen Kanal und eine Schleife oben in der Datei zu übergeben. Mit dieser Schleife verbinden wir einen Benutzer mit allen Kanälen seiner Gruppengespräche. Aus diesem Grund haben wir auf der Serverseite die Methode belong_to_conversation verwendet. Die IDs der Konversationen werden vom Kunden weitergeleitet. Diese Methode auf der Serverseite stellt sicher, dass ein Benutzer wirklich zu einer bereitgestellten Konversation gehört.

    Wenn Sie darüber nachdenken, hätten wir diese Schleife auch auf der Serverseite erstellen können und müssten uns nicht um den gesamten Bestätigungsprozess kümmern. Hier ist jedoch ein Grund, warum wir eine ID eines Gesprächs von der Clientseite weitergeben. Wenn neue Benutzer zu einer Gruppenkonversation hinzugefügt werden, möchten wir sie sofort mit dem Kanal der Konversation verbinden, ohne dass eine Seite neu geladen werden muss. Die ID des passablen Gesprächs ermöglicht es uns, dies mühelos zu erreichen. Im nächsten Abschnitt erstellen wir einen eindeutigen Kanal für jeden Benutzer, um Benachrichtigungen in Echtzeit zu erhalten. Wenn neue Benutzer zu einer Gruppenkonversation hinzugefügt werden, rufen wir die Funktion subToGroupConversationChannel über ihre eindeutigen Benachrichtigungskanäle auf und verbinden sie mit dem Gruppenkonversationskanal. Wenn wir die ID einer Konversation nicht an einen Kanal übergeben könnten, wären Verbindungen zu neuen Kanälen erst nach einem Seiten-Reload aufgetreten. Es gibt keine Möglichkeit, neue Benutzer dynamisch mit einem Konversationskanal zu verbinden.

    Jetzt können wir Gruppennachrichten in Echtzeit senden und empfangen. Versuchen Sie, die Gesamtfunktionalität anhand eigener Spezifikationen zu testen.

    Übernehmen Sie die Änderungen.

    git add -A
    git commit -m "Erstellt eine conversation.js in der
    Assets / Javascripts / Channels / Gruppe "

    Definieren Sie im Group :: ConversationsController eine Aktualisierungsaktion

    Erstellen Sie den Group :: AddUserToConversationService, der dafür sorgt, dass ein ausgewählter Benutzer zu einer Konversation hinzugefügt wird

    Testen Sie den Service mit Spezifikationen:

    Wir führen gerade private und Gruppengespräche. Es fehlen noch ein paar Nuancen, die wir später implementieren werden, aber die Kernfunktionalität ist hier. Benutzer können einzeln kommunizieren oder bei Bedarf einen gesamten Chatroom mit mehreren Personen erstellen.

    Übernehmen Sie die Änderungen.

    git add -A
    git commit -m "Erstelle eine Gruppe :: AddUserToConversationService und teste es"

    Bote

    Was ist der Zweck eines Boten? Auf mobilen Bildschirmen lädt die App den Messenger, anstatt ein Gesprächsfenster zu öffnen. Auf größeren Bildschirmen können Benutzer wählen, wo sie chatten möchten, im Konversationsfenster oder im Messenger. Wenn der Messenger das gesamte Browserfenster ausfüllt, sollte die Kommunikation angenehmer sein.

    Da wir dieselben Daten und Modelle verwenden, müssen wir nur Gespräche in einer anderen Umgebung eröffnen. Generieren Sie einen neuen Controller, um Anforderungen zum Öffnen einer Konversation im Messenger zu verarbeiten.

    Schienen g Controller Messenger

    Mit den Aktionen get_private_conversation und get_group_conversation wird die ausgewählte Konversation eines Benutzers abgerufen. Mit den Vorlagen dieser Aktionen wird eine ausgewählte Konversation an den Platzhalter für die Konversation angehängt. Jedes Mal, wenn eine neue Konversation zum Öffnen ausgewählt wird, wird die alte entfernt und durch eine neu ausgewählte ersetzt.

    Routen für die Aktionen definieren:

    Übernehmen Sie die Änderungen.

    git add -A
    git commit -m "Erstelle einen MessengersController und definiere Routen zu seinen Aktionen"

    In der Steuerung befindet sich eine open_messenger-Aktion. Mit dieser Aktion können Sie von einer beliebigen Seite direkt zum Messenger wechseln und eine ausgewählte Konversation wiedergeben. Auf kleineren Bildschirmen chatten Benutzer über Messenger und nicht über Konversationsfenster. In Kürze wechseln wir die Links für kleinere Bildschirme, um Konversationen im Messenger zu eröffnen.

    Erstellen Sie eine Vorlage für die Aktion open_messenger

    git add -A
    git commit -m "Erstelle eine open_messenger.html.erb in den / messengers"

    Dann sehen wir ConversationForMessengerSerivce, das das Objekt einer ausgewählten Konversation abruft. Erstellen Sie den Service:

    Spezifikationen für den Service hinzufügen:

    Übernehmen Sie die Änderungen.

    git add -A
    git commit -m "ConversationForMessengerSerivce erstellen und Spezifikationen hinzufügen"

    Erstellen Sie eine Vorlage für die Indexaktion:

    Dies wird der Bote selbst sein. Im Messenger sehen wir eine Liste der Benutzergespräche und eines ausgewählten Gesprächs. Erstellen Sie die Teildateien:

    Definieren Sie die Hilfsmethode:

    Versuchen Sie es mit den Spezifikationen selbst zu testen.

    Erstellen Sie die Teildateien für Links, um Konversationen zu öffnen:

    Erstellen Sie nun einen Teil für den Konversationsraum. Ausgewählte Konversationen werden dort gerendert:

    Übernehmen Sie die Änderungen.

    git add -A
    git commit -m "Eine Vorlage für die Indexaktion von MessengersController erstellen"

    Erstellen Sie eine Vorlage für die Aktion get_private_conversation:

    Erstellen Sie eine _private_conversation.html.erb-Datei:

    Diese Datei gibt eine private Konversation im Messenger wieder. Beachten Sie auch, dass wir einige Teilausschnitte aus den privaten Konversationsansichten wiederverwenden. Erstellen Sie den Teil _details.html.erb:

    Übernehmen Sie die Änderungen.

    git add -A
    git commit -m "Erstellt eine Vorlage für den MessengersController
    get_private_conversation action "

    Wenn wir zum Messenger gehen, ist es besser, keine Dropdown-Menüs in der Navigationsleiste zu sehen. Warum? Wir möchten keine Konversationsfenster im Messenger rendern, da dies sonst chaotisch aussehen würde. Ein Gesprächsfenster und der Messenger gleichzeitig, um mit der gleichen Person zu chatten. Das wäre ein sehr fehlerhaftes Design.

    Verbieten Sie zunächst, dass die Fenster von Konversationen auf der Messenger-Seite gerendert werden. Gar nicht so schwer. Denken Sie zur Steuerung daran, wie die Fenster von Konversationen in der App gerendert werden. Sie werden in der Datei application.html.erb gerendert. Dann haben wir Instanzvariablen @private_conversations_windowsund @group_conversations_windows. Diese Variablen sind Arrays von Gesprächen. Anstatt nur Konversationen von diesen Arrays zu rendern, definieren Sie Hilfsmethoden, um zu entscheiden, ob diese Arrays Benutzern zugewiesen werden oder nicht, je nachdem, auf welcher Seite sie sich befinden. Befinden sich Benutzer auf der Messenger-Seite, erhalten sie ein leeres Array und keine Konversationsfenster wird gerendert.

    Ersetzen Sie diese Instanzvariablen durch die Hilfsmethoden private_conversations_windows und group_conversations_windows. Definieren Sie diese nun im ApplicationHelper

    Wickeln Sie sie mit Spezifikationen

    Übernehmen Sie die Änderungen

    git add -A
    git commit -m "
    Definieren Sie private_conversations_windows und group_conversations_windows
    Hilfsmethoden innerhalb des ApplicationHelper und testen Sie sie "

    Erstellen Sie als Nächstes eine alternative Teildatei für den Header der Navigation, damit Dropdown-Menüs nicht gerendert werden. Im NavigationHelper haben wir zuvor die Hilfemethode nav_header_content_partials definiert. Hiermit wird festgelegt, welche Kopfzeile der Navigation gerendert werden soll.

    In der

    Layouts / Navigation / Header

    Verzeichnis erstellen Sie eine _messenger_header.html.erb-Datei

    Gestalte den Messenger. Erstellen Sie eine messenger.scss-Datei im Partialsdirectory

    Übernehmen Sie die Änderung

    git add -A
    git commit -m "Erstelle eine messenger.scss innerhalb der Partials"

    Fügen Sie in der Datei desktop.scss innerhalb der minimalen Breite: 767px hinzu

    Wenn wir auf eine Konversation klicken, um sie zu öffnen, möchten wir in der Lage sein, vorherige Nachrichten irgendwie zu laden. Wir könnten einen sichtbaren Link zum Laden hinzufügen. Oder wir können automatisch eine bestimmte Anzahl von Nachrichten laden, bis die Bildlaufleiste angezeigt wird, sodass ein Benutzer vorherige Nachrichten laden kann, indem er einen Bildlauf nach oben durchführt. Erstellen Sie eine Hilfsmethode, die sich darum kümmert

    Testen Sie es mit eigenen Angaben. Erstellen Sie die Teildateien

    Übernehmen Sie die Änderungen

    git add -A
    git commit -m "Definiere eine autoload_messenger_messages in der
    Shared :: MessagesHelper "

    Verwenden Sie die Hilfsmethode in der Datei _load_more_messages.js.erb direkt über <% = render remove_link_to_messages%>

    Jetzt haben wir append_previous_messages_partial_path und
    replace_link_to_private_messages_partial_path Hilfsmethoden, die wir aktualisieren sollten, um sie mit dem Messenger kompatibel zu machen

    Erstellen Sie eine fehlende Teildatei

    Aktualisieren Sie eine andere Methode

    Erstellen Sie die Teildatei

    Testen Sie die Hilfsmethoden mit eigenen Angaben.

    Übernehmen Sie die Änderungen

    git add -A
    git commit -m "
    - Aktualisieren Sie die Hilfsmethode append_previous_messages_partial_path in
      Shared :: MessagesHelper
    - Aktualisieren Sie die Methode replace_link_to_private_messages_partial_path in
      Private :: MessagesHelper "

    Nachdem Sie auf den Link zum erstmaligen Laden von Nachrichten geklickt haben, lädt die App automatisch die vorherigen Nachrichten, bis in der Nachrichtenliste eine Bildlaufleiste angezeigt wird. Fügen Sie JavaScript hinzu, damit der erste Klick ausgeführt wird:

    Wenn Sie den Pfad / messenger besuchen, sehen Sie den Messenger:

    Dann können Sie jede Ihrer Konversationen eröffnen.

    Übernehmen Sie die Änderungen.

    git add -A
    git commit -m "Erstelle eine messenger.js"

    Wenn Benutzer auf kleineren Bildschirmen auf den Link der Navigationsleiste klicken, um eine Konversation zu öffnen, sollte ihre Konversation im Messenger statt in einem Konversationsfenster geöffnet werden. Um dies zu ermöglichen, erstellen wir verschiedene Links für kleinere Bildschirme.

    Fügen Sie im Teil _private.html.erb der Navigation, in dem ein Link zum Öffnen einer privaten Unterhaltung gespeichert ist, einen zusätzlichen Link für Geräte mit kleinerem Bildschirm hinzu. Fügen Sie diesen Link direkt unter dem Link "open_private_conversation_path" in der Datei hinzu

    Auf kleineren Bildschirmen wird dieser Link anstelle des vorherigen für größere Bildschirme angezeigt. Fügen Sie einen zusätzlichen Link hinzu, um auch Gruppengespräche zu öffnen

    Der Grund, warum wir unterschiedliche Links auf unterschiedlichen Bildschirmgrößen sehen, ist, dass wir zuvor CSS für Linkklassen mit größerem Bildschirm und Linkklassen mit kleinerem Bildschirm festgelegt haben.

    Übernehmen Sie die Änderungen.

    git add -A
    git commit -m "Innerhalb von _private.html.erb und _group.html.erb im
    Layouts / Navigation / Header / Dropdowns / Unterhaltungen, Alternative hinzufügen
    Links für kleinere Geräte zum Öffnen von Gesprächen "

    Die Versionen von Messenger auf Desktop- und Mobilgeräten werden sich ein wenig unterscheiden. Schreiben Sie etwas JavaScript in die messenger.js. Nachdem ein Benutzer zum Öffnen einer Konversation geklickt hat, ermittelt js, ob eine mobile Version angezeigt wird oder nicht.

    Wenn Sie jetzt eine Unterhaltung auf einem mobilen Gerät eröffnen, sieht dies folgendermaßen aus

    Übernehmen Sie die Änderung.

    git add -A
    git commit -m "Füge JavaScript zu messenger.js hinzu, um eine andere anzuzeigen
    Messenger-Version auf mobilen Geräten "

    Machen Sie jetzt Gruppengespräche auf dem Messenger funktionsfähig. Der Großteil der Arbeit mit dem Messenger ist bereits erledigt, sodass das Einrichten von Gruppengesprächen viel einfacher wird. Wenn Sie in den MessengersController zurückblicken, haben wir die Aktion get_group_conversation. Erstellen Sie eine Vorlagendatei dafür:

    Erstellen Sie anschließend eine Datei, um eine Gruppenkonversation im Messenger wiederzugeben:

    Erstellen Sie seine Partials:

    Übernehmen Sie die Änderungen:

    git add -A
    git commit -m "Erstellen Sie eine Vorlage get_group_conversation.js.erb und
    seine Teilungen in den Boten "

    So sehen Gruppengespräche im Messenger aus:

    5. Benachrichtigungen

    Die Anwendung verfügt bereits über alle grundlegenden Funktionen. In diesem Abschnitt konzentrieren wir uns auf die Verbesserung dieser wichtigen Funktionen. Sofortige Benachrichtigungen, wenn andere Benutzer versuchen, mit Ihnen in Kontakt zu treten, sorgen für eine bessere Benutzererfahrung. Informieren Sie die Benutzer, wann immer sie eine Kontaktanfrage erhalten oder an einer Gruppenkonversation teilnehmen.

    Kontaktanfragen

    Generieren Sie einen Benachrichtigungskanal, der alle Benachrichtigungen des Benutzers verarbeitet.

    Schienen g Kanalbenachrichtigung

    Übernehmen Sie die Änderung.

    git add -A
    git commit -m "Benachrichtigungskanal erstellen"

    Jeder Benutzer erhält einen eigenen Benachrichtigungskanal. Dann haben wir den ContactRequestBroadcastJob, der Kontaktanfragen und -antworten sendet.

    Generieren Sie den Job.

    schienen g job contact_request_broadcast

    Erstellen Sie einen Teil von _contact_request.html.erb, der zum Hinzufügen von Kontaktanfragen im Dropdown-Menü der Navigationsleiste verwendet wird. In diesem Fall fügen wir diese Anforderungen dynamisch mit dem ContactRequestBroadcastJob hinzu

    Lösen Sie den Job jedes Mal aus, wenn ein neuer Kontaktdatensatz erstellt wird:

    Übernehmen Sie die Änderungen.

    git add -A
    git commit -m "Einen ContactRequestBroadcastJob erstellen"

    Erstellen Sie dann in der Navigationsleiste selbst ein Dropdown-Menü:

    Definieren Sie die Hilfsmethode nav_contact_requests_partial_path:

    Schließen Sie die Methode mit specs ab und erstellen Sie die Teildateien:

    Rendern Sie in der Datei _dropdowns.html.erb die Datei _contact_requests.html.erb direkt unter den Konversationen. Daher wurde in der Navigationsleiste ein Dropdown-Menü mit Kontaktanfragen angezeigt

    Übernehmen Sie die Änderungen.

    git add -A
    git commit -m "
    - Erstellen Sie eine _contact_requests.html.erb in der
      Layouts / Navigation / Header / Dropdowns
    - Definiere einen nav_contact_requests_partial_path in NavigationHelper "

    Erstellen Sie auch eine Teildatei für eine einzelne Kontaktanfrage:

    Übernehmen Sie die Änderung.

    git add -A
    git commit -m "Erstelle eine _request.html.erb in der
    Layouts / Navigation / Header / Dropdowns "

    Fügen Sie CSS hinzu, um das Dropdown-Menü der Kontaktanfragen zu formatieren und zu positionieren:

    Übernehmen Sie die Änderungen.

    git add -A
    git commit -m "Füge CSS in navigation.scss hinzu, um das zu formatieren und zu positionieren
    Kontaktanfragen Dropdown-Menü "

    In der Navigationsleiste sehen wir jetzt ein Dropdown-Menü für Kontaktanfragen.

    Wir haben den Benachrichtigungskanal und die Aufgabe, Aktualisierungen von Kontaktanfragen zu senden. Jetzt müssen wir eine Verbindung auf der Clientseite herstellen, damit Benutzer Daten in Echtzeit senden und empfangen können.

    Beachten Sie, dass bei Anweisungen, bei denen eine Kontaktanfrage angenommen und abgelehnt wurde, leere Codeblöcke vorhanden sind. Sie können hier herumspielen und Ihren eigenen Code hinzufügen.

    Erstellen Sie auch eine Datei contact_requests.js, um DOM-Änderungen nach bestimmten Ereignissen durchzuführen und durchgeführte Aktionen mit der Callback-Funktion contact_request_response an den gegnerischen Benutzer zu senden

    Entfernen Sie auch nach dem Senden einer neuen Kontaktanfrage aus einem Konversationsfenster die Option, die Anfrage erneut zu senden. Fügen Sie in der Datei options.js der Konversation Folgendes hinzu:

    Jetzt werden Kontaktanfragen in Echtzeit bearbeitet und die Benutzeroberfläche wird nach bestimmten Ereignissen geändert.