Skip to content

Philosophie des State-Managements

🎯 Kernfrage

Wenn die Anwendung immer größer wird, wie können Komponenten elegant Daten teilen und synchronisieren? Du könntest auf folgendes Problem stoßen: Der Nutzer legt ein Produkt in den Warenkorb, aber die Warenkorb-Anzahl in der Kopfzeile wird nicht aktualisiert; zwei nicht verwandte Komponenten benötigen dieselben Daten, wissen aber nicht, wie sie diese übergeben sollen. Dieses Kapitel führt dich von der „chaotischen Datenübergabe" zum „klaren State-Management".


1. Warum „Komponentisierung und State-Management"?

1.1 Von der Werkstatt zur Fabrik: Die Entwicklung der Frontend-Entwicklung

Bevor wir richtig anfangen, eine Frage vorab: Hast du schon einmal versucht, in der Küche ein großes Festmahl zuzubereiten?

Wenn du nur für dich selbst eine Schüssel Nudeln kochst, ist das ganz einfach – ein Topf, eine Handvoll Nudeln, etwas Würze, in zehn Sekunden erledigt. Aber wenn du ein Restaurant eröffnest und jeden Tag Hunderte von Gästen bedienst, kannst du nicht mehr einfach „machen, wonach dir ist". Du brauchst standardisierte Rezepte, klare Aufgabenteilung und einheitliche Beschaffungsprozesse, damit jedes Gericht gleichbleibend hochwertig ist und die Küche effizient arbeitet.

Genauso ist es in der Frontend-Entwicklung. Wenn eine Person ein kleines Projekt schreibt, ist es egal, wo der Code liegt. Aber wenn das Team wächst und das Projekt komplexer wird, braucht man eine systematische Methode, um Code zu organisieren und Daten zu verwalten. Genau das lösen Komponentisierung und State-Management.

🤔 Was sind „Komponenten" und „State"?

Bevor wir weitermachen, erklären wir zwei Kernbegriffe:

Komponente (Component): Wie ein Lego-Baustein – jeder Baustein ist ein eigenständiger Teil mit eigener Form, Farbe und Funktion. Du kannst mehrere Bausteine zusammensetzen, um eine komplexe Burg zu bauen. In der Frontend-Entwicklung kann ein Button, ein Formular oder eine Navigationsleiste eine Komponente sein.

State (Zustand): Das ist das „Gedächtnis" einer Komponente. Zum Beispiel ein Button, der sich „merkt", ob er deaktiviert oder aktiviert ist; eine Warenkorb-Komponente, die sich „merkt", welche Produkte darin sind. State verändert sich, und State-Änderungen lösen UI-Updates aus.

Komponentisierung + State-Management = Organisierter Code + Klarer Datenfluss

🏠 Werkstatt-Modus

  • Code steht in einer Datei, wie alle Gerichte in einem Topf zu kochen
  • Daten werden überall hin übergeben, wie Kellner, die mit Tabletts im Restaurant herumirren
  • Eine Änderung kann andere Stellen beeinflussen, wie zu viel Salz, das das ganze Gericht ruiniert

🏭 Fabrik-Modus

  • Code ist in Komponenten aufgeteilt, wie ein Restaurant in Service, Küche und Einkauf gegliedert ist
  • Daten werden zentral verwaltet, wie ein einheitliches Lager- und Liefersystem
  • Die Auswirkungen von Änderungen sind klar abgegrenzt, wie ein Gericht zu wechseln, ohne das ganze Restaurant zu beeinträchtigen

1.2 Eine wahre Leidensgeschichte: Warum du State-Management verstehen musst

Du sagst vielleicht: „Ich benutze doch Vue/React? Die haben doch schon State-Management?" Lass mich eine wahre Geschichte erzählen, dann verstehst du, warum ein systematisches Verständnis von Komponentisierung und State-Management so wichtig ist.

Xiaomeis Leidensgeschichte

Xiaomei war Product Managerin bei einem E-Commerce-Unternehmen und wechselte zur Frontend-Entwicklung. Sie übernahm gerade die Überarbeitung der Warenkorb-Funktion. Vorher hatte sie mit alten jQuery-Projekten gearbeitet, jetzt sollte sie auf Vue 3 umstellen.

Xiaomei dachte: „Die Warenkorb-Logik ist einfach, ich speichere einfach ein Array." Also fing sie an zu programmieren:

  • In der Produktdetail-Komponente verwendete sie ein Array cart, um die Warenkorbdaten zu speichern
  • In der Warenkorb-Seiten-Komponente definierte sie noch ein Array cartItems
  • In der Header-Navigations-Komponente gab es noch eine Variable cartCount

Die Probleme traten schnell auf:

  1. Daten nicht synchron: Der Nutzer legte ein Produkt auf der Detailseite in den Warenkorb, aber die Daten auf der Warenkorbseite wurden nicht aktualisiert
  2. Doppelter Code: Xiaomei musste mehrere „In den Warenkorb"-Funktionen schreiben, verteilt auf verschiedene Komponenten
  3. Schwierige Wartung: Das Marketing wollte eine „Warenkorb leeren"-Funktion, und Xiaomei stellte fest, dass sie drei Stellen ändern musste

Später bat sie den Frontend-Architekten Aqiang um Rat. Er sah sich den Code an und sagte: „Du hast den Kardinalfehler des State-Managements begangen – dieselben Daten an mehreren Orten zu speichern."

Die Lösung war einfach: Mit Pinia einen globalen Warenkorb-State-Management-Store erstellen, aus dem alle Komponenten lesen und schreiben. Nach dieser Änderung waren alle Probleme gelöst.

Xiaomei verstand von da an eine wichtige Lektion: Ohne Verständnis von Komponentisierung und State-Management schreibst du schwer wartbaren „Spaghetti-Code".

💡 Kernbotschaft

Komponentisierung und State-Management sind keine „Zusatzfunktionen" von Frameworks, sondern das Fundament moderner Frontend-Entwicklung. Wenn du sie verstehst, kannst du klare Architekturen entwerfen, wartbaren Code schreiben und in der Teamarbeit souverän agieren.


2. Kernkonzepte: Das Wesen der Komponentisierung verstehen

🤔 Was ist „komponentenbasiertes Denken"?

Komponentenbasiertes Denken ist eine Methode, um komplexe Benutzeroberflächen in unabhängige, wiederverwendbare Code-Einheiten mit klar abgegrenzter Verantwortung zu zerlegen.

