--- name: "GetStorage Patterns" description: "Local storage with GetStorage for preferences, caching, and offline-first patterns" version: "1.0.0" --- # GetStorage Patterns ## Initialization ```dart // main.dart void main() async { await GetStorage.init(); runApp(MyApp()); } ``` ## Storage Service Pattern ```dart class StorageService { final GetStorage _box; StorageService() : _box = GetStorage(); // Token management String? get token => _box.read('auth_token'); Future setToken(String token) => _box.write('auth_token', token); Future clearToken() => _box.remove('auth_token'); // User data Map? get userData => _box.read>('user_data'); Future setUserData(Map data) => _box.write('user_data', data); // Preferences bool get isDarkMode => _box.read('dark_mode') ?? false; Future setDarkMode(bool value) => _box.write('dark_mode', value); String get locale => _box.read('locale') ?? 'en'; Future setLocale(String locale) => _box.write('locale', locale); // Clear all Future clearAll() => _box.erase(); // Listen to changes void listenKey(String key, Function(dynamic) callback) { _box.listenKey(key, callback); } } ``` ## Local Data Source Pattern ```dart class UserLocalDataSource { final GetStorage _storage; static const String _usersKey = 'cached_users'; static const String _userKeyPrefix = 'cached_user_'; static const Duration _cacheDuration = Duration(hours: 24); UserLocalDataSource(this._storage); Future cacheUser(UserModel user) async { final cacheData = { 'user': user.toJson(), 'timestamp': DateTime.now().toIso8601String(), }; await _storage.write('$_userKeyPrefix${user.id}', cacheData); } Future getCachedUser(String id) async { final cacheData = _storage.read>('$_userKeyPrefix$id'); if (cacheData == null) return null; // Check cache expiration final timestamp = DateTime.parse(cacheData['timestamp']); if (DateTime.now().difference(timestamp) > _cacheDuration) { await _storage.remove('$_userKeyPrefix$id'); return null; } return UserModel.fromJson(cacheData['user']); } Future cacheUsers(List users) async { final cacheData = { 'users': users.map((u) => u.toJson()).toList(), 'timestamp': DateTime.now().toIso8601String(), }; await _storage.write(_usersKey, cacheData); } Future?> getCachedUsers() async { final cacheData = _storage.read>(_usersKey); if (cacheData == null) return null; final timestamp = DateTime.parse(cacheData['timestamp']); if (DateTime.now().difference(timestamp) > _cacheDuration) { await _storage.remove(_usersKey); return null; } final List usersList = cacheData['users']; return usersList.map((json) => UserModel.fromJson(json)).toList(); } Future clearCache() async { await _storage.erase(); } } ``` ## GetX Service Integration ```dart class CacheService extends GetxService { final GetStorage _storage; CacheService() : _storage = GetStorage(); Future init() async { await GetStorage.init(); return this; } // Reactive cache final _cachedData = {}.obs; T? get(String key) { return _storage.read(key); } Future put(String key, T value, {Duration? expiry}) async { if (expiry != null) { final expiryData = { 'value': value, 'expiry': DateTime.now().add(expiry).toIso8601String(), }; await _storage.write(key, expiryData); } else { await _storage.write(key, value); } _cachedData[key] = value; } Future remove(String key) async { await _storage.remove(key); _cachedData.remove(key); } bool has(String key) { return _storage.hasData(key); } } ``` ## Best Practices - Initialize GetStorage before running app - Use type-safe reads (`read`, `read`, etc.) - Implement cache expiration for time-sensitive data - Clear cache on logout - Use separate keys for different data types - Listen to changes for reactive updates