R

ReflexKR

Reflex-Dokumentation

Full-Stack-Webentwicklung mit Python und Reflex

·

Kursüberblick

1

Reflex kennenlernen und Umgebung einrichten

2

Die Oberfläche mit Komponenten zeichnen

3

State und Vars: Daten zeichnen die Oberfläche

4

Events und Formulare: Kunden hinzufügen

5

Daten aufbereiten und Diagramme

6

Zusammenfassung, Debugging und nächste Schritte

·

Anhang

Full-Stack-Webentwicklung mit Python und Reflex
Lektion 3

Zeit 1:25–2:10

State und Vars: Daten zeichnen die Oberfläche

In dieser Lektion legst du die Kundendaten im State ab und lässt Tabelle und Badge aus diesen Daten zeichnen. Dabei lernst du das wichtigste Konzept in Reflex kennen: die Var.

3-1. Die Form der Daten festlegen: dataclass (5 Min.)

import dataclasses


@dataclasses.dataclass
class User:
    name: str
    email: str
    gender: str
  • Das ist der „Bauplan“, der festlegt, welche Felder ein Kunde hat. Ein Objekt erzeugst du mit User(name="...", email="...", gender="...").
  • Ein Dictionary ({"name": ...}) würde auch funktionieren. Mit einer dataclass fängt der Editor aber Tippfehler in Feldnamen ab, und im Oberflächen-Code kannst du mit Punkt-Notation wie user.name zugreifen.

3-2. Die State-Klasse (10 Min.)

class State(rx.State):
    users: list[User] = [
        User(name="Danilo Sousa", email="danilo@example.com", gender="Male"),
        User(name="Zahra Ambessa", email="zahra@example.com", gender="Female"),
    ]
  • Klassenvariablen einer Klasse, die von rx.State erbt, werden zu State-Variablen (State Vars). Der Wert, den du hier hinschreibst, ist der Anfangswert.
  • Die Typannotation (: list[User]) ist Pflicht. Anhand des Typs entscheidet Reflex, in welchem Format (JSON) die Daten an den Browser gehen und welche Methoden du darauf verwenden kannst.
  • Der State liegt im Speicher des Servers, und zwar getrennt für jede Browser-Session. Kunden, die du hinzufügst, sehen andere nicht, und weil das keine Datenbank ist, werden sie auch nicht dauerhaft gespeichert. Dauerhafte Speicherung ist eine der Erweiterungsaufgaben in Lektion 6.

3-3. Var: kein „Wert“, sondern ein „Ausdruck, der an die Oberfläche geht“ (15 Min.)

In Lektion 1 hieß es: „Oberflächen-Funktionen werden beim Start der App nur einmal ausgeführt.“ Was steckt dann in State.users, wenn du es in einer Oberflächen-Funktion verwendest? Gib es einfach mal aus:

>>> type(State.users).__name__
'ArrayCastedVar'
>>> print(State.users.length())
reflex___state____state__tutorial_261019___tutorial_261019____state.users_rx_state_.length

Statt einer Kundenliste bekommst du einen JavaScript-Ausdruck. Genau das ist eine Var. Wenn die Oberflächen-Funktion läuft, gibt es noch keine Nutzer und keine Daten. Deshalb wird nur ein Versprechen angelegt: „Lies diesen Wert später im Browser.“

Darum kannst du einen Teil der Python-Syntax nicht auf Vars anwenden. Hier die Fehler, die Reflex 0.10 tatsächlich ausgibt, und die jeweilige Alternative:

Was du willstCode, der nicht gehtFehlermeldungDer Reflex-Weg
Anzahl ermittelnlen(State.users)TypeError: object of type 'ArrayCastedVar' has no len()State.users.length()
Bedingung"a" if State.n > 1 else "b"VarTypeError: Cannot convert Var ... to boolrx.cond(State.n > 1, "a", "b")
Schleifefor u in State.users:VarTypeError: Cannot iterate over Var ...rx.foreach(State.users, show_user)
Aufwendige VerarbeitungIn der Oberflächen-Funktion rechnen—Im Event oder in einer @rx.var (Computed Var) rechnen

Vergleiche und Rechnungen zwischen Vars (State.page + 1) oder Vars in einem f-String (f"Insgesamt {State.total} Kunden") funktionieren dagegen problemlos, weil die Operation selbst in einen JavaScript-Ausdruck übersetzt wird.

Hinweis für Lehrende — Diese Tabelle ist der wichtigste Teil des Kurses. Die meisten Fehler, auf die Einsteiger in Reflex stoßen, haben hier ihren Ursprung. Für ein Video empfiehlt sich folgender Ablauf: absichtlich len(State.users) schreiben und die Fehlermeldung zeigen, fragen „Warum geht das nicht?“ und dann mit der print-Ausgabe oben antworten.

Jetzt ersetzen wir das Platzhalter-Badge im Header durch die echte Kundenanzahl.

rx.badge(
    State.users.length(),     # Var statt "2"
    variant="soft",
    color_scheme="gray",
    radius="full",
),

