Start / Seminare / Quarkus für Spring-Boot-Teams
Modul
Dependency Injection von Spring zu CDI
4 Kapitel in diesem Modul-Video · Laufzeit
Transkript
Der gesprochene Text dieses Moduls zum Mitlesen, Überfliegen und Durchsuchen. Ein Klick auf einen Zeitstempel springt an die Stelle im Video.
Dependency Injection von Spring zu CDI
0:00 Dependency Injection ist der Baustein, den Sie am häufigsten anfassen — und deshalb der, bei dem eine Migration am schnellsten spürbar wird. Die gute Nachricht: Quarkus bietet eine Kompatibilitätsschicht, mit der Ihre gewohnten Spring-Annotationen weiter funktionieren. Die wichtige Nachricht: Diese Schicht liest Spring-Annotationen, aber sie führt keinen Spring aus.
0:21 Dieser eine Satz entscheidet darüber, was funktioniert und was still im Nichts verläuft. In diesem Modul sehen wir beides an — die Kompatibilitätsschicht als Zwischenschritt und CDI als Ziel.
Dependency Injection von Spring zu CDI
0:33 Wir sind beim ersten der drei Bausteine, die Sie täglich benutzen. Nach diesem Modul wissen Sie, welche Spring-Annotation worauf abgebildet wird, wo die Grenzen liegen und wie eine schrittweise Umstellung aussieht, die nach jedem Schritt noch lauffähig ist. Danach folgen REST und Konfiguration — die beiden anderen Bausteine des ersten Tages.
Spring-DI-Annotationen und ihre Kompatibilitätsschicht
0:53 Beginnen wir mit dem bequemen Weg: Die Annotationen bleiben, wie sie sind. Sehen wir uns an, wie weit dieser Weg trägt — und wo er endet. Die Extension für Spring-DI erlaubt, bekannte Annotationen weiterzuverwenden. Wichtig ist, was dabei tatsächlich passiert: Die Spring-Klassen und -Annotationen dienen ausschließlich als Metadaten — als Etikett, das Quarkus liest.
1:16 Die Infrastrukturklassen von Spring selbst werden nicht ausgeführt. Das Bild: Sie behalten die Beschriftung Ihrer Schalter, aber dahinter liegt eine komplett neue Elektrik. Solange Sie die Schalter so benutzen wie vorgesehen, merken Sie keinen Unterschied. Sobald Sie hinter die Blende greifen, schon. Diese Tabelle müssen Sie nicht auswendig können, aber ein Muster sollte hängen bleiben.
1:40 Die drei Stereotypen für Komponenten, Services und Repositories landen alle beim selben Ziel — einem Singleton. Das heißt: Die feinen Bedeutungsunterschiede, die Sie in Spring vielleicht bewusst gesetzt haben, verschwinden hier. Konfigurationsklassen werden zu einem anwendungsweiten Scope, Bean-Methoden zu Producern. Und die letzten beiden Zeilen sind die ehrlichsten: Component Scanning und Import gibt es schlicht nicht, weil beides zur Laufzeit suchen würde — und Quarkus hat zu diesem Zeitpunkt längst entschieden.
2:09 Diese vier Punkte kosten am meisten Zeit, deshalb lohnt es sich, sie zu kennen, bevor man sie erlebt. Optionale Injektion im Spring-Stil gibt es nicht — dafür brauchen Sie den CDI-Weg über eine Instance. Bei Sammlungen ist nur die Liste unterstützt, nicht Set oder Map. Bei Mehrdeutigkeit fällt Quarkus nicht auf den Bean-Namen zurück, wie Spring es tut; Sie müssen benennen.
2:31 Und bedingte Beans werden ignoriert, weil zur Bauzeit noch keine Laufzeitbedingung feststeht. Der letzte Punkt ist der gefährlichste, weil er lautlos passiert: Die Bean ist einfach da, obwohl die Bedingung nie erfüllt war.
CDI Beans und Quarkus ArC
2:45 Damit zum Zielbild. CDI ist kein exotischer Ersatz, sondern ein Standard, der dieselben Aufgaben löst — mit ein paar Begriffen, die Sie kurz einordnen müssen. Der wichtigste Begriff ist der Scope. Bei den sogenannten normalen Scopes — anwendungsweit oder pro Anfrage — bekommen Sie beim Injizieren nicht das Objekt selbst, sondern einen Stellvertreter, einen Client Proxy.
3:08 Das eigentliche Objekt entsteht erst beim ersten Methodenaufruf. Bei Pseudo-Scopes wie Singleton bekommen Sie die Instanz direkt. Das Bild: Der Proxy ist die Telefonnummer eines Handwerkers. Sie können sie weitergeben, ohne dass jemand losfahren muss — der Handwerker kommt erst, wenn wirklich angerufen wird. Das spart Startzeit und löst nebenbei Zyklen auf.
3:31 Hier sehen Sie oben und unten dasselbe fachliche Ding, einmal in Spring-Schreibweise, einmal in CDI. Der Punkt dieser Folie ist nicht die Syntax, sondern wie klein der Unterschied ist. Genau deshalb ist die Umstellung machbar — und genau deshalb wird sie oft zu leicht genommen. Denn was Sie hier nicht sehen, ist die Entscheidung dahinter: Aus einem Service wird ein Singleton, wenn Sie es nicht anders sagen.
3:54 Ob das für Ihre Bean richtig ist, verrät Ihnen keine Tabelle. Und die Fußnote gilt für beide Varianten: Konstruktorinjektion bleibt der empfohlene Weg. CDI ist kein reduziertes Spring, es hat eigene Stärken. Producer-Methoden ersetzen Bean-Methoden aus Konfigurationsklassen. Qualifier trennen sauber, wenn es mehrere Implementierungen derselben Schnittstelle gibt — sie sind die typisierte Antwort auf das, was in Spring oft über Namen gelöst wird.
4:21 Events erlauben eine Entkopplung innerhalb des Prozesses, ohne dass Sie dafür einen Broker brauchen. Und Interceptors übernehmen, was vorher über Aspekte lief. Wer nur mechanisch übersetzt, verschenkt genau diese vier Möglichkeiten. Der erste Punkt ist der berühmteste Anfängerfehler: Eine Bean wird nur reflektiv benutzt, ArC hält sie für ungenutzt und entfernt sie.
4:43 Die Lösung ist eine einzige Annotation — man muss sie nur kennen. Der zweite Punkt betrifft die Wahl des Scopes: Singleton ist bequem, aber falsch, wenn ein Stellvertreter gebraucht würde. Der dritte ist die fehlende Indizierung einer Fremdbibliothek. Und der vierte ist eine Gewohnheit: Feldinjektion wird beibehalten, obwohl sie Tests erschwert.
5:04 Wenn Sie ohnehin jede Klasse anfassen, stellen Sie gleich auf Konstruktorinjektion um.
Schrittweise Umstellung
5:09 Bleibt die Frage nach dem Weg. Alles auf einmal umzustellen ist verlockend, weil es sich nach Sauberkeit anfühlt — und es ist der sicherste Weg in einen Zustand, in dem nichts mehr läuft. Die Kompatibilitätsschicht ist ein Zwischenschritt, kein Ziel. Die Quarkus-Dokumentation sagt das selbst sehr deutlich: Für neue und dauerhaft gepflegte Anwendungen wird CDI empfohlen.
5:31 Die Spring-Variante hat trotzdem ihren Wert — sie senkt den Aufwand der ersten Migrationsstufe erheblich und erlaubt, zuerst zu prüfen, ob die Anwendung auf Quarkus überhaupt läuft. Das Bild: Sie ziehen in ein neues Haus zunächst mit den alten Möbeln ein. Aber Sie sollten wissen, dass Sie das tun — und wann Sie sie ersetzen.
5:50 Diese Kette beschreibt genau die Reihenfolge, die wir im ganzen Seminar verwenden. Zuerst bleibt Spring-DI, und Sie beantworten eine einzige Frage: Läuft die Anwendung überhaupt auf Quarkus? Erst wenn das geklärt ist, wird Schicht für Schicht auf CDI umgestellt. Und der letzte Kasten ist der, der am häufigsten vergessen wird: die Kompatibilitätsschicht wieder entfernen.
6:12 Solange sie im Build steht, wissen Sie nicht, ob Sie fertig sind — denn was noch auf sie angewiesen ist, fällt erst beim Entfernen auf. Fünf Schritte, und der erste ist der wichtigste: Nehmen Sie eine Komponente samt ihren Abhängigkeiten in einem Schnitt, nicht mitten im Graphen. Beim Scope bitte nicht mechanisch übersetzen, sondern kurz überlegen, welche Lebensdauer das Objekt wirklich hat. Konstruktorinjektion als Standard.
6:38 Wertzugriffe aus der Konfiguration wandern auf die typisierten Gegenstücke — dazu mehr in Modul sechs. Und nach jedem Schnitt laufen die Tests. Die Fußnote ist wichtig: Spring-Boot-Testfunktionen deckt die Kompatibilitätsschicht nicht ab, dafür brauchen Sie den Quarkus-Weg. Die vier Punkte beschreiben vier Wege, sich das Leben schwer zu machen. Mitten im Abhängigkeitsgraph anzufangen hinterlässt einen Mischzustand, den niemand mehr überblickt.
7:05 Die Kompatibilitätsschicht dauerhaft im Build zu lassen bedeutet, dass sich nie jemand zuständig fühlt, sie loszuwerden. Scopes mechanisch zu übersetzen heißt, die Lebensdauer dem Zufall zu überlassen. Und der vierte ist der teuerste: umzustellen, bevor Tests das alte Verhalten festhalten. Dann haben Sie hinterher zwar neuen Code, aber keine Aussage darüber, ob er dasselbe tut.
Übung
7:28 Jetzt probieren wir beides an Pfandkreis aus — erst die bequeme Variante, dann die saubere. Und wir machen die Probe aufs Exempel. Die Aufgabe hat bewusst zwei Stufen. Zuerst bringen Sie die Abrechnungskomponente mit ihren Spring-Annotationen unter Quarkus zum Laufen. Erst danach stellen Sie sie auf CDI um — mit bewusst gewähltem Scope, mit Konstruktorinjektion und mit typisierter Konfiguration statt einzelner Werte.
7:53 So ist jeder Schritt einzeln prüfbar, und wenn etwas bricht, wissen Sie sofort, woran es lag. Das ist dieselbe Logik, die wir später auf die gesamte Migration anwenden. Achten Sie beim Umstellen besonders auf den Scope: Die Abrechnung hält womöglich Zustand zwischen zwei Aufrufen, und dann ist ein anwendungsweiter Scope etwas anderes als ein Singleton.
8:14 Der vierte Schritt ist der eigentliche Test dieser Übung: Entfernen Sie die Extension für Spring-DI und bauen Sie neu. Was jetzt bricht, war vorher nur scheinbar migriert — es hing weiter an der Kompatibilitätsschicht. Diesen Handgriff sollten Sie sich merken, denn er funktioniert bei jeder Kompatibilitätsschicht in diesem Seminar: bei Spring Web, bei Spring Data. Das Entfernen ist der Nachweis.
8:37 Alles davor ist eine Absichtserklärung. Und noch etwas, das über diese Übung hinausreicht: Wenn Sie ohnehin jede Klasse anfassen, ist das der günstigste Zeitpunkt, Feldinjektion durch Konstruktorinjektion zu ersetzen. Diese Gelegenheit kommt so bequem nicht wieder. Vier Punkte für die Nachbesprechung. Erstens bleibt die Extension gern im Build stehen, obwohl längst keine Spring-Annotation mehr vorkommt — sie kostet dann nur noch Buildzeit.
9:03 Zweitens wird beim Tauschen aus einer zustandsbehafteten Bean versehentlich ein Singleton; das fällt erst unter Last auf, und dann unschön. Drittens bleibt der Konfigurationszugriff auf einzelnen Strings stehen, statt typisiert zu werden. Und viertens werden die Tests erst am Ende angefasst und melden dann alles gleichzeitig — statt Schritt für Schritt.
Lieber mit Trainer? Dieses Modul ist Teil unserer Team-Schulungen — mit Übungen, Ihrem eigenen Code und Fragen, die ein Video nicht beantwortet. Mehr erfahren →