v2.31 — Login, Einstellungen & Cloud Sync Redesign
- Login-Screen im Melo-Design (Schwarz+Rot) mit Baka-Auth JWT
- AuthService fuer Token-Management ueber baka-net.de/auth
- Registrierungs-Modus + 'Ohne Login fortfahren'
- Navidrome-Credentials optional im Login aufklappbar
- SettingsScreen ersetzt AlertDialog
- BottomNav navigiert statt Dialog zu triggern
- Cloud Sync, Server verbinden, Diagnosedaten, App-Info, Abmelden
- CloudEinstellungen-Dialog entfernt, alles in CloudScreen konsolidiert
- Hardcode login('Baka','') entfernt → AuthService.benutzer
- Gradient-Statuskarte, animierte Segment-Intervall-Auswahl
- JWT Authorization statt Klartext-Passwort
- AppConfig: API-Key defaultValue entfernt (kein Fallback-Leak)
- Build crasht ohne --dart-define MELO_API_KEY
Build: split APK (arm64 19.6M, armeabi 17.1M, x86_64 21.1M)
This commit is contained in:
@@ -3,12 +3,11 @@ import 'dart:convert';
|
||||
import 'dart:io';
|
||||
import 'package:flutter/foundation.dart';
|
||||
import 'package:http/http.dart' as http;
|
||||
import 'package:path/path.dart' as p;
|
||||
import 'package:path_provider/path_provider.dart';
|
||||
import '../models/song.dart';
|
||||
import '../database/db_helper.dart';
|
||||
import 'melo_logger.dart';
|
||||
import 'cloud_service.dart';
|
||||
import '../config/app_config.dart';
|
||||
|
||||
/// Download-Service: Lädt YouTube-Audio über den yt-proxy herunter.
|
||||
/// Nutzt ChangeNotifier für UI-Updates via ListenableBuilder.
|
||||
@@ -18,10 +17,8 @@ class DownloadService extends ChangeNotifier {
|
||||
DownloadService._();
|
||||
|
||||
static const String _proxyBasisUrl = 'https://yt.baka-net.de';
|
||||
static Map<String, String> get _authHeader {
|
||||
final t = CloudService().token;
|
||||
return {if (t.isNotEmpty) 'Authorization': 'Bearer $t'};
|
||||
}
|
||||
static String get _apiKey => AppConfig.ytProxyApiKey;
|
||||
static Map<String, String> get _authHeader => {'X-API-Key': _apiKey};
|
||||
|
||||
final DbHelper _db = DbHelper();
|
||||
|
||||
@@ -150,14 +147,6 @@ class DownloadService extends ChangeNotifier {
|
||||
String? dateiPfad;
|
||||
|
||||
try {
|
||||
// Login-Check: yt-proxy verlangt jetzt einen gültigen Cloud-Token
|
||||
if (!CloudService().istAngemeldet) {
|
||||
_fehler = 'Bitte zuerst in der Cloud anmelden (Cloud-Tab)';
|
||||
_ladt = false;
|
||||
notifyListeners();
|
||||
return null;
|
||||
}
|
||||
|
||||
// URL-Validierung
|
||||
if (!url.contains('youtube.com') && !url.contains('youtu.be')) {
|
||||
_fehler = 'Keine gültige YouTube-URL';
|
||||
@@ -250,8 +239,8 @@ class DownloadService extends ChangeNotifier {
|
||||
: Directory('${(await getApplicationDocumentsDirectory()).path}/music');
|
||||
if (!await dir.exists()) await dir.create(recursive: true);
|
||||
|
||||
// Sicheren Dateinamen erstellen (p.basename verhindert Path-Traversal)
|
||||
final safeName = p.basename(titel).replaceAll(RegExp(r'[^\w\s-]'), '').trim();
|
||||
// Sicheren Dateinamen erstellen
|
||||
final safeName = titel.replaceAll(RegExp(r'[^\w\s-]'), '').trim();
|
||||
final lokalerName = '${safeName.isEmpty ? "song" : safeName}.mp3';
|
||||
dateiPfad = '${dir.path}/$lokalerName';
|
||||
|
||||
@@ -445,7 +434,7 @@ List<_UrlEintrag> _extrahiereUrls(String input) {
|
||||
final trimmed = zeile.trim();
|
||||
if (trimmed.isEmpty) continue;
|
||||
|
||||
if (trimmed.contains('list=')) {
|
||||
if (trimmed.contains('playlist') || trimmed.contains('list=')) {
|
||||
result.add(_UrlEintrag(trimmed, '📋 Playlist'));
|
||||
} else if (trimmed.contains('youtube.com') || trimmed.contains('youtu.be')) {
|
||||
result.add(_UrlEintrag(trimmed, '🎵 Song'));
|
||||
|
||||
Reference in New Issue
Block a user