import 'package:cloud_firestore/cloud_firestore.dart'; import 'package:firebase_core/firebase_core.dart'; import 'package:http/http.dart' as http; import '../auth/auth_service.dart'; import '../sync/r2_upload_service.dart'; abstract class CloudAccountCleanup { Future deleteCloudData(); } class AccountCloudCleanupService implements CloudAccountCleanup { final AuthService _auth; final FirebaseFirestore? _firestore; final http.Client _client; final String _workerUrl; AccountCloudCleanupService({ required this._auth, FirebaseFirestore? firestore, http.Client? client, String? workerUrl, }) : _firestore = firestore ?? _resolveFirestore(), _client = client ?? http.Client(), _workerUrl = (workerUrl ?? R2UploadService.defaultWorkerUrl).replaceAll(RegExp(r'/+$'), ''); static FirebaseFirestore? _resolveFirestore() { try { if (Firebase.apps.isNotEmpty) return FirebaseFirestore.instance; } catch (_) {} return null; } @override Future deleteCloudData() async { final user = _auth.currentUser; if (user == null || user.isAnonymous) throw StateError('A permanent account is required.'); final token = await _auth.getIdToken(true); if (token == null || token.isEmpty) throw StateError('A valid account session is required.'); final response = await _client.delete( Uri.parse('$_workerUrl/account/cloud-data'), headers: {'Authorization': 'Bearer ${token.trim()}'}, ).timeout(const Duration(seconds: 30)); if (response.statusCode < 200 || response.statusCode >= 300) { throw StateError('MotorCloud cleanup was not completed (${response.statusCode}).'); } final firestore = _firestore; if (firestore == null) throw StateError('MotorCloud database is unavailable.'); final userRef = firestore.collection('users').doc(user.uid); final rides = await userRef.collection('rides').get(); final motorcycles = await userRef.collection('motorcycles').get(); final batch = firestore.batch(); for (final doc in rides.docs) { batch.delete(doc.reference); } for (final doc in motorcycles.docs) { batch.delete(doc.reference); } batch.delete(userRef); await batch.commit(); } }