3-4. Eine Funktion für eine Zeile: show_user (5 Min.)

def show_user(user: User):
    return rx.table.row(
        rx.table.cell(user.name),
        rx.table.cell(user.email),
        rx.table.cell(user.gender),
        style={"_hover": {"bg": rx.color("gray", 3)}},
        align="center",
    )
  • Als Typ steht zwar User da, tatsächlich kommt aber eine Var an, die auf einen User verweist. Auch user.name wird zum Ausdruck „Lies den name des Kunden in dieser Zeile“. Dass die Punkt-Notation funktioniert, verdankst du den Feldern, die du in der dataclass deklariert hast.
  • style={"_hover": {...}} ist der Style, wenn der Mauszeiger darüber liegt. Schlüssel, die mit _ beginnen, wie _hover oder _focus, entsprechen CSS-Zustandsselektoren wie :hover.

3-5. Die Tabelle und rx.foreach (10 Min.)

Unter dem Header kommt die Tabelle als zweites Kind in die Karte.

rx.box(
    rx.table.root(
        rx.table.header(
            rx.table.row(
                rx.table.column_header_cell("Name"),
                rx.table.column_header_cell("Email"),
                rx.table.column_header_cell("Gender"),
            )
        ),
        rx.table.body(rx.foreach(State.users, show_user)),
        variant="ghost",
        size="3",
        width="100%",
    ),
    overflow_x="auto",                                   # horizontales Scrollen auf schmalen Bildschirmen
    width="100%",
    border_top=f"1px solid {rx.color('slate', 4)}",
    border_bottom=f"1px solid {rx.color('slate', 4)}",
    padding_x="12px",
),
  • Aufbau der Tabelle: root > header (Kopfzeile) + body (Datenzeilen) > row > cell. Das entspricht <table>, <thead>, <tbody>, <tr> und <td> in HTML.
  • rx.foreach(Listen-Var, Funktion) wendet die Funktion im Browser auf jedes Element der Liste an. Du übergibst nur den Namen der Funktion und rufst sie nicht auf (show_user, nicht show_user()).
  • Für eine feste Liste wie die Kopfzeile darfst du dagegen ein normales Python-for verwenden, weil die Werte schon zur Compile-Zeit feststehen. Beispiel: *[rx.table.column_header_cell(h) for h in ["Name", "Email", "Gender"]]

Im Browser prüfen — In der Karte erscheint eine Tabelle mit 2 Kunden, und die 2 im Badge kommt jetzt aus State.users.length(). Fährst du mit der Maus über eine Zeile, wird ihr Hintergrund hellgrau.

localhost:3000

Live-Vorschau

Customers

2

Your customer directory and audience breakdown.

NameEmailGender
Danilo Sousadanilo@example.comMale
Zahra Ambessazahra@example.comFemale
Lektion 3 fertig: Die 2 Kunden aus dem State als Tabelle

Übungen

  1. Füge den Anfangswerten einen weiteren Kunden hinzu und prüfe, ob das Badge auf 3 springt.
  2. Zeige mit rx.cond statt der Tabelle den Text „Noch keine Kunden vorhanden“, wenn es 0 Kunden gibt. Tipp: rx.cond(State.users.length() > 0, Tabelle, rx.text(...))
  3. Schreib absichtlich len(State.users) und lies dir die Fehlermeldung selbst durch.

Checkpoint

  • Die Tabelle zeigt 2 Kunden, und das Badge zeigt 2.
  • Du kannst erklären, was eine Var ist und warum len/if/for darauf nicht funktionieren.
  • Du weißt, warum du die Funktion an rx.foreach übergibst, ohne sie aufzurufen.

← Zurück

Lektion 2 · Die Oberfläche mit Komponenten zeichnen

Weiter →

Lektion 4 · Events und Formulare: Kunden hinzufügen

Über neue Lektionen informiert werden

Wir schicken dir eine E-Mail, wenn dieser Kurs neue Lektionen bekommt oder ein Folgekurs erscheint.

Erhoben: deine E-Mail-Adresse · Zweck: Hinweise auf neue Lektionen oder den Start dieses Kurses · Speicherdauer: bis du die Löschung verlangst. Keine andere Nutzung, keine Weitergabe. Antworte einfach auf eine Benachrichtigung, dann löschen wir sie sofort.

Fragen & Antworten

Frag alles zu dieser Lektion. Fragen aus allen Sprachversionen dieser Seite erscheinen hier gemeinsam.

Wird als reiner Text angezeigt, ohne Links oder Formatierung.

R

ReflexKR

Python und Reflex zum Anfassen. Alle Beispiele wurden mit Reflex 0.10.0 ausgeführt und geprüft.

ReflexKR ist kostenlos und ohne Werbebanner. Wenn es dir geholfen hat, kannst du es mit einem Kaffee unterstützen. ☕ Spendier uns einen Kaffee

Hinweis zu Affiliate-Links
한국어English日本語简体中文EspañolDeutsch

© 2026 ReflexKR · Since 2026 · CC BY-NC 4.0

Built with Reflex