Ein Vergleich: Stell dir vor, du baust einen Computer zusammen. Du kaufst CPU, Arbeitsspeicher, Festplatte und Grafikkarte einzeln und setzt sie dann zusammen. Jedes Teil hat eine klare Funktion, und du kannst ein Teil jederzeit austauschen, ohne die anderen zu beeinträchtigen.

Komponentisierung macht Frontend-Code genauso „modular" – jede Komponente kümmert sich um ihre eigene Aufgabe und arbeitet über klar definierte Schnittstellen mit anderen Komponenten zusammen.

2.1 Komponentisierung mit einem Restaurant-Vergleich verstehen

Verwenden wir den Restaurant-Vergleich, um die Kernideen der Komponentisierung zu verstehen:

Konzept🍽️ Restaurant-VergleichTatsächliche FunktionKonkretes Beispiel
KomponenteDie verschiedenen Abteilungen des Restaurants (Service, Küche, Einkauf)Jede Abteilung kümmert sich um ihre eigene AufgabeButton-Komponente für Klicks, Formular-Komponente für Eingaben
Props (Eigenschaften)Die Bestellung, die der Gast dem Kellner gibtElternkomponente übergibt Daten an KindkomponenteElternkomponente übergibt „Benutzernamen" an Avatar-Komponente
Events (Ereignisse)Der Kellner meldet der Küche „Neue Bestellung"Kindkomponente meldet der Elternkomponente, was passiert istButton-Komponente meldet der Elternkomponente „Ich wurde geklickt"
State (Zustand)Die „aktuelle Bestellliste" der KücheIntern gespeicherte Daten der KomponenteWarenkorb-Komponente merkt sich, welche Produkte darin sind

📊 Was kannst du aus der Tabelle erkennen?

Lass uns die Tabelle Zeile für Zeile durchgehen:

Komponente: So wie ein Restaurant verschiedene Abteilungen hat, besteht eine Frontend-Seite aus verschiedenen Komponenten. Jede Komponente ist ein unabhängiger Teil mit eigener Verantwortung.

Props: So übergibt eine Elternkomponente Daten an eine Kindkomponente. Wie ein Gast, der dem Kellner sagt, was er essen möchte, kann die Elternkomponente über Props Daten (z.B. Benutzername, Produktinformationen) an die Kindkomponente übergeben. Beachte: Props sind „einseitig", nur von Eltern zu Kind, nicht umgekehrt.

Events: Wenn eine Kindkomponente die Elternkomponente benachrichtigen muss (z.B. Button geklickt, Formular abgeschickt), löst sie ein Event aus. Wie ein Kellner, der nach der Bestellung die Küche informiert „mit dem Kochen zu beginnen". So bleibt der Datenfluss einseitig – die Kindkomponente kann die Daten der Elternkomponente nicht direkt ändern, sondern nur „Nachrichten senden".

State: Das ist das interne „Gedächtnis" der Komponente. So wie die Küche sich merken muss, welche Bestellungen gerade anstehen, muss eine Komponente ihren Zustand merken (z.B. welche Produkte im Warenkorb sind, ob ein Button deaktiviert ist). Wenn sich der State ändert, aktualisiert die Komponente automatisch die Oberfläche.

🌳Component HierarchyComponent relationships like a family tree
Imagine working in a company org chart: the CEO (root component) sits at the top, departments (parent components) report below, and employees (child components) live inside each department. That is a component tree.
👑
App (Root)
CEO - global management
📌
Header
Navigation department
📄
Main Content
Main content department
📑
Sidebar
Sidebar team
🛍️
ProductList
Product list team
🏷️
ProductCard
Product card employee
🔻
Footer
Footer department
👆 Click any node above to inspect its responsibility.
💡Core idea:Components are like an org chart: parents coordinate the whole, children handle focused responsibilities. Data flows downward, events report upward.

2.2 Props und Events: Der „offizielle Kanal" zwischen Eltern- und Kindkomponenten

In Frontend-Frameworks (Vue, React) sind Props und Events der Standardweg für die Kommunikation zwischen Eltern- und Kindkomponenten.

Vue-Beispiel:

vue
<!-- Parent.vue - Elternkomponente -->
<template>
  <div>
    <!-- Wie einem Kellner die Speisekarte zu geben: Daten über Props übergeben -->
    <Child
      :user-name="currentUser.name"
      :is-admin="currentUser.isAdmin"
      @delete-user="handleDelete"
    />
  </div>
</template>

<script setup>
import { ref } from 'vue'
import Child from './Child.vue'

const currentUser = ref({
  name: 'Zhang San',
  isAdmin: true
})

const handleDelete = (userId) => {
  console.log('Benutzer löschen:', userId)
  // Lösche-Logik verarbeiten
}
</script>
vue
<!-- Child.vue - Kindkomponente -->
<template>
  <div class="user-card">
    <h3>{{ userName }}</h3>
    <span v-if="isAdmin" class="badge">Administrator</span>
    <button @click="requestDelete">Benutzer löschen</button>
  </div>
</template>

<script setup>
// Von der Elternkomponente übergebene Daten empfangen
const props = defineProps({
  userName: { type: String, required: true },
  isAdmin: { type: Boolean, default: false }
})

// Auslösbare Events definieren
const emit = defineEmits(['delete-user'])

const requestDelete = () => {
  // Die Elternkomponente per Event benachrichtigen
  emit('delete-user', props.userName)
}
</script>

💡 Kernprinzip

Props nach unten, Events nach oben – das ist die goldene Regel der Komponentenkommunikation.

  • Die Elternkomponente übergibt Daten über props an die Kindkomponente (wie Aufgaben an Mitarbeiter zu delegieren)
  • Die Kindkomponente benachrichtigt die Elternkomponente über events, was passiert ist (wie ein Mitarbeiter, der Bericht erstattet)

So bleibt der Datenfluss klar und einseitig, und das Chaos von „jeder kann Daten ändern" wird vermieden.

📦Props Data FlowOne-way delivery from parent to child
Imagine working at a delivery company: packages (data) can only move from sender (parent component) to recipient (child component). The recipient cannot change the package directly, and can only call back with an event.
👨 Parent Component (Sender)
Package content:Alex (25 years old)
Package color:Light
📮 Send package:
:user:theme
One-way props flow
👦 Child Component (Recipient)
📬 Receive package:
userAlex (25 years old)
themeLight
💡Core idea:Props are one-way data flow. The parent is the sender and the child is the recipient. Children should not mutate props directly; they emit events so the parent can update state.

