persist<T> method

(AsyncValue<T>, void Function(T)) persist<T>({
  1. required Future<T> read(),
  2. required Future<void> write(
    1. T
    ),
})

A mechanism to persist changes made in state that manages its own state. See the docs for usage information.

Defines a way to interact with a storage provider of your choice through the read and write parameters.

read is only called once; it is assumed that if write is successful, then calling read again would reflect the new state that we already have access to. Thus, calling read again is skipped as an optimization.

See also: hydrate, which will compose more nicely with side effects that manage their own state by simply persisting their state. persist acts like a state assembled with hydrate.

Implementation

(AsyncValue<T>, void Function(T)) persist<T>({
  required Future<T> Function() read,
  required Future<void> Function(T) write,
}) {
  final readFuture = use.callonce(read);
  final readState = use.future(readFuture);
  final (state: writeState, :mutate, clear: _) = use.mutation<T>();

  final state = (writeState ?? readState).fillInPreviousData(readState.data);

  void persist(T data) {
    mutate(() async {
      await write(data);
      return data;
    }());
  }

  return (state, persist);
}