Podcast

Ruby on Rails

Das Full-Stack-Web-Framework

In dieser Folge spricht Robert Glaser mit Stefan Tilkov über das Web-Framework Ruby on Rails. Robert stellt die Hauptbestandteile und aktuellen Neuerungen des Frameworks vor und schildert seine Erfahrungen im täglichen Umgang mit Rails.
Weitere Episoden anhören

Shownotes & Links

Tutorials, Know-How und Aktuelles

Neues in Rails 4 und 5

Transkript

Transkript ausklappen / einklappen

Robert Glaser: Hi Stefan, grüß dich.

Stefan Tilkov: Sag mir kurz, was du in deinem Leben so anstellst.

Robert Glaser: In meinem Leben… Also beruflich bin ich natürlich bei innoQ angestellt als Berater und seit vielen, vielen Jahren mittlerweile. Und beschäftige mich halt zu sehr großen Teilen mit der Entwicklung von Ruby on Rails- oder Ruby- Anwendungen, mehrheitlich im Enterprise-Kontext. Und so eins meiner anderen Steckenpferde ist das Thema UI und UX.

Stefan Tilkov: Zu dem wir auch schon mal einen Podcast aufgenommen haben.

Robert Glaser: Genau, der letzte war es glaube ich, ja.

Stefan Tilkov: OK. Gut, dann lass uns doch direkt einsteigen. Es ist eigentlich erstaunlich, dass wir noch keine Episode zu Rails gemacht haben, obwohl das bei uns durchaus eine große Rolle spielt.

Robert Glaser: Das ist wirklich sehr erstaunlich.

Stefan Tilkov: Unter der Annahme, dass es Leute gibt, die nicht wissen, was das iStefan Tilkov: gib' uns doch eine kurze Definition und eine kurze Erklärung, was sich hinter Rails verbirgt.

Robert Glaser: Ok. Gibt’s die Leute noch, die nicht wissen, was das ist?

Stefan Tilkov: Bestimmt.

Robert Glaser: Nein, natürlich gibt’s die. Ruby on Rails ist eigentlich nichts weiter, als ein Web-Framework. Also ein Framework, um Webanwendungen zu erstellen. Was sicherlich in den vergangenen Jahren so ein bisschen Verwirrung gestiftet hat, ist, dass der Name der Programmiersprache, in der dieses Web-Framework geschrieben ist und in der man Anwendungen damit schreibt, mit in dem Framework-Namen enthalten ist. Also Ruby on Rails, Ruby ist die Programmiersprache, Rails das Framework. Hat sicher ein bisschen Verwirrung gestiftet, gerade bei Anfängern oder Leuten, die nicht in der Technologie so lange schon unterwegs sind. Die das vielleicht für eine Programmiersprache halten, Ruby on Rails. Aber eigentlich ist Rails das Framework und Ruby die Sprache.

Stefan Tilkov: Dann lass und doch das vielleicht auch noch ganz kurz abhandeln. Was zeichnet Ruby als Sprache aus?

Robert Glaser: Ja, Ruby ist erstmal eine dynamische Programmiersprache, eine interpretierte Sprache – Skriptsprache auch genannt. Das heißt, ähnlich zu PHP, Python und den anderen dynamischen Sprachen, die man vielleicht so kennt, schreibe ich einfach meine Programme in Textdateien und ein Interpreter lässt die laufen und interpretiert die Befehle zur Laufzeit. Das heißt, ich kompiliere nicht, wie ich das vielleicht bei Java tun würde oder Scala oder sonst was, sondern es ist halt eine interpretierte Sprache.

Stefan Tilkov: Und was unsere Scala-Freunde massiv abschreckend wird, es ist natürlich auch eine dynamisch-getypte Programmiersprache wie die anderen, die sich so schimpfen, auch.

Robert Glaser: Genau, vollkommen richtig.

Stefan Tilkov: Das kann man gut oder schlecht finden. Ich nehme an, du findest das gut.

Robert Glaser: Ich finde das gut. Das ist natürlich immer eine Glaubensfrage, wie du schon richtig gesagt hast. Ich glaube, dass das auch ein wichtiger Punkt ist, warum man sehr produktiv Anwendungen entwickeln kann mit Ruby und vor allem Rails. Widerum die andere Seite wird mir da wahrscheinlich nicht so beipflichten, aber ich glaube, die Diskussion wird bis in die Unendlichkeit zu führen sein.

Stefan Tilkov: Ein Argument, das ich – da muss ich aber doch kurz fragen – ein Argument, das ich häufig höre ist, “Weil der Compiler die Typfehler nicht findet, musst du Tests schreiben, die die Typfehler finden.” Ist das dein Gefühl, also schreibst du Tests, die auf Typfehler untersuchen? Schreibst du überhaupt Tests?

Robert Glaser: Ich schreibe Tests. Skandalöserweise. Nein, also das stimmt schon, dass man sicher in der Entwicklung mit Ruby und vor allem Rails sehr viele Tests schreiben muss und auch sollte. Sicher nicht des Hauptteils wegen, um Typfehler, Typkonvertierungsfehler abzufangen, sondern einfach, um Sachen zu entdecken – also gerade diese nil-checkings, nil-Fehler, die auftreten können, die findet man sonst nicht wirklich gut. Also das ist sicher ein Aspekt, warum es keinen Compiler gibt, dass das zu Fehlern führt.

Stefan Tilkov: Ok. Gut, dann lass uns Ruby verlassen, vielleicht machen wir mal eine separate Episode dazu. Aber jetzt lass uns uns auf Rails stürzen. Du hast gesagt, das ist ein Web-Framework. Es ist – das muss man vielleicht noch genauer sagen – ein Full-Stack-Web-Framework. Da ist alles drin, also für die Java-Leute unter uns nicht vergleichbar mit Struts oder JSF, sondern eher mit dem ganzen J2EE-Stack oder vielleicht Play. Was sind denn die Bestandteile, aus denen Rails besteht?

