flutter_cache_store 0.2.0-beta2

  • README.md
  • CHANGELOG.md
  • Example
  • Installing
  • Versions
  • new71

flutter_cache_store

A flexible cache manager for Flutter.

This package is highly inspired by flutter_cache_manager. Can be easily switched to each other.

Quick Start

import 'package:flutter_cache_store/flutter_cache_store.dart';

void demo(String url) async {
  final store = await CacheStore.getInstance();
  final file = await store.getFile(url);
  // do something with file...
}

APIs

CacheStore

void api() async {
  // set expiration policy.
  // must be called before `CacheStore.getInstance` or will raise an exception.
  // default: LessRecentlyUsedPolicy(maxCount: 999)
  CacheStore.setPolicy(LessRecentlyUsedPolicy(maxCount: 4096));

  // get a singleton store instance
  CacheStore store = await CacheStore.getInstance(
      clearNow: true // default: false - whether to clean up immediately
      );

  // fetch a file from an URL and cache it
  File file = await store.getFile(
    'url', // GET method
    key: null, // use custom string instead of URL
    headers: {}, // same as http.get
    flushCache: false, // whether to re-download the file
  );

  // flush specific files by keys
  await store.flush([
    'key', // key (default is the URL) passed to `getFile`
  ]);

  // remove all cached files
  await store.clearAll();
}

Cache File Structure

By default, the cached files will be saved under $TEMP/cache_store. $TEMP is generated by path_provider. The default temp filenames are timestamp-based 11 chars.

You can customize your own file structure under $TEMP/cache_store by overriding Policy. There is an example:

Let's suppose your are developing a reader for novels, and your app will cache chapters of books. Your API returns some IDs of books and chapters, and an ID only contains digits.

// Extends a Policy class and override `generateFilename`
class LRUCachePolicy extends LessRecentlyUsedPolicy {
  LRUCachePolicy({int maxCount}) : super(maxCount: maxCount);

  @override
  String generateFilename({final String key, final String url}) =>
      key; // use key as the filename
}

void customizedCacheFileStructure() async {
  // Set it as your Policy
  CacheStore.setPolicy(LRUCachePolicy(maxCount: 4096));

  // get a singleton store instance
  CacheStore store = await CacheStore.getInstance();

  // fetch a file from an URL and cache it
  String bookId = 'book123';
  String chapterId = 'ch42';
  String chapterUrl = 'https://example.com/book123/ch42';
  File file = await store.getFile(
    chapterUrl,
    key: '$bookId/$chapterId', // use IDs as path and filename
  );

  // Your file will be cached as `$TEMP/cache_store/book123/ch42`
}

About Policy

Currently, there is only one policy available. More policies may be added soon.

  1. LessRecentlyUsedPolicy

    Less Recently Used files will be removed when reached maxCount. Each time you access a file will update its used timestamp.

     new LessRecentlyUsedPolicy(
       maxCount: 999, // default: 999
     );
    

    The current version is super naive. It's simply sorting all items by last used timestamp. So it still possibly hits performance because of O(N*logN) complexity with a very large number.

How to implement your own policy

The interface is a simple abstract class. You only have to implement a few methods.

abstract class CacheStorePolicy {
  // IT'S THE ONLY METHOD YOU HAVE TO IMPLEMENT.
  // `store` will invoke this method from time to time.
  // Make sure return all expired items at once.
  // then `store` will manage to remove the cached files.
  // you also have to save your data if need to persist some data.
  Future<Iterable<CacheItem>> cleanup(Iterable<CacheItem> allItems);

  // will be invoked when store.clearAll called.
  Future<void> clearAll(Iterable<CacheItem> allItems) async {}

  // will invoke only once when the `store` is created and load saved data.
  // you need to load persistent data and restore items' payload.
  // only returned items will be cached. others will be recycled later.
  Future<Iterable<CacheItem>> restore(List<CacheItem> allItems) async => allItems;

  // event when a new `CacheItem` has been added to the cache.
  // you may need to attach a `CacheItemPayload` instance to it.
  Future<void> onAdded(final CacheItem addedItem) async {}

  // event when an item just been accessed.
  // you may need to attach or update item's payload.
  Future<void> onAccessed(final CacheItem accessedItem, bool flushed) async {}

  // event when a request just finished.
  // the response headers will be passed as well.
  Future<void> onDownloaded(final CacheItem item, final Map<String, String> headers) async {}

  // event when `store.flush` has called
  Future<void> onFlushed(final Iterable<CacheItem> flushedItems) async {}

  // filename (including path) relative to `CacheItem.rootPath`.
  // usually ignore this unless need a better files structure.
  // you must provide valid filenames.
  String generateFilename({final String key, final String url}) =>
      Utils.genName(); // timestamp based random filename
}
  • Tips

    You don't have to implement all of the onAdded, onAccessed and onDownloaded. Only override the one you needed. For example:

    1. You can create a FIFO policy with onAdded
    2. Least Frequently Used policy can be implement with only onAccessed
    3. Standard http cache can just use onDownloaded

Change Log

[0.2.0-beta2] - Released on 2018-11-10

Breaking Changes

  • Changed interface of CacheStorePolicy.generateFilename to make it easier to customize your own cache file structure.

