Websiteentwicklung: Ruby on Rails: Erste Rails Applikation


Die Rails Applikation erzeugen

Bearbeiten

Bei der Arbeit mit Ruby on Rails spielt nicht nur der eigentliche Source-Code, sondern auch die Kommandozeile eine wichtige Rolle. Schon der erste Schritt passiert auf der Kommandozeile: um die Grund-Struktur der Rails-Applikation zu erzeugen wird der rails-Befehl aufgerufen:

 rails new hallowelt 
 cd hallowelt

Damit wird eine Reihe von Ordnern und Dateien erzeugt:

 

Die Kommandozeile wird auch weiterhin (mehrfach) gebraucht. (Ab jetzt sind alle Befehle im Hauptordner der App abzusetzen.)

Das Programm bundle installiert die richtigen Gems

 bundle install

Das Programm rake führt Befehle aus, die im Rakefile definiert sind. Bevor wir starten können, müssen wir die Datenbank mit folgendem Befehl erzeugen:

 rake db:migrate

Nun können wir den Webserver auf der Kommandozeile starten:

 rails server


Nun kann ich mir die App am localhost auf port 3000 im Browser ansehen:

 http://localhost:3000/

Scaffolding

Bearbeiten

Nach dem Model-View-Controller Prinzip müssen wir für unsere Datenbank der Hallo-Welt Meldungen

  1. eine Tabelle in der Datenbank anlegen
  2. ein Model erzeugen
  3. einen Controller (mit eventuell verschiedenen Actions) erzeugen
  4. für die Actions jeweils Views erzeugen

Rails hilft uns, das Alles auf einmal zu machen.

Scaffold erzeugen

Bearbeiten

Dazu verwenden wir das generate-script und erzeugen damit ein scaffold - ein Gerüst:

 rails generate scaffold Hallo von:string meldung:text farbe:string

Das erste Argument hallo ist der Name des Modells, danach folgen die Eigenschaften und Datentypen des Modells.

In diesem Fall will ich zu jedem "hallo" abspeichern: von dem die Meldung ist, den Text der Meldung und welche Farbe die Meldung haben soll.

Nun müssen wir noch die Datenbank-Tabelle wirklich anlegen, das geschieht mit

 rake db:migrate

Die Datenbank

Bearbeiten

Mit dem Befehl

 rails dbconsole

startet man eine shell für die Datenbank. Hier kann man z.B. mit

 .schema hallos

die gerade angelegte Tabelle betrachten:

 CREATE TABLE "hallos" (
     "id"         INTEGER         PRIMARY KEY AUTOINCREMENT NOT NULL, 
     "von"        varchar(255), 
     "meldung"    text, 
     "farbe"      varchar(255), 
     "created_at" datetime NOT NULL, 
     "updated_at" datetime NOT NULL
 );

Als Name für das Modell hatten wir Hallo gewählt, rails hat automatisch die Mehrzahl für die Bezeichnung der Tabelle gewählt.

Ein Primärschlüssel namens id und die beiden Felder created_at und updated_at wurden ebenfalls automatisch angelegt.

Die Datentypen wurden auch von Ruby auf Datenbank übersetzt: aus string wurde varchar(255).

Das Modell in app/models/hallo.rb

Bearbeiten

Die Klassen-Datei für das Modell wurde angelegt, ist aber noch leer.

Hier könnten wir Methoden eintragen die die innere Logik des Modells abbilden.