2.3 Einseitiger Datenfluss: Warum darf man Props nicht direkt ändern?

Viele Anfänger machen einen Fehler: Sie ändern den Wert von Props direkt in der Kindkomponente.

vue
<!-- ❌ Falscher Ansatz -->
<script setup>
const props = defineProps({
  count: { type: Number, default: 0 }
})

// Props direkt ändern – das ist verboten!
props.count = 10  // Wird einen Fehler auslösen
</script>

Warum darf man Props nicht direkt ändern?

Stell dir vor: Du leihst ein Buch aus der Bibliothek (Props) und kritzelt dann darin herum (Props ändern). Andere, die dieses Buch ausleihen (andere Komponenten), sehen dann auch deine Kritzeleien – das führt zu Chaos. Der richtige Weg: Wenn du Daten ändern musst, lass es die Elternkomponente tun, die Kindkomponente „bittet" nur darum.

vue
<!-- ✅ Richtiger Ansatz -->
<script setup>
const props = defineProps({
  count: { type: Number, default: 0 }
})

const emit = defineEmits(['update-count'])

// Die Elternkomponente per Event um Änderung bitten
const increment = () => {
  emit('update-count', props.count + 1)
}
</script>

3. Vom „Chaos" zur „Ordnung": Die Evolution der Komponentenkommunikation

🤔 Warum ist Evolution nötig?

Wenn das Projekt wächst, wird die Kommunikation zwischen Komponenten immer komplexer. Schauen wir uns an, wie ein echtes Team Schritt für Schritt zu einer klaren State-Management-Lösung gelangt ist.

Es geht nicht nur um „Tool-Upgrades", sondern um einen Wandel der gesamten Denkweise – vom „beliebigen Übergeben von Daten" zum „Entwerfen klarer Datenflüsse".

3.1 Die Evolutions-Landkarte

Die folgende Tabelle zeigt die vier Phasen der Evolution der Komponentenkommunikation. Du kannst sehen, wie Probleme Schritt für Schritt gelöst wurden:

PhaseKommunikationsartTypische ProblemeKernveränderung
Phase 1: Freie ÜbergabeDirekte Änderung, globale VariablenDaten nicht synchron, schwer zu debuggenKeine Regeln, alles ist erlaubt
Phase 2: Props/EventsStandard-Kommunikation Eltern-KindProps Drilling (Weiterreichen durch viele Ebenen)Regeln vorhanden, aber tiefe Verschachtelung ist mühsam
Phase 3: State-Management-BibliothekenVuex/Redux/PiniaLernaufwand, Boilerplate-CodeDaten zentral verwaltet, einfaches Debugging
Phase 4: Moderne AnsätzeComposables/Atomare State-VerwaltungNeue Konzepte müssen verstanden werdenFlexibler, schlanker
📡Event BusMessage delivery like a radio station
Imagine working at a radio station: any department (component) can publish messages through the station (Event Bus), and every radio (listener) can receive them without knowing the sender.
📻
Radio Station (Event Bus)
📌
Header
📻 Listening
📑
Sidebar
📻 Listening
🛍️
ProductList
📻 Listening
🛒
Cart
📻 Listening
👆 Click any department above to simulate broadcasting; other active departments will receive it.
💡Core idea:Event Bus is like a radio station: any component can send or receive messages without knowing the other side exists. It suits simple cross-component communication, but listeners should be removed when components unmount.

📊 Was kannst du aus der Tabelle erkennen?

Lass uns die Tabelle Zeile für Zeile durchgehen:

Phase 1 → Phase 2: Von „keinen Regeln" zu „Regeln". Das ist ein qualitativer Sprung – du beginnst, standardisierte Props/Events-Kommunikation zu verwenden, der Datenfluss wird klar. Aber der Preis ist: Wenn die Komponentenhierarchie tief ist, müssen Daten Ebene für Ebene durchgereicht werden, was mühsam ist (das ist Props Drilling).

Phase 2 → Phase 3: Von „verteilter Verwaltung" zu „zentraler Verwaltung". Du beginnst, State-Management-Bibliotheken wie Vuex/Redux zu verwenden und legst geteilte Daten in einem globalen „Store" ab, aus dem alle Komponenten lesen und schreiben. Das löst Props Drilling, aber der Lernaufwand steigt.

Phase 3 → Phase 4: Von „schwergewichtig" zu „leichtgewichtig". Neue Ansätze (wie Vue 3's Composition API, React's Hooks) machen State-Management flexibler und schlanker. Du brauchst nicht mehr zwingend einen globalen Store, sondern kannst kleine State-Einheiten nach Bedarf kombinieren.

Zusammenfassung: Evolution bedeutet nicht nur „bessere Tools zu verwenden", sondern ein Upgrade der gesamten Denkweise – vom beliebigen Übergeben von Daten zum Entwerfen klarer Datenflüsse.

3.2 Phase 1: Freie Übergabe – Der Beginn des Chaos

Warum nennen wir es „freie Übergabe"? Weil es in dieser Phase keine Regeln gibt – Daten werden übergeben, wie man will: globale Variablen, direkte Änderungen, Event-Busse überall.

Typisches Szenario: Warenkorbdaten überall verstreut

javascript
// Produktdetail-Komponente
export default {
  data() {
    return {
      localCart: []  // Verwaltet eine eigene Kopie der Warenkorbdaten
    }
  },
  methods: {
    addToCart(product) {
      this.localCart.push(product)
      // Versucht, mit anderen Komponenten zu synchronisieren
      window.cart = this.localCart  // ❌ Globale Variable!
    }
  }
}

// Warenkorb-Seiten-Komponente
export default {
  data() {
    return {
      cartItems: []  // Noch eine Kopie der Warenkorbdaten
    }
  },
  mounted() {
    // Versucht, aus globaler Variable zu lesen
    this.cartItems = window.cart || []  // ❌ Unzuverlässig!
  }
}

// Header-Navigations-Komponente
export default {
  data() {
    return {
      cartCount: 0  // Und noch eine dritte Kopie!
    }
  },
  mounted() {
    // Polling auf Änderungen (wie absurd)
    setInterval(() => {
      this.cartCount = window.cart?.length || 0
    }, 1000)  // ❌ Schlechte Performance!
  }
}

Merkmale dieser Phase:

  • Vorteile: Einfach und direkt, kein Lernaufwand
  • Nachteile: Daten verstreut, schwer zu synchronisieren, schwer zu debuggen, völliges Durcheinander

3.3 Phase 2: Props/Events – Die Etablierung von Regeln

