ricostruzione sessione manuale per aggirare gorouter che distrugge il token

This commit is contained in:
2026-06-02 10:20:25 +02:00
parent 808de7b354
commit 27a5bc16bc
2 changed files with 62 additions and 8 deletions

View File

@@ -1,4 +1,5 @@
import 'package:flutter/material.dart'; import 'package:flutter/material.dart';
import 'package:flux/main.dart';
import 'package:supabase_flutter/supabase_flutter.dart'; import 'package:supabase_flutter/supabase_flutter.dart';
class SetPasswordScreen extends StatefulWidget { class SetPasswordScreen extends StatefulWidget {
@@ -16,6 +17,15 @@ class _SetPasswordScreenState extends State<SetPasswordScreen> {
bool _obscurePassword = true; bool _obscurePassword = true;
String? _errorMessage; String? _errorMessage;
// Variabile per abilitare l'inserimento
bool _isSessionReady = false;
@override
void initState() {
super.initState();
_forceSessionRecovery();
}
@override @override
void dispose() { void dispose() {
_passwordController.dispose(); _passwordController.dispose();
@@ -23,17 +33,58 @@ class _SetPasswordScreenState extends State<SetPasswordScreen> {
super.dispose(); super.dispose();
} }
// 🎯 LA VERA MAGIA: RICOSTRUIAMO LA SESSIONE A MANO
Future<void> _forceSessionRecovery() async {
try {
// 1. Prendiamo il frammento dalla cassaforte
final fragment = initialRecoveryFragment ?? Uri.base.fragment;
if (fragment.contains('access_token=')) {
// 2. Dividiamo la stringa in una mappa chiave:valore
final params = Uri.splitQueryString(fragment);
final refreshToken = params['refresh_token'];
if (refreshToken != null) {
// 3. Forziamo Supabase a loggare l'utente col refresh token!
await Supabase.instance.client.auth.setSession(refreshToken);
if (mounted) {
setState(() {
_isSessionReady = true;
_errorMessage = null;
});
}
return;
}
}
// Fallback: se Supabase ce l'aveva già fatta miracolosamente
if (Supabase.instance.client.auth.currentSession != null) {
setState(() => _isSessionReady = true);
}
} catch (e) {
print("Errore ripristino manuale sessione: $e");
}
}
Future<void> _submitNewPassword() async { Future<void> _submitNewPassword() async {
if (!_formKey.currentState!.validate()) return; if (!_formKey.currentState!.validate()) return;
if (!_isSessionReady) {
setState(() {
_errorMessage =
"Sincronizzazione di sicurezza fallita. Il link potrebbe essere scaduto.";
});
return;
}
setState(() { setState(() {
_isLoading = true; _isLoading = true;
_errorMessage = null; _errorMessage = null;
}); });
try { try {
// 🥷 LA MOFFA DEL NINJA: Aggiorniamo la password dell'utente corrente // Ora questo updateUser troverà la sessione viva e vegeta!
// che si è loggato in automatico grazie al token nell'URL
await Supabase.instance.client.auth.updateUser( await Supabase.instance.client.auth.updateUser(
UserAttributes(password: _passwordController.text.trim()), UserAttributes(password: _passwordController.text.trim()),
); );
@@ -47,11 +98,6 @@ class _SetPasswordScreenState extends State<SetPasswordScreen> {
backgroundColor: Colors.green, backgroundColor: Colors.green,
), ),
); );
// Non serve forzare i redirect qui!
// Il SessionCubit nel costruttore ha un listener su 'onAuthStateChange'.
// Sentirà che l'utente ora è perfettamente valido, richiamerà 'initializeSession()'
// e lo scaricherà automaticamente nella pagina di Onboarding corretta.
} }
} on AuthException catch (e) { } on AuthException catch (e) {
setState(() { setState(() {

View File

@@ -1,3 +1,4 @@
import 'dart:developer';
import 'dart:io'; import 'dart:io';
import 'package:firebase_core/firebase_core.dart'; import 'package:firebase_core/firebase_core.dart';
@@ -48,9 +49,16 @@ import 'package:flux/features/settings/ui/settings.dart';
import 'package:flutter_web_plugins/url_strategy.dart'; import 'package:flutter_web_plugins/url_strategy.dart';
import 'package:url_launcher/url_launcher.dart'; import 'package:url_launcher/url_launcher.dart';
String? initialRecoveryFragment;
void main() async { void main() async {
WidgetsFlutterBinding.ensureInitialized(); WidgetsFlutterBinding.ensureInitialized();
print("URL VERO ALL'AVVIO: ${Uri.base.toString()}"); final initialUri = Uri.base;
if (initialUri.fragment.contains('access_token=')) {
initialRecoveryFragment = initialUri.fragment;
log(
"Ninja attivato: Token catturato in cassaforte! $initialRecoveryFragment",
);
}
await dotenv.load(fileName: ".env"); await dotenv.load(fileName: ".env");
// Inizializza le dipendenze PRIMA di lanciare l'app // Inizializza le dipendenze PRIMA di lanciare l'app