"""Wann gilt ein TMDB-Treffer als sicher genug? — ohne Netz geprueft. ## Der Befund des Commanders (28.08.2026) > „Was ist mit dem Cover auf Windows Rippy? In der Web Version haben wir ein > cover." Es gab keins, weil es gar keinen Treffer gab. Der Grund war nicht Windows, sondern eine Bedingung im Pre-Scan: if movie.get("title", "").lower() == kandidat.lower(): An seiner Disc gemessen: 'Evangelion 2.22' 1 Treffer Evangelion: 2.0 You Can (Not) Advance 'Evangelion' 20 Treffer irgendein Evangelion Der EINZIGE Treffer auf den vollen Disc-Titel war der richtige Film, mit Poster — und wurde verworfen, weil der Titel nicht woertlich gleich war. ## Warum die Trefferzahl und nicht die Aehnlichkeit „Evangelion 2.22" gegen „Evangelion: 2.0 You Can (Not) Advance" ergibt 0,51 Aehnlichkeit — das steht als Messung schon laenger im Code und faellt durch jedes sinnvolle Gatter. Die SPEZIFITAET der Anfrage sagt mehr: Wer auf den vollen Disc-Titel eine Handvoll Treffer bekommt, hat gefragt wie jemand, der weiss was er sucht. Wer 20 bekommt, hat geraten. Diese Tests spritzen die Clients ein — kein Netz, keine Schluessel, keine Disc. """ import pytest class FakeTMDB: """Ein TMDB, das genau die gemessenen Antworten liefert.""" def __init__(self, treffer_je_suche, details=None): self.treffer = treffer_je_suche self.details = details or {} self.gefragt = [] def search_movie(self, begriff): self.gefragt.append(begriff) return self.treffer.get(begriff, []) def search_tv(self, begriff): return [] def get_movie_details(self, kennung): return self.details.get(kennung) def get_tv_details(self, kennung): return None def find_by_imdb(self, kennung): return None class StummerClient: def lookup(self, *a, **k): return None DETAILS_2_0 = { 22843: { "title": "Evangelion: 2.0 You Can (Not) Advance", "release_date": "2009-06-27", "overview": "Der Pilotin Mari gelingt es …", "poster_path": "/hpChtHPoXGTfhphnHGXj2kGXZeH.jpg", "backdrop_path": "/pzsVGcufDdBLmvagKyLFKaeA4O5.jpg", "runtime": 112, "genres": [{"name": "Animation"}], } } def _prescan(tmdb): from prescan.prescan import PreScan p = PreScan() p.tmdb = tmdb p.jikan = StummerClient() p.omdb = StummerClient() return p def _toc(titel): return {"title": titel, "year": None, "tracks": [], "duration": 0, "disc_type": "Blu-ray", "fingerprint": "TEST|1"} def test_der_einzige_treffer_auf_den_vollen_titel_gilt(): """DER Fall des Commanders. Vorher: kein Treffer, kein Cover, 30 %.""" tmdb = FakeTMDB( {"Evangelion 2.22": [{"id": 22843, "title": "Evangelion: 2.0 You Can (Not) Advance"}]}, DETAILS_2_0) ergebnis = _prescan(tmdb)._scan_video("/dev/x", _toc("Evangelion 2.22")) assert ergebnis.confidence == 0.8 assert ergebnis.title == "Evangelion: 2.0 You Can (Not) Advance" assert ergebnis.year == 2009 assert ergebnis.metadata["poster_path"], "ohne poster_path gibt es kein Cover" assert ergebnis.metadata["source"] == "tmdb" def test_woertlich_gleicher_titel_bleibt_sicherer(): """Ein exakter Treffer muss weiterhin hoeher stehen als ein spezifischer.""" tmdb = FakeTMDB( {"Logan": [{"id": 22843, "title": "Logan"}]}, {22843: dict(DETAILS_2_0[22843], title="Logan")}) ergebnis = _prescan(tmdb)._scan_video("/dev/x", _toc("Logan")) assert ergebnis.confidence == 0.95 def test_zwanzig_treffer_gelten_NICHT_als_sicher(): """Wer 20 Treffer bekommt, hat geraten — das darf kein 80-Prozent-Fund werden. Es bleibt beim ehrlichen Vorschlag.""" viele = [{"id": 1000 + i, "title": "Evangelion %d" % i} for i in range(20)] tmdb = FakeTMDB({"Evangelion": viele}, {1000: dict(DETAILS_2_0[22843], title="Irgendein Evangelion")}) ergebnis = _prescan(tmdb)._scan_video("/dev/x", _toc("Evangelion")) assert ergebnis.confidence == 0.6, "20 Treffer sind kein sicherer Fund" def test_treffer_auf_eine_GEKUERZTE_variante_gilt_nicht_als_sicher(): """Die Spezifitaet zaehlt nur, wenn der VOLLE Disc-Titel gefragt wurde. Sonst wuerde „Der Herr der Ringe: Die zwei Tuerme" ueber die Kuerzung „Der Herr" zu einem 80-Prozent-Fund fuer irgendetwas. """ tmdb = FakeTMDB( {"Evangelion": [{"id": 22843, "title": "Neon Genesis Evangelion"}]}, {22843: dict(DETAILS_2_0[22843], title="Neon Genesis Evangelion")}) ergebnis = _prescan(tmdb)._scan_video("/dev/x", _toc("Evangelion 2.22")) # Der volle Titel lieferte nichts, die Kuerzung schon -> nur Vorschlag. assert ergebnis.confidence == 0.6 def test_ohne_jeden_treffer_bleibt_es_ehrlich_bei_dreissig_prozent(): ergebnis = _prescan(FakeTMDB({}))._scan_video("/dev/x", _toc("Gibt Es Nicht")) assert ergebnis.confidence == 0.3 assert ergebnis.metadata["type"] == "unknown" @pytest.mark.parametrize("anzahl,erwartet", [(1, 0.8), (3, 0.8), (4, 0.6)]) def test_die_schwelle_liegt_bei_drei(anzahl, erwartet): """Drei ist grosszuegig genug fuer Neuauflagen und Regie-Fassungen desselben Films, aber eng genug, um Raten auszuschliessen.""" treffer = [{"id": 22843 + i, "title": "Film %d" % i} for i in range(anzahl)] details = {22843: dict(DETAILS_2_0[22843], title="Film 0")} tmdb = FakeTMDB({"Ein Sehr Genauer Titel": treffer}, details) ergebnis = _prescan(tmdb)._scan_video("/dev/x", _toc("Ein Sehr Genauer Titel")) assert ergebnis.confidence == erwartet