Others

  • Updated document and example.
  • Fixed some bugs.

[0.1.3-beta] - Released on 2018-11-10

  • Some bug fixes.
  • Document updates.
  • Better 0 size files handling.

[0.1.1-beta] - Released on 2018-11-04

  • Finished basic designs.
  • Updated documentation to match requirements
  • Started to use in my own project.

example/example.dart

import 'dart:io';
import 'package:flutter_cache_store/flutter_cache_store.dart';

void demo(String url) async {
  final store = await CacheStore.getInstance();
  final file = await store.getFile(url);
  // do something with file...
}

void api() async {
  // set expiration policy.
  // must be called before `CacheStore.getInstance` or will raise an exception.
  // default: LessRecentlyUsedPolicy(maxCount: 999)
  CacheStore.setPolicy(LessRecentlyUsedPolicy(maxCount: 4096));

  // get a singleton store instance
  CacheStore store = await CacheStore.getInstance(
      clearNow: true // default: false - whethere to clean up immediately
      );

  // fetch a file from an URL and cache it
  File file = await store.getFile(
    'url', // GET method
    key: null, // use custom string instead of URL
    headers: {}, // same as http.get
    flushCache: false, // whether to re-download the file
  );

  // flush specific files by keys
  await store.flush([
    'key', // key (default is the URL) passed to `getFile`
  ]);

  // remove all cached files
  await store.clearAll();
}

// Extends a Policy class and override `generateFilename`
class LRUCachePolicy extends LessRecentlyUsedPolicy {
  LRUCachePolicy({int maxCount}) : super(maxCount: maxCount);

  @override
  String generateFilename({final String key, final String url}) =>
      key; // use key as the filename
}

void customizedCacheFileStructure() async {
  // Set it as your Policy
  CacheStore.setPolicy(LRUCachePolicy(maxCount: 4096));

  // get a singleton store instance
  CacheStore store = await CacheStore.getInstance();

  // fetch a file from an URL and cache it
  String bookId = 'book123';
  String chapterId = 'ch42';
  String chapterUrl = 'https://example.com/book123/ch42';
  File file = await store.getFile(
    chapterUrl,
    key: '$bookId/$chapterId', // use IDs as path and filename
  );

  // Your file will be cached as `$TEMP/cache_store/book123/ch42`
}

Use this package as a library

1. Depend on it

Add this to your package's pubspec.yaml file:


dependencies:
  flutter_cache_store: ^0.2.0-beta2

2. Install it

You can install packages from the command line:

with Flutter:


$ flutter packages get

Alternatively, your editor might support flutter packages get. Check the docs for your editor to learn more.

3. Import it

Now in your Dart code, you can use:


import 'package:flutter_cache_store/flutter_cache_store.dart';
  
Version Uploaded Documentation Archive
0.2.0-beta2 Nov 10, 2018 Go to the documentation of flutter_cache_store 0.2.0-beta2 Download flutter_cache_store 0.2.0-beta2 archive
0.1.4-beta Nov 10, 2018 Go to the documentation of flutter_cache_store 0.1.4-beta Download flutter_cache_store 0.1.4-beta archive
0.1.3-beta Nov 10, 2018 Go to the documentation of flutter_cache_store 0.1.3-beta Download flutter_cache_store 0.1.3-beta archive
0.1.2-beta Nov 10, 2018 Go to the documentation of flutter_cache_store 0.1.2-beta Download flutter_cache_store 0.1.2-beta archive
0.1.1-beta Nov 4, 2018 Go to the documentation of flutter_cache_store 0.1.1-beta Download flutter_cache_store 0.1.1-beta archive
0.1.0-beta Nov 4, 2018 Go to the documentation of flutter_cache_store 0.1.0-beta Download flutter_cache_store 0.1.0-beta archive
0.0.4-beta Nov 4, 2018 Go to the documentation of flutter_cache_store 0.0.4-beta Download flutter_cache_store 0.0.4-beta archive
Popularity:
Describes how popular the package is relative to other packages. [more]
43
Health:
Code health derived from static analysis. [more]
100
Maintenance:
Reflects how tidy and up-to-date the package is. [more]
95
Overall:
Weighted score of the above. [more]
71
Learn more about scoring.

We analyzed this package on Nov 14, 2018, and provided a score, details, and suggestions below. Analysis was completed with status completed using:

  • Dart: 2.0.0
  • pana: 0.12.6
  • Flutter: 0.11.3

Platforms

Detected platforms: Flutter

References Flutter, and has no conflicting libraries.

Maintenance suggestions

Package is pre-release. (-5 points)

Pre-release versions should be used with caution, their API may change in breaking ways.

Dependencies

Package Constraint Resolved Available
Direct dependencies
Dart SDK >=2.0.0-dev.68.0 <3.0.0
flutter 0.0.0
http ^0.12.0 0.12.0
path_provider ^0.4.0 0.4.1
shared_preferences ^0.4.0 0.4.3
synchronized ^1.5.0 1.5.3
Transitive dependencies
async 2.0.8
charcode 1.1.2
collection 1.14.11
http_parser 3.1.3
meta 1.1.6
path 1.6.2
sky_engine 0.0.99
source_span 1.4.1
string_scanner 1.0.4
typed_data 1.1.6
vector_math 2.0.8