All articles

Flutter State Management: Provider, Riverpod, or Bloc?

What state management solves in Flutter, when setState is enough, how Provider, Riverpod, and Bloc differ in practice, how to pick one for your team, and the structure that keeps a Flutter app maintainable whichever library you choose.

Mobile Development|Published |9 min read
Person using a smartphone next to a laptop on a desk

Ask five Flutter developers which state management library to use and you will hear five answers, often with strong feelings attached. The debate hides a simpler truth. The library matters less than where you put your logic and how data flows through the app. Still, the choice affects how you test, how new developers onboard, and how much boilerplate you write. Here is how the main options compare and how we choose between them on client projects.

What Problem Are We Solving?

Flutter rebuilds widgets from state. Some state belongs to one widget, such as whether a dropdown is open or the text in a field. Other state is shared across screens, such as the logged-in user, the cart, or a list loaded from an API. Ephemeral state is fine inside a StatefulWidget with setState. App state needs a home outside the widget tree so several screens can read it, it survives navigation, and business logic can be tested without building widgets.

The Main Options

OptionHow it worksStrengthsTrade-offs
setStateState lives in a StatefulWidget and the widget rebuilds itselfBuilt in, nothing to learnDoes not scale to shared state, and logic gets mixed into UI code
Provider with ChangeNotifierA class holds state and calls notifyListeners, and widgets listen through the widget treeSmall API, used in the official Flutter documentation, easy for beginnersDepends on BuildContext, and runtime errors appear when a provider is missing
RiverpodProviders are declared globally and read through a ref, with built-in support for async dataCompile-time safety, easy testing with overrides, good handling of loading and error statesMore concepts to learn, and the API has changed across major versions
Bloc or CubitUI sends events or calls methods, and the bloc emits new immutable statesVery predictable, clear separation, strong tooling and testing libraryMore files and boilerplate, which can feel heavy for small apps

Other libraries such as GetX and MobX exist and have their fans. For long-lived business apps we stay with the options above because they have large communities, clear documentation, and patterns that most Flutter developers you hire will already know.

How We Choose

  • Small app or a team new to Flutter: Provider with ChangeNotifier. It follows the official app architecture guide and is easy to explain.
  • Most new business apps with a lot of API data: Riverpod. AsyncValue makes loading, error, and data states explicit, and overrides make tests short.
  • Large teams, regulated domains, or apps with complex flows such as payments: Bloc. The strict event to state model makes behaviour easy to trace and review.
  • An existing codebase: keep what it uses unless it is causing real problems. Mixing three libraries in one app is worse than any single choice.

Structure Matters More Than the Library

  1. 1Put API calls and local storage in repository classes. Widgets and state classes never call http or a database directly.
  2. 2Keep business rules in the state layer, such as a Notifier, Cubit, or ChangeNotifier, so they can be unit tested without widgets.
  3. 3Make state objects immutable and create new copies on change. Packages such as freezed reduce the boilerplate.
  4. 4Model loading, success, empty, and error states explicitly so every screen handles all of them.
  5. 5Inject repositories so tests can replace them with fakes.
  6. 6Group code by feature, such as auth, orders, and profile, rather than by type, so a feature can be understood in one folder.

Performance Tips

  • Listen only to the part of the state a widget needs, using select in Provider and Riverpod or buildWhen in Bloc, to avoid rebuilding whole screens.
  • Push state consumers down the tree so a small widget rebuilds instead of its parent.
  • Use const constructors wherever possible.
  • Check rebuilds with the Flutter DevTools performance view in profile mode on a real device.

A clean repository layer and well-defined states make any of these libraries pleasant. Without them, none of them will save the project.

Our Flutter training builds the same small app with Provider, Riverpod, and Bloc side by side, so teams can see the differences in real code and agree on one standard before starting their own project.

Key takeaways

  • Use setState for state that belongs to one widget, and a state management library for shared app state.
  • Provider is the simplest start, Riverpod fits most API-heavy apps, and Bloc suits large teams and complex flows.
  • Keep one approach per codebase instead of mixing libraries.
  • Repositories, immutable state, and explicit loading and error states matter more than the library.
  • Rebuild only what changes by selecting the exact state a widget needs.

Related articles

More articles on software development, AI, cloud, and infrastructure.

Hands sorting printed tax forms and receipts next to a calculator
AI Development|

Automating Document Data Entry With AI: Invoices, Receipts, and Forms

How AI reads invoices, receipts, ID cards, and forms and turns them into structured data, how OCR and large language models fit together, why validation and human review still matter, how to measure accuracy, and what to watch for with personal data.

Aerial view of a busy container port with cranes and stacked shipping containers
DevOps|

Deploying Applications to Kubernetes With Helm: A Practical Guide

What Helm charts are, how values and templates work, how to structure a chart for several environments, upgrade and rollback safely, keep secrets out of Git, test charts in CI, and decide between Helm and Kustomize.

Looking for a software development partner?

Tell us about your project, what you need to build, and the challenges you are facing. We can discuss the technical approach, scope, timeline, and estimated cost.

Start a conversation