mirror of
https://github.com/Dvorinka/1356.git
synced 2026-06-05 04:22:55 +00:00
small fix, don't worry about it
This commit is contained in:
@@ -1,17 +1,23 @@
|
||||
import 'dart:async';
|
||||
import '../models/user_model.dart';
|
||||
import '../../bootstrap/supabase_client.dart';
|
||||
import '../../core/utils/unit_conversion_utils.dart';
|
||||
import 'package:supabase_flutter/supabase_flutter.dart' as supabase;
|
||||
import 'package:google_sign_in/google_sign_in.dart';
|
||||
|
||||
class AuthRepository {
|
||||
final supabase.SupabaseClient _client;
|
||||
final supabase.SupabaseClient? _client;
|
||||
StreamSubscription<supabase.AuthState>? _authStateSubscription;
|
||||
|
||||
AuthRepository([supabase.SupabaseClient? client]) : _client = client ?? supabaseClient;
|
||||
AuthRepository([supabase.SupabaseClient? client]) : _client = client;
|
||||
|
||||
Stream<User?> get authStateChanges {
|
||||
return _client.auth.onAuthStateChange.map((data) {
|
||||
final client = supabaseClient;
|
||||
if (client == null) {
|
||||
// Return a stream that never emits if Supabase is not initialized
|
||||
return Stream.empty();
|
||||
}
|
||||
return client.auth.onAuthStateChange.map((data) {
|
||||
final session = data.session;
|
||||
if (session?.user != null) {
|
||||
return _mapSupabaseUserToAppUser(session!.user);
|
||||
@@ -21,39 +27,53 @@ class AuthRepository {
|
||||
}
|
||||
|
||||
User? get currentUser {
|
||||
final user = _client.auth.currentUser;
|
||||
final client = supabaseClient;
|
||||
if (client == null) return null;
|
||||
final user = client.auth.currentUser;
|
||||
return user != null ? _mapSupabaseUserToAppUser(user) : null;
|
||||
}
|
||||
|
||||
bool get isAuthenticated => _client.auth.currentUser != null;
|
||||
bool get isAuthenticated {
|
||||
final client = supabaseClient;
|
||||
if (client == null) return false;
|
||||
return client.auth.currentUser != null;
|
||||
}
|
||||
|
||||
String? get currentUserId => _client.auth.currentUser?.id;
|
||||
String? get currentUserId {
|
||||
final client = supabaseClient;
|
||||
if (client == null) return null;
|
||||
return client.auth.currentUser?.id;
|
||||
}
|
||||
|
||||
Future<bool> isSessionValid() async {
|
||||
final session = _client.auth.currentSession;
|
||||
assert(_client != null, 'Client must not be null');
|
||||
final session = _client!.auth.currentSession;
|
||||
if (session == null) return false;
|
||||
|
||||
|
||||
final now = DateTime.now();
|
||||
final expiresAt = session.expiresAt;
|
||||
if (expiresAt == null) return true;
|
||||
|
||||
|
||||
return now.isBefore(DateTime.fromMillisecondsSinceEpoch(expiresAt * 1000));
|
||||
}
|
||||
|
||||
Future<void> refreshSession() async {
|
||||
assert(_client != null, 'Client must not be null');
|
||||
try {
|
||||
await _client.auth.refreshSession();
|
||||
await _client!.auth.refreshSession();
|
||||
} catch (e) {
|
||||
throw Exception('Failed to refresh session: $e');
|
||||
}
|
||||
}
|
||||
|
||||
Future<supabase.Session?> getCurrentSession() async {
|
||||
return _client.auth.currentSession;
|
||||
assert(_client != null, 'Client must not be null');
|
||||
return _client!.auth.currentSession;
|
||||
}
|
||||
|
||||
void listenToAuthStateChanges(Function(User?) callback) {
|
||||
_authStateSubscription = _client.auth.onAuthStateChange.listen((data) {
|
||||
assert(_client != null, 'Client must not be null');
|
||||
_authStateSubscription = _client!.auth.onAuthStateChange.listen((data) {
|
||||
final session = data.session;
|
||||
if (session?.user != null) {
|
||||
callback(_mapSupabaseUserToAppUser(session!.user));
|
||||
@@ -68,22 +88,25 @@ class AuthRepository {
|
||||
}
|
||||
|
||||
Future<void> signInWithEmail(String email, String password) async {
|
||||
await _client.auth.signInWithPassword(email: email, password: password);
|
||||
assert(_client != null, 'Client must not be null');
|
||||
await _client!.auth.signInWithPassword(email: email, password: password);
|
||||
}
|
||||
|
||||
Future<void> signUpWithEmail(String email, String password, String username) async {
|
||||
final response = await _client.auth.signUp(
|
||||
Future<void> signUpWithEmail(String email, String password, String username, {double? heightCm, double? weightKg, int? age, Gender? gender, HeightUnit? heightUnit, WeightUnit? weightUnit}) async {
|
||||
assert(_client != null, 'Client must not be null');
|
||||
final response = await _client!.auth.signUp(
|
||||
email: email,
|
||||
password: password,
|
||||
data: {'username': username},
|
||||
);
|
||||
|
||||
|
||||
if (response.user != null) {
|
||||
await _createUserProfile(response.user!.id, username, email);
|
||||
await _createUserProfile(response.user!.id, username, email, heightCm: heightCm, weightKg: weightKg, age: age, gender: gender, heightUnit: heightUnit, weightUnit: weightUnit);
|
||||
}
|
||||
}
|
||||
|
||||
Future<void> signInWithGoogle() async {
|
||||
assert(_client != null, 'Client must not be null');
|
||||
try {
|
||||
final GoogleSignIn googleSignIn = GoogleSignIn(
|
||||
scopes: ['email', 'profile'],
|
||||
@@ -109,6 +132,7 @@ class AuthRepository {
|
||||
}
|
||||
|
||||
Future<void> _handleGoogleUser(dynamic googleUser) async {
|
||||
assert(_client != null, 'Client must not be null');
|
||||
try {
|
||||
final googleAuth = await googleUser.authentication;
|
||||
final idToken = googleAuth.idToken;
|
||||
@@ -118,7 +142,7 @@ class AuthRepository {
|
||||
throw Exception('No ID token or access token from Google sign-in');
|
||||
}
|
||||
|
||||
final response = await _client.auth.signInWithIdToken(
|
||||
final response = await _client!.auth.signInWithIdToken(
|
||||
provider: supabase.OAuthProvider.google,
|
||||
idToken: idToken,
|
||||
accessToken: accessToken,
|
||||
@@ -133,17 +157,20 @@ class AuthRepository {
|
||||
}
|
||||
|
||||
Future<void> signInWithGithub() async {
|
||||
await _client.auth.signInWithOAuth(
|
||||
assert(_client != null, 'Client must not be null');
|
||||
await _client!.auth.signInWithOAuth(
|
||||
supabase.OAuthProvider.github,
|
||||
);
|
||||
}
|
||||
|
||||
Future<void> signOut() async {
|
||||
await _client.auth.signOut();
|
||||
assert(_client != null, 'Client must not be null');
|
||||
await _client!.auth.signOut();
|
||||
}
|
||||
|
||||
Future<void> resetPassword(String email) async {
|
||||
await _client.auth.resetPasswordForEmail(email);
|
||||
assert(_client != null, 'Client must not be null');
|
||||
await _client!.auth.resetPasswordForEmail(email);
|
||||
}
|
||||
|
||||
Future<void> updateProfile({
|
||||
@@ -151,8 +178,15 @@ class AuthRepository {
|
||||
String? bio,
|
||||
String? avatarUrl,
|
||||
bool? isPublicProfile,
|
||||
double? heightCm,
|
||||
double? weightKg,
|
||||
int? age,
|
||||
Gender? gender,
|
||||
HeightUnit? heightUnit,
|
||||
WeightUnit? weightUnit,
|
||||
}) async {
|
||||
final userId = _client.auth.currentUser?.id;
|
||||
assert(_client != null, 'Client must not be null');
|
||||
final userId = _client!.auth.currentUser?.id;
|
||||
if (userId == null) throw Exception('User not authenticated');
|
||||
|
||||
final updates = <String, dynamic>{};
|
||||
@@ -160,23 +194,36 @@ class AuthRepository {
|
||||
if (bio != null) updates['bio'] = bio;
|
||||
if (avatarUrl != null) updates['avatar_url'] = avatarUrl;
|
||||
if (isPublicProfile != null) updates['is_public_profile'] = isPublicProfile;
|
||||
if (heightCm != null) updates['height_cm'] = heightCm;
|
||||
if (weightKg != null) updates['weight_kg'] = weightKg;
|
||||
if (age != null) updates['age'] = age;
|
||||
if (gender != null) updates['gender'] = gender.toDatabaseString();
|
||||
if (heightUnit != null) updates['height_unit'] = heightUnit.code;
|
||||
if (weightUnit != null) updates['weight_unit'] = weightUnit.code;
|
||||
updates['updated_at'] = DateTime.now().toIso8601String();
|
||||
|
||||
await _client
|
||||
await _client!
|
||||
.from('users')
|
||||
.update(updates)
|
||||
.eq('id', userId);
|
||||
}
|
||||
|
||||
Future<User> _createUserProfile(String userId, String username, String email) async {
|
||||
Future<User> _createUserProfile(String userId, String username, String email, {double? heightCm, double? weightKg, int? age, Gender? gender, HeightUnit? heightUnit, WeightUnit? weightUnit}) async {
|
||||
assert(_client != null, 'Client must not be null');
|
||||
final now = DateTime.now().toIso8601String();
|
||||
|
||||
try {
|
||||
// First try with the regular client (might fail due to RLS)
|
||||
final response = await _client.from('users').insert({
|
||||
final response = await _client!.from('users').insert({
|
||||
'id': userId,
|
||||
'username': username,
|
||||
'email': email,
|
||||
'height_cm': heightCm,
|
||||
'weight_kg': weightKg,
|
||||
'age': age,
|
||||
'gender': gender?.toDatabaseString(),
|
||||
'height_unit': heightUnit?.code ?? HeightUnit.metric.code,
|
||||
'weight_unit': weightUnit?.code ?? WeightUnit.metric.code,
|
||||
'created_at': now,
|
||||
'updated_at': now,
|
||||
}).select();
|
||||
@@ -192,6 +239,12 @@ class AuthRepository {
|
||||
'id': userId,
|
||||
'username': username,
|
||||
'email': email,
|
||||
'height_cm': heightCm,
|
||||
'weight_kg': weightKg,
|
||||
'age': age,
|
||||
'gender': gender?.toDatabaseString(),
|
||||
'height_unit': heightUnit?.code ?? HeightUnit.metric.code,
|
||||
'weight_unit': weightUnit?.code ?? WeightUnit.metric.code,
|
||||
'created_at': now,
|
||||
'updated_at': now,
|
||||
}).select();
|
||||
@@ -206,6 +259,12 @@ class AuthRepository {
|
||||
id: userId,
|
||||
username: username,
|
||||
email: email,
|
||||
storedAge: age,
|
||||
heightCm: heightCm,
|
||||
weightKg: weightKg,
|
||||
gender: gender,
|
||||
heightUnit: heightUnit ?? HeightUnit.metric,
|
||||
weightUnit: weightUnit ?? WeightUnit.metric,
|
||||
createdAt: DateTime.parse(now),
|
||||
updatedAt: DateTime.parse(now),
|
||||
);
|
||||
@@ -217,14 +276,21 @@ class AuthRepository {
|
||||
id: userId,
|
||||
username: username,
|
||||
email: email,
|
||||
storedAge: age,
|
||||
heightCm: heightCm,
|
||||
weightKg: weightKg,
|
||||
gender: gender,
|
||||
heightUnit: heightUnit ?? HeightUnit.metric,
|
||||
weightUnit: weightUnit ?? WeightUnit.metric,
|
||||
createdAt: DateTime.parse(now),
|
||||
updatedAt: DateTime.parse(now),
|
||||
);
|
||||
}
|
||||
|
||||
Future<void> _ensureUserProfileExists(String userId, dynamic supabaseUser) async {
|
||||
assert(_client != null, 'Client must not be null');
|
||||
try {
|
||||
final existingProfile = await _client
|
||||
final existingProfile = await _client!
|
||||
.from('users')
|
||||
.select('id')
|
||||
.eq('id', userId)
|
||||
@@ -270,6 +336,10 @@ class AuthRepository {
|
||||
countdownEndDate: data['countdown_end_date'] != null
|
||||
? DateTime.parse(data['countdown_end_date'])
|
||||
: null,
|
||||
gender: data['gender'] != null ? Gender.fromString(data['gender']) : null,
|
||||
storedAge: data['age'] as int?,
|
||||
heightCm: (data['height_cm'] as num?)?.toDouble(),
|
||||
weightKg: (data['weight_kg'] as num?)?.toDouble(),
|
||||
createdAt: DateTime.parse(data['created_at']),
|
||||
updatedAt: DateTime.parse(data['updated_at']),
|
||||
);
|
||||
|
||||
@@ -1,6 +1,7 @@
|
||||
import 'package:supabase_flutter/supabase_flutter.dart' as supabase;
|
||||
import '../models/user_model.dart' as app;
|
||||
import '../../core/errors/failure.dart';
|
||||
import '../../core/utils/unit_conversion_utils.dart';
|
||||
|
||||
class UserRepository {
|
||||
final supabase.SupabaseClient _client;
|
||||
@@ -35,6 +36,12 @@ class UserRepository {
|
||||
String? instagramHandle,
|
||||
String? tiktokHandle,
|
||||
String? websiteUrl,
|
||||
Gender? gender,
|
||||
DateTime? birthDate,
|
||||
double? heightCm,
|
||||
double? weightKg,
|
||||
HeightUnit heightUnit = HeightUnit.metric,
|
||||
WeightUnit weightUnit = WeightUnit.metric,
|
||||
}) async {
|
||||
try {
|
||||
final updates = <String, dynamic>{};
|
||||
@@ -46,6 +53,12 @@ class UserRepository {
|
||||
if (instagramHandle != null) updates['instagram_handle'] = instagramHandle;
|
||||
if (tiktokHandle != null) updates['tiktok_handle'] = tiktokHandle;
|
||||
if (websiteUrl != null) updates['website_url'] = websiteUrl;
|
||||
if (gender != null) updates['gender'] = gender.toDatabaseString();
|
||||
if (birthDate != null) updates['birth_date'] = birthDate.toIso8601String().split('T').first;
|
||||
if (heightCm != null) updates['height_cm'] = heightCm;
|
||||
if (weightKg != null) updates['weight_kg'] = weightKg;
|
||||
updates['height_unit'] = heightUnit.code;
|
||||
updates['weight_unit'] = weightUnit.code;
|
||||
updates['updated_at'] = DateTime.now().toIso8601String();
|
||||
|
||||
final response = await _client
|
||||
|
||||
Reference in New Issue
Block a user