64 lines
2.2 KiB
Dart
64 lines
2.2 KiB
Dart
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<void> 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<void> 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();
|
|
}
|
|
}
|