Robert Glaser: Ja Full-Stack-Framework war der richtige Begriff. Also ein Full-Stack-Framework ist ja eigentlich auch nicht so fest definiert. Aber man fasst da typischerweise Web-Frameworks drunter, die halt mehr bieten, als die Funktion, Strings zusammen zu kleben und über HTTP auszuliefern. Bei Rails kommt dazu, dass Active Record seit jeher ein fester Bestandteil des Frameworks ist, was ein ORM-Mapper ist, also eine SQL-Abstraktion. Das heißt, ich muss kein SQL schreiben, um beispielsweise Records aus meiner Datenbank zu lesen und im Applikationskontext zu verwenden. Das sorgt immer wieder für mehr oder weniger heiße Diskussionen, was das im Web-Framework zu suchen hat. Den Diskussionen kann man sich teilweise anschließen, aber auch das führt wahrscheinlich nie zu irgendeinem Endergebnis. Ich finde es oft sehr praktisch und es ist auch immernoch fester Bestandteil von Rails, weil man einfach oft den Fall hat, dass man eben Datenbankoperationen durchführen muss.

Stefan Tilkov: Ok, lass uns vielleicht mal durch die Bestandteile durchgehen, die sich aus dem MVC-Modell ergeben.

Robert Glaser: Genau. Also Rails richtet sich auch nach dem MVC-Modell aus. Die M-Ebene, also die Modell-Ebene, wird eben von ActiveRecord gekapselt – also ActiveRecord ist der ORM-Mapper – die C-Ebene, die Controller-Ebene von ActionController. ActionController ist einfach eine Klasse, von der typischerweise Application- Controller erben und die einfach für die HTTP-Interaktion zuständig sind. Die dritte Ebene, der View-Layer, wird von ActionView gekapselt. Und ActionView besteht aus einzelnen Bestandteilen, wie z.B. ERB, was für Embedded Ruby steht. Das ist der sogenannte Template-Renderer. Damit kann ich meine HTML-Templates schreiben – es müssen nicht unbedingt HTML-Templates sein, aber mehrheitlich sind es das eben im Web-Framework – und kann mit sogenannten Markern, ähnlich wie man das vielleicht auch von PHP kennt, wenn man damit schon mal in Berührung gekommen ist.

Stefan Tilkov: Oder JSPs.

Robert Glaser: JSPs, genau – kann man halt Ruby-Code in Templates ausführen.

Stefan Tilkov: Ok, also die Templates sind das, woran dann der Controller-Teil deligiert. Also ich habe einen Controller, der ist in Ruby implementiert, der reagiert auf die eingehenden HTTP-Requests und die Views werden dann von dem ActionView-Teil gekapselt. Wie stelle ich denn die Verbindung her zwischen Controllern und der Außenwelt?

Robert Glaser: Genau. Also das war nur der grobe Überflug. Wenn man ins Detail geht, genauer gesagt, wie die HTTP-Requests dann letztenendes im Controller landen, da gibt es noch ein Zwischenstück. Das nennt sich das sogenannte Routing in Rails. Das ist erstmal so nicht abgedeckt in diesem MVC-Begriff, ist aber dennoch Bestandteil. Und der sogenannte Rails-Router, der kümmert sich eben um dieses HTTP-Mapping. Da drin kann ich wie in so einer Landkarte definieren, auf welche URIs meine Anwendung denn hört. Also seien das konkrete URIs oder URI- Patterns. Und ich kann dann sagen, wohin diese Pfade denn führen sollen, kann die mit Controllern verbinden und Methoden von diesen Controllern. Man muss dazu wissen, dass in Rails, wenn ein HTTP-Request auf die Anwendung auftrifft, wird immer eine Controller-Instanz erzeugt. Und diese Instanz hat Instanz- Methoden, natürlich, und die nennen sich in Rails Actions. Und diese Actions verbinde ich einfach, um dieses Landkartenbeispiel nochmal zu bemühen, in dem Router. Und das stellt diese Verbindung sicher.

Stefan Tilkov: Muss ich das für jede einzelne Action machen oder wie kriege ich das zusammen gefummelt?

Robert Glaser: Früher war das so in Rails, also in sehr frühen Versionen, dass da so ein Catch-All drin war. Das heißt, er hat immer ein bestimmtes URI-Schema, nämlich Controllers/Action, auf eben den Controllernamen und die Action gemappt. Was natürlich sehr generisch war und sehr einfach, weil du musstest dieses “Routing pflegen” nicht mehr betreiben. Das haben sie vor etlichen Versionen – ich glaube in 2.2 / 2.3, es ist schon so lange her, ich weiß das nicht mehr genau – haben sie das entfernt und sind dazu über gegangen zu sagen, die Leute müssen wirklich speziell das eintragen, was sie halt wollen. Ich kann allerdings, wenn ich RESTful – da haben wir schon wieder so ein Keyword – Resourcen habe in meiner Anwendung, kann ich Helper-Methoden benutzen, die mir eben ganz viele dieser Einträge erzeugen, die ich sonst z.B. für diese sieben RESTful Actions, die ich in der CRUD-Anwendung habe – CRUD, entschuldige für dieses Fremdwort: Create, Read, Update, Delete –, also diese Standardoperationen auf Objekten, da gibt es Helper in Rails, die mir dann diese ganzen Routen generieren. Das heißt, ich muss nicht sieben Routen oder fünf Routen dann da eintragen manuell, das macht der dann für mich.

