- Einstieg: Thema nennen, Kuerzel DI einfuehren
- Nicht auf dem Titel verweilen
- Sektionsauftakt: Warm-up und Kontext
- Roadmap kurz zeigen: 10 Stationen, heute alles ein roter Faden
- Kurz vorstellen, Bezug zum Projekt herstellen
- Nachfragen, welche Backends/Frameworks im Projekt genutzt werden
- Ziel der Folie: alle im Thema abholen und Semesterziel verankern
- Mit einem Beispiel aus der Praxis starten (z.B. "Wir haben am Ende alles in einem Service gehabt...")
- Herausarbeiten lassen, dass Kopplung, Testbarkeit und Teamarbeit leiden
- Noch keine Loesung im Detail verraten
- Diagramm nutzen, um Bauchgefuehl zu erzeugen
- Injector baut ServiceA1/ServiceB1 und injiziert sie in den Client
- Schnell, interaktiv halten
- Ergebnisse laut wiederholen ("Viele von euch..."), um spaeter Bezug zu nehmen
- Kein langes Ausdiskutieren, nur Stimmungsbild
- Explizit Bezug zu den beiden Spring-Boot-Vorlesungen herstellen
- DI ist ein Querschnittsthema, das in vielen Technologien wiederkehrt
- Motivieren: "Wenn ihr das heute gut versteht, spart ihr euch spaeter viel Frust."
- Typische Erfahrungen der Studierenden einsammeln ("Wer hat sowas schon gemacht?")
- Diese Vorgehensweise ist nachvollziehbar, kippt aber ab einer bestimmten Groesse
- Typische Erfahrungen der Studierenden einsammeln ("Wer hat sowas schon gemacht?")
- Diese Vorgehensweise ist nachvollziehbar, kippt aber ab einer bestimmten Groesse
- Code einmal laut "lesen", auf Zeile mit new EmailService() zeigen
- Frage: "Was passiert, wenn wir eine andere Implementierung brauchen?"
- Noch keine Loesung an dieser Stelle, nur Problemgefuehl verstaerken
- Stichpunkte mit Beispielen aus dem Code verknuepfen (Testbarkeit, Wartbarkeit, Wiederverwendung)
- Studierende kurz ergaenzen lassen, ob ihnen weitere Probleme einfallen
- 1-2 Minuten Silent Thinking oder Austausch in Zweiergruppen
- Erwartung: Tests ohne DI werden sehr umstaendlich
- Anschliessend 1-2 Antworten einholen und auf die naechste Folie ueberleiten
- Pseudocode als Aufhaenger: gemeinsam fragen "Wie wuerden wir das jetzt testen?"
- Typische Antworten (Log pruefen, Fake-Server) notieren und als fragil markieren
- Dann als Motivation fuer saubere DI nutzen
- Bruecke schlagen: "Wir wollen Abhaengigkeiten sichtbar und austauschbar machen."
- Betonung auf Testbarkeit, Teamarbeit und klare Vertraege
- Diese Punkte immer wieder als roter Faden aufgreifen
- Jetzt Begriffe sauber legen: Dependency, IoC, DIP
- Begriffe sind das Fundament fuer die Framework-Teile spaeter
- Begriff sehr einfach halten, viele Beispiele nennen (Logger, Repo, Config)
- Studierende bitten, spontan weitere Dependencies aus ihren Projekten zu nennen
- Mit Alltagsmetapher arbeiten (z.B. Restaurant: Kochen selbst vs. bekocht werden)
- DI ist eine konkrete Art, diese Umkehr der Kontrolle umzusetzen
- Nicht zu tief in Theoriediskussion abgleiten
- Kurz auf SOLID verweisen, nicht jedes Detail erklaeren:
- Single Responsibility (Einzelverantwortung), Open/Closed (Offen/Geschlossen)
- Liskov Substitution, Interface Segregation, Dependency Inversion
- Fokus: High-Level haengt von Abstraktionen ab, nicht von Implementierungen
- Mit einfachem Beispiel (Interface vs. konkrete Klasse) verankern
- Code Schritt fuer Schritt erklaeren
- Nachfragen: "Wo stecken hier die Abstraktionen? Wo waeren konkrete Implementierungen denkbar?"
- Erwartung: EmailPort ermoeglicht die Austauschbarkeit
- Kurz nachfragen, ob jemand bereits einen Service Locator gesehen hat (z.B. alte Frameworks)
- DI macht Abhaengigkeiten sichtbar in Signaturen, Service Locator versteckt sie
- Keine religioese Debatte, nur Problemstellen benennen
- Fragen nacheinander stellen, jeweils kurz 1-2 Antworten einholen
- Falls wenig Resonanz: Antworten selbst skizzieren und betonen, warum Abstraktionen hilfreich sind
- Vorteil "fertig initialisiertes Objekt" betonen
- Frage in die Runde: "Was spricht gegen viele Konstruktorparameter?"
- Erwartete Antwort: zu viele Dependencies als Design-Signal
- Drei Formen klar nebeneinanderstellen, alle haben dasselbe Grundziel
- Ankuendigen: Constructor Injection wird der Standard, die anderen bleiben als Werkzeuge im Kopf
- Vorteil "fertig initialisiertes Objekt" betonen
- Frage in die Runde: "Was spricht gegen viele Konstruktorparameter?"
- Erwartete Antwort: zu viele Dependencies als Design-Signal
- Implementierung laesst sich zur Laufzeit wechseln
- Gleichzeitig Risiko unvollstaendig initialisierter Objekte
- Beispiel fragen: "Wo koennte das sinnvoll sein?" (z.B. optionaler Logger)
- Kommt eher in Frameworks vor als im eigenen Domaenenmodell
- Nicht zu sehr vertiefen, nur als Ergaenzung zeigen
- Im Alltag selten explizit noetig
- Tabelle als Gegenueberstellung nutzen
- Studierende aktiv fragen, welche Variante sie spontan bevorzugen und warum
- Constructor Injection als Default-Option klar empfehlen
- Aufgabe stellen und 2 Minuten fuer Austausch geben
- Loesungserwartung: Logger meist Constructor oder ggf. Setter
- FeatureToggleService je nach Dynamik eher Setter/wechselbare Implementierung
- Ergebnisse kurz im Plenum sammeln
- Singleton ist nicht automatisch schlecht, es kommt auf den Zustand an
- Frage: "Was passiert, wenn config zur Laufzeit geaendert wird?" Risiken von Mutable State anreissen
- Mit einem Bug-Beispiel einsteigen ("Logger merkt sich zu viel", "User-Kontext wird geteilt")
- Lebensdauer ist genauso wichtig wie die Wahl der Abhaengigkeiten
- Begriffe Singleton, Transient, Request sauber definieren
- Auf bekannte Frameworks beziehen (Angular, Nest, Spring)
- Kurz nachfragen, wo die Studierenden diese Begriffe schon gesehen haben
- Singleton ist nicht automatisch schlecht, es kommt auf den Zustand an
- Frage: "Was passiert, wenn config zur Laufzeit geaendert wird?" Risiken von Mutable State anreissen
- Unterschiede mit kleinen Beispielen illustrieren (RequestContext vs. Berechnungsobjekt)
- Viele Frameworks bringen diese Scopes bereits mit, DI hilft beim bewussten Einsatz
- Loesungserwartung diskutieren:
- DatabaseConnectionPool: Singleton/aehnlicher globaler Scope
- ShoppingCart: Session/Request/Benutzer-spezifisch
- FeatureFlagCache: Singleton mit periodischer Aktualisierung
- Antworten der Studierenden ernst nehmen, Unterschiede begruenden
- Zeigen, wie der Container selbst beim Bauen Abhaengigkeiten aufloest
- Frage: "Wo wird entschieden, welche konkrete Implementierung genutzt wird?"
- Erwartung: in der Registrierung, nicht in der Fachlogik
- Begriff "Container" entmystifizieren: im Kern nur ein smarter Objekt-Bauer
- Beispiele aus bekannten Frameworks nennen (NestJS, Spring, Angular)
- Ziel: Angst vor "Magie" nehmen
- Registrierung vs. Aufloesung klar machen
- Frage: "Wuerdet ihr lieber manuell ueberall new schreiben oder zentral konfigurieren?"
- Vorteile fuer Konfiguration sammeln
- Code nicht Zeile fuer Zeile implementieren lassen, die Idee erklaeren:
- Map von Tokens zu Factories, Lazy-Bau von Singletons
- Echte Frameworks haben mehr Features, bauen aber auf diesem Prinzip auf
- Zeigen, wie der Container selbst beim Bauen Abhaengigkeiten aufloest
- Frage: "Wo wird entschieden, welche konkrete Implementierung genutzt wird?"
- Erwartung: in der Registrierung, nicht in der Fachlogik
- Das Konzept auf ihr Projekt mappen: Welche Module waeren sinnvoll (User, Board, Notifications ...)?
- Kurz Ideen sammeln
- Konfigurationsquellen mit realen Beispielen verbinden (ENV-Variablen, .env-Datei)
- Offene Diskussion zulassen, aber zeitlich im Blick behalten
- Betonen: Container darf nicht "magisch alles koennen", sondern soll bewusst eingesetzt und verstanden werden
- Von den Konzepten zu Leitplanken fuer das eigene Projekt
- Leitplanken als Checkliste fuer das Projekt vorstellen
- Vorschlagen, diese Punkte in Code-Reviews explizit zu verwenden ("Hat die Klasse klare Dependencies?")
- Beispiele aus typischen Projekten nennen (z.B. UserService macht alles)
- Studierende fragen, ob sie solche Klassen kennen
- Loesungsidee: nach Bounded Contexts und Verantwortlichkeiten schneiden
- Als Geruchsindikator darstellen: viele Dependencies, Klassendesign pruefen
- Bei mehr als 4-5 Dependencies kritisch werden und pruefen, ob aufgeteilt werden kann
- Auf statische Singletons und globale Variablen eingehen
- Typische Testprobleme schildern (Zustand bleibt zwischen Tests)
- Alternative: explizite Injection und klarer Lebenszyklus
- Ein einfaches Beispiel skizzieren (User/Order)
- Zyklen sind technisch (Container-Fehler) und fachlich ein Warnsignal
- Loesung ueber neue Fassade oder Events
- Null Object Pattern kurz erklaeren: Default-Implementierung statt ueberall if-Checks
- Beispiel NoopLogger/NoopMetrics
- DI ist ideal, um solche Defaults zentral einzuhaengen
- Jetzt selbst anwenden: drei kurze Uebungen plus Quiz
- Erwartete Loesung: Dependencies u.a. DbClient, ConsoleLogger, req, res
- Diskussion: was sollte per DI kommen (DbClient, Logger), was bleibt Framework-Infrastruktur (req/res)
- Ergebnis sichtbar notieren
- Nach der Arbeitsphase gemeinsam markieren: new ConsoleLogger() im Code ist ein Hinweis auf fehlende DI
- Loesungsskizze muendlich entwickeln:
- Interface Logger mit info()
- Konstruktor nimmt Logger entgegen
- Container registriert ConsoleLogger
- Optional fragen, wie ein FakeLogger im Test aussieht (z.B. Array von Messages sammeln)
- Erwartete Zuordnung:
- ConfigService: meist Singleton
- RequestContext: Request/Session
- DiscountCalculator ohne Zustand: oft Transient oder stateless Service
- Diskussionsunterschiede zwischen Teams zulassen und begruenden lassen
- Fragen nacheinander stellen, Studierende antworten lassen
- Falls unsicher: Stichworte am Whiteboard sammeln (IoC vs DI, Vorteile Constructor Injection, Probleme globaler Singletons, Symptome God Service)
- Zweiter Framework-Blick: dieselben Prinzipien auf der JVM
- Nur Ueberblick, kein Volltutorial; die Details kommen in Spring Boot Teil 1 und 2
- Studierende mit Java-Erfahrung kurz berichten lassen, wo sie Spring/Spring Boot schon gesehen haben
- Anhand der Annotationen erklaeren, wie der Container weiss, was er registrieren soll
- Parallele zu Annotationen als Registrierung und zum eigenen Container ziehen
- Nicht alle Annotationen im Detail erklaeren, nur Rollen skizzieren
- Constructor Injection im Java-Code hervorheben
- Frage: "Was wuerde passieren, wenn wir hier zusaetzlich @Autowired am Feld nutzen?"
- Gelegenheit, kurz auf Field Injection vs Constructor Injection hinzuweisen
- Zeigen, dass hier explizit Beans registriert werden, aehnlich zu unseren Container-Registrierungen
- Beispiel "FakeMailClient vs SmtpMailClient" andeuten und als Uebergang zu Profiles nutzen
- Konzepte an praktischen Szenarien erklaeren (dev/test/prod)
- Studierende fragen, wie sie aktuell Test- und Prod-Konfiguration unterscheiden
- Bruecke schlagen zu austauschbaren Implementierungen via DI
- Wieder betonen: dieselben Prinzipien, andere Sprache/Framework
- Verstaendnis der DI-Kernideen hilft, sich in verschiedenen Stacks schnell zurechtzufinden
- Zum Abschluss: zusammenfassen und den Bogen zu den naechsten Vorlesungen schlagen
- Kernaussagen noch einmal klar und langsam formulieren
- Studierende bitten, in eigenen Worten zu wiederholen, was DI fuer sie bedeutet
- Offene Fragen notieren
- Explizit ankuendigen, was praktisch erwartet wird (Live-Coding, Workshops)
- Gelegenheit geben, Wuensche zu Themen zu aeussern (z.B. Testing, spezifische Framework-Fragen)