88 lines
2.3 KiB
Dart
88 lines
2.3 KiB
Dart
/// PocketBase sign-in state. Local tx/bank data is unchanged by auth.
|
|
library;
|
|
|
|
import 'package:flutter/foundation.dart';
|
|
import 'package:pocketbase/pocketbase.dart';
|
|
|
|
import '../services/storage_service.dart';
|
|
import '../utils/constants.dart';
|
|
|
|
/// Owns the PocketBase client, session persistence, and login/logout.
|
|
class AuthController extends ChangeNotifier {
|
|
AuthController(this._storage);
|
|
|
|
final StorageService _storage;
|
|
PocketBase? _client;
|
|
|
|
PocketBase get client {
|
|
final pb = _client;
|
|
if (pb == null) {
|
|
throw StateError('AuthController.init() must be called before use.');
|
|
}
|
|
return pb;
|
|
}
|
|
|
|
bool get isLoggedIn => _client?.authStore.isValid ?? false;
|
|
|
|
RecordModel? get user => _client?.authStore.record;
|
|
|
|
String? get email {
|
|
final value = user?.getStringValue('email');
|
|
return value == null || value.isEmpty ? null : value;
|
|
}
|
|
|
|
String? get name {
|
|
final value = user?.getStringValue('name');
|
|
return value == null || value.isEmpty ? null : value;
|
|
}
|
|
|
|
String get displayName {
|
|
final n = name;
|
|
if (n != null && n.isNotEmpty) return n;
|
|
final e = email;
|
|
if (e != null && e.isNotEmpty) return e.split('@').first;
|
|
return 'Account';
|
|
}
|
|
|
|
String get initials {
|
|
final source = name ?? email ?? '?';
|
|
final parts = source.trim().split(RegExp(r'\s+'));
|
|
if (parts.length >= 2 && parts[0].isNotEmpty && parts[1].isNotEmpty) {
|
|
return '${parts[0][0]}${parts[1][0]}'.toUpperCase();
|
|
}
|
|
if (source.isNotEmpty) return source[0].toUpperCase();
|
|
return '?';
|
|
}
|
|
|
|
Future<void> init() async {
|
|
final store = AsyncAuthStore(
|
|
save: (String data) async {
|
|
if (data.isEmpty) {
|
|
await _storage.clearPocketBaseAuth();
|
|
} else {
|
|
await _storage.setPocketBaseAuth(data);
|
|
}
|
|
},
|
|
initial: _storage.pocketBaseAuth,
|
|
);
|
|
_client = PocketBase(kPocketBaseUrl, authStore: store);
|
|
_client!.authStore.onChange.listen((_) => notifyListeners());
|
|
notifyListeners();
|
|
}
|
|
|
|
Future<void> login({
|
|
required String email,
|
|
required String password,
|
|
}) async {
|
|
await client
|
|
.collection(kPocketBaseUsersCollection)
|
|
.authWithPassword(email.trim(), password);
|
|
notifyListeners();
|
|
}
|
|
|
|
Future<void> logout() async {
|
|
client.authStore.clear();
|
|
notifyListeners();
|
|
}
|
|
}
|