313 Zeilen
11 KiB
Python
313 Zeilen
11 KiB
Python
"""
|
|
Basis-Controller für Plattform-spezifische Funktionalität.
|
|
"""
|
|
|
|
import logging
|
|
from PyQt5.QtCore import QObject
|
|
from typing import Dict, Any, Optional, Tuple
|
|
import random
|
|
|
|
from views.tabs.generator_tab_factory import GeneratorTabFactory
|
|
from views.tabs.accounts_tab import AccountsTab
|
|
# SettingsTab import entfernt - wird nicht mehr verwendet
|
|
|
|
class BasePlatformController(QObject):
|
|
"""Basis-Controller-Klasse für Plattformspezifische Logik."""
|
|
|
|
# Konstanten auf Klassen-Ebene
|
|
MOBILE_PROBABILITY = {
|
|
'instagram': 0.7,
|
|
'tiktok': 0.9,
|
|
'facebook': 0.5
|
|
}
|
|
|
|
MIN_AGE = 13
|
|
DEFAULT_EMAIL_DOMAIN = "z5m7q9dk3ah2v1plx6ju.com"
|
|
|
|
def __init__(self, platform_name, db_manager, proxy_rotator, email_handler, language_manager=None):
|
|
super().__init__()
|
|
self.platform_name = platform_name
|
|
self.logger = logging.getLogger(f"{platform_name.lower()}_controller")
|
|
|
|
# Modelle
|
|
self.db_manager = db_manager
|
|
self.proxy_rotator = proxy_rotator
|
|
self.email_handler = email_handler
|
|
self.language_manager = language_manager
|
|
|
|
# Tabs
|
|
self._generator_tab = None
|
|
self._accounts_tab = None
|
|
|
|
# Worker Thread
|
|
self.worker_thread = None
|
|
|
|
# Optional: Session Controller (Clean Architecture)
|
|
self.session_controller = None
|
|
|
|
# Optional: Forge Dialog
|
|
self.forge_dialog = None
|
|
|
|
# Plattformspezifische Initialisierungen
|
|
self.init_platform()
|
|
|
|
def set_tabs(self, generator_tab, accounts_tab):
|
|
"""
|
|
Setzt die Tab-Referenzen.
|
|
|
|
Args:
|
|
generator_tab: Generator-Tab
|
|
accounts_tab: Accounts-Tab
|
|
"""
|
|
self._generator_tab = generator_tab
|
|
self._accounts_tab = accounts_tab
|
|
|
|
def init_platform(self):
|
|
"""
|
|
Initialisiert plattformspezifische Komponenten.
|
|
Diese Methode sollte von Unterklassen überschrieben werden.
|
|
"""
|
|
pass
|
|
|
|
def get_generator_tab(self):
|
|
"""Gibt den Generator-Tab zurück oder erstellt ihn bei Bedarf."""
|
|
if not self._generator_tab:
|
|
self._generator_tab = self.create_generator_tab()
|
|
return self._generator_tab
|
|
|
|
def get_accounts_tab(self):
|
|
"""Gibt den Accounts-Tab zurück oder erstellt ihn bei Bedarf."""
|
|
if not self._accounts_tab:
|
|
self._accounts_tab = self.create_accounts_tab()
|
|
return self._accounts_tab
|
|
|
|
# get_settings_tab Methode entfernt - Settings-Tab wird nicht mehr verwendet
|
|
|
|
|
|
def create_generator_tab(self):
|
|
"""
|
|
Erstellt den Generator-Tab mit der Factory.
|
|
Unterklassen können diese Methode überschreiben für spezielle Anforderungen.
|
|
|
|
Returns:
|
|
QWidget: Plattform-spezifischer oder generischer Generator-Tab
|
|
"""
|
|
return GeneratorTabFactory.create_tab(self.platform_name, self.language_manager)
|
|
|
|
def create_accounts_tab(self):
|
|
"""
|
|
Erstellt den Accounts-Tab.
|
|
Diese Methode sollte von Unterklassen überschrieben werden.
|
|
"""
|
|
return AccountsTab(self.platform_name, self.db_manager, self.language_manager)
|
|
|
|
# create_settings_tab Methode entfernt - Settings-Tab wird nicht mehr verwendet
|
|
|
|
|
|
def start_account_creation(self, params):
|
|
"""
|
|
Startet die Account-Erstellung.
|
|
Diese Methode sollte von Unterklassen überschrieben werden.
|
|
|
|
Args:
|
|
params: Parameter für die Account-Erstellung
|
|
"""
|
|
# Feature 5: Process Guard - Prüfe ob Prozess starten darf
|
|
from utils.process_guard import get_guard
|
|
guard = get_guard()
|
|
|
|
can_start, error_msg = guard.can_start("Account-Erstellung", self.platform_name)
|
|
if not can_start:
|
|
# Zeige Fehlermeldung
|
|
generator_tab = self.get_generator_tab()
|
|
generator_tab.show_error(error_msg)
|
|
return
|
|
|
|
# Guard Lock setzen
|
|
guard.start("Account-Erstellung", self.platform_name)
|
|
|
|
self.logger.info(f"Account-Erstellung für {self.platform_name} gestartet")
|
|
# In Unterklassen implementieren
|
|
|
|
def validate_inputs(self, inputs):
|
|
"""
|
|
Validiert die Eingaben für die Account-Erstellung.
|
|
|
|
Args:
|
|
inputs: Eingaben für die Account-Erstellung
|
|
|
|
Returns:
|
|
(bool, str): (Ist gültig, Fehlermeldung falls nicht gültig)
|
|
"""
|
|
# Basis-Validierungen
|
|
if not inputs.get("full_name"):
|
|
return False, "Bitte geben Sie einen vollständigen Namen ein."
|
|
|
|
# Alter prüfen
|
|
age_text = inputs.get("age_text", "")
|
|
if not age_text:
|
|
return False, "Bitte geben Sie ein Alter ein."
|
|
|
|
# Alter muss eine Zahl sein
|
|
try:
|
|
age = int(age_text)
|
|
inputs["age"] = age # Füge das konvertierte Alter zu den Parametern hinzu
|
|
except ValueError:
|
|
return False, "Das Alter muss eine ganze Zahl sein."
|
|
|
|
# Alter-Bereich prüfen
|
|
if age < 13 or age > 99:
|
|
return False, "Das Alter muss zwischen 13 und 99 liegen."
|
|
|
|
# Telefonnummer prüfen, falls erforderlich
|
|
if inputs.get("registration_method") == "phone" and not inputs.get("phone_number"):
|
|
return False, "Telefonnummer erforderlich für Registrierung via Telefon."
|
|
|
|
return True, ""
|
|
|
|
def _determine_profile_type(self) -> str:
|
|
"""Bestimmt den Profil-Typ basierend auf Platform-Wahrscheinlichkeiten"""
|
|
mobile_prob = self.MOBILE_PROBABILITY.get(self.platform_name.lower(), 0.5)
|
|
return 'mobile' if random.random() < mobile_prob else 'desktop'
|
|
|
|
def _generate_fingerprint_for_platform(self) -> Optional[Any]:
|
|
"""Generiert Fingerprint mit Fehlerbehandlung"""
|
|
try:
|
|
if not hasattr(self, 'session_controller') or not self.session_controller:
|
|
return None
|
|
|
|
profile_type = self._determine_profile_type()
|
|
|
|
# Prüfe ob fingerprint_service existiert
|
|
if hasattr(self.session_controller, 'fingerprint_service'):
|
|
return self.session_controller.fingerprint_service.generate_fingerprint(
|
|
profile_type=profile_type,
|
|
platform=self.platform_name.lower()
|
|
)
|
|
except Exception as e:
|
|
self.logger.warning(f"Fingerprint-Generierung fehlgeschlagen: {e}")
|
|
|
|
return None
|
|
|
|
def _setup_ui_for_creation(self):
|
|
"""Bereitet die UI für die Account-Erstellung vor"""
|
|
generator_tab = self.get_generator_tab()
|
|
generator_tab.set_running(True)
|
|
generator_tab.clear_log()
|
|
generator_tab.set_progress(0)
|
|
|
|
def _connect_worker_signals(self):
|
|
"""Verbindet Worker-Signals mit UI-Elementen"""
|
|
if not self.worker_thread:
|
|
return
|
|
|
|
generator_tab = self.get_generator_tab()
|
|
|
|
# Forge-Dialog Signals
|
|
if self.forge_dialog:
|
|
self.worker_thread.update_signal.connect(self.forge_dialog.set_status)
|
|
self.worker_thread.log_signal.connect(self.forge_dialog.add_log)
|
|
self.worker_thread.progress_signal.connect(self.forge_dialog.set_progress)
|
|
|
|
# Generator-Tab Signals (Backup)
|
|
self.worker_thread.log_signal.connect(lambda msg: generator_tab.add_log(msg))
|
|
self.worker_thread.progress_signal.connect(lambda value: generator_tab.set_progress(value))
|
|
|
|
# Error und Finished Handling
|
|
self.worker_thread.error_signal.connect(self._handle_error)
|
|
self.worker_thread.finished_signal.connect(self._handle_finished)
|
|
|
|
def _show_forge_dialog(self):
|
|
"""Zeigt den Forge-Animation Dialog"""
|
|
try:
|
|
from views.widgets.forge_animation_widget import ForgeAnimationDialog
|
|
|
|
generator_tab = self.get_generator_tab()
|
|
parent_widget = generator_tab.window()
|
|
|
|
self.forge_dialog = ForgeAnimationDialog(parent_widget)
|
|
self.forge_dialog.cancel_clicked.connect(self.stop_account_creation)
|
|
self.forge_dialog.closed.connect(self.stop_account_creation)
|
|
|
|
self.forge_dialog.start_animation()
|
|
self.forge_dialog.show()
|
|
except Exception as e:
|
|
self.logger.warning(f"Konnte Forge-Dialog nicht anzeigen: {e}")
|
|
|
|
def _handle_error(self, error_msg: str):
|
|
"""Gemeinsame Fehlerbehandlung"""
|
|
# Forge-Dialog schließen
|
|
if hasattr(self, 'forge_dialog') and self.forge_dialog:
|
|
self.forge_dialog.close()
|
|
self.forge_dialog = None
|
|
|
|
# Fehler anzeigen
|
|
generator_tab = self.get_generator_tab()
|
|
generator_tab.show_error(error_msg)
|
|
generator_tab.set_running(False)
|
|
|
|
def _handle_finished(self, result: dict):
|
|
"""Gemeinsame Behandlung bei Abschluss"""
|
|
# Forge-Dialog schließen
|
|
if hasattr(self, 'forge_dialog') and self.forge_dialog:
|
|
self.forge_dialog.close()
|
|
self.forge_dialog = None
|
|
|
|
# Normale Verarbeitung
|
|
self.handle_account_created(result)
|
|
|
|
def stop_account_creation(self):
|
|
"""Stoppt die Account-Erstellung"""
|
|
if self.worker_thread and self.worker_thread.isRunning():
|
|
self.worker_thread.stop()
|
|
generator_tab = self.get_generator_tab()
|
|
generator_tab.add_log(f"{self.platform_name}-Account-Erstellung wurde abgebrochen")
|
|
generator_tab.set_running(False)
|
|
generator_tab.set_progress(0)
|
|
|
|
# Forge-Dialog schließen falls vorhanden
|
|
if hasattr(self, 'forge_dialog') and self.forge_dialog:
|
|
self.forge_dialog.close()
|
|
self.forge_dialog = None
|
|
|
|
def handle_account_created(self, result):
|
|
"""
|
|
Verarbeitet erfolgreich erstellte Accounts.
|
|
Sollte von Unterklassen überschrieben werden für spezifische Logik.
|
|
"""
|
|
generator_tab = self.get_generator_tab()
|
|
generator_tab.set_running(False)
|
|
|
|
# Standard-Implementierung - kann von Unterklassen erweitert werden
|
|
self.logger.info(f"Account erfolgreich erstellt für {self.platform_name}")
|
|
|
|
def stop_account_creation(self):
|
|
"""
|
|
Stoppt die Account-Erstellung (Default-Implementierung).
|
|
|
|
Diese Methode kann von Unterklassen überschrieben werden für spezielle Anforderungen.
|
|
Sie stellt sicher dass:
|
|
1. Der Process Guard freigegeben wird
|
|
2. Der Worker-Thread gestoppt wird
|
|
3. Die UI zurückgesetzt wird
|
|
4. Dialoge geschlossen werden
|
|
"""
|
|
# Guard-Freigabe (wichtig: VOR Worker-Stop)
|
|
from utils.process_guard import get_guard
|
|
guard = get_guard()
|
|
if guard.is_locked():
|
|
guard.end(success=False)
|
|
self.logger.info("Guard freigegeben bei Stop (BaseController)")
|
|
|
|
# Worker stoppen falls vorhanden
|
|
if self.worker_thread and self.worker_thread.isRunning():
|
|
self.worker_thread.stop()
|
|
generator_tab = self.get_generator_tab()
|
|
generator_tab.add_log(f"{self.platform_name}-Account-Erstellung wurde abgebrochen")
|
|
generator_tab.set_running(False)
|
|
generator_tab.set_progress(0)
|
|
|
|
# Forge-Dialog schließen falls vorhanden
|
|
if hasattr(self, 'forge_dialog') and self.forge_dialog:
|
|
self.forge_dialog.close()
|
|
self.forge_dialog = None |