fetch method

Future<T> fetch({
  1. required Future<T> fetcher(),
  2. Duration staleTime = Duration.zero,
  3. Duration cacheTime = const Duration(minutes: 5),
  4. int retries = 3,
})

Fetches data using the provided fetcher and configuration.

Implementation

Future<T> fetch({
  required Future<T> Function() fetcher,
  Duration staleTime = Duration.zero,
  Duration cacheTime = const Duration(minutes: 5),
  int retries = 3,
}) async {
  if (_isDisposed) throw StateError('Controller is disposed');

  _latestFetcher = fetcher;
  _latestCacheTime = cacheTime;
  _latestRetries = retries;

  if (isFresh(staleTime)) {
    return value.data!;
  }

  _scheduleCacheRemoval(cacheTime);

  if (_fetchFuture != null) {
    return _fetchFuture!;
  }

  value = value.copyWith(
    status: value.hasData ? value.status : QueryStatus.fetching,
    isFetching: true,
  );

  _fetchFuture =
      _executeWithRetries(fetcher, retries, const Duration(seconds: 1));

  try {
    final data = await _fetchFuture!;
    if (!_isDisposed) {
      value = value.copyWith(
        status: QueryStatus.success,
        data: data,
        isFetching: false,
        dataUpdatedAt: DateTime.now(),
      );
    }
    _fetchFuture = null;
    return data;
  } catch (e) {
    if (!_isDisposed) {
      value = value.copyWith(
        status: QueryStatus.error,
        error: e,
        isFetching: false,
        errorUpdatedAt: DateTime.now(),
      );
    }
    _fetchFuture = null;
    rethrow;
  }
}