Das Chaos der freien Übergabe ließ das Team erkennen: Wir brauchen Regeln. Also begannen sie, die vom Framework bereitgestellten Standard-Kommunikationswege zu verwenden: Props und Events.

Typisches Szenario: Props Drilling

vue
<!-- Vorfahr-Komponente: App.vue -->
<template>
  <div class="app">
    <!-- Benutzerinformationen durch alle Ebenen reichen -->
    <Layout :user-name="userName" />
  </div>
</template>

<script setup>
import { ref } from 'vue'
import Layout from './Layout.vue'

const userName = ref('Zhang San')
</script>
vue
<!-- Zwischenebene: Layout.vue -->
<template>
  <div class="layout">
    <Header :user-name="userName" />  <!-- Nur durchreichen, nicht verwendet -->
    <Main>
      <Page :user-name="userName" />  <!-- Nur durchreichen, nicht verwendet -->
    </Main>
  </div>
</template>

<script setup>
const props = defineProps({
  userName: String
})
</script>
vue
<!-- Wo es tatsächlich gebraucht wird: Header.vue -->
<template>
  <header>
    <span>{{ userName }}</span>  <!-- Endlich verwendet! -->
  </header>
</template>

<script setup>
const props = defineProps({
  userName: String
})
</script>

Merkmale dieser Phase:

  • Vorteile: Klarer Datenfluss, einseitiger Fluss, leicht verständlich
  • Nachteile: Props Drilling (Weiterreichen durch viele Ebenen ist mühsam), schwierige Kommunikation zwischen nicht verwandten Komponenten

🤔 Was ist Props Drilling?

Props Drilling bedeutet: Daten müssen durch viele Zwischenkomponenten Ebene für Ebene nach unten gereicht werden, aber diese Zwischenkomponenten verwenden die Daten gar nicht wirklich.

Es ist, als müsstest du ein Paket an jemanden im fünften Stock liefern, aber die Regel besagt, dass es auf jeder Etage quittiert werden muss. Die Leute im ersten bis vierten Stock reichen das Paket nur weiter – sie brauchen es nicht, müssen aber daran beteiligt sein. Das ist offensichtlich umständlich.

3.4 Phase 3: State-Management-Bibliotheken – Zentrale Verwaltung

Der Schmerz von Props Drilling brachte State-Management-Bibliotheken (Vuex, Redux, Pinia) hervor. Ihr Kerngedanke: Geteilte Daten in einem globalen „Store" ablegen, aus dem alle Komponenten lesen und schreiben.

Typisches Szenario: Warenkorb mit Pinia verwalten

javascript
// stores/cart.js - Globaler Warenkorb-State
import { defineStore } from 'pinia'
import { ref, computed } from 'vue'

export const useCartStore = defineStore('cart', () => {
  // Alle Warenkorbdaten sind hier zentralisiert
  const items = ref([])

  // Computed Property: Anzahl der Produkte
  const itemCount = computed(() =>
    items.value.reduce((sum, item) => sum + item.quantity, 0)
  )

  // Methode: Produkt hinzufügen
  const addItem = (product) => {
    const existing = items.value.find(item => item.id === product.id)
    if (existing) {
      existing.quantity++
    } else {
      items.value.push({ ...product, quantity: 1 })
    }
  }

  return {
    items,
    itemCount,
    addItem
  }
})
vue
<!-- Produktdetail-Komponente -->
<script setup>
import { useCartStore } from '@/stores/cart'

const cart = useCartStore()

const addToCart = (product) => {
  cart.addItem(product)  // Direkter Aufruf, kein Weiterreichen nötig
}
</script>
vue
<!-- Header-Navigations-Komponente -->
<template>
  <header>
    <span>Warenkorb ({{ cart.itemCount }})</span>
  </header>
</template>

<script setup>
import { useCartStore } from '@/stores/cart'

const cart = useCartStore()  // Direkt lesen, automatisch synchronisiert
</script>

Merkmale dieser Phase:

  • Vorteile: Daten zentral verwaltet, löst Props Drilling, leistungsstarke Debugging-Tools
  • Nachteile: Lernaufwand, zusätzlicher Code nötig (Boilerplate), für einfache Projekte möglicherweise Over-Engineering

3.5 Phase 4: Moderne Ansätze – Flexibel und schlank

State-Management-Bibliotheken sind zwar mächtig, aber haben auch das Problem „mit Kanonen auf Spatzen zu schießen". Für kleine und mittlere Projekte sind flexiblere, leichtere Lösungen entstanden.

Typisches Szenario: State-Logik mit Composable/Hooks wiederverwenden

javascript
// composables/useCart.js - Wiederverwendbare Warenkorb-Logik
import { ref, computed } from 'vue'

export function useCart() {
  const items = ref([])

  const itemCount = computed(() =>
    items.value.reduce((sum, item) => sum + item.quantity, 0)
  )

  const addItem = (product) => {
    const existing = items.value.find(item => item.id === product.id)
    if (existing) {
      existing.quantity++
    } else {
      items.value.push({ ...product, quantity: 1 })
    }
  }

  return {
    items,
    itemCount,
    addItem
  }
}
vue
<!-- In jeder Komponente verwendbar -->
<script setup>
import { useCart } from '@/composables/useCart'

// Jeder Aufruf erstellt eine neue State-Instanz
// Geeignet für lokalen State innerhalb einer Komponente
const { items, itemCount, addItem } = useCart()
</script>

Merkmale dieser Phase:

  • Vorteile: Flexibel, leichtgewichtig, kombinierbar, nach Bedarf einsetzbar
  • Nachteile: Erfordert Verständnis von kompositionsbasiertem Denken, komponentenübergreifendes Teilen benötigt zusätzliche Behandlung

4. State-Management-Bibliotheken im Detail: Vuex vs Pinia vs Redux

🤔 Wie wählt man eine State-Management-Bibliothek aus?

Angesichts verschiedener State-Management-Bibliotheken fragst du dich vielleicht: Welche soll ich nehmen?

Es gibt nicht die „beste" Bibliothek, nur die „passendste". Berücksichtige bei der Wahl diese Faktoren:

  • Welches Framework nutzt du? Vue → Pinia, React → Redux/Zustand
  • Wie groß ist das Projekt? Kleine Projekte → Composable, große Projekte → State-Management-Bibliothek
  • Welche Erfahrung hat das Team? Wähle, was das Team kennt, oder was wenig Lernaufwand bedeutet

