fix(windows): Vollstaendiger Rundgang durch die Docker-Reste
Ampel / ampel (push) Successful in 1m20s

Commander: „Bro, du musst alles was rippy jetzt im code hat für Windows
Bauen! Jeden pfad, alles wo die tools drauf zugreifen. Diese Rippy version
MUSS 100% Windows Kompatibel sein. Prüfe bitte den kompletten Quellcode nach
Docker Resten."

Systematisch gesucht statt Fundstelle fuer Fundstelle: feste POSIX-Pfade,
Linux-Programme, POSIX-eigene Aufrufe, `shutil.which`, `posixpath` auf echten
Pfaden, Container-Texte. Sechs echte Fehler dabei.

## 1. `/dev/{name}` in drei Endpunkten — der schwerste

Das UI ruft `/devices/{id}/eject`, `/scan-tracks` und `/tracks` mit der
Kennung aus der Geraeteliste auf, unter Windows also `G`. Gebaut wurde daraus
`/dev/G` — steht in keiner Laufwerksliste. **Auswerfen und „Disc scannen"
antworteten unter Windows IMMER mit 404**, ohne dass irgendwo stand, warum.

Hin- und Rueckweg gehoeren zusammen: Beide Treiber haben jetzt `kennung()`
und `pfad_zu_kennung()`. Wer die Kennung vergibt, loest sie auch auf.

## 2. `os.path.isdir("/app")` — zum zweiten Mal

Nach `caps.py` (heute frueh) auch in `ablauf.py`: Der eigenstaendige
Windows-Rippy hielt sich fuer einen FREMDEN Worker und haette sich selbst
vorgeworfen, Container-Pfade nicht zu erreichen — auf einer Maschine ohne
Container. Die Entscheidung ist jetzt einspritzbar; vorher hing der Test
daran, ob es einen Ordner `/app` gibt.

## 3. `shutil.which` in `schluessel.py`

Ausgerechnet im Modul, das es NUR unter Windows gibt: Es suchte makemkvcon im
PATH, wo unter Windows nie ein Programm aus „Programme" steht. Die
Schluessel-Automatik fuer 4K-UHD lief damit nie an.

## 4. `posixpath.join` auf echten Pfaden

`rohdaten.py` baute `C:\Roh/datei.mkv` — gemischte Trenner, die im UI falsch
aussehen und jeden Vergleich brechen.

## 5. Container-Pfad in einer Nutzermeldung

„Roh-Datei bleibt in /app/temp erhalten" nennt jetzt den echten Ordner. Wer
die Datei retten will, sucht sonst am falschen Ort.

## 6. Container-Pfade als UI-Vorbelegung

Rip-Dialog und `useBetrieb` starteten mit `/app/media`, bis die Antwort da
war. Leer ist ehrlicher: Es behauptet nichts.

## Und HandBrakes „Code 0"

Code 0 heisst ERFOLG. Rippy meldete trotzdem „fehlgeschlagen", weil die Datei
nicht am erwarteten Ort lag: **HandBrake bestimmt den Container aus dem
PRESET, nicht aus der Endung** — ein MP4-Preset schreibt `.mp4` neben das
verlangte `.mkv`. Jetzt erzwingt `--format` den Container passend zur Endung
(an HandBrake 1.11.2 gegengeprueft), und falls doch etwas daneben liegt, wird
es gefunden statt weggeworfen.

## Der Waechter

`test_keine_container_reste.py` prueft mechanisch, dass im Windows-Weg kein
Container-Pfad ohne Begruendung steht. Die Ausnahmen stehen namentlich mit
Grund da (Linux-Zweige, benannte Rueckfaelle) — und ein zweiter Test wirft
jede Ausnahme raus, die niemand mehr braucht.

Ueber den Tokenizer, nicht ueber „faengt mit Anfuehrungszeichen an": Der
erste Anlauf blieb prompt an seinem eigenen `r\"\"\"`-Docstring haengen.

887 Tests gruen, ruff sauber.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
This commit is contained in:
Hitonabi
2026-08-29 16:14:10 +02:00
co-authored by Claude Opus 5
parent 1a529f4e75
commit 1b84ec2a45
11 changed files with 384 additions and 23 deletions
+21 -3
View File
@@ -867,7 +867,8 @@ def erster_vorhandener_ordner(pfad: str, isdir=None, dirname=None) -> str:
def _erreichbarkeit_pruefen(raw_container: str, raw_lokal: str,
final_container: str, final_lokal: str) -> str:
final_container: str, final_lokal: str,
fremd=None) -> str:
"""Kann DIESER Worker Quelle und Ziel überhaupt sehen? Klartext oder "".
Befund 25.07.2026 am Job 95afdc89, live: Das gezielte Routing an den
@@ -889,7 +890,20 @@ def _erreichbarkeit_pruefen(raw_container: str, raw_lokal: str,
Quelle — sonst scheitert es erst beim Schreiben, nach Stunden Rechenzeit.
"""
mapping = os.getenv("RIPPY_PATH_MAP", "")
fremder_worker = not os.path.isdir("/app")
# ⚠️ Hier stand `not os.path.isdir("/app")` (Befund 29.08.2026) — dasselbe
# Muster wie in `caps.py`. Im Image stimmt es; auf einem Windows-PC gibt
# es `/app` nicht, und der eigenstaendige Rippy hielt sich fuer einen
# FREMDEN Worker. Er haette sich dann selbst vorgeworfen, die
# Container-Pfade nicht zu erreichen — auf einer Maschine ohne Container.
#
# `fremd` ist einspritzbar, damit BEIDE Faelle ueberall pruefbar sind:
# Vorher haing der Test daran, ob es einen Ordner `/app` gibt, und war
# damit an den laufenden Rechner gebunden.
if fremd is None:
from caps import _extern
fremd = _extern() == "ja"
fremder_worker = fremd
for zweck, container, lokal in (
("die Quelle (Rohdaten)", raw_container, raw_lokal),
@@ -1067,7 +1081,11 @@ def komprimieren(job_id: str, raw_dir: str, final_dir: str):
"status": "error",
"error": (
f"Kompression fehlgeschlagen bei {os.path.basename(quelle)}: "
f"{hb.get('error')} — Roh-Datei bleibt in /app/temp erhalten"
# Den ECHTEN Ordner nennen, nicht „/app/temp" (Befund
# 29.08.2026). Auf Windows gibt es den nicht, und wer die
# Roh-Datei retten will, sucht sonst am falschen Ort.
f"{hb.get('error')} — Roh-Datei bleibt unter "
f"{os.path.dirname(quelle)} erhalten"
),
}
_job_abschliessen(job_id, ergebnis)