local_value 0.0.2 local_value: ^0.0.2 copied to clipboard
A new Flutter package project.
NOTE: SUPER EARLY ALPHA. Most of the implementation is complete. I need to do other homework for today so I can't finish the tests / docs, but this version should be useable.
Features #
helps save / load / delete singletons to local storage.
you can specify if the document is a application document, temporary document, support document, or shared prefrence. The distinction can be found here.
In short:
DocumentType.document
: data that is user generated and cannot be recreated. (ex. my high score in a local-only game)DocumentType.support
: data that is NOT user generated and cannot be recreated. (ex. automatically set config files)DocumentType.temporary
: data that can be cleared at any time. (ex. caching a downloaded json)DocumentType.prefs
: user prefrences (ex. should the app open in light mode)
NOTE: uses shared_preferences on the backend instead of real files. this is because on web, there is no notion of files.
Use cases #
Saving the logged in user:
class CurrentUser {
final int id;
final String name;
final Color favoriteColor;
// insert toJson here
// insert fromJson here
}
final locallyPersistedUser = localSingleton<CurrentUser>(
documentType: DocumentType.document,
fileName: 'current_user',
fromJson: CurrentUser.fromJson,
toJson: (currentUser) => currentUser.toJson());
//save and load the user to memory like this:
CurrentUser? myCurrentUser = await locallyPersistedUser.read();
await locallyPersistedUser.write(someUser);
Caching many things to memory to avoid redundant network calls:
class CurrentUser {
final int id;
final String name;
final Color favoriteColor;
// insert toJson here
// insert fromJson here
}
final userCache = LocalSingleton<UserCache>(
fileName: 'current_user'
);
await UserCache(userId: 1).save(maybeUserOne);
Usage #
//preface: import it!
import 'package:local_value/local_value.dart';
//first, create some sort of data model you want to save to local storage.
//can be a primative (just use LocalJsonFile<int> or similar)
class CounterObj {
int value;
CounterObj(this.value);
}
//then, call localJsonFile to build a localJsonFile:
//localJson File
final counterFile = localJsonFile<CounterObj>(
documentType: DocumentType.document,
fileName: 'counter',
fromJson: (counterJson) => CounterObj(counterJson['value'] as int),
toJson: (counterObj) => {'value': counterObj.value});
//or LocalTxtFile
localTxtFile(documentType: DocumentType.document, fileName: 'counter')
//read from it
CounterObj? myCurrentCounter = await counterStorage.read();
//write to it
await counterStorage.write(myCurrentCounter ?? CounterObj(8));
//clear it
await counterStorage.clear();
Integration with Dependency Injection #
If you're looking to integrate with dependency injection for testing, look no further. The underlying classes (LocalTxtFile
and LocalJsonFile
) are exposed, so that you can subclass them. Something like this wouldn't work:
//DON'T DO THIS! THIS WILL NOT WORK.
getIt.registerSingleton(localTxtFile(fileName: 'blah1', documentType: ...));
getIt.registerSingleton(localTxtFile(fileName: 'blah2', documentType: ...)); //this will fail, since LocalTxtFile already registered
instead, we can subclass TxtFile
:
class BlahOne extends LocalTxtFile {
BlahOne() : super(
documentType: DocumentType.document,
fileName: 'blah1'
);
}
class BlahTwo extends LocalTxtFile {
BlahTwo() : super(
documentType: DocumentType.document,
fileName: 'blah2'
);
}
//now we can register them inside get_it:
getIt.registerSingleton(BlahOne());
getIt.registerSingleton(BlahTwo());
Additional information #
If you find an issue, please post it on the github.
I will be back if it proves useful to flesh it out! PR's welcome!