Der folgende Inhalt stellt die Eigenschaften und Einsatzszenarien der wichtigsten State-Management-Bibliotheken im Detail vor.

4.1 Vergleich der wichtigsten State-Management-Bibliotheken

EigenschaftReduxVuexPiniaZustand
FrameworkReactVueVueReact
LernkurveSteilMittelFlachFlach
Boilerplate-CodeVielMittelWenigSehr wenig
TypeScriptGutGutHervorragendHervorragend
Debugging-ToolsLeistungsstarkGutHervorragendGut
EinsatzszenarioGroße ProjekteMittelgroße bis große Vue 2/3-ProjekteNeue Vue 3-ProjekteKleine bis mittlere React-Projekte

📊 Was kannst du aus der Tabelle erkennen?

Lass uns die Tabelle Zeile für Zeile durchgehen:

Redux: Die etablierte State-Management-Bibliothek des React-Ökosystems. Vorteile: strenge Regeln, leistungsstarke Debugging-Tools. Nachteile: viel Boilerplate-Code, steile Lernkurve. Geeignet für große Projekte und Teams, die strenge Standards benötigen.

Vuex: Die offizielle State-Management-Bibliothek der Vue 2-Ära. Das Design-Konzept ähnelt Redux, ist aber besser auf das reaktive System von Vue abgestimmt. Kann immer noch verwendet werden, aber für neue Projekte wird Pinia empfohlen.

Pinia: Die von Vue 3 offiziell empfohlene State-Management-Bibliothek der neuen Generation. Schlanke Syntax, gute TypeScript-Unterstützung, geringer Lernaufwand. Das ist die erste Wahl für Vue 3-Projekte.

Zustand: Eine leichtgewichtige State-Management-Bibliothek im React-Ökosystem. Extrem minimale API, fast kein Boilerplate-Code. Geeignet für kleine bis mittlere React-Projekte.

📊State Management ComparisonWhere different tools fit
Imagine shopping in a supermarket: small trips use a basket (Zustand), larger trips use a cart (Pinia), and enterprise purchasing uses professional logistics (Redux). Pick the tool that matches the need.
Tool
Difficulty
Size
Framework
🔄Redux
Hard
7KB
React/Vue/Angular
🌿Vuex
Medium
4KB
Vue Only
🍍Pinia
Easy
2KB
Vue 3 Only
🐻Zustand
Easy
1KB
React Only
🍍
Pinia

Intuitive, type-safe, flexible Vue Store

🎯 Best for
first choice for new Vue 3 projects, TypeScript-heavy apps, simpler state management
✅ Pros
lightweight design; native TypeScript support
❌ Cons
Vue 3 focused; younger ecosystem
💡Recommendation:For new Vue 3 projects, choose Pinia. For small and medium React projects, choose Zustand. For large enterprise apps, choose Redux Toolkit. Match the tool to project scale.

4.2 Pinia in der Praxis: Die empfohlene Wahl für Vue 3

Pinia ist die vom Vue-Team offiziell empfohlene State-Management-Bibliothek, speziell für Vue 3 entwickelt. Sie ist schlanker und einfacher zu bedienen als Vuex.

Warum heißt es Pinia?

Pinia ist das spanische Wort für „Ananas". Eine Ananas ist eine Frucht, die aus vielen kleinen Einzelblüten besteht – jede Blüte ist unabhängig, aber zusammen bilden sie ein einheitliches Ganzes. Das spiegelt genau das Design-Konzept von Pinia wider – jeder Store ist unabhängig, kann aber kombiniert verwendet werden.

Kernkonzepte:

Vollständiges Code-Beispiel anzeigen
javascript
// stores/user.js - Benutzer-State-Management
import { defineStore } from 'pinia'
import { ref, computed } from 'vue'

export const useUserStore = defineStore('user', () => {
  // 1. State: Daten speichern
  const userInfo = ref(null)
  const isLoggedIn = computed(() => !!userInfo.value)

  // 2. Actions: Methoden zum Ändern der Daten
  const login = async (username, password) => {
    const response = await fetch('/api/login', {
      method: 'POST',
      body: JSON.stringify({ username, password })
    })
    const user = await response.json()
    userInfo.value = user  // Direkt ändern, Pinia behandelt die Reaktivität
  }

  const logout = () => {
    userInfo.value = null
  }

  // 3. Getters: Computed Properties
  const displayName = computed(() => {
    return userInfo.value?.name || 'Gast'
  })

  return {
    userInfo,
    isLoggedIn,
    login,
    logout,
    displayName
  }
})

In Komponenten verwenden:

vue
<template>
  <div class="user-panel">
    <span v-if="user.isLoggedIn">Willkommen, {{ user.displayName }}</span>
    <button v-if="user.isLoggedIn" @click="user.logout">Abmelden</button>
    <button v-else @click="showLoginDialog">Anmelden</button>
  </div>
</template>

<script setup>
import { useUserStore } from '@/stores/user'

// Store direkt abrufen, alle Inhalte sind reaktiv
const user = useUserStore()

const showLoginDialog = () => {
  // Login-Dialog anzeigen...
}
</script>

Vorteile von Pinia:

VorteilBeschreibungVergleich mit Vuex
Schlanke APIKeine Mutations nötig, State direkt ändernVuex benötigt getrennte Mutations und Actions
TypeScript-freundlichNative Typableitung, keine zusätzliche KonfigurationVuex benötigt komplexe Typdefinitionen
Automatische ModularisierungJede Store-Datei wird automatisch zum ModulVuex benötigt manuelle Namespaced-Konfiguration
Geringere GrößeCa. 1 KB nach dem BundlingVuex ca. 3 KB
🍍Vuex vs PiniaOld and new Vue state management
Imagine ordering at a restaurant: Vuex is like a traditional restaurant where different departments (state/mutations/actions) fill different forms; Pinia is like a fast-food counter where one composable API handles the flow.
🌿VuexClassic
✅ Options API
✅ Separate State / Mutations / Actions
❌ More boilerplate
❌ Weaker TypeScript support
🍍PiniaRecommended
✅ Composition API
✅ Removes Mutations and simplifies code
✅ Excellent TypeScript support
✅ Automatic code splitting
Pinia Code Example
// stores/counter.js
export const useCounterStore = defineStore('counter', () => {
  const count = ref(0)

  function increment() {
    count.value++
  }

  return { count, increment }
})
💡Recommendation:Use Pinia directly for new Vue 3 projects. Its syntax is simpler and TypeScript support is stronger. Vuex is still fine for existing apps, but gradual migration to Pinia is recommended.

