| j / k | Scroll down / up |
| gg | Scroll to top |
| G | Scroll to bottom |
| ⌘K / / | Open search |
| ? | Show this help |
| Esc | Close search / help |
| n / N | Next / previous section |
| h | Go to landing |
| d | Go to docs |
| : | Command mode — type section name |
Press ? or Esc to close
Right-sized for mobile. No repository/usecase ceremony. One Store per feature orchestrates everything: network, local DB, and cache freshness.
| Class | Knows about | Does |
|---|---|---|
DataSource | Network only | Raw HTTP calls, returns Response |
Local | sqflite only | CRUD + freshness check via cached_at |
BaseStore | Network errors, cache logic | Error wrapping, cache orchestration |
Store | DataSource + Local | Extends BaseStore, decides strategy |
class ProfileDataSource {
final ApiClient _client;
ProfileDataSource(this._client);
Future<Response> getMyProfile() => _client.get('/api/v1/profile');
Future<Response> updateMyProfile(UpdateProfileBody body) =>
_client.put('/api/v1/profile', data: body.toJson());
Future<Response> getOrganisations({int page = 1, String? search}) =>
_client.get('/api/v1/organisations', params: {'page': page, 'search': search});
} Future<ProfileModel?> getIfFresh({
Duration maxAge = const Duration(hours: 1),
}) async {
final rows = await db.query(ProfileTable.table, limit: 1);
if (rows.isEmpty) return null;
final cachedAt = rows.first[ProfileTable.cachedAt] as int;
final age = DateTime.now().millisecondsSinceEpoch - cachedAt;
if (age > maxAge.inMilliseconds) return null; // stale
return ProfileModel.fromMap(rows.first);
}
Future<void> upsert(ProfileModel model) async {
await db.insert(ProfileTable.table, {
...model.toMap(),
ProfileTable.cachedAt: DateTime.now().millisecondsSinceEpoch,
}, conflictAlgorithm: ConflictAlgorithm.replace);
} | Layer | Tool | Purpose |
|---|---|---|
| In-memory | Cubit state | Session cache — instant, free, always present |
| Persistent | sqflite (opt-in) | Offline-safe, survives restart |
| Freshness | cached_at column | Staleness detection per table |
| Preferences | SharedPrefs | Primitives only: locale, theme, flags |