fix: Gast-Zugang-Sperre, veralteter Token, Doppel-Tap, Hinweistext (Branch-Review)
Behebt die Findings aus dem abschließenden Gesamt-Branch-Review für feature/youtube-gast-zugang, alle in einem Rutsch: - KRITISCH: Gast-Modus war eine Einbahnstraße — einmal "Als Gast fortfahren" getippt, war _AnmeldeDialog (einziger Baka-Login-Einstieg, auch für Melo-Cloud-Sync) dauerhaft unerreichbar. Neu: GastZugang.verwerfen() plus "Anmelden"-Knopf neben der Gast-Statuszeile in beiden Screens. - WICHTIG: zugriffOk prüfte den rohen gast.hatToken statt istGastModus — ein alter Gast-Token konnte den Auto-Login-Rückfallweg für Server-User verdecken. istGastModus wird jetzt vor zugriffOk berechnet und dort verwendet. - WICHTIG: CHANGELOG ergänzt — der Server-Endpunkt POST /api/guest-token fehlt noch (separates Vorhaben). - Doppel-Tap-Schutz für den Gast-Button in beiden Screens. - Widersprüchlicher Hinweistext im YT-Suche-Tab (verlangte Baka-Login direkt über dem Gast-Button) korrigiert. - Zwei Gast-Tests in youtube_search_screen_test.dart bekommen jetzt echtes gast:-Wiring in YtSearchService/YtDownloadService. - 2 neue Regressionstests fürs Anmelden-Escape-Hatch. Getestet: volle Suite grün (602 Tests, 1 skipped, 0 failed), flutter analyze ohne Befund. Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01CcDiyJdVRqh1TtJk5JiabX
This commit is contained in:
co-authored by
Claude Sonnet 5
parent
b32f3198f8
commit
d20f01adee
@@ -38,6 +38,9 @@ class _YoutubeSearchScreenState extends State<YoutubeSearchScreen> {
|
||||
/// Fehlertext, falls das Holen des Gast-Tokens scheitert.
|
||||
String? _gastFehler;
|
||||
|
||||
/// Verhindert Mehrfach-Anfragen bei schnellem Doppel-Antippen.
|
||||
bool _gastLaeuft = false;
|
||||
|
||||
@override
|
||||
void initState() {
|
||||
super.initState();
|
||||
@@ -56,11 +59,18 @@ class _YoutubeSearchScreenState extends State<YoutubeSearchScreen> {
|
||||
}
|
||||
|
||||
Future<void> _alsGastFortfahren() async {
|
||||
if (_gastLaeuft) return;
|
||||
final gast = context.read<GastZugang>();
|
||||
setState(() => _gastFehler = null);
|
||||
setState(() {
|
||||
_gastFehler = null;
|
||||
_gastLaeuft = true;
|
||||
});
|
||||
final fehler = await gast.holeToken();
|
||||
if (!mounted) return;
|
||||
if (fehler != null) setState(() => _gastFehler = fehler);
|
||||
setState(() {
|
||||
_gastLaeuft = false;
|
||||
if (fehler != null) _gastFehler = fehler;
|
||||
});
|
||||
}
|
||||
|
||||
@override
|
||||
@@ -81,10 +91,10 @@ class _YoutubeSearchScreenState extends State<YoutubeSearchScreen> {
|
||||
final auth = context.watch<BakaAuth>();
|
||||
final gast = context.watch<GastZugang>();
|
||||
final suche = context.watch<YtSearchService>();
|
||||
final istGastModus = !_serverUser && !auth.istAngemeldet && gast.hatToken;
|
||||
final zugriffOk = auth.istAngemeldet ||
|
||||
(_serverUser && !_autoLoginFehlgeschlagen) ||
|
||||
gast.hatToken;
|
||||
final istGastModus = !_serverUser && !auth.istAngemeldet && gast.hatToken;
|
||||
istGastModus;
|
||||
|
||||
return SafeArea(
|
||||
child: Column(
|
||||
@@ -116,8 +126,12 @@ class _YoutubeSearchScreenState extends State<YoutubeSearchScreen> {
|
||||
Padding(
|
||||
padding: const EdgeInsets.symmetric(horizontal: 16, vertical: 4),
|
||||
child: Text(
|
||||
'Die Suche läuft über den Baka-Server. Dafür brauchst du '
|
||||
'deine Baka-Anmeldung (siehe Download-Tab).',
|
||||
_serverUser
|
||||
? 'Die Suche läuft über den Baka-Server. Dafür brauchst '
|
||||
'du deine Baka-Anmeldung (siehe Download-Tab).'
|
||||
: 'Die Suche läuft über den Baka-Server. Melde dich mit '
|
||||
'deinem Baka-Konto an (siehe Download-Tab) oder '
|
||||
'nutze sie eingeschränkt als Gast.',
|
||||
style: const TextStyle(color: MeloTheme.text2, fontSize: 13),
|
||||
),
|
||||
),
|
||||
@@ -131,7 +145,7 @@ class _YoutubeSearchScreenState extends State<YoutubeSearchScreen> {
|
||||
icon: const Icon(Icons.person_outline),
|
||||
label: const Text('Als Gast fortfahren (5 Downloads/Tag)',
|
||||
style: TextStyle(fontSize: 16)),
|
||||
onPressed: _alsGastFortfahren,
|
||||
onPressed: _gastLaeuft ? null : _alsGastFortfahren,
|
||||
),
|
||||
),
|
||||
),
|
||||
@@ -148,11 +162,21 @@ class _YoutubeSearchScreenState extends State<YoutubeSearchScreen> {
|
||||
if (istGastModus)
|
||||
Padding(
|
||||
padding: const EdgeInsets.symmetric(horizontal: 16, vertical: 4),
|
||||
child: Text(
|
||||
gast.verbleibend == null
|
||||
? 'Als Gast unterwegs (5 Downloads/Tag)'
|
||||
: 'Als Gast unterwegs — noch ${gast.verbleibend} von 5 heute',
|
||||
style: const TextStyle(color: MeloTheme.text2, fontSize: 13),
|
||||
child: Row(
|
||||
children: [
|
||||
Expanded(
|
||||
child: Text(
|
||||
gast.verbleibend == null
|
||||
? 'Als Gast unterwegs (5 Downloads/Tag)'
|
||||
: 'Als Gast unterwegs — noch ${gast.verbleibend} von 5 heute',
|
||||
style: const TextStyle(color: MeloTheme.text2, fontSize: 13),
|
||||
),
|
||||
),
|
||||
TextButton(
|
||||
onPressed: gast.verwerfen,
|
||||
child: const Text('Anmelden'),
|
||||
),
|
||||
],
|
||||
),
|
||||
),
|
||||
if (suche.laeuft) const LinearProgressIndicator(),
|
||||
|
||||
Reference in New Issue
Block a user