4.3 Redux in der Praxis: Die klassische Wahl für React

Redux ist die klassischste State-Management-Bibliothek im React-Ökosystem, bekannt für ihren strengen einseitigen Datenfluss.

Warum heißt es Redux?

Redux ist die Abkürzung für „Reduced Flux". Flux war ein von Facebook vorgeschlagenes Anwendungsarchitekturmuster, und Redux hat das Flux-Konzept vereinfacht, daher der Name „Reduced Flux".

Kernprinzipien:

  1. Single Source of Truth: Der gesamte State der Anwendung wird in einem Objektbaum gespeichert
  2. State ist schreibgeschützt: Die einzige Möglichkeit, den State zu ändern, ist das Auslösen einer Action
  3. Änderungen durch reine Funktionen: Reducer müssen reine Funktionen sein
Vollständiges Code-Beispiel anzeigen
javascript
// 1. Action Types definieren
const ADD_TODO = 'ADD_TODO'
const TOGGLE_TODO = 'TOGGLE_TODO'

// 2. Action Creators definieren
const addTodo = (text) => ({
  type: ADD_TODO,
  payload: { id: Date.now(), text, completed: false }
})

const toggleTodo = (id) => ({
  type: TOGGLE_TODO,
  payload: { id }
})

// 3. Reducer definieren (reine Funktion)
const initialState = {
  todos: []
}

const todoReducer = (state = initialState, action) => {
  switch (action.type) {
    case ADD_TODO:
      return {
        ...state,
        todos: [...state.todos, action.payload]
      }
    case TOGGLE_TODO:
      return {
        ...state,
        todos: state.todos.map(todo =>
          todo.id === action.payload.id
            ? { ...todo, completed: !todo.completed }
            : todo
        )
      }
    default:
      return state
  }
}

// 4. Store erstellen
import { createStore } from 'redux'
const store = createStore(todoReducer)

In React verwenden:

jsx
import { useSelector, useDispatch } from 'react-redux'

function TodoList() {
  // State lesen
  const todos = useSelector(state => state.todos)

  // Dispatch-Funktion abrufen
  const dispatch = useDispatch()

  return (
    <ul>
      {todos.map(todo => (
        <li
          key={todo.id}
          onClick={() => dispatch(toggleTodo(todo.id))}
          style={{ textDecoration: todo.completed ? 'line-through' : 'none' }}
        >
          {todo.text}
        </li>
      ))}
    </ul>
  )
}

Vor- und Nachteile von Redux:

VorteileNachteile
Strenger Datenfluss, leicht zu debuggenViel Boilerplate-Code, steile Lernkurve
Time-Travel-DebuggingSelbst einfacher State benötigt viel Code
Reichhaltiges Middleware-ÖkosystemNicht für kleine Projekte geeignet
Vorhersagbare State-UpdatesErfordert Verständnis funktionaler Programmierkonzepte
🔄Redux Data FlowA one-way circular data pipeline
Imagine working in a library: readers (View) submit borrowing forms (Action), librarians (Reducer) review them and update inventory records (Store), then the notice board (View update) refreshes.
Current inventory:0books
💡Core idea:Redux is a one-way data-flow loop: View dispatches Action → Reducer pure function handles it → Store updates → View re-renders. State is predictable and easier to debug.
MobX ReactivityAutomatic dependency tracking
Imagine watching a magic show: when the magician (Observable) changes an object, every audience member watching it (Reaction) notices automatically without manual notifications.
📦Observable State
Learn MobX
Understand reactivity
🔄Automatic Reaction
Total:2 items
Completed:1 items
💡Core idea:MobX automatically tracks relationships between state and reactions. When state changes, related updates run automatically. You change data, and the UI follows.
🐻Zustand & JotaiLightweight React state management
Imagine working in a convenience store: Zustand is like one shared warehouse, while Jotai splits products into small independent cells (Atoms) that can be used on demand.
📦Single StoreManage all state centrally
Minimal APINo Provider wrapper required
🎯Fine-grained SubscriptionOnly rerender the components that need it
// Zustand Store
import { create } from 'zustand'

const useStore = create((set) => ({
  bears: 0,
  increasePopulation: () => set((state) => ({
    bears: state.bears + 1
  }))
}))

// Use inside a component
function BearCounter() {
  const bears = useStore((state) => state.bears)
  return <div>{bears} bears around here</div>
}
💡Recommendation:Zustand fits small and medium projects with a clean API. Jotai fits scenarios that need fine-grained control and modular state. Both support TypeScript and do not require a Provider.

5. Praxisleitfaden: Wie entwirft man State-Management?

🤔 Wann braucht man eine State-Management-Bibliothek?

Nicht jedes Projekt braucht eine State-Management-Bibliothek. Bevor du eine einführst, stelle dir diese Fragen:

  1. Wie viele Komponenten müssen diese Daten teilen?

    • Nur 2-3 Komponenten → Props/Events reichen
    • 5+ Komponenten → State-Management-Bibliothek in Betracht ziehen
  2. Ändern sich diese Daten häufig?

    • Fast nie (z.B. Benutzerinformationen) → Provide/Inject
    • Häufig (z.B. Warenkorb) → State-Management-Bibliothek
  3. Wie groß ist das Team?

    • Einzelperson oder kleines Team → Einfache Lösungen reichen
    • Großes Team → Strenge Regeln und leistungsstarke Debugging-Tools nötig

Denk daran: Fang einfach an und rüste bei Bedarf auf.

5.1 Prinzipien des State-Designs

Egal für welche State-Management-Lösung du dich entscheidest, du solltest diese Prinzipien befolgen:

Prinzip 1: Single Source of Truth

Dieselben Daten sollten nur an einem Ort gespeichert werden. Definiere nicht dieselben Daten mehrfach in verschiedenen Komponenten.

javascript
// ❌ Falsch: Daten überall verstreut
const ProductDetail = { cart: [] }
const CartPage = { items: [] }
const Header = { count: 0 }

// ✅ Richtig: Daten zentral verwalten
const cartStore = { items: [] }  // Die einzige Datenquelle

Prinzip 2: Immutability

Beim Ändern von State solltest du neue Objekte erstellen, statt das Original direkt zu verändern.

javascript
// ❌ Falsch: Direkte Änderung
state.items.push(newItem)

// ✅ Richtig: Neues Objekt erstellen
state.items = [...state.items, newItem]

Prinzip 3: State nach oben, Events nach unten

