data_repository 0.4.4 copy "data_repository: ^0.4.4" to clipboard
data_repository: ^0.4.4 copied to clipboard

A data repository for flutter, manages both local and remote api access

A data repository for flutter, manages both local and remote api access

Features #

see sample here

Getting started #

Define your implementation of local and remote repositories.

The local repository manages caching and retrieving data localy, while the remote repository manages retrieving data from a remote source. I would recommend using GetIt for this

   GetIt.I.registerSingleton<LocalRepository>(HiveRepository());
    GetIt.I.registerSingleton<RemoteRepository>(
        RemoteRepository((HttpApiProvider())));

create an API service class. This is just a class where you define your API requests

class PostApi  {
  ApiRequest<Post, Post> create(CreatePostDto body) {
    return ApiRequest<Post, Post>(
        baseUrl: baseUrl,
        path: ApiUrls.department,
        method: ApiMethods.post,
        body: body.toJson,
        dataKey: 'data',
        error: ErrorDescription(),
        interceptors: [
        HeaderInterceptor({
                'Authorization': 'Bearer $token',
                "Content-Type": "application/json",
                "Accept": "application/json",
        }),
          JsonInterceptor<ErrorModel>(DepartmentModels.factories),
          NetworkDurationInterceptor(),
        ]);
  }
}

Create a resository class and extend the DataRepository class

Here you need to initialize your local and remote repository implementations.

class PostRepository extends DataRepository {
  final _api = PostApi();

  PostRepository()
      : super(GetIt.I<LocalRepository>(), GetIt.I<RemoteRepository>());

  Future<ApiResponse<Post, Post>> createPost(CreatePostDto body) async {
    return await handleRequest(_api.create(body));
  }

you can use your repository in you view model to fetch data and manage state based on the response.

 void createPost() async {
    emit(state.loading());

    final response = await _repository.createPost(CreatePostDto(
        title: state.title ?? '',
        content: state.content ?? '',
        image: state.image ?? ''));

    if (response.isSuccessful) {
      emit(PostCreated('Register success', state));
    } else {
      // print((response.error as ApiError).message);
      emit(ErrorState(response.error as ApiError, state));
    }
  }

caching #

in your repository, you can set CacheDescription to define if you want request to be cached. you set the key, and the lifespan


  Future<ApiResponse<List<Post>, Post>> getPost() async {
    return await handleRequest(_api.getPost(),
        cache: CacheDescription('posts-list',
            lifeSpan: CacheDescription.oneMinute));
  }

interceptors #

You can define interceptors to intercept request or response objects Interceptors run before a request is fulfilled, and after response is gotten. To create an interceptor, extend the ApiInterceptor class and override onRequest to intercept request and onResponse to intercept response and onError to intercept request error.


class NetworkDurationInterceptor extends ApiInterceptor {
  Map<String, int> timestamp = {};

  @override
  ApiResponse<ResponseType, InnerType> onResponse<ResponseType, InnerType>(
      ApiResponse<ResponseType, InnerType> response) {
    if (kDebugMode) {
      print(
          'NetworkDurationInterceptor ${response.statusCode}, ${response.request.requestId}, $timestamp ${timestamp[response.request.requestId]}');
    }

    var duration = DateTime.now().millisecondsSinceEpoch -
        (timestamp.remove(response.request.requestId) ?? 00);

    if (kDebugMode) {
      print('request completed in $duration milliseconds');
    }

    return response.copyWith(extra: {...?response.extra, 'duration': duration});
  }

  @override
  ApiRequest<ResponseType, InnerType> onRequest<ResponseType, InnerType>(
      ApiRequest<ResponseType, InnerType> request) {
    timestamp
        .addAll({request.requestId: DateTime.now().millisecondsSinceEpoch});
    return request; //.copyWith(: );
  }

  @override
  ApiResponse<ResponseType, InnerType> onError<ResponseType, InnerType>(
      ApiResponse<ResponseType, InnerType> response) {
    var duration = DateTime.now().millisecondsSinceEpoch -
        (timestamp.remove(response.request.requestId) ?? 00);

    if (kDebugMode) {
      print('request completed with error in $duration milliseconds');
    }

    return response.copyWith(extra: {...?response.extra, 'duration': duration});
  }
}

Check the example app for sample code More examples comming soon

3
likes
140
pub points
61%
popularity

Publisher

verified publisherwiseminds.cc

A data repository for flutter, manages both local and remote api access

Repository (GitHub)
View/report issues

Documentation

API reference

License

MIT (LICENSE)

Dependencies

flutter, http, http_parser, mime, path_provider

More

Packages that depend on data_repository