Für die Validierung der Daten bietet Rails viele Praktische Kurz-Schreibweisen an. Wenn wir z.B. sicherstellen wollen, dass als Farbe nur ein HTML-Farbcode wie #FF0033 gespeichert werden kann, dann reicht dazu eine Zeile im Modell:

 validates :farbe, :format => { :with => /^#......$/,  :message => "nur Farb-Code mit # und 6 Stellen (hexadezimal) erlaubt" }
  Dazu gibt es einen Rails Guide [1] Validations

Das erste Argument ist der Name der Spalte / der Eigenschaft, mit dem benannten Argument :with gibt man eine Regular Experssion zur Überprüfung an, und mit :message eine passende Fehlermeldung.

Der Controller in app/controllers/hallos_controller.rb

Bearbeiten

Diese Datei ist umfangreich: sie enthält 7 vorgefertigte Actions:

  • index - listet alle Meldungen auf
  • show - zeigt eine bestimmte meldung an (ID notwendig!)
  • new - zeigt ein Eingabeformular für eine neue Meldung an (weiter bei create)
  • edit - zeigt eine Meldung in einem Bearbeitungsformular an (ID notwendig!, weiter bei update)
  • create - erzeugt eine neue Meldung
  • update - verändert eine Meldung
  • destroy - löscht eine Meldung (ID notwendig!)

Betrachten wir die einfachste Action: show zeigt eine bestimmte Meldung an. Beim Aufruf dieser Action muss eine id als Parameter übergeben werden:

 def show
   @hallo = Hallo.find(params[:id])
   respond_to do |format|
     format.html # show.html.erb
     format.json { render json: @hallo }
   end
 end


Über den Parameter id wird der Datensatz Hallo als Objekt geladen und in der Instanzvariable @hallo des Controllers gespeichert.

Die Action funktioniert aber nicht nur für den Fall, dass Sie HTML als Output liefern soll. Auch JSON als Output ist vorgesehen. Dafür sind 4 weiter Zeile Code notwendig:

 def show
   @hallo = Hallo.find(params[:id])
   respond_to do |format|
     format.html # show.html.erb
     format.json { render json: @hallo }
   end
 end

Routing - von der URL zur Action

Bearbeiten

Mit dem Kommandozeilen-Befehl rake routes kann man sehen wie URLs, Controller, Actions zusammen hängen. Dies wird in der Datei config/routes.rb festgelegt, wurde aber durch das Scaffolding automatisch erledigt. Hier der Output von rake routes:

       hallos GET    /hallos(.:format)                  {:action=>"index", :controller=>"hallos"}
              POST   /hallos(.:format)                  {:action=>"create", :controller=>"hallos"}
    new_hallo GET    /hallos/new(.:format)              {:action=>"new", :controller=>"hallos"}
   edit_hallo GET    /hallos/:id/edit(.:format)         {:action=>"edit", :controller=>"hallos"}
        hallo GET    /hallos/:id(.:format)              {:action=>"show", :controller=>"hallos"}
              PUT    /hallos/:id(.:format)              {:action=>"update", :controller=>"hallos"}
              DELETE /hallos/:id(.:format)              {:action=>"destroy", :controller=>"hallos"}

Ganz links ist für manche Routes ein Name angegeben, den man innerhalb von Views und Controllern verwenden kann. In der zweiten Spalte finden Sie die HTTP Methode, anschießend die URL und zuletzt die Kombination von Controller und Action die hier aufgerufen werden.

Die erste Route hallos ruft die action index auf und alle Hallo-Meldungen werden angezeigt.

Die route mit dem namen hallo (3.von unten) bedeutet also: Wenn mit GET ein Aufruf von http://localhost:3000/hallos/14 erfolgt, dann wird der Controller hallos mit Action show aufgerufen. Wo :id steht kann also eine Zahl eingesetzt werden. Wo :format steht kann json eingefügt werden: Wenn mit GET ein Auftruf von http://localhost:3000/hallos/14.json erfolgt, dann wird der Controller hallos mit Action show aufgerufen, er soll dann JSON als Output produzieren.

Nun wäre ein guter Zeitpunkt die Applikation auszuprobieren und ein paar Meldungen einzufügen, wieder zu verändern oder zu löschen

Die Views in app/views/hallos/*.html.erb

Bearbeiten

Vier Views wurden automatisch angelegt:

  • index.html.erb - listet alle Meldungen auf
  • show.html.erb - zeigt eine bestimmte meldung an (ID notwendig!)
  • new.html.erb - zeigt ein Eingabeformular für eine neue Meldung an (weiter bei create)
  • edit.html.erb - zeigt eine Meldung in einem Bearbeitungsformular an (ID notwendig!, weiter bei update)

Das Format der Views ist Embedded Ruby (Endung .erb). Eine View besteht hauptsächlich aus HTML, mit <% ... %> kann Ruby eingebettet werden das ausgeführt wird. Mit <%= ... %> kann Ruby eingebettet werden das Output liefert. Dabei werden hauptächlich die Instanz-Variablen des Controllers verwendet.


Die View show.html.erb zeigt eine Meldung an.

   <p id="notice"><%= notice %></p>

    <p>
      <b>Von:</b>
      <%=h @hallo.von %>
    </p>
    <p>
      <b>Meldung:</b>
      <%=h @hallo.meldung %>
    </p>
    <p>
      <b>Farbe:</b>
      <%=h @hallo.farbe %>
    </p>
    <%= link_to 'Edit', edit_hallo_path(@hallo) %> |
    <%= link_to 'Back', hallos_path %>

Die beiden letzten Zeilen erzeugen zwei Links. Das erste Argument von link_to ist der Link-Text. Das zweite Argument ist die URL. Hier werden Methoden aufgerufen, die automatisch für alle benannten routes vorhanden sind (siehe rake routes).

Die route hallo braucht keine Parameter, mit hallo_path erhält man die URL ohne Hostnamen, mit hallo_url die vollständige URL.

Bei edit_hallo ist es etwas komplizierter: diese Route muss wissen, welches Objekt gemeint ist. Hier kann man als Argument entweder das ganze Objekt oder nur die id des Objekts übergeben. Auch hier gibt es wieder die Formen edit_hallo_path und edit_hallo_url.

Die Darstellung der Meldung können wir ganz verändern: Die Farbe wird wirklich als Farbe verwendet und nicht als Text angezeigt

   <div class="meldung">
        <p><%=h @hallo.von %> sagt:</p>
        <blockquote style="color: <%= @hallo.farbe %>"><%=h @hallo.meldung %></blockquote>
    </div>
    <%= link_to 'Edit', edit_hallo_path(@hallo) %> |
    <%= link_to 'Back', hallos_path %>


Verändern Sie auch index.html.erb so, dass die Farbe wirklich als Farbe verwendet wird! Achtung: in der index-View gibt es zwei Variablen: @hallos ist ein Array aller Meldungen, hallo ist die jeweils aktuelle Meldung.

Eine neue Homepage einsetzen

Bearbeiten

Der hallo-Controller wäre ein sehr gut Homepage für unsere 'Hallo Welt' Applikation. Um das zu erreichen, muss man die Datei public/index.html löschen und in config/routes.rb folgende Zeile einfügen:

 root :to => "hallos#index"

Damit ist die erste Webapplikation in Ruby on Rails fertig.


  1. Rails Guide Validations