Geteilter State sollte in der nächsten gemeinsamen Vorfahr-Komponente oder im globalen Store platziert werden, nicht verteilt in verschiedenen Kindkomponenten.

vue
<!-- ❌ Falsch: State in der Kindkomponente -->
<Parent>
  <Child :data="childData" @update="childData = $event" />
</Parent>

<!-- ✅ Richtig: State in der Elternkomponente -->
<Parent>
  <Child :data="parentData" @update="parentData = $event" />
</Parent>

5.2 Praxisbeispiel: State-Design für einen E-Commerce-Warenkorb

Lass uns das bisher Gelernte zusammenführen und ein State-Management für einen E-Commerce-Warenkorb entwerfen.

Anforderungsanalyse:

  • Produktlistenseite kann Produkte zum Warenkorb hinzufügen
  • Warenkorbseite kann Produkte anzeigen, Mengen ändern, Produkte löschen
  • Header-Navigation zeigt die Anzahl der Produkte im Warenkorb
  • Auswahl/Abwahl von Produkten, Berechnung des Gesamtpreises der ausgewählten Produkte
  • Daten in localStorage persistieren

State-Design (Pinia):

javascript
// stores/cart.js
import { defineStore } from 'pinia'
import { ref, computed } from 'vue'

export const useCartStore = defineStore('cart', () => {
  // ============ State ============
  const items = ref([])  // Warenkorb-Produktliste
  const selectedIds = ref([])  // Ausgewählte Produkt-IDs

  // Daten aus localStorage wiederherstellen
  const initFromStorage = () => {
    const stored = localStorage.getItem('cart')
    if (stored) {
      try {
        const data = JSON.parse(stored)
        items.value = data.items || []
        selectedIds.value = data.selectedIds || []
      } catch (e) {
        console.error('Fehler beim Lesen der Warenkorbdaten:', e)
      }
    }
  }

  // In localStorage persistieren
  const persist = () => {
    localStorage.setItem('cart', JSON.stringify({
      items: items.value,
      selectedIds: selectedIds.value
    }))
  }

  // ============ Getters (Computed Properties) ============
  const itemCount = computed(() =>
    items.value.reduce((sum, item) => sum + item.quantity, 0)
  )

  const totalPrice = computed(() =>
    items.value.reduce((sum, item) => sum + item.price * item.quantity, 0)
  )

  const selectedItems = computed(() =>
    items.value.filter(item => selectedIds.value.includes(item.id))
  )

  const selectedTotalPrice = computed(() =>
    selectedItems.value.reduce((sum, item) => sum + item.price * item.quantity, 0)
  )

  // ============ Actions (Methoden) ============
  const addItem = (product) => {
    const existing = items.value.find(item => item.id === product.id)
    if (existing) {
      existing.quantity += product.quantity || 1
    } else {
      items.value.push({
        ...product,
        quantity: product.quantity || 1
      })
    }
    persist()
  }

  const updateQuantity = (productId, quantity) => {
    const item = items.value.find(item => item.id === productId)
    if (item) {
      if (quantity <= 0) {
        removeItem(productId)
      } else {
        item.quantity = quantity
        persist()
      }
    }
  }

  const removeItem = (productId) => {
    items.value = items.value.filter(item => item.id !== productId)
    selectedIds.value = selectedIds.value.filter(id => id !== productId)
    persist()
  }

  const toggleSelection = (productId) => {
    const index = selectedIds.value.indexOf(productId)
    if (index > -1) {
      selectedIds.value.splice(index, 1)
    } else {
      selectedIds.value.push(productId)
    }
    persist()
  }

  // Initialisierung
  initFromStorage()

  return {
    // State
    items,
    selectedIds,
    // Getters
    itemCount,
    totalPrice,
    selectedItems,
    selectedTotalPrice,
    // Actions
    addItem,
    updateQuantity,
    removeItem,
    toggleSelection
  }
})

In Komponenten verwenden:

vue
<!-- Produktdetailseite: ProductDetail.vue -->
<template>
  <div class="product-detail">
    <h2>{{ product.name }}</h2>
    <p class="price">¥{{ product.price }}</p>
    <button @click="addToCart">In den Warenkorb</button>
  </div>
</template>

<script setup>
import { useCartStore } from '@/stores/cart'

const props = defineProps({
  product: Object
})

const cart = useCartStore()

const addToCart = () => {
  cart.addItem({
    id: props.product.id,
    name: props.product.name,
    price: props.product.price
  })
}
</script>
vue
<!-- Header-Navigation: Header.vue -->
<template>
  <header class="header">
    <div class="logo">Mein Shop</div>
    <nav>
      <RouterLink to="/">Startseite</RouterLink>
      <RouterLink to="/cart">
        Warenkorb ({{ cart.itemCount }})
      </RouterLink>
    </nav>
  </header>
</template>

<script setup>
import { useCartStore } from '@/stores/cart'

const cart = useCartStore()  // Direkt verwenden, reagiert automatisch auf Änderungen
</script>

6. Häufige Fallstricke und wie man sie vermeidet

⚠️ In diese Fallstricke tappen 90% der Anfänger

In der Praxis des State-Managements gibt es einige besonders häufige Fehler. Lass mich die häufigsten Fallstricke zusammenfassen und erklären, wie man sie vermeidet.

6.1 Fallstrick 1: Props oder State direkt ändern

Falscher Code:

javascript
// ❌ Props direkt ändern
props.user.name = 'Li Si'

// ❌ Vuex State direkt ändern
store.state.user.name = 'Li Si'

// ❌ Array-Element direkt ändern
state.items[0].name = 'Neuer Name'

Warum ist das falsch?

Frontend-Frameworks (Vue/React) müssen Datenänderungen „verfolgen" können, um die Oberfläche automatisch zu aktualisieren. Wenn du Objekte oder Arrays direkt änderst, kann das Framework die Änderung möglicherweise nicht erkennen, was dazu führt, dass die Oberfläche nicht aktualisiert wird.

Richtiger Ansatz:

javascript
// ✅ Vue 3 / Pinia: Top-Level-Eigenschaften direkt ändern
store.user.name = 'Li Si'  // Pinia behandelt die Reaktivität automatisch

// ✅ Vue 2 / Vuex: Über Mutation
mutations: {
  UPDATE_USER_NAME(state, newName) {
    state.user.name = newName
  }
}

// ✅ Array ändern: Neues Array erstellen
state.items = state.items.map((item, index) =>
  index === 0 ? { ...item, name: 'Neuer Name' } : item
)

