Hydrated Bloc

Pub Version Build Status Code Coverage style: effective dart MIT License Starware Bloc Library

An extension to the bloc state management library which automatically persists and restores bloc states and is built on top of hydrated_cubit.


hydrated_bloc exports a Storage interface which means it can work with any storage provider. Out of the box, it comes with its own implementation: HydratedStorage.

HydratedStorage is built on top of path_provider for a platform-agnostic storage layer. The out-of-the-box storage implementation reads/writes to file using the toJson/fromJson methods on HydratedBloc and should perform very well for most use-cases (performance reports coming soon). HydratedStorage is supported for desktop (example).


1. Use HydratedStorage

void main() async {
  HydratedBloc.storage = await HydratedStorage.build();

2. Extend HydratedBloc and override fromJson/toJson

enum CounterEvent { increment, decrement }

class CounterBloc extends HydratedBloc<CounterEvent, int> {
  CounterBloc() : super(0);

  Stream<int> mapEventToState(CounterEvent event) async* {
    switch (event) {
      case CounterEvent.decrement:
        yield state - 1;
      case CounterEvent.increment:
        yield state + 1;

  int fromJson(Map<String, dynamic> json) => json['value'] as int;

  Map<String, int> toJson(int state) => { 'value': state };

Now our CounterBloc is a HydratedBloc and will automatically persist its state. We can increment the counter value, hot restart, kill the app, etc... and our CounterBloc will always retain its state.

Custom Storage Directory

By default, all data is written to temporary storage which means it can be wiped by the operating system at any point in time.

An optional storageDirectory can be provided to override the default temporary storage directory:

HydratedBloc.storage = await HydratedStorage.build(
  storageDirectory: await getApplicationDocumentsDirectory(),

Custom Hydrated Storage

If the default HydratedStorage doesn't meet your needs, you can always implement a custom Storage by simply implementing the Storage interface and initializing HydratedBloc with the custom Storage.

// my_hydrated_storage.dart

class MyHydratedStorage implements Storage {
  dynamic read(String key) {
    // TODO: implement read

  Future<void> write(String key, dynamic value) async {
    // TODO: implement write

  Future<void> delete(String key) async {
    // TODO: implement delete

  Future<void> clear() async {
    // TODO: implement clear
// main.dart

HydratedBloc.storage = MyHydratedStorage();




Hydrated Bloc is Starware.
This means you're free to use the project, as long as you star its GitHub repository.
Your appreciation makes us grow and glow up. ⭐