import 'package:flutter/foundation.dart'; import 'package:supplements/logging.dart'; import '../services/database_sync_service.dart'; import '../services/auto_sync_service.dart'; import 'settings_provider.dart'; class SimpleSyncProvider with ChangeNotifier { final DatabaseSyncService _syncService = DatabaseSyncService(); // Callback for UI refresh after sync VoidCallback? _onSyncCompleteCallback; // Auto-sync service AutoSyncService? _autoSyncService; // Track if current sync is auto-triggered bool _isAutoSync = false; // Getters SyncStatus get status => _syncService.status; String? get lastError => _syncService.lastError; DateTime? get lastSyncTime => _syncService.lastSyncTime; bool get isConfigured => _syncService.isConfigured; bool get isSyncing => status == SyncStatus.downloading || status == SyncStatus.merging || status == SyncStatus.uploading; bool get isAutoSync => _isAutoSync; AutoSyncService? get autoSyncService => _autoSyncService; // Auto-sync error handling getters bool get isAutoSyncDisabledDueToErrors => _autoSyncService?.isAutoDisabledDueToErrors ?? false; int get autoSyncConsecutiveFailures => _autoSyncService?.consecutiveFailures ?? 0; String? get autoSyncLastError => _autoSyncService?.lastErrorMessage; bool get hasAutoSyncScheduledRetry => _autoSyncService?.hasScheduledRetry ?? false; // Configuration getters String? get serverUrl => _syncService.serverUrl; String? get username => _syncService.username; String? get password => _syncService.password; String? get remotePath => _syncService.remotePath; SimpleSyncProvider() { // Set up callbacks to notify listeners _syncService.onStatusChanged = (_) => notifyListeners(); _syncService.onError = (_) => notifyListeners(); _syncService.onSyncCompleted = () { notifyListeners(); // Trigger UI refresh callback if set _onSyncCompleteCallback?.call(); }; // Load saved configuration and notify listeners when done _loadConfiguration(); } /// Set callback to refresh UI data after sync completes void setOnSyncCompleteCallback(VoidCallback? callback) { _onSyncCompleteCallback = callback; } /// Initialize auto-sync service with settings provider void initializeAutoSync(SettingsProvider settingsProvider) { _autoSyncService = AutoSyncService( syncProvider: this, settingsProvider: settingsProvider, ); if (kDebugMode) { printLog('SimpleSyncProvider: Auto-sync service initialized'); } } /// Triggers auto-sync if enabled and configured void triggerAutoSyncIfEnabled() { _autoSyncService?.triggerAutoSync(); } Future _loadConfiguration() async { await _syncService.loadSavedConfiguration(); notifyListeners(); // Notify UI that configuration might be available } Future configure({ required String serverUrl, required String username, required String password, required String remotePath, }) async { _syncService.configure( serverUrl: serverUrl, username: username, password: password, remotePath: remotePath, ); notifyListeners(); } Future testConnection() async { return await _syncService.testConnection(); } Future syncDatabase({bool isAutoSync = false}) async { if (!isConfigured) { throw Exception('Sync not configured'); } _isAutoSync = isAutoSync; notifyListeners(); try { await _syncService.syncDatabase(); } catch (e) { if (kDebugMode) { printLog('Sync failed in provider: $e'); } rethrow; } finally { _isAutoSync = false; notifyListeners(); } } void clearError() { _syncService.clearError(); notifyListeners(); } /// Resets auto-sync error state and re-enables auto-sync if it was disabled void resetAutoSyncErrors() { _autoSyncService?.resetErrorState(); notifyListeners(); } String getStatusText() { final syncType = _isAutoSync ? 'Auto-sync' : 'Sync'; // Check for auto-sync specific errors first if (isAutoSyncDisabledDueToErrors) { return 'Auto-sync disabled due to repeated failures. ${autoSyncLastError ?? 'Check sync settings.'}'; } switch (status) { case SyncStatus.idle: if (hasAutoSyncScheduledRetry) { return 'Auto-sync will retry shortly...'; } return 'Ready to sync'; case SyncStatus.downloading: return '$syncType: Downloading remote database...'; case SyncStatus.merging: return '$syncType: Merging databases...'; case SyncStatus.uploading: return '$syncType: Uploading database...'; case SyncStatus.completed: return '$syncType completed successfully'; case SyncStatus.error: // For auto-sync errors, show more specific messages if (_isAutoSync && autoSyncLastError != null) { return 'Auto-sync failed: $autoSyncLastError'; } return '$syncType failed: ${lastError ?? 'Unknown error'}'; } } @override void dispose() { _autoSyncService?.dispose(); super.dispose(); } }