Stefan Tilkov: Man sieht auch – das war natürlich eine rhetorische Frage, weil ein bisschen was weiß ich auch noch aus alten Zeiten – im Prinzip ist das eine Art DSL, was man in dem Routing drin hat, die es da eben ganz einfach macht, solche Sachen – auch verschachtelte Resourcen und ähnliches Zeug, was das Herz des REST Verfechters höher schlagen lässt – möglichst einfach zu erstellen.

Robert Glaser: Genau. Also der Router nutzt eine in Ruby implementierte DSL, was gerade, wenn ich Schulungen halte für Einsteiger, oftmals zu Verwirrung führt, weil die Teilnehmer meistens noch keinen Ruby-Kontakt hatten, noch keine Ruby-Erfahrung, Rails ist für sie neu und dann kommt noch die DSL eben dazu. Man hat dann ohnehin Mühe, all diese Sachen an wenigen Tagen zu erschlagen und dann kommt diese DSL dazu, aber sie dient – letztenendes hat sie schon ihren Nutzen – sie dient dazu, dass man, wenn man so dieses Routing-File mal überfliegt im täglichen Entwicklungsrhythmus, dann findet man schnell die Sachen, die man so gepflegt hat.

Stefan Tilkov: Das ist auch der eine zentrale Punkt, an dem man das alles sieht, ne?

Robert Glaser: Genau.

Stefan Tilkov: Also wenn man wissen will, auf welche URIs das Ding reagiert, gibt man das da an.

Robert Glaser: Ja.

Stefan Tilkov: Ok. Gut, REST haben wir schon erwähnt, Rails gibt sich Mühe, möglichst RESTful zu sein, zumindest was so die Nutzung von URIs und HTTP-Methoden angeht.

Robert Glaser: Genau, wobei das auch stückweise kam, natürlich. Also Rails war glaube ich eines der ersten Web-Framework, wenn nicht das erste – lass mich nicht lügen – was ein gewisses Maß an REST-Support in die Web-Framework-Ecke gebracht hat. Eben durch die Sachen, die wir schon besprochen haben. Was in frühen Versionen noch nicht ging, waren so Sachen, wie dass ich den Accept-Header setzen konnte und ich habe die richtige Resource zurück bekommen. Das hat Rails anfänglich dadurch gelöst, dass ich auf der URI das Format eben spezifiziere, was ich erwarte.

Stefan Tilkov: .xml

Robert Glaser: .xml, .json, was auch immer. Das geht mittlerweile, ich war ganz überrascht. Ich hatte mich über die Jahre daran gewöhnt, dass ich das immernoch tun muss, aber das geht seit etlichen Versionen wohl.

Stefan Tilkov: Ok.

Robert Glaser: Das ist so ein Beispiel. Genau das PATCH-Verb wurde, ich glaube letzter Jahr, eingeführt. Also das HTTP-Verb PATCH, weil man vorher PUT benutzt hat, um Records zu updaten und, ja das hat man einfach ein wenig feingranularer ausgerichtet jetzt.

Stefan Tilkov: Lass uns vielleicht kurz noch über diesen View-Teil sprechen. Gibt es da Abstraktionen oder hat man nur diese eine Template-Ebene, in der man alles drin abdeckt?

Robert Glaser: Also du hast natürlich die Templates, kannst da ERB drin benutzen, aber das führt natürlich, wie man sich vielleicht denken kann oder auch schon Erfahrungen mit gemacht hat, in großen Anwendungen schnell zu sehr unübersichtlichen Templates, die aus HTML-Fragmenten bestehen und immer diesen Markern, die dann evtl. umfangreichste Schleifen abwickeln. Und dazu bietet Rails halt so ein Zwischenglied, sag ich mal, zwischen Controller und Views und das sind die sogenannten Helpers, die auch regelmäßig zu einer hasserfüllten Diskussion in der Ruby-Community sorgen. Weil die einen sehr prozeduralen PHP-Charakter irgendwie haben. Und das sind einfach Methoden, die ich in meinem View aufrufen kann und in diesen Methoden kann ich mit Plain-Ruby Dinge machen. Da wiederum gibt es Helper, die dann HTML ausspucken. Das heißt, wenn ich im View in die Situation gerate, dass ich mehr Ruby als Plain-HTML brauche, nehme ich wahrscheinlich einen Helper. Der Nachteil ist, dass Helper einfach nur Methoden in Modulen sind, in Ruby-Modulen, die überall verfügbar sind. Das heißt, ich kann nicht wirklich objektorientiert mit diesen Dingern arbeiten, es sind einfach Methoden, die ich in meinem gesamten View-Kontext überall aufrufen kann. Das führt in großen Projekten schnell dazu, dass man merkt, man drückt dann Namespacing in Methodennamen aus. Und das ist ja dieser klassischen Smell, wo man merkt, das skaliert einfach nicht, deswegen haben viele Leute Sachen / Alternativen geschaffen, wie z.B. die sich nach Presenter- oder Decorator- Patterns ausrichten – hat der ein oder andere sicher schon mal gehört. Das sind Gems, wie Draper usw. usf., die den sogenannten Decorator- oder Presenter-Ansatz in Rails etablieren.

Stefan Tilkov: Gem wäre so ein wiederverwendbares Modul in Ruby.

Robert Glaser: Genau, ja.

Stefan Tilkov: Ok. Über den ORM haben wir noch nicht wirklich gesprochen.

Robert Glaser: Ja.

Stefan Tilkov: Wie funktioniert dieser OR-Mapper? ActiveRecord hast du schon gesagt, als Muster.

Robert Glaser: Genau. ActiveRecord – der ActiveRecord ist ja eigentlich ein Pattern von Martin Fowler, vor Ewigkeiten etabliert. Und das besagt einfach, ein ActiveRecord ist eben ein Record aus einer Datenbanktabelle, eine Zeile aus einer Datenbanktabelle, wo ich mich nicht als Entwickler drum kümmern muss, die Getter und Setter für die einzelnen Spalten zu definieren, sondern der ActiveRecord ließt das Schema der Datenbanktabelle ein und gibt dem Entwickler damit die Getter und Setter schon vor. Das heißt, wenn man eine neue Rails-Anwendung startet oder in bestehende Rails-Anwendungen eintaucht, wird einem auffallen, dass da teilweise leere Modell-Klassen sind – das sorgt auch in Schulungen immer wieder zu Verwunderung, diese Magie, warum da nicht schon direkt Berge von Gettern und Settern definiert sind. Das ist so ein Beispiel für eins der Haupt-Rails-Paradigmen: “Convention over Configuration”. Also ich soll nicht immer wiederkehrende Abläufe als Entwickler machen müssen, um grundlegene Operationen auszuführen.

Stefan Tilkov: Das bedeutet im Prinzip, dass alle Spalten, die ich in der Datenbanktabelle habe, automatisch als Attribute einer Klasse zur Verfügung gestellt werden.

Robert Glaser: Ja genau, richtig.

Stefan Tilkov: Wie sieht es mit Relationen aus, mit 1:n- oder m:n-Beziehungen zwischen Klassen?

Robert Glaser: Das ist ganz interessant, weil Relationen muss ich dann doch wieder selber anlegen, in meinen Modellen. Das heißt, ich muss den Modellen sagen, welcher Fremdschlüssel sich auf welche andere Tabelle bezieht. Wenn ich mich allerdings an Rails-Konventionen halte, wie beispielsweise “Ein Fremdschlüssel ist immer klein geschrieben, hat den Singularbegriff der anderen Tabelle und endet mit _id”. Dann kann Rails diese Mappings automatisch herstellen. Ich muss trotzdem sagen: has_many oder has_one für den jeweiligen Relationstyp und ihm das einfach konfigurieren. Das war immer so eine Sache, die steht ein bisschen im Widerspruch zu diesen “Convention over Configuration”-Sachen, weil ich das dann doch letztenendes wieder manuell eintragen muss.

Stefan Tilkov: Wie frage ich die Datenbank ab? Wie funktioniert das mit Querys?

Robert Glaser: Das sorgt auch immer wieder für hellste Begeisterung in den Schulungen, die ich ab und zu mache und das ist auch ein guter Catcher, um Leute von Rails zu überzeugen, sag ich mal. Weil wir machen dann in den Schulungen z.B. Übungen, wo wir einfach nur die ActiveRecord-API nutzen, um Datenbankrecords abzufragen, zu schreiben, zu ändern usw. Und das können die Leute super im Terminal mitmachen. Also das sorgt dann immer für Begeisterung, wenn man einfach Tabellennamen, also Modellklassenname.find(x) und da schmeißt man einfach eine Zahl rein [Anm.: für x], die für den Fremdschlüssel steht, und damit wird sie selektiert. Das ganze geht weiter über komplexere WHERE-Bedingungen und das kann ich alles, ohne SQL schreiben zu müssen, abfackeln.

Stefan Tilkov: Wobei, das klingt so ein bisschen – ich weiß nicht, ist das wirklich so – mir kommt das immer so vor, dass man schon noch weiß, was man da tut. Also es ist nicht so, als ob der OR-Mapper einem die Illusion vermittelt, als wäre da drunter keine relationale Datenbank. Also man hat schon noch das Gefühl, dass man weiß, wo lang man da navigiert oder siehst du das nicht so?

Robert Glaser: Ja, ActiveRecord ist über die Jahre auch deutlich mächtiger geworden. Irgendwann kamen ActiveRelation als Bestandteil mit rein, was eine komplette relationale Algebra abbilden will und das auch in großen Teilen tut. Das war in früheren Rails-Versionen nicht der Fall, d.h. das hat für mich als Entwickler letztenendes das Ergebnis, dass ich einfach komplexe Bedinungen wie OR oder AND schon recht SQL-nah, aber dennoch objektorientiert mit Methoden und – was weiß ich – Spaltenobjekten dort abbilden kann.

Stefan Tilkov: Ok. Also wir haben irgendwie diesen Datenbank-Layer, den manche Leute nicht im Web-Framework vermuten würden, der gehört irgendwie mit dazu. Wir haben Controller und Views. Das ist ja alles irgendwie normaler Umfang, das haben irgendwie andere Web-Frameworks auch. Was sind so Besonderheiten? Also ein Stichwort, was wir vorher besprochen hatten, war das Thema “Asset-Pipeline”, was bei Rails dabei ist, was man sich bei anderen selbst bauen muss. Kannst du erklären, was sich dahinter verbirgt?

Robert Glaser: Genau, die Asset-Pipeline – sorgt für Hass und Freude gleichermaßen.

Stefan Tilkov: Das hast du jetzt schon das fünfte Mal gesagt, das scheint – ist das so, dass es in der Rails-Community immer jemanden gibt, der ein Feature hasst und andere, die es lieben?

Robert Glaser: Definitiv, aber das ist glaube ich auch so ein bisschen Kultur, sage ich mal. Es gibt halt den großen “DHH”, also David Heinemeier Hansson, der das Framework ursprünglich geschrieben hat. Der sagt halt immernoch, gibt halt immernoch zu großen Teilen die Richtung vor und hat auch gesagt, Rails war schon immer die Speerspitze in der Web-Framework-Entwicklung und das soll es auch bleiben. Und dazu gehören eben auch teilweise erstmal unpopuläre Entscheidungen, wie beispielsweise vielleicht so eine Asset-Pipeline zu etablieren. Aber das sind Entscheidungen, die er auch argumentiert, indem er sagt, ein wichtiger Teil der heutigen Webentwicklung sind eben auch Assets. Und Assets stehen dann sinnbildlich für Bilder, Javascripts, Stylesheets. Er nennt das jetzt First-Level-Citizens, d.h. er betrachtet sie gleichwertig zu Backend-Rubyklassen, Rubymodellen, Controllern usw., weil sie eben derartig wichtig sind für ihn. Und mit der Asset-Pipeline hat man halt versucht, ein Werkzeug den Entwicklern an die Hand zu geben, mit dem sie eben ihre Assets nach Konvention in bestimmte Ordner legen können und die wiederkehrenden Aufgaben, die sich halt im Laufe der Webentwicklung heraus kristallisiert haben, abzunehmen. Typischstes Beispiel ist z.B.: irgendwann haben die Leute angefangen, ihre Assets, also ihre Javascripts und Stylesheets, zu konkatenieren. Ich glaube, wir hatten unsere erste Podcast-Episode, die hat sich genau darum gedreht und um Frontend-Optimierung. Und genau dieses Thema der Frontend-Optimierung greift halt die Asset-Pipeline auf. Rails, also “DHH” und andere haben gesagt, das ist ein Task, den Leute immer machen, in vielen Webprojekten, deswegen sollte das Framework das übernehmen können. So Dinge wie Konkatenierung, dann vielleicht das Fingerprinting von Dateinamen, dass man einen Inhaltshash in den Dateinamen codiert. Das sind so Best-Practices, die einfach das Framework übernehmen soll, weil man es sonst eh immer wieder auf Produktions-Deployments tun würde.

Stefan Tilkov: Das Feature haben wir glaube ich tatsächlich in der allerersten Folge besprochen. Dieses Fingerprinting, damit man sozusagen für jede Datei eine eindeutige URI bekommt, damit man das Zeug auf ewig cachen kann. Bring mich sowas, genauso wie das Konkatenieren, in der Entwicklung nicht um den Verstand? Also werde ich nicht wahnsinnig, wenn ich im Entwicklungsmodus auf einmal sowas, solche Sachen da drin habe?

Robert Glaser: Da hast du vollkommen recht. In dem Entwicklungsmodus war Rails bisher so, dass ich einfach – ich muss halt Helper nutzen, um meine Assets einzubinden. Sei es jetzt ein Bild, da muss ich den ImageTagHelper benutzen, oder den JavascriptIncludeTag- oder den StylesheetLinkTagHelper.

Stefan Tilkov: Das heißt, ich schreibe nicht das HTML da hin, um das zu inkludieren, sondern ich schreibe einen von diesen in Ruby verfügbaren Helpern in so einem Ausdruck, um das zu machen.

Robert Glaser: Genau, weil diese Helper stellen sicher, dass in der lokalen Entwicklungsumgebung, wo du bist, die Pfade richtig gesetzt werden und im Produktions-Deployment auch. Lokal willst du sowas gar nicht haben, dass wenn du lokal entwickelst, dann willst du bei jedem Browser-Reload die Assets alle da haben und willst nicht nicht, dass immer da irgendwelche Assets vorkompiliert und konkateniert werden. Das brauchst du lokal nicht. Weil lokal die Ladegeschwindigkeit mit diesen paar Millisekunden nicht ausschlaggebend ist. Das sorgt halt für Verwirrung, weil die Asset-Pfade, die Rails lokal in deiner Entwicklungsumgebung schreibt, durchaus anders sind, als in der Produktionsumgebung. Da hast du kein Fingerprinting in den Dateien usw. usf. Das hat halt dazu geführt, dass Leute vergessen haben, diese Helper zu benutzen, die Sachen funktionieren auf der Entwicklungsumgebung total toll, dann werden sie deployt und dann funktioniert nichts mehr, weil eben für die Produktionsumgebung erwartet wird, dass diese Helper benutzt werden.

Stefan Tilkov: Aber dieser Gedanke von den Umgebungen, der ist ganz interessant. Dass man offensichtlich in der Entwicklungsumgebung und in der Produktion unterschiedliche Dinge hat. Es bezieht sich glaube ich auch auf das Neuladen von Klassen?

Robert Glaser: Genau.

Stefan Tilkov: Das ist glaube ich auch so.

Robert Glaser: Ja, das Auto-Loading. Also das Auto-Loading ist auch ein wichtiger Bestandteil von Rails. Das heißt, ich kann einfach Klassen in vorgegebene Ordner schmeißen und muss die nirgendwo requiren, sondern Rails lädt die alle automatisch. Das will man auf Produktion wahrscheinlich nicht, weil das eben auch ein bisschen Performance kostet und in der Produktionsumgebung geht man halt hin und lädt beim Hochfahren der Anwendung im Applikationsserver all diese Businessklassen, Library-Code usw.

Stefan Tilkov: Du hast vorhin gesagt, dass du eine interpretierte Sprache hast, wo du mit dem Texteditor halt Sourcecode-Dateien schreibst, die interpretiert werden. Wie sieht denn dein Entwicklungsprozess aus? Arbeitest du mit einer IDE oder mit einem einfachen Texteditor?

Robert Glaser: Also ich arbeite seit jeher mit einem mehr oder weniger einfachen Texteditor. Der wechselt auch Saison-mäßig. Mittlerweile benutze ich den Atom-Editor von Github. Ärgere mich teilweise auch noch so ein bisschen, dass der noch nicht so ganz reif ist, wie ich es gern erwarten würde, aber das Plugin-System finde ich ganz nett. Wahrscheinlich ist es nächstes Jahr wieder was anderes, aber ich habe nie

Stefan Tilkov: Solange, bis du irgendwann zum Emacs findest.

Robert Glaser: Wahrscheinlich, genau.

Stefan Tilkov: Da arbeiten wir noch dran.

Robert Glaser: Meine Vim-Versuche, die sind regelmäßig zum Scheitern verurteilt gewesen. Ich belasse es dabei, das auf Servern zu benutzen. Ja, aber ich habe Kollege, der liebe Till z.B., der ist heißer Verfechter von NetBeans und benutzt das auch tatsächlich täglich für die Ruby- und Rails-Entwicklung. Einfach, weil das für in konfortabler ist, diese Syntaxvervollständigung zu haben. Er kann direkt mit CMD-Klick in Klassendefinitionen springen, was ich übrigens auch sehr konfortabel finde. Das geht mit normalen Texteditoren natürlich nicht.

Stefan Tilkov: Wenn der Compile-Step wegfällt, wie ist das dann, wenn du irgendwas änderst im Source-Code, ist das sofort da oder musst du irgendwas tun, damit das in deiner Entwicklungsumgebung, in deiner Testumgebung deployt wird?

Robert Glaser: Wenn du lokal was änderst, dann reicht es quasi, das Browserfenster, in dem deine Anwendung geöffnet ist, die Seite, die vielleicht diesen Code da nutzt, neu zu laden und dann hast du den neuen Effekt. Da wird also nichts kompiliert im Hintergrund und sofort verfügbar. Es gibt auch da andere Fallstricke, wenn man seinen Code z.B. in Ordner legt, die nicht Auto-Loadable sind, dann werden die natürlich lokal auch nur einmal geladen und nicht auf Änderungen untersucht.

Stefan Tilkov: Ok und das funktioniert auch wieder logischerweise nur in der Entwicklungsumgebung so. In der Produktionsumgebung wird nicht bei jedem Request alles neu geladen.

Robert Glaser: Genau, in der Produktionsumgebung wird zu großen Teilen gecachet dann auch.

Stefan Tilkov: Wie sieht es mit Tests aus? Testet man in der Railswelt?

Robert Glaser: Man testet sogar wie verrückt. Also ich glaube, keine Community hat mehr Test-Frameworks und Paradigmen geschaffen, als die von Ruby.

Stefan Tilkov: Mehr Test-Frameworks als andere Leute Tests.

Robert Glaser: Genau. Also man sieht das ja alleine daran, dass Kollegen von mir sogar in Java-Enterprise-Projekten Ruby-Test-Frameworks einsetzen, eben weil es da so viele Aspekte und vielseitige Formen gibt. Behavior-Driven-Development, d.h. ich schreibe Szenarien in vielleicht einer Menschensprache oder etwas, was sich der menschlichen Sprache annähert. All das hat aber nie seinen Einzug in Rails gefunden, weil “DHH” halt immernoch sagt, dieses Standard-Test-Unit-Framwork – so heißt es in Ruby, das Standard-Test-Framework – nutzen wir für Unit-Tests, Controller-Tests und Integration-Tests. Und das muss genug des Guten sein. Wer was anderes möchte, kann sich ein anderes Gem nehmen zum testen.

Stefan Tilkov: Wie ist denn deine Einschätzung, also jetzt machst du das schon ein Weilchen, hast vorher viele andere Dinge gemacht. Findest du Rails immernoch gut oder ist das jetzt Legacy von vor ein paar Jahren? Würdest du freiwillig Rails wählen, wenn du ein neuen Projekt startest?

Robert Glaser: Also ich würde es auf jeden Fall immernoch wählen. Ich tue mich natürlich auch so ein bisschen um, wenn es die Zeit erlaubt und die Möglichkeiten gibt. Habe mir auch mal Node angeguckt und die Frameworks, die es in dem Umfeld gibt. Diverse andere Sachen. Ich war in der Scala-Play-Schulung, da war ich einen Tag dabei. Und ich war – ohne jetzt bashen zu wollen – aber ich war wirklich skandalös erschrocken, wie unproduktiv das ganze immernoch ist. Wie behäbig ich mich da tue, vielleicht lag es auch an mir, das mag sein, aber ich würde jedes Mal immernoch zu Rails raten.

Stefan Tilkov: Ist das eine Sache, also viele Leute haben so die Einstellung, wenn man Rails startet, das es so toll am Anfang in der Produktivität, wegen der Generatoren, habe ich schon ein paar Mal gehört. Benutzt zu diese Generatoren, die es da gibt, mit denen man mal eben schnell für eine Ressource die komplette CRUD-Logik erzeugen kann?

Robert Glaser: Ja, du sprichst diese sogenannten Scaffolds an, diese Gerüste oder Gerüstbaufunktionen. Die benutze ich selber schon lange nicht mehr in Produktionsprojekten und auch in Spieleprojekten und sonst was nicht mehr. Ich sehe aber durchaus den Reiz, auch heute noch, für Einsteiger, dass das halt sehr schnell zu Erfolgserlebnissen führt. Ich sehe es auch in den Schulungen immer wieder. Man muss halt so den Wissensstand berücksichtigen. Also wenn wir langjährigen Railsentwickler das mal so abschätzig abtun, das sollten wir nicht tun. Wir müssen es ja nicht benutzen, wir können auch Leuten auf unserem Wissensstand empfehlen, das nicht zu tun, weil es halt sehr viel Code generiert, den ich dort wieder wegschmeiße oder der veraltet. Aber Einsteiger und Leute, die noch nicht so lang dabei sind, für die ist das schon beeindruckend, was sie damit auf die Beine stellen können. Wir haben ja vor nicht langer Zeit einen RailsGirls-Workshop hier bei uns in Monheim gemacht und auch da hat das in vielen Teams durchaus für Begeisterung gesorgt, weil die Frauen dann eben gesehen haben, wie einfach das ist, eine lauffähige Webanwendung mit klickbaren Views und fertigen Formularen zu kriegen.

Stefan Tilkov: Ok. Lass uns vielleicht kurz ein bisschen über den aktuellen Status sprechen. Wo sind wir jetzt bei Rails 4.x?

Robert Glaser: Wir sind bei Rails 4.1 und zum Tag, an dem wir hier heute reden, ist die Version 4.2 in der vierten Beta verfügbar. So typischerweise folgen dann noch so ein bis zwei RCs nach der Beta-Phase und dann kommt auch die finale Version mal raus. Deswegen, ich rechne jetzt damit, dass das im Dezember noch der Fall sein dürfte. Genau, wir sind also bei 4.2 demnächst.

Stefan Tilkov: Und was gibt’s oder was gab es in letzter Zeit spannendes Neues? Bei mir ist es ja ein weilchen her, das letzte was ich kenne, ist Version 3-irgendwas. Was gibt es in der vierer und was gibt es in den nächsten Versionen zu erwarten, was neu ist?

Robert Glaser: Also du hast Version drei kurz angesprochen. Version drei war wirklich ein gewaltiger Umbruch, weil das komplette Framework halt mehr oder weniger alleine vom Yehuda Katz umgebaut wurde. Einfach um den internen Motor mal komplett auszutauschen. Das ist dann hochgradig modular geworden, Rails, was es vorher nicht war. Das heißt, ich kann jetzt sehr einfach ActiveRecord auch abstöpseln seit Rails3, ohne dass mir sämtliche Sachen auf den Kopf fallen. Das mache ich sogar oft, wenn ich einfach keinen OR-Mapper brauche. Dann schalte ich ihn einfach ab und gut ist. Rails3 hat damit sehr viel Schmerzen verursacht in vielen Upgrades von Projekten. Rails4 ist natürlich auch, das hört sich erstmal nach einer riesigen neuen Version an, aber da sind deutlich weniger interne Änderungen angefallen. Da kamen wirklich mehrheitlich ein, zwei, drei, vier neue Features hinzu. Unter anderem besseres Caching nach dem Russian-Doll-Pattern, das können wir in den Shownotes verlinken. Rails 4.1 kam dann kurze Zeit danach und das waren alles so Feature-Releases, wo man sich nicht mehr drum gekümmert hat, immer das Framework neu zu bauen, die Interna neu zu machen. Mit 4.2 kommt jetzt z.B. zum ersten Mal eine Abstraktion für Queues. Das heißt, nennt sich ActiveJob und das soll halt eine einheitliche API für Queueing mir bieten. Das heißt, wenn ich jetzt DelayedJob bisher benutzt habe, das ist so ein Gem, um asynchrone Jobs auszuführen, wie beispielsweise Exports zu generieren, Mails zu verschicken usw. Oder halt andere Frameworks und Librarys benutzt habe. Die können sich jetzt alle nach der ActiveJob-API orientieren und egal welche Queue ich da nutze, ich habe immer dieselbe API, nämlich die von ActiveJob. Das ist so ein großes neues Feature, was jetzt demnächst kommt.

Stefan Tilkov: Was zur Hölle sind Turbolinks?

Robert Glaser: Cooler Name, oder?

Stefan Tilkov: Ja, super. Wäre ich gern selber drauf gekommen.

Robert Glaser: Turbolinks machen im Prinzip das, was wir alle vielleicht mal so gemacht haben, als Ajax gerade heiß war, vor etlichen Jahren. Da sind wir ja auf den Trichter gekommen, dass wir deutliche Speed-Verbesserungen erreichen können, wenn wir nicht immer die komplette Seite, samt ihrem Rahmenlayout, vom Server an den Client schicken, sondern nur den Teil, den Schnipsel der Seite, der sich eigentlich ändert, durch die Nutzerinteraktion. In dem Fall einen Link zu klicken, sei es nun auf ein User-Formular oder auf eben eine Liste von Usern. Da wurde nur dieser Teil, nämlich die Liste oder das Formular, übertragen. Rails geht halt mit den sogenannten Turbolinks hin und schafft dafür so einen Standard, wir das geht. Das heißt einfach, dass alle Links, die ich in meiner Anwendung mit Rails-Helpern erzeuge, standardmäßig in einer neuen Railsanwendung an diese sogenannten Turbolinks gebunden werden. Immer, wenn ich auf einen Link klicke, greift ein Stück Javascript auf diesen Link-Klick-Event und holt vom Server nur den tatsächlichen View und spart das Rendern des Rahmenlayouts.

Stefan Tilkov: Und das ganze ist bestimmt unobstrusive und Roca-compliant.

Robert Glaser: Das ist sogar unobstrusive und Roca-compliant, weil es hat halt den Effekt, wenn das Javascript aus ist, nicht funktioniert, kaputt ist, nur zur Hälfte übertragen wurde oder von der Telekom zerhackt wurde, dann funktioniert das trotzdem, weil ich eben einfach normale Links in meiner Anwendung habe. Und wenn ich die klicke, dann wird halt die ganze Seite geladen.

Stefan Tilkov: Schönes Beispiel eigentlich für das, was man so machen kann, wenn man diesem Ansatz folgt.

Robert Glaser: Genau.

Stefan Tilkov: Ok, gut. Eine Frage ist mir noch eingefallen: JRuby?

Robert Glaser: Ja?

Stefan Tilkov: Geht? Geht nicht?

Robert Glaser: JRuby geht super.

Stefan Tilkov: Geht super. Machen wir sogar, oder? Machen wir in diversen Projekten.

Robert Glaser: Wir machen das tatsächlich in vielen Projekten. Wobei man auch differenzieren muss, wir haben ein, zwei Projekte mit wirklich widrigen Deployment-Szenarien unter Windows. Selbst da kann man natürlich Rails-Anwendungen ans Laufen kriegen. Also wir machen tatsächlich eine Anwendung, die im IIS von Microsoft und im Tomcat und JRuby unter Windows läuft.

Stefan Tilkov: Also JRuby, für die, die es nicht wissen, ist eine Ruby-Implementierung, die auf der JVM läuft.

Robert Glaser: Ganz genau, ja.

Stefan Tilkov: Und die stellt dann halt die Brücke her, sodass man eine normale – was heißt normale – eine Java-Deploymentumgebung nutzen kann, wenn man eine Ruby on Rails Anwendung deployen will.

Robert Glaser: Genau. Also es gibt da sicher auch mit JRuby Fallstricke, wahrscheinlich auch zu genüge, die man aber nicht in jedem Kontext erwischt. Also wir haben viele von denen erwischt, eben wegen Windows. Aber wir haben auch andere Projekte, die das unter Linux machen, und das sind das schon wieder ganz anders aus. Aber das Team bemüht sich halt auch, da in der Windows-Richtung besser zu werden – also das JRuby-Core-Team. Man hat auch einen CI-Server, der unter Windows läuft. Also das sollte sich deutlich bessern. Aber es ist halt ganz interessant, weil man dann auch Ruby on Rails in JVM-Umgebungen einfach nutzen kann und da kommt man natürlich bei vielen Kunden im Geschäftsumfeld dann auch an Projekte und kann die einfach davon überzeugen, eben die Produktivität von Rails ein bisschen zu nutzen, in den Projekten.

Stefan Tilkov: Ok. Wenn man starten will, falls einer unserer Hörer Lust hat, sich darum zu kümmern, was ist ein guter Einstieg?

Robert Glaser: Ein guter Einstieg ist es auf jeden Fall, immernoch empfehle ich die tatsächlich, diese berühmten Tutorial-Videos “Build your own Blog in ten minutes” (oder “fifteen minutes”). Dieses Video war damals von “DHH” aufgenommen, als Rails gerade raus kam, und da hat er einfach in so einem ScreenCast gezeigt, wie er einen Blog baut in 15 Minuten mit Rails. Das ist natürlich irgendwann hoffnungslos veraltet gewesen, weil Rails sich halt sehr schnell weiter entwickelt und so ein Video dann nicht mit skaliert. Dann empfehle ich immer wieder, vielleicht erstmal kein Rails Buch zu kaufen, sondern wirklich die Ruby on Rails Guides zur Rate zu ziehen – http://guides.rubyonrails.org/. Das ist einfach eine quasi in Buchform geschriebene Sammlung von Anleitungen und How-Tos zu den Komponenten von Rails. Und diese Texte werden mit den Rails Versionen versioniert. Das heißt, die sind immer sehr sehr aktuell. Was ein Buch gar nicht bieten kann. Bücher gibt es sicher auch gute, können wir in den Shownotes noch ein paar verlinken. Wer Interesse hat, das für sein Team zu machen, kann bestimmt nochmal auch bei uns eine Rails-Schulung bekommen.

Stefan Tilkov: Da können wir bestimmt drüber reden.

Robert Glaser: Ja.

Stefan Tilkov: Ok. Gut. Hast du noch berühmte letzte Worte? Was erwartest du für die Zukunft? Bleibst du bei Rails? Machst du was anderes?

Robert Glaser: Ich bleibe erstmal bei Rails. Gehe aber immer mit offenen Augen durch die Welt. Aber da gibt es bisher nicht so überragende, überzeugende konkurrierende Frameworks. Ja ansonsten steht noch Rails 5 am Horizont. Ich glaube, das ist für Frühling oder Sommer 2015 so ein bisschen angedacht. Wird wahrscheinlich fest Ruby 2.2 erfordern. Und wird nochmal größere Umbauten mit sich bringen, ähnlich wie Rails 3. Dadurch, dass man jetzt sehr viel alten Balast über Bord wirft, viele Meta-Programmierungsgeschichten können weg fallen, da Ruby jetzt Standard-Sprachmittel dafür bietet. Das wird sicher nochmal spannend, ob es dann kracht, beim Upgrade unserer vielen Anwendungen.

Stefan Tilkov: Alles klar. Ok, dann danke ich dir vielmals. Wir haben uns natürlich – wie immer – nur an der Oberfläche gekratzt.

Robert Glaser: Definitiv, ja.

Stefan Tilkov: Mal gucken, ob wir vielleicht noch eine Stufe tiefer rein gehen können. Ansonsten freuen wir uns wie immer über Feedback und bis zum nächsten Mal. Danke dir Robert.

Robert Glaser: Vielen Dank.

In Memoriam ∞ CEO & Principal Consultant

Stefan Tilkov war Geschäftsführer und Principal Consultant bei INNOQ Deutschland, wo er sich vorwiegend mit der strategischen Beratung von Kunden im Umfeld von Softwarearchitekturen beschäftigte. Er war Autor des Buchs “REST und HTTP”, Mitherausgeber von “SOA-Expertenwissen” (beide dpunkt.verlag), Autor zahlreicher Fachartikel und häufiger Sprecher auf internationalen Konferenzen.

Wir trauern um Stefan.

Head of Data and AI

Robert Glaser ist Head of Data & AI bei INNOQ. Mit einem Hintergrund im Software Engineering und einer Leidenschaft für benutzerfreundliche Webanwendungen begleitet er heute Unternehmen durch die KI-Landschaft. Dabei unterstützt er sie bei der Entwicklung von Strategien und Produkten für schwierige technische Herausforderungen. Fasziniert von der Vielseitigkeit generativer KI, moderiert er den Podcast “AI und jetzt”. Ihm ist die Brücke zwischen Technologie und Business ein Herzensanliegen. In seiner Freizeit erkundet er die lokale Food Szene.