6.2 Fallstrick 2: State in Gettern ändern

Falscher Code:

javascript
// ❌ State in Getter ändern
getters: {
  doubleCount(state) {
    state.count *= 2  // Seiteneffekt!
    return state.count
  }
}

Warum ist das falsch?

Getter sollten „reine Funktionen" sein, die nur berechnen und Werte zurückgeben, ohne Seiteneffekte (State-Änderungen). Wenn du State in einem Getter änderst, kann das zu Endlosschleifen und schwer debuggaren Problemen führen.

Richtiger Ansatz:

javascript
// ✅ Getter berechnet nur, ändert nicht
getters: {
  doubleCount(state) {
    return state.count * 2
  }
}

// ✅ Wenn eine Änderung nötig ist, verwende eine Action
actions: {
  doubleCountAndSave({ commit }) {
    commit('SET_DOUBLE_COUNT')
  }
}

6.3 Fallstrick 3: Vergessen, Event-Listener zu bereinigen

Falscher Code:

javascript
// ❌ Vergessen, das Abonnement zu kündigen
export default {
  created() {
    EventBus.$on('cart-updated', this.handleCartUpdate)
  }
  // Komponente wurde zerstört, aber der Listener besteht weiter!
}

Warum ist das falsch?

Wenn eine Komponente zerstört wird, aber der Event-Listener weiter besteht, führt das zu Memory Leaks (belegter Speicher kann nicht freigegeben werden). In Single-Page-Anwendungen wechseln Nutzer ständig zwischen Seiten, und diese nicht bereinigten Listener sammeln sich an, was schließlich zu einer trägen Seite führt.

Richtiger Ansatz:

javascript
// ✅ Abonnement rechtzeitig kündigen
export default {
  created() {
    EventBus.$on('cart-updated', this.handleCartUpdate)
  },
  beforeUnmount() {  // Vue 3: beforeUnmount, Vue 2: beforeDestroy
    EventBus.$off('cart-updated', this.handleCartUpdate)
  }
}

6.4 Fallstrick 4: Übermäßiger Einsatz von State-Management

Falscher Code:

javascript
// ❌ Jeden State in den Store legen
const store = useStore()
store.inputValue = 'Benutzereingabe'
store.isModalOpen = true
store.currentTab = 'profile'

Warum ist das falsch?

Nicht jeder State muss in einen globalen Store. Wenn ein State nur in einer Komponente verwendet wird (z.B. Eingabefeld-Wert, Modal-Sichtbarkeit), gehört er in die Komponente selbst. Übermäßiger Einsatz von State-Management macht den Code unnötig komplex.

Richtiger Ansatz:

javascript
// ✅ Lokalen State innerhalb der Komponente verwalten
const inputValue = ref('')

// ✅ Nur State, der geteilt werden muss, kommt in den Store
const userInfo = useUserStore()  // Mehrere Komponenten brauchen Benutzerinformationen
const cart = useCartStore()  // Mehrere Komponenten brauchen Warenkorbdaten

7. Zusammenfassung und Empfehlungen

7.1 Rückblick auf die Kernkonzepte

Lass uns die Kernkonzepte von Komponentisierung und State-Management in einer Tabelle zusammenfassen:

KonzeptKurz erklärtGelöstes ProblemTypische Tools
KomponentisierungDie Oberfläche in unabhängige, wiederverwendbare Teile zerlegenCode-Wiederverwendung, Trennung der VerantwortlichkeitenVue/React-Komponenten
PropsElternkomponente übergibt Daten an KindkomponenteEltern-Kind-KommunikationVue/React eingebaut
EventsKindkomponente benachrichtigt ElternkomponenteKind-Eltern-KommunikationVue/React eingebaut
StateIntern in der Komponente gespeicherte DatenZustand der Komponente merkenVue/React eingebaut
State-Management-BibliothekGlobalen, geteilten State zentral verwaltenKomponentenübergreifende Kommunikation, Props DrillingPinia, Redux, Zustand
Single Source of TruthDieselben Daten nur an einem Ort speichernDateninkonsistenz, SynchronisationsproblemeKernprinzip der State-Management-Bibliotheken

7.2 Empfehlungen für verschiedene Szenarien

SzenarioEmpfohlene LösungBegründung
Eltern-Kind-KommunikationProps + EventsIm Framework eingebaut, einfach und direkt
Werte über mehrere EbenenProvide / InjectVermeidet Weiterreichen durch jede Ebene
Lokaler State in Komponenteref / useStateEinfach, keine zusätzlichen Tools nötig
Mittelgroßes Vue-ProjektPiniaOffiziell empfohlen, geringer Lernaufwand
Mittelgroßes React-ProjektZustandExtrem schlank, kein Boilerplate-Code
Großes Vue-ProjektPinia + KonventionenFlexibel und erweiterbar
Großes React-ProjektRedux ToolkitStrenge Standards, reichhaltiges Ökosystem
Logik komponentenübergreifend wiederverwendenComposable / HooksFlexibel, kombinierbar

7.3 Lernempfehlungen

Für Anfänger:

  1. Erst die Grundlagen beherrschen: Props, Events, State – diese grundlegenden Konzepte verstehen
  2. Mit kleinen Projekten anfangen: Nicht sofort eine State-Management-Bibliothek einsetzen
  3. Viel Code schreiben: Noch so viel Theorie ist weniger wert als praktische Übung

Für Fortgeschrittene:

  1. Quellcode lesen: Die Funktionsweise von Pinia/Redux verstehen
  2. Patterns lernen: Gängige Design-Patterns kennenlernen (z.B. Observer-Pattern, Publish-Subscribe-Pattern)
  3. Das Ökosystem im Blick behalten: Zugehörige Tools lernen (z.B. DevTools, Middleware)

Behalte diese Kernprinzipien im Kopf:

  1. Fang einfach an: Führe nicht zu früh komplexe State-Management-Bibliotheken ein
  2. Single Source of Truth: Vermeide, dieselben Daten an mehreren Orten zu speichern
  3. Immutability: Erstelle neue Objekte beim Ändern von State, statt direkt zu ändern
  4. Nach Bedarf wählen: Wähle die passende Lösung basierend auf Projektgröße und Team

Ich hoffe, dieser Artikel hilft dir, ein umfassendes Verständnis von Komponentisierung und State-Management aufzubauen. Wenn du in echten Projekten auf komplexe Datenflussprobleme stößt, weißt du, wo du ansetzen, wie du entwerfen und wie du implementieren kannst.