FutureBuilder ist ein Widget in Flutter, das seine Benutzeroberfläche automatisch auf der Grundlage des aktuellen Zustands von AsyncSnapshot neu aufbaut, der aus einem übergebenen Future gewonnen wird. Im Gegensatz zum manuellen Aufruf von setState nach await bietet FutureBuilder einen deklarativen Ansatz: Er abonniert das Future beim ersten Rendern und ruft die Builder-Funktion bei jeder Zustandsänderung auf — Laden, Fehler oder fertige Daten. Laut der Flutter API Reference (2026) ist FutureBuilder besonders nützlich zum Laden von Daten aus dem Netzwerk, Lesen aus einer Datenbank und beliebigen asynchronen Operationen, bei denen die UI einen Ladeindikator, eine Fehlermeldung oder fertigen Inhalt anzeigen soll.
Wichtige Punkte
FutureBuilder ist ein integriertes Flutter-Widget aus dem widgets-Paket, das ein Future
Im Gegensatz zu StreamBuilder, der mit Datenströmen (Stream) arbeitet, ist FutureBuilder für einmalige asynchrone Operationen konzipiert: HTTP-Anfrage, Dateilesen, Datenbankabfrage. FutureBuilder verwaltet das Abonnement des Future selbst: Beim ersten Aufbau startet er das Future und verfolgt dessen Abschluss. Wenn das Widget zerstört wird, bricht FutureBuilder das Future nicht ab — das liegt in der Verantwortung des Entwicklers.
Laut dem Flutter Cookbook (2026) wird FutureBuilder für Fälle empfohlen, in denen eine asynchrone Operation einmal bei der Bildschirminitialisierung ausgeführt wird. Für wiederkehrende Operationen oder Datenströme verwenden Sie StreamBuilder. Beide Widgets folgen demselben reaktiven UI-Muster, aber FutureBuilder ist für einmalige Anfragen optimiert.
Die interne Implementierung von FutureBuilder abonniert das Future mit Future.then und catchError. Beim Start setzt FutureBuilder connectionState auf ConnectionState.waiting und ruft den Builder mit leeren Daten auf. Bei erfolgreichem Abschluss wechselt connectionState zu ConnectionState.done mit Daten. Bei einem Fehler wird snapshot.error mit dem Fehlerobjekt gefüllt. Jede Änderung löst einen Widget-Neuaufbau aus.
AsyncSnapshot ist ein Container-Objekt, das FutureBuilder bei jeder Zustandsänderung an die Builder-Funktion übergibt. Es enthält alle Informationen über den aktuellen Status der asynchronen Operation: ob der Ladevorgang läuft, welche Daten empfangen wurden oder ob ein Fehler aufgetreten ist. Das Verständnis von AsyncSnapshot ist der Schlüssel zum korrekten Aufbau der UI mit FutureBuilder.
| Eigenschaft | Typ | Beschreibung |
|---|---|---|
| connectionState | ConnectionState | Aktueller Verbindungszustand (none, waiting, active, done) |
| data | T? | Vom Future empfangene Daten (null bis zum Abschluss oder bei Fehler) |
| error | Object? | Fehlerobjekt, wenn das Future mit einer Ausnahme abgeschlossen wurde |
| hasData | bool | true, wenn data nicht null und connectionState ConnectionState.done ist |
| hasError | bool | true, wenn das Future mit einem Fehler abgeschlossen wurde |
Der ConnectionState-Enum definiert die Phase einer asynchronen Operation. None — Anfangszustand, wenn das Future noch nicht gestartet wurde (selten verwendet, typischerweise beim ersten Aufbau ohne initialData). Waiting — das Future wird ausgeführt, Daten noch nicht empfangen. Active — wird nur von StreamBuilder für Streams mit partiellen Daten verwendet. Done — das Future ist abgeschlossen, Daten sind über snapshot.data oder Fehler über snapshot.error verfügbar.
Die ordnungsgemäße Behandlung aller AsyncSnapshot-Zustände in der Builder-Funktion ist eine zwingende Voraussetzung für Produktionscode. Wenn Sie den waiting-Zustand nicht behandeln, sieht der Benutzer während des Ladens einen leeren Bildschirm. Wenn Sie hasError nicht behandeln, erhält der Benutzer eine Exception ohne Erklärung. Das empfohlene Muster: hasError prüfen → hasData prüfen → standardmäßig Laden anzeigen.
FutureBuilder kann in mehreren Standardmustern verwendet werden, die jeweils eine bestimmte Aufgabe lösen. Schauen wir uns die Hauptszenarien an: Daten laden bei Initialisierung, Laden mit Caching, parallele Anfragen und Fehlerbehandlung mit Wiederholung.
Das häufigste Muster — FutureBuilder in der build-Methode eines StatefulWidget oder StatelessWidget. Das Future wird von initState übergeben oder direkt in build erstellt. Es ist wichtig, das Future nicht bei jedem Neuaufbau in der build-Methode zu erstellen — dies führt zu wiederholten Anfragen. Verwenden Sie ein in einem State-Feld gespeichertes Future.
Um wiederholte Anfragen zu vermeiden, kann FutureBuilder mit CachedNetworkImage oder einem lokalen Cache kombiniert werden. Nach dem ersten Laden werden die Daten im Arbeitsspeicher oder in SharedPreferences gespeichert, und FutureBuilder zeigt zwischengespeicherte Daten sofort an, während parallel aus dem Netzwerk aktualisiert wird. Dies verbessert die UX durch sofortige Reaktion.
Laut pub.dev (2026) ist Caching besonders relevant für Bilder und Datenlisten. FutureBuilder mit CachedNetworkImageProvider zeigt automatisch ein zwischengespeichertes Bild an, und bei dessen Fehlen — einen Ladeindikator gefolgt von der heruntergeladenen Datei.
FutureBuilder und manuelle Zustandsverwaltung über setState sind zwei Ansätze für asynchrone UI in Flutter. Jeder hat seine Vor- und Nachteile. Die Wahl hängt von der Bildschirmkomplexität und der Anzahl asynchroner Operationen ab.
FutureBuilder punktet mit Einfachheit: Sie müssen keine Felder für Ladezustand, Daten und Fehler deklarieren — alles wird über AsyncSnapshot verwaltet. Er ist ideal für einfache Bildschirme mit einer asynchronen Operation (eine HTTP-Anfrage, Datenbanklesen). Bei 5+ asynchronen Operationen auf einem Bildschirm erzeugt FutureBuilder jedoch übermäßige Verschachtelung — was zu einer „Pyramide“ verschachtelter FutureBuilder führt.
setState mit manuellen Zustandsflags gibt mehr Kontrolle und Lesbarkeit für komplexe Logik. Für Bildschirme mit mehreren abhängigen Anfragen (Benutzer laden → Bestellungen laden → Bestelldetails laden) ist es besser, setState mit ChangeNotifier oder Bloc zu verwenden. Laut dem Flutter State Management Guide (2026) werden für komplexe Szenarien Riverpod oder Bloc gegenüber FutureBuilder empfohlen, da sie eine bessere Trennung von Logik und Darstellung bieten.
Betrachten wir ein praktisches FutureBuilder-Beispiel zum Laden einer Benutzerliste von einer REST-API. Der Code demonstriert die korrekte Behandlung aller drei AsyncSnapshot-Zustände: Laden, Fehler und fertige Daten.
class UserListPage extends StatefulWidget {
const UserListPage({super.key});
@override
State<UserListPage> createState() => _UserListPageState();
}
class _UserListPageState extends State<UserListPage> {
final Future<List<User>> usersFuture = UserRepository().fetchUsers();
@override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(title: const Text('Benutzer')),
body: FutureBuilder<List<User>>(
future: usersFuture,
builder: (context, AsyncSnapshot<List<User>> snapshot) {
if (snapshot.hasError) {
return Center(
child: Column(
mainAxisAlignment: MainAxisAlignment.center,
children: [
const Icon(Icons.error_outline, size: 48, color: Colors.red),
const SizedBox(height: 16),
Text('Fehler: ${snapshot.error}'),
],
),
);
}
if (snapshot.hasData) {
final users = snapshot.data!;
return ListView.builder(
itemCount: users.length,
itemBuilder: (context, index) {
return ListTile(
leading: CircleAvatar(backgroundImage: NetworkImage(users[index].avatarUrl)),
title: Text(users[index].name),
subtitle: Text(users[index].email),
);
},
);
}
return const Center(child: CircularProgressIndicator());
},
),
);
}
}
Im Beispiel behandelt FutureBuilder alle drei Zustände. Bei einem Fehler wird ein Symbol mit einer Fehlermeldung angezeigt. Bei erfolgreichem Laden — eine ListView mit Avataren und Namen. Während des Ladens — ein CircularProgressIndicator. Das Future wird als Klassenfeld deklariert, was wiederholte Aufrufe beim Neuaufbau verhindert. Dieses Muster deckt 90% der FutureBuilder-Verwendungsszenarien in mobilen Apps ab.
Häufig gestellte Fragen
FutureBuilder ruft den Builder bei jeder Future-Zustandsänderung auf: das erste Mal bei der Erstellung (connectionState: none oder waiting), das zweite Mal bei Abschluss (connectionState: done). Wenn das Eltern-Widget neu aufgebaut wird, wird auch FutureBuilder neu aufgebaut. Um wiederholte Aufrufe zu vermeiden, stellen Sie sicher, dass das Future außerhalb der build-Methode erstellt wird — andernfalls erstellt jeder build-Aufruf ein neues Future.
Speichern Sie das Future in einem StatefulWidget-Feld (in initState) oder verwenden Sie Memoization. Wenn das Future innerhalb der build-Methode erstellt wird, erstellt jeder build-Aufruf ein neues Future, und FutureBuilder startet die asynchrone Operation neu. Für StatelessWidget verwenden Sie das cached_future-Paket oder keep-alive-Widgets, damit das Future unabhängig von Neuaufbauten einmal ausgeführt wird.
FutureBuilder ist für einmalige asynchrone Operationen konzipiert (eine HTTP-Anfrage, ein Datenbanklesen). StreamBuilder arbeitet mit Datenströmen, die im Laufe der Zeit mehrere Werte ausgeben können (Chat, Preisaktualisierungen, Geolokalisierung). StreamBuilder unterstützt ConnectionState.active für partielle Daten, während FutureBuilder nur waiting und done unterstützt.
Für mehrere parallele Futures verwenden Sie Future.wait und übergeben das Ergebnis an einen einzigen FutureBuilder. Future.wait nimmt eine Liste von Futures entgegen und gibt ein Future zurück — wenn alle Futures abgeschlossen sind, erhält der Builder ein Array von Ergebnissen. Für sequenzielle Anfragen verwenden Sie eine Future.then-Kette innerhalb eines Future oder verschachtelte FutureBuilder (weniger lesbar). Eine Alternative ist das riverpod-Paket mit AsyncValue für mehrere asynchrone Zustände.
FutureBuilder bricht das Future nicht automatisch ab. Zum Abbrechen verwenden Sie CancelableOperation aus dem async-Paket oder einen benutzerdefinierten Mechanismus über ein cancelled-Flag im State. Setzen Sie das Flag in dispose() und überprüfen Sie es nach Abschluss des Future vor dem Aufruf von setState. Alternativ verwenden Sie das riverpod-Paket mit AutoDispose, das asynchrone Operationen beim Verlassen des Bildschirms automatisch abbricht.
Zusammenfassung
Wir entwickeln eine mobile Applikation schlüsselfertig
IT Sectr entwickelt seit 2017 iOS- und Android-Apps für Startups und Unternehmen. Wir beraten Sie und schlagen die beste Lösung vor.
Lesen Sie auch