We're sorry but this page doesn't work properly without JavaScript enabled. Please enable it to continue.
Feedback

Data Flow Patterns in Angular 2

00:00

Formale Metadaten

Titel
Data Flow Patterns in Angular 2
Serientitel
Anzahl der Teile
16
Autor
Lizenz
CC-Namensnennung 3.0 Unported:
Sie dürfen das Werk bzw. den Inhalt zu jedem legalen Zweck nutzen, verändern und in unveränderter oder veränderter Form vervielfältigen, verbreiten und öffentlich zugänglich machen, sofern Sie den Namen des Autors/Rechteinhabers in der von ihm festgelegten Weise nennen.
Identifikatoren
Herausgeber
Erscheinungsjahr
Sprache

Inhaltliche Metadaten

Fachgebiet
Genre
Abstract
Angular 2 enthält viele neue Konzepte zum Umgang mit Events und Daten innerhalb der Applikation. Durch die Integration von Reactive Extensions (RxJS) in das Framework können Entwickler auf eine mächtige Library zurückgreifen, die den Umgang mit asynchronen Operationen (wie Events und XHR) wesentlich erleichtert und die Performance der Applikation deutlich verbessern kann. Weitere Performancesteigerungen sind darüber hinaus durch den Einsatz von Immutable-Datenstrukturen (Immutable.js) möglich. Der Vortrag vermittelt die Grundlagen und Vorteile von RxJS und Immutable.js im Zusammenspiel mit Angular 2.
DatenflussGoogle MapsApp <Programm>TemplateKommunikationINGA <Programm>JavaScriptProgrammierungBetafunktionVersion <Informatik>Open SourceManufacturing Execution SystemOperatorFilterung <Stochastik>DatentransformationClientAPIHTTPEin-AusgabeDetektionTyp <Informatik>TICSRoutingAttributierte GrammatikCodeDatenstrukturDatentypEigenwertproblemInformationKommunikationMengeSchnittstelleUNIXZeichenketteFunktion <Mathematik>Physikalische GrößeProgrammierungFRAMEWORK <Programm>AnwendungssoftwareSenderMAPLeadOperatorChipkarteIndexLaufzeitLEKTOR <Programmiersprache>MomentenproblemRAMRang <Mathematik>ZählenE-MailVersion <Informatik>Apple <Marke>ServerEckeNichtlinearer OperatorParametersystemOrbit <Mathematik>WEBTemplateASIA <Programm>EARNACCESS <Programm>Hauptreihe <Mathematik>SchnittmengeEin-AusgabeStrom <Mathematik>TAXPascal-ZahlendreieckInstanz <Informatik>RandPOWER <Computerarchitektur>James <Programm>EinfügungsdämpfungDatenstromJavaScriptBrowserSun <Marke>European Physical SocietyKomponente <Software>ClientEreignishorizontQuoteWeb SiteBenutzerprofilPalm <Marke>Objekt <Kategorie>InternetdienstARM <Computerarchitektur>OISCSocket-SchnittstelleSkypeDemoszene <Programmierung>Google MapsYouTubeMechanismus-Design-TheorieSoftwareentwicklerApp <Programm>TuningGanze FunktionSystemprogrammZugbeanspruchungNetzadresseDetektionHTTPQuellcodeGraphische PrimitiveKonstruktor <Informatik>SelektorDickeVorlesung/Konferenz
Transkript: Deutsch(automatisch erzeugt)
Ja, hört man mich gut soweit? Perfekt. Ja, ich möchte heute so ein bisschen über Dataflow-Patterns in Angular 2 sprechen. Das ist mein erster Talk und ich habe gedacht, ich probiere das jetzt auch mal aus,
wie das so funktioniert. Und ich habe in der letzten Zeit so ein bisschen die Erfahrung mit Angular 2 gesammelt. Kurz zu meiner Person, wie schon gesagt, ich arbeite bei Adesso, beschäftige mich da eigentlich auch mit AngularJS, baue da eine große Anwendung seit zwei Jahren, also doch schon etwas größer. Und habe jetzt in den letzten Jahren ein bisschen damit begonnen,
eine Open Source Library für Google Maps zu schreiben. Also dass ihr ganz einfach mit Angular 2 halt Google Maps erzeugen könnt und das halt in euren Angular 2 Applikationen verwenden könnt. Dabei hat man natürlich eine ganze Menge gelernt.
Und bei Angular 2 ist es ja aktuell so, dass wir in einem RC-Status sind. Wir haben die erste RC-Version bekommen und wir sind ja auf einem guten Weg, dass auch irgendwann jetzt mal die stabile Version rauskommt. Da sind wir noch nicht ganz, aber man merkt schon, was das Framework für Konzepte hat und dass da eine Menge Power hintersteckt.
Natürlich die wichtigste Neuerung, die wir wirklich haben, finde ich, ist das Konzept von Components. Also dass unsere Applikation einen sogenannten Component Tree darstellt, wo ich im Prinzip eine Root Component habe, was meine Applikation darstellt, was wir vielleicht aus NG App von Angular 1 kennen
und dann halt darunter immer Child Components habe, die dann meine Anwendungsteile darstellen. Das hat natürlich auch bei Angular 1.5 eine Rolle gespielt. Ab 1.3 gab es ja auch eine Syntax, wo ich sagen konnte, okay, ich schreibe jetzt in einem mehr oder weniger Component Style meine Anwendung
und in 1.5 haben wir natürlich dann ja auch diesen Component Syntax bekommen, den wir jetzt ja auch schon aktiv verwenden können. Ich habe das Ganze auch hier nochmal in so einem Beispiel dargestellt, wie das vielleicht aussehen könnte in so einer kleinen Applikation, dass ich halt eine Root Component habe, die heißt jetzt hier einfach mal Application.
Dann habe ich vielleicht noch irgendwo eine Main Navigation, das heißt, da hätte ich auch nochmal eine separate Component mit einem Template und vielleicht auch irgendwo in der Anwendung darstellt so eine User Liste, wo ich halt meine Liste der Benutzer darstellen möchte. Das wäre wie gesagt alles so ein Component Tree
und ich wollte jetzt einfach mal, damit jeder abgeholt wird, der vielleicht noch nicht Angular 2 gesehen hat, kurz mal eine kleine App dazu zeigen, wie die jetzt hier aussehen könnte. Das haben wir heute schon kennengelernt in den anderen Talks. Dieses Beispiel ist jetzt hier mit TypeScript geschrieben, was ja auch die primäre Sprache ist,
die man eigentlich mit Angular 2 verwenden sollte, aus meiner Sicht. Wir haben also hier oben eine definierte Component mit dem My App Selector, also muss das ein Element sein namens My App auf der Seite und habe dann dazu einfach ein festes Template definiert. Das natürlich auch mit dem ECMAScript 6 Multiline Strings,
was eigentlich ganz praktisch ist, wenn man kurze Templates hat und habe dann in meiner Komponente hier unten gesagt, dass es einen Titel gibt, das ist vom Typ String und habe dann dort einfach Text hinterlegt. Dann muss ich noch als letztes, das kennt man auch so ein bisschen von Angular 1, diese Bootstrap Methode aufrufen,
wo ich dann einfach meine Applikation initialisiere. Angular 2 sucht sich das entsprechende Element auf meiner Seite, was dann so halt aussehen könnte. Ich habe das jetzt mal ein bisschen runtergebrochen, aber letztendlich brauche ich dann irgendwo in meiner Index.html halt dieses Element, was ich definiert habe und dann wird halt die Anwendung gebootstrapped. Das ist erst mal so grob der Aufbau, wer das vielleicht noch nicht gesehen hat.
Ja, dann noch ein weiteres wichtiges Thema ist die Component Kommunikation. Wie kann ich jetzt mit diesen einzelnen Komponenten kommunizieren? Das muss ja auch irgendwie möglich sein, Daten übergeben oder Events weitergeben.
Da könnte es vielleicht so einen Fall geben. Ich habe vielleicht so ein User, User App und da habe ich vielleicht in dieser Root Component userdefiniert als Object mit einem Username und einer E-Mail Adresse und habe jetzt vielleicht so eine Component geschrieben, die mir jetzt diesen Nutzer schön aufbereitet darstellen kann in so einer Card.
Da muss ich natürlich jetzt dieser Card Component irgendwie diesen User übergeben. Und auch dafür gibt es ein ja nicht grundlegend neues Konzept im Vergleich mit Angular 1, aber es hat sich schon ein bisschen geändert, wie man das Ganze halt jetzt umgesetzt hat. Und zwar sind das die entsprechenden Inputs,
die wir jetzt definieren können, wo wir sagen können, was kann ich jetzt von der Außenwelt in meine Komponente rein geben? Auch hierzu habe ich jetzt noch mal das Beispiel gemacht. Das ist jetzt hier diese dargestellte User App, also diese Root Komponente, was ich als mit dieser Bootstrap Methode
aufrufen würde in meiner Applikation. Habe auch hier wieder diesen Component Decorator verwendet. Habe gesagt, der Selektor ist meine App und muss jetzt hier halt noch mal explizit angeben, welche anderen Komponenten ich denn in meinem Template verwenden möchte. In dem Fall ist es diese User Card, die ich mir auch dann oben importiert habe,
was einfach jetzt in einem anderen TypeScript File liegt und habe dann da auch wieder ein Template definiert, wo ich im Prinzip jetzt diese User Card halt aufrufe über dieses User minus Card Element und dann die entsprechenden Details des Users über ein Input an die Komponente weitergebe.
So hier auch nochmal die ja das User Card Element, also das, was dann den konkreten Nutzer darstellen würde. Da sieht man jetzt auch diesen Input Decorator, den ich hier definiert habe.
Also das importiere ich ja auch nochmal aus dem Core Package, was man ganz oben in der ersten Zeile sieht. Und was ich dann dort unter Karte Details reinbekomme, ist natürlich der konkrete Nutzer, den ich, wenn ich noch mal kurz zurückgehe, hier dann in dem Template übergeben habe. Ich habe gesagt Karte Details gleich User und dadurch kriege ich dann
die Nutzer Information in meine Komponente reingegeben und kann dann einfach mit Karte Details arbeiten und habe den entsprechenden User dann zur Aufbereitung da. Ja, das ist die eine Möglichkeit, Daten in diese Komponente reinzugeben
über einfache Objekte oder Strings oder sonst was, worauf ich aber heute noch zu sprechen kommen möchte und das auch ein großer Teil in Angular 2 sein wird, ist RxJS. Das werden vielleicht auch noch nicht viele gehört haben. Das hat sich meiner Meinung nach in den letzten Monaten,
seitdem Angular 2 irgendwie darauf gesetzt hat und gesagt hat, wir integrieren das fest in das Framework, ist das halt erst richtig aufgepoppt und wird jetzt immer mehr zu einem Thema. So fühlt es sich zumindest an. Was man auch sagen muss, ist RxJS ist halt fest in das Framework integriert. Also es ist eine feste Dependency und auch viele APIs
in dem Framework selber basieren auf der API von RxJS. Und ihr könnt jetzt auch in dem Framework sehr gut mit RxJS kommunizieren. Das werden wir uns jetzt mal angucken in einfachen Beispielen. Die API, die da zum Zuge kommt, ist grundsätzlich erst mal observables.
Vielleicht hat das schon mal der eine oder andere gehört. Ich habe hier auch noch mal einen kleinen Überblick über die über die Funktionen von RxJS gegeben. Also es ist eine Library für Reactive Programming. Das ist auch ein Begriff, was in letzter Zeit immer mehr auftaucht.
Ist auch aktuell noch im Meta-Status. Also die Version 5 wird gerade noch aktiv entwickelt. Ist also gleichzusetzen mit RxJS, die sind jetzt nicht mehr im Beta-Status, aber es ist halt gerade noch in Entwicklung und noch nicht für Produktion gedacht. Wird auch von sehr großen Filmen entwickelt.
Netflix ist da so der Haupttreiber. Vielleicht hat der eine oder andere schon mal Ben Lesch gehört. Der ist so ein bisschen der Lead-Ingenieur dahinter und treibt das Projekt halt für die neue Version 5. Das ganze Projekt RxJS gibt es schon ein paar Jahre. Das sieht man halt auch an der Version 5. Aber wie gesagt, jetzt seitdem Angular 2 das halt einsetzt,
wird es immer mehr ein Thema. Genau und das wichtigste, ja, der wichtigste Baustein für diese reaktive Programmierung ist halt das observable, was wir uns heute auch noch angucken wollen. Wo man im Prinzip, ja, reaktive Programmierung
auch in seinen Angular 2 Apps bringen kann. Ja, was sind observables? Da möchte ich zuerst drauf eingehen. Was können wir damit überhaupt machen? Wenn wir uns das heute mal angucken, was wir so für Primitiven haben im JavaScript-Bereich für Asynchronität, aber auch für synchrone Ereignisse,
sage ich mal, da haben wir zum Beispiel die ganz normalen Functions. Das ist also nach dem Pull-Prinzip und es arbeitet synchron. Ich rufe die Funktion auf und bekomme Ergebnis zurück. Das wäre erst mal die Plain Function, die wir im JavaScript schon immer hatten.
Dann in ECMAScript 2015 haben wir die Iterators dazu bekommen, wo ich halt über beliebige, ja, Datenmengen iterieren kann mit diesen Next-Aufrufen, die der ein oder andere schon mal vielleicht gesehen hat. Da ist aber auch das Pull-Prinzip. Das heißt, ich kriege mehrere Ergebnisse zurück,
nicht wie bei einer Funktion nur eins. Muss aber aktiv danach fragen, dass ich den nächsten Wert bekomme. Das ist so ein bisschen der Unterschied dazwischen. Dann auf der anderen Seite nach dem Push-Prinzip. Also ich werde benachrichtigt im Prinzip, wenn es ein Value gibt.
Das sind die Promises, die haben wir jetzt auch schon ein bisschen länger. Die gibt es auch schon in Angular 1 seit zig Jahren. Die haben aber den Nachteil, dass sie nur genau einen Wert eigentlich zurückgeben. Entweder war vielleicht ein Ajax-Request erfolgreich oder es hat schiefgelaufen, weil 500 auf dem Server oder sonst was.
Aber Promises ist erst mal dafür ausgelegt, dass wirklich nur ein Wert zurückkommt. Und in diese Lücke, die wir jetzt da oben sehen. Ja, diese Lücke füllt im Prinzip, füllen im Prinzip die Observables, die wir uns jetzt gleich mal angucken werden. Denn die arbeiten nach diesem Push-Prinzip. Das heißt, ich werde benachrichtigt, wenn es einen neuen Wert gibt.
Die können aber auch mehrere Werte zurückgeben und nicht nur ein, wie bei Promises. Das hat der große Vorteil, warum es auch vielleicht attraktiv ist bei WebSockets zum Beispiel. Bei WebSockets kriege ich ja über eine undefinierte Zeitraum kriege ich irgendwie Nachrichten zurück. Das ist mit Promises nicht schön abzubilden, weil Promises im Prinzip nur einen Wert zurückgeben kann.
Und dafür sind auch Observables sehr gute Primitive, kann man sagen. Ben Lesch hat auch mal gesagt, ja, Observables oder RxJS sind, ja, ist Lodash für asynchrone Daten im Prinzip.
Also wenn ich einen Ajax Call mache oder WebSockets Kommunikation habe. Ich habe nämlich noch eine ganze Menge Operators, die wir gleich noch kennenlernen werden, wo ich dann halt diese asynchronen Daten ströme. Das sind ja im Prinzip Ströme, weil über einen undefinierten Zeitraum neue Werte reinkommen. Ich diese Werte auch noch transformieren kann,
genauso wie ich das vielleicht aus Lodash kenne, diese ganzen Funktionen und sonst was. Das habe ich auch in RxJS. So, dann möchte ich mal kurz einen kleinen Einstieg machen. Wie denn jetzt so ein Observable überhaupt erzeugt wird?
Ich habe hier aus der RxJS Package das Observable importiert. Da kann ich einfach so eine Create Methode aufrufen. Und diese Create Methode erzeugt mir im Prinzip ein neues Observable. So was ich jetzt der Observable in dieser Create Methode übergeben muss,
ist im Prinzip der Code, der ausgeführt werden soll. Wenn einer sich jetzt über dieses Observable informieren lassen möchte, wenn es also einen neuen Wert gibt, dann würde genau diese Methode ausgeführt werden. Der Unterschied ist aber zu Promises,
dass man jetzt vielleicht denken könnte, wenn ich hier dieses Observable erzeuge, dann wird auch der Code in dieser Methode aufgerufen und er würde jetzt hier vielleicht jede Sekunde einen neuen Wert zurückgeben. Das ist diese NEX Methode, die wir hier sehen. Damit kann ich halt neue Werte zurückgeben in diesem Observable.
Das ist aber nicht der Fall, sondern diese Methode, die ich jetzt hier definiert habe, die wird halt nur aufgerufen, wenn sich auch einer aktiv darüber informieren lassen möchte. Und das geht über diese Subscribed Methode, die wir jetzt sehen. Das sieht dann so aus.
Ich hole mir also mein Observable, was ich hier oben erzeugt habe und rufe die Subscribed Methode auf. Und das erste Argument ist gleichzusetzen mit das, was wir bei Promise Then kennen. Also wenn ich Then aufrufe, gebe da eine Funktion rein, dann wird dort die Funktion aufgerufen, wenn diese asynchroner Operation fertiggestellt worden ist.
Das Gleiche ist hier der Fall. Und auch erst jetzt, wenn ich wirklich diese Subscribed Methode aufgerufen habe, wird der Code da oben ausgeführt, die wir in dieser Observer Funktion gesehen haben. Erst dann wird es wirklich aktiv aufgerufen. Das ist also schon mal vom Konzept her ein bisschen unterschiedlich zu den Reihen Promises.
Die erzeugt man halt, dann rennt der Code los. Und hier muss man wirklich aktiv sagen, ja, Subscribed. Und dann wird wirklich auch der Code da oben erst ausgeführt. Ja, hier sieht man dann auch nochmal die Demo dazu.
Also er würde jetzt hier jede Sekunde im Prinzip einen neuen Wert zurückgeben. Ich habe da hier ein Konsolok einfach eingeschrieben und dementsprechend würde man dann auch alle neue Werte sozusagen zurückbekommen, was dann halt der Unterschied zu den Promises ist.
Jetzt gibt es aber noch eine weitere Geschichte, die man auch nicht per Promises machen kann. Und zwar kann man das Ganze auch noch mit einem Unsubscribed aufrufen. Ich habe hier wieder mein Observable, ich habe hier ein neues Observable erzeugt. Das ermittelt hier mit dieser Next Methode jetzt jede Sekunde auch wieder einen neuen Wert.
Also gibt jede Sekunde einen neuen Wert zurück. Was ich hier aber zusätzlich gemacht habe, ist eine Funktion zurückzugeben. Diese Unsubscribed Methode. Und die wird aufgerufen, wenn ich sage, ich möchte mich nicht mehr über neue Werte informieren lassen.
Das sehen wir jetzt gleich noch. Das sehe dann nämlich so aus. Ich habe auch hier wieder jetzt meine Subscribed Methode aufgerufen, möchte mich also über die Werte informieren lassen. Das heißt, da oben der Code würde jetzt loslaufen. Und dann habe ich hier unten noch mal einen weiteren Call gemacht.
Wenn ich jetzt sage, nach zweieinhalb Sekunden möchte ich mich nicht mehr über neue Werte informieren lassen, dann würde genau die Methode aufgerufen werden, die wir da oben zurückgeben. Also Return Function Unsubscribed. Das ist also die Funktion, wo wir aufräumen können. Wo wir wissen, der Nutzer möchte jetzt nicht mehr über neue Werte informiert werden,
weil er die Operation vielleicht abgebrochen hat. Und ich kann dann halt in dieser Funktion aufräumen. Und aufräumen heißt in dem Fall, dass ich dieses Intervall, was ich oben erzeugt habe, kläre, dass das nicht halt weiter noch im Browser ausgeführt wird. Das heißt, auch da bin ich ein bisschen flexibler im Gegensatz zu Promises
und kann dort irgendwelche Sachen abbrechen, aufräumen, wenn ich weiß, ich möchte jetzt nicht mehr über neue Werte informiert werden. Genau, hier sieht man das jetzt auch mal ein Beispiel. Ich bekomme mal zwei Werte und die drei sehe ich jetzt hier nicht mehr, weil halt nach zweieinhalb Sekunden im Prinzip diese Unsubscribed Methode aufgerufen wird.
Ja, hier auch noch mal im Vergleich mit den Promises. Promises haben wir ja schon ein bisschen länger. Man sieht hier, Promises hat ja zwei Funktionen, die ich übergeben kann. Einmal für den Erfolgsfall, wenn mein AJAX Request
zu leicht erfolgreich durchgelaufen ist und einmal für den Fehlerfall. Und so kann ich das händeln. Bei den Observables ist es auch erst mal gleichzusetzen. Die ersten beiden Methoden sind im Prinzip gleich aufgebaut, nur dass man bei der ersten Funktion, die ich übergebe, halt weiß, dass es halt auch mehrere Werte geben kann, die dort reingegeben werden.
Bei der Subscribed Methode gibt es aber trotzdem noch einen dritten Parameter, den ich übergeben kann, also eine dritte Funktion. Und das hat einfach den Hintergrund, dass ich dort mich informieren lassen kann, wenn dieses Observable wirklich fertig gelaufen ist.
Also wenn ich sage in diesem Observable, da kommt jetzt kein neuer Wert. Diese Operation ist wirklich für immer abgebrochen. Dann kann ich mich über diese dritte Funktion darüber informieren lassen und noch irgendwelche Logik ausführen, die vielleicht für den Fall noch relevant sein könnte. Das habe ich hier oben auch mal gemacht. Ich habe halt gesagt,
ich gebe erst mal einen Wert zurück, eine Eins sofort, wenn dieses Observable ja subscribt wird und habe dann gesagt, nach einer Sekunde soll er nochmal zwei zurückgeben und dann halt diese Complete Methode aufrufen. Ja, hier sieht man das auch nochmal.
Ich bekomme also zwei Werte zurück und dann würde im Prinzip diese Completed Methode oder Funktionen aufgerufen werden, die wir hier ganz unten sehen. Ja, zu diesen Observables, die wir jetzt gesehen haben, wie wir die grundlegend erst mal erzeugen können, gibt es auch noch Operators, also das, was wir vielleicht aus LODASH kennen.
Diese ganzen Utility Methoden, auch die gibt es in RxDS für diese Observables. Das könnte hier mal so aussehen. Auch hier habe ich jetzt wieder diesen Timer, den wir jetzt schon ein paar mal gesehen haben. Was ich hier aber zusätzlich mache, ist ein Operator Anwenden namens MAP.
Den gibt es ja auch bei JavaScript Arrays. Ist ja alles bekannt soweit, nur dass ich das jetzt hier auf jeden Wert anwenden kann, der irgendwie ja zurückgegeben wird mit dieser NEXT Methode. Das heißt, wenn wir uns das hier oben angucken, jede Sekunde wird ein Wert zurückgegeben und dieser Counter hochgezählt. Und das würde dann durch diese MAP Methode zuerst durchlaufen.
Und der Wert würde mal zwei dann halt zurückgegeben werden. Das heißt, ich kann diesen Wert dort auch noch mal transformieren in irgendein Format, was ich gerne habe. Und das, was dann in dieser MAP Methode rauskommt, das wird dann im Prinzip an meine Subscribed Methode weitergegeben.
Also sehr praktisch. Und im Prinzip wird es dazu, dass wir dann auch zwei und vier sozusagen rausbekommen, weil es erst durch die MAP Methode läuft. So das erst mal kurz zu den Observables als kleine Grundlage. Observables oder XJS besser gesagt ist eigentlich kompletten.
Ja, hat eigentlich einen kompletten TORG verdient. Und es gibt noch insgesamt 100 Operators, die man anwenden kann. Also es ist sehr mächtig. Man kann damit sehr viel Kram machen. Ich habe mal hier nur so ein paar gängige drauf gepackt. Filter kennen wir, Plug kennen wir vielleicht auch Slow Dash,
Gruppierung, Scan. Also da gibt es eine ganze Menge und das muss man sich halt auch separat einfach mal angucken. So hier auch noch mal ein kurzer Vergleich mit Observables, wo jetzt halt die Unterschiede liegen, die wir jetzt auch so ein bisschen gesehen haben, dass Promises halt genau einen Wert zurückgeliefert.
Bei Observables können es 0 bis N sein. Es ist einfach nicht definiert, wie viele da wirklich zurückkommen. Promises kann man auch aktuell nicht abbrechen. Und auch das ist ein Thema, was aktuell in Diskussion ist. Da wird heiß diskutiert auf GitHub, ob das so klug wäre,
ein Promise auch abzubrechen. Da scheinen sich so ein bisschen die Geister. Muss man einfach mal abwarten, wie es da in Zukunft einfach weitergeht. Ja, genau. Bei dem Observable kann ich das halt mit Unsubscribe dann auch wirklich konkret abbrechen. Und bei Promises natürlich habe ich jetzt keine konkreten Operators,
die ich noch irgendwie anwenden kann. Da kann ich mich zwar irgendwie behelfen, aber ich habe halt nichts Aktives, was die API mir einfach bietet, was wir gerade mit MAP gesehen haben als Beispiel. Genau, das ist mal als kleine als kleiner Vergleich. Ich hatte ja gesagt, RxJS ist fest integriert.
Also wir haben eine feste Abhängigkeit. Wenn ein Angular 2 Projekt aufsetzt, müsste auch RxJS installieren und mit ins Projekt einbinden. Was man da vielleicht auch noch zu sagen kann an der Stelle dieser Observable Standard, der wird auch aktuell
als JavaScript Standard diskutiert. Da gibt es auch schon Proposal, was jetzt, glaube ich, auch in letzter Zeit ein bisschen weitergegangen ist. Also es kann sein, dass wir irgendwann nativ wirklich im Browser diese Observables auch bekommen. Da muss man einfach mal abwarten, wie das in nächster Zeit da weitergeht.
So, um jetzt mal wieder auf Angular 2 zurückzukommen. Man fragt sich natürlich jetzt, warum habe ich das jetzt alles erklärt? Weil ich jetzt noch mal zurückkommen wollte, wo man das jetzt auch wirklich im Framework sieht oder auch anwenden kann, diese Observables. Indirekt verwendet man die schon, wenn man die Outputs von Angular 2 verwendet.
Ich kann ja, wenn man nochmal auf diese User App zurückkommt mit dieser User Card, kann ich ja auch von Komponenten mich informieren lassen über irgendein Ereignis. Das haben wir heute auch schon ein paar Mal gesehen. Vielleicht möchte diese User Card sagen, dass der Benutzer vielleicht auf den E-Mail senden Button geklickt hat.
Und da möchte ich mich in meiner User App von informieren lassen, wenn das der User vielleicht gemacht hat. Und dafür sind halt genau diese Outputs gedacht. Das könnte dann vielleicht so aussehen. Ich habe also immer noch meinen User, den ich übergebe, über Card Details und lasse mich über ein Event informieren, send E-Mail,
wo ich dann eine Methode aufrufe, um zum Beispiel ein E-Mail-Formular anzuzeigen. Könnte vielleicht ein gängiger Fall sein. Das ist unter der Haube auch ein Observable. Also im Framework ist das Ganze so integriert. Das Ganze nennt sich Event Emitter.
Wird man vielleicht auch schon mal gesehen haben, wenn man so enger zwei Komponenten geschrieben hat. Und ich habe das auch hier noch mal dargestellt, wie das Ganze aussieht. Was man hier jetzt macht, ist im Prinzip ein neues Observable für dieses Send E-Mail Event zu erzeugen.
Also Event Emitter. Man sieht also nicht wirklich, dass es ein Observable ist. Aber unter der Haube ist es das. Das wird halt jetzt aktiv versteckt. Und man soll es auch nicht direkt so verwenden. Aber unter der Haube ist es wirklich ein RxJS Observable. Und auch hier sieht man, dass ich jetzt halt diese Methode E-Mail
klickt aufrufe, wenn der User da vielleicht auf eine Überschrift jetzt in dem Fall geklickt hat und rufe dann über this send E-Mail die Emit-Methode auf. Das ist eigentlich das, was wir vorhin gesehen haben über die NEXT Methode. Also diese Emit-Methode ist im Prinzip nichts anderes unter der Haube, was diese NEXT Methode macht.
Und das wird dann halt aktiv von dem Framework verwendet für die Change Detection, für die Informierung der anderen Komponenten, die sich auf dieses Event registriert haben. Das passiert dann alles unter der Haube. Ja, was wir jetzt gesehen haben, ist ja im Prinzip, dass wir Inputs haben, um Daten in andere Elemente zu geben.
Um damit dann zu arbeiten über die Inputs und über die Outputs sozusagen ja, uns über Events informieren lassen können in diesen einzelnen Komponenten. Soweit so gut. Das ist ja auch bekannt unter Unidirectional Dataflow,
was bei React ja auch schon länger ein Thema ist und was jetzt halt auch bei Angular 2 ein Thema wird. Nächstes Thema ist die sogenannte Async Pipe. Wer den Begriff Pipe noch nicht kennt, das sind im Prinzip die Filter aus Angular 1
und bei Angular 2 gibt es halt einen bestimmten Filter, der sich jetzt einfach Async nennt. Womit ich jetzt auch diese Observables ja einfach auch ganz leicht verwenden kann. Ich kann nämlich Folgendes machen. Auch hier mal eine kleine Komponente oder auch gleich eine Applikation im Prinzip.
Ich habe jetzt hier in meiner App so einen Counter initialisiert, was ein Observable ist. Man sieht auch hier, das ist ein Generic. Also wenn ihr TypeScript verwendet, wird das Ganze noch ein bisschen leichter zu handeln, weil ihr genau wisst, was da aus diesem Observable rauskommt für den Datentyp
und habe jetzt hier einfach gesagt, dass ich auch hier jede Sekunde diesen Counter hochzähle und habe dann noch zusätzlich eine Methode zurückgegeben. Das sieht man dann ganz hier unten, wo dann im Prinzip wieder dieser Intervall geklärt wird, wenn sich jetzt keiner mehr aktiv an diesen Event subscribt.
Was dann hier passiert in dem Template ist, dass ich diesen Async Pipe da oben verwende. Da sieht man das ja in dem Template und diese ganze Logik, also das, was wir eigentlich jetzt vorher manuell gemacht haben, das Subscribe aufrufen und dann irgendwas eine Funktion übergeben. Das macht im Prinzip jetzt AngularJS für uns unter der Haube
und kann halt mit diesen Observables jetzt einfach umgehen und würde dann im Prinzip auch den Wert, diesen Counter, wenn er sich jetzt hochzählt, auch wirklich im Template aktualisieren. Also das kriegen wir alles mit dieser Async Pipe einfach geschenkt, weil er genau weiß, wie er mit Observables umgehen muss.
Vielleicht am Rande auch noch die Info, dass ihr auch dort Promises verwenden könnt mit dieser Async Pipe. Also es ist nicht nur auf Observables ausgelegt, sondern auch auf Promises. Auch da wäre dann die Möglichkeit, das ganz leicht so ein Template zu verwenden. Eine weitere Geschichte, wo Promises, nicht Promises, Observables eine Rolle spielen, sind Formularfelder.
Auch da gibt es eine Möglichkeit, mit Observables zu arbeiten. Das habe ich auch hier nochmal in einem Beispiel ja fertig gemacht. Und zwar habe ich hier mal ein ganz einfaches Formular zusammengestellt. Man sieht hier, dass ich ein Energy Form Control verwende,
wo ich im Prinzip ein Input reingebe, was jetzt einfach vom Typ Control ist, was man hier sieht. Das hat einfach Logik in sich von Angular 2, was jetzt konkret dieses Formularfeld beschreibt. Und zusätzlich habe ich dann noch ein Result definiert,
was ein Observable ist von Type Any. Das wäre jetzt auch erstmal möglich, wenn man sich jetzt nicht auf einen Typ festlegen möchte. Und im Prinzip das, was jetzt in dieser Init Methode steht, das ist einfach ein Life Cycle Event. Das spielt jetzt nicht so eine große Rolle. Die Methode wird einfach aufgerufen, wenn die Komponente initialisiert worden ist.
Dann rufe ich dieses My Input auf. Also das ist ja das, was hinter diesem Control steckt. Und dieses My Input hat ein Attribut, was sich Value Changes nennt. Und hinter diesen Value Changes versteckt sich ein Observable, was ich jetzt halt in meiner Anwendungslogik verwenden kann.
Und da kann ich dann wieder ganz normal alle Operators benutzen, die mir jetzt halt von RxJS gegeben sind, um dann zum Beispiel hier auch diese Map Methode aufzurufen und den Wert dann mal 2 zu nehmen, was der Benutzer halt eingetippt hat. Und das kann ich natürlich dann wieder in Kombination
mit der Async Pipe benutzen und einfach den Wert, der da transformiert worden ist, mit der Map Methode direkt im Template anzeigen. Das ist also eine Sache, die finde ich halt sehr praktisch, dass man halt an Input Felder drankommen kann und da direkt ein Observable bekommt, womit man dann arbeiten kann,
wenn es Veränderungen in dem Feld gibt. Das ist halt schon super praktisch. Eine weitere Geschichte, wo sich auch Observables finden, ist in dem HTTP Package. In Angular 2 haben wir das so aufgebaut,
dass der HTTP Client, den man verwenden kann, ein separates Package ist. Also ich muss das separat installieren, wenn ich das verwenden möchte. Und auch da spielen Observables eine Rolle. Hier noch mal kurz zusammengefasst ist halt ein XHR Client, um, wie wir das auch in Angular 1 Anwendung kennen, einfach AJAX Request zu machen.
Ich bekomme halt noch so ein paar Features dazu, wie die für das Unit Testing wichtig ist, wenn ich irgendwelche Request mocken möchte, die nicht ans Backend weitergehen sollen. Dann habe ich da halt noch so ein paar Mocking Features dabei, die ich nutzen kann. Ja, hier auch noch mal ein kleines Beispiel,
wie ich jetzt die HTTP Client, den HTTP Client von Angular 2 verwenden kann. Da hole ich mir per Dependency Injection einen Instanz von diesem HTTP Service rein, was man in dem Konstruktor hier sieht. Und in dieser NG OnInit Methode rufe ich dann einfach mit this.http.get
meine API auf, wo jetzt vielleicht mein JSON API liegt. Und diesem ja das Ergebnis aus dieser Get Methode ist ein Observable. Und das Observable ja gibt Werte zurück vom Typ Response. Also das ist einfach
ein Objekt mit verschiedenen Methoden. Und eine Methode ist halt diese Jason Methode, wo ich halt sagen kann, wenn ich Jason vor meiner Schnittstelle zurückbekommen habe, möchte ich das vielleicht als JavaScript Objekt parsen. Und das passiert dann konkret mit dieser Jason Methode. Und ich kann das dann halt auch direkt wieder in meinem Template
so verwenden mit der Async Pipe. Was man auch hier sieht, ist, dass ich die Pipes auch kombinieren kann. Das heißt, ich kann als erstes diese Async Pipe aufrufen, was meine Observable subscribt und auf den Wert wartet. Und wenn dieser Wert halt ausgeführt worden ist, lasse ich das nochmal durch eine Jason Pipe laufen,
was dann im Prinzip dieses JavaScript Objekt wieder in einen lesbaren String umwandelt. Macht natürlich jetzt nicht real wirklich Sinn, aber soll einfach mal verdeutlichen, dass man die auch gut hintereinander packen kann, die Dinge. So als letztes zum Thema Observables könnt ihr auch Folgendes machen.
Das könnte vielleicht auch ein Anwendungsfall sein, wie ich schon mal am Anfang geschrieben habe. Könnte nicht nur Objekte als Inputs in eure Komponenten reingeben, sondern ihr könnte theoretisch auch sagen, ich gebe Observables in meine Komponente rein. Auch das würde funktionieren. Vielleicht hier mal als Beispiel so ein kleiner Stock Component,
wo ich vielleicht den aktuellen Stock Price reingebe. Und auch den könnte ich dann mit dieser Async Pipe einfach aufrufen und hätte dann sozusagen auch da die Möglichkeit, mit Observables zu arbeiten. Dann möchte ich noch kurz auf das Thema Performance kommen.
Die Performance in Angular 2 ist natürlich sehr stark angestiegen. Da hat sich schon viel gebessert. Auch die Change Detection ist davon eine Performance. Man hört manchmal so zehnmal schneller geworden,
schon schon sehr viel schneller insgesamt für die Anwendung geworden. Man kann aber auch da noch ein bisschen Tuning machen und die Anwendung halt so strukturieren, dass zum Beispiel die Change Detection nur da laufen muss, wo sich auch zum Beispiel Inputs geändert haben. Da möchte ich jetzt noch mal kurz drauf zu sprechen kommen.
Da wäre ja das Keyword im Prinzip Change Detection Strategy. Wenn wir uns das mal angucken. Da möchte ich auch noch mal kurz auf den Talk verweisen, der gleich noch kommt von dem Pascal Precht. Der wird ja noch ein bisschen über die Change Detection sprechen.
Da werdet ihr das dann wahrscheinlich noch viel genauer erklärt bekommen, als ich das jetzt hier mache. Ich möchte nur einfach kurz mal auf so ein paar Tuning Möglichkeiten zu sprechen kommen, die ihr einfach habt. Ich habe mal hier so einen Fall gemacht, dass ich hier so eine einfache Applikation habe, oben so eine Routekomponente,
dann so eine User Profile Komponente, wo vielleicht der Benutzer dargestellt wird. Und dann habe ich noch rechts so eine Hauptnavigation. Die müssen wir uns jetzt nicht weiter angucken. Jetzt stellen wir uns mal vor, dass in diesem User Objekt, was wir oben links sehen, diese E-Mail Adresse irgendwie zur Laufzeit geändert wird. Also in meiner Applikations Logik durch irgendein Event,
was vielleicht durch den Nutzer ausgelöst worden ist, steht da auf einmal in diesem Objekt eine andere E-Mail Adresse drin. Könnte ein gängiger Anwendungsfall sein. Was dann passiert. Ist in der Anwendung oder in der in dem Framework, dass ein Event ausgelöst worden ist. Wir haben auch heute schon mal gehört, das Ganze funktioniert
unter der Haube mit Zone.JS, das checkt halt jedes Event, was irgendwie in dem Browser stattfindet. Und das würde jetzt im Prinzip auch die Change Detection auslösen. Also wenn jetzt irgendeiner hier this.user.email gleich ein neuer Wert aufgerufen hat, dann würde jetzt im Prinzip auch diese Change Detection ausgelöst werden. Das könnte dann im Prinzip so aussehen.
Also es ändert sich jetzt die E-Mail Adresse auf new.abc.de. Wir haben also einen neuen Wert. Das ist durch irgendein Event ausgelöst worden, durch einen Klick, durch keine Ahnung, ein User hat irgendwas anderes ins Feld eingegeben. Dann würde im Prinzip die Change Detection jetzt für alle Komponenten laufen,
die in dieser Anwendung halt irgendwie registriert sind. Das wäre erst mal so das Standardfalten nach jedem Browser Event wird in der einzelnen Komponenten gecheckt, ob sich irgendwas aktualisieren muss im Template. Das wäre so das Standardfalten. Um das jetzt ein bisschen schneller zu machen, gibt es da kommen wir jetzt wieder zurück auf die Change Detection
Strategy, die Möglichkeit, die sogenannte on push Strategie zu verwenden, was dazu führt, dass wirklich nur gecheckt wird in diesem Komponent, wenn sich auch wirklich die Inputs ändern, also nur die Inputs und nicht bei jedem Browser Event, was theoretisch alles Mögliche sein könnte.
Das führt aber auch gleichzeitig dazu, dass diese Inputs mit einem Deep Equal Check geprüft werden. Das heißt, es muss sich aktiv wirklich die Objektreferenz ändern, damit es als Änderung gekennzeichnet wird in der Applikation und für diese neue Komponente dann auch wirklich die Change Detection läuft.
Wie man vielleicht weiß, sind so Deep Equal Checks schon ziemlich langsam und allein das ist schon ein bisschen der Performance Vorteil, weil gleich drei Gleichzeichen zu checken ist halt schon viel, viel schneller in JavaScript. Und das führt halt dazu, dass die Anwendung auch da ein bisschen weniger Zeit braucht, um diese Checks dann wirklich durchzuführen.
Hier nochmal auf das Beispiel zurück. Ich habe jetzt mal hier für diese Komponenten diese on push Methode eingeschaltet für das User Profile und die Main Navigation und auch hier nochmal das Beispiel, dass sich halt irgendwo in der Anwendung diese E-Mail Adresse ändert,
was jetzt dazu führt, dass sich leider gar nichts tut. Denn wenn ich jetzt this.user.email aufrufe und da einen neuen Wert hinterlege, dann hat sich aber leider nicht die Objektreferenz geändert, weil ich habe im Prinzip nur in diesem Objekt ein Wert geändert.
Jetzt habe ich da mehrere Möglichkeiten, das Ganze zu lösen. Und eine wollte ich heute mal kurz zeigen, und zwar ImmutableJS. Das wird man vielleicht mal aus dem React Thema kennen. Mit ImmutableJS bekomme ich halt Immutable Datenstrukturen, die ich verwenden kann.
Da werden eine ganze Menge unterstützt. Und der Anwendungsfall ist halt zum Beispiel, ich setze jetzt eine neue E-Mail Adresse und wenn ich diese neue Adresse setze, bekomme ich halt ein komplett neues Objekt, was halt kopiert worden ist. Und ich habe dann auch eine andere Objektreferenz. Das heißt, in diesem Fall würde dann auch die Change Detection wieder loslaufen.
Um das mal ein bisschen klarer zu machen, habe ich auch hier noch mal ja, ImmutableJS mal kurz angeschmissen. Ich habe mal hier gesagt, ich erzeuge eine Map. Das passiert da oben mit diesem Book. Da ist ein Title definiert. Und jetzt gibt es halt eine Methode, um jetzt bestimmte Attribute zu aktualisieren, zum Beispiel diesen Title.
Da kann ich halt sagen New Title. Und das spuckt mir im Prinzip ein komplett neues Objekt draus. Diese Set-Operation. Und wenn ich halt diese beiden Objekte miteinander vergleiche, haben die halt eine andere Objektreferenz. Und diesen Mechanismus könnte ich dann halt nutzen, um halt die Change Detection
ja, damit dann auszulösen, weil es halt eine andere Objektreferenz geworden ist. Eine Demo habe ich dazu auch vorbereitet. Die zeige ich jetzt hier aus Zeitgründen nicht. Das werde ich aber auch noch mal hochladen, wer das vielleicht mal sich angucken möchte. Da ist dann halt genau ja, dieser Set-Mechanismus aufgerufen worden.
Das ist dann das, was jetzt hier im Prinzip passieren würde. Das habe ich hier noch mal kurz dargestellt. Ich merke mir halt diesen neuen User. Also rufe diese Set-Methode auf. Möchte das E-Mail Attribut verändern mit der neuen E-Mail Adresse. Dadurch bekomme ich eine neue Objektreferenz. Und auch dann würde Folgendes passieren.
Er erkennt dieser User, den ich da übergebe, der Komponente hat eine neue Objektreferenz. Also muss ich da die Change Detection ausführen. Und dann würde auch dementsprechend in der Komponente, in dem Template ja, die neue E-Mail Adresse angezeigt werden. Ja, also, wie gesagt, ist nicht so einfach erst mal im ersten Moment, das alles, diese neuen APIs aufzunehmen.
Da muss man, die muss man sich auch mal separat alle ganz in Ruhe angucken. Aber man sieht halt, das Framework unterstützt sie alle sehr, sehr gut. Genau, auch hier nochmal zurück, dass gleich der Talk von Pascal Precht stattfindet, wo ihr dann nochmal weiter Details zur Change Detection erklärt bekommt.
Ja, weiterführende Themen vielleicht für euch, die jetzt nochmal sich weiter da einlesen möchten. Die ja das Team von Angular ist halt gerade aktuell dabei, eine ganze Menge Reaktive,
ja, Libraries rund um Angular 2 aufzubauen. Das bekannteste wäre hier vielleicht der Store, also NGIX Store, was man vielleicht kennt aus dem React Bereich. Redux ist da so ein Begriff. Das ist im Prinzip Redux mit Observables, also auch sehr mächtige Geschichte. Ist auch, glaube ich, einen eigenen Talk wert.
Aber wer da einfach mal reingucken möchte, da gibt es eine ganze Menge aktuell. Und auch für RxJS gibt es auf Eckerd.io eine ganze Menge sehr guter Kurse, auch von den Entwicklern von RxJS, wo man einfach mal reingucken kann. Das ist auch sehr zu empfehlen.
Dann noch ein kurzes Fazit. Und dann haben wir es auch geschafft. Ihr habt ja gesehen, mit Angular 2 könnt ihr sehr viele Kommunikationswege einschlagen, mit verschiedenen Datentypen arbeiten, mit Observables arbeiten, mit Immutable.js sehr gut arbeiten. Und da halt einfach Performance Vorteile rausziehen.
Alles das ist mit dem Framework sehr gut möglich. Was man aber auch sagen muss, habe ich jetzt auch schon ein paar Mal gesagt, RxJS ist sehr mächtig, bietet uns sehr viele Methoden. Dauert aber auch eine ganze Menge Zeit, bis man sich da wirklich eingearbeitet hat. Das muss man sich halt separat wirklich angucken zu Angular 2 und sich da einfach einarbeiten.
Die Change Detection ist sehr schnell. Das haben wir jetzt auch schon ein paar Mal gehört. Aber natürlich, wenn ihr on push verwenden könnt und wirklich nur die Inputs checken müsst in dieser Komponente, dann solltet ihr das auch aktivieren. Somit hat man einfach schon Performance Vorteile in der Anwendung geschenkt.
Und als letztes sollte man sich auf jeden Fall auch in diesem ganzen Angular 2 Context, der jetzt so langsam aufkommt, auch mal auf React schauen, weil da sind halt in den letzten Jahren ziemlich viele Konzepte entstanden rund um Components, wie man Components schneidet. Und diese Konzepte machen halt auch sehr stark in dem Angular 2 Kontext Sinn.
Von daher auch in diesem Kontext sollte man auf jeden Fall mal reinschauen. Ja, das war's soweit.