fix: Ghostscript-Angebot log nicht mehr, fehlende Voraussetzungen dokumentiert (v0.7.1)
Befunde aus dem ersten echten Erstinstallations-Test auf frischen Debian-12- und Debian-13-Containern. Der Weg selbst hat getragen (Basis-Install, Instanz-Anlage, zweite Instanz, Update mit Rauchtest, Rollback) — diese Stellen haben gelogen oder gefehlt: - Das Ghostscript-Backports-Angebot auf Debian 12 war ein garantierter Leerlauf, der "aktualisiert ✓" meldete: bookworm-backports enthaelt gar kein ghostscript (am Paketindex verifiziert). Die Routine sucht jetzt den echten Kandidaten, vergleicht vorher/nachher und raeumt eine nur zur Probe angelegte Quelle wieder weg. - Derselbe untaugliche Rat stand in der Preflight-Meldung, der pdfa_level-Warnung, config.example.toml und vier Doku-Dateien — ueberall ersetzt durch die echten Optionen. - Mehrzeilige Log-Hinweise waren durch "echo -e" zerrissen und nicht kopierbar; log_* nutzt jetzt printf mit %s. - pip-freeze.txt landete beim Rollback als /pip-freeze.txt im Wurzelverzeichnis, liegt jetzt unter opt/pdf-ocr-hotfolder/. - git und sudo fehlen auf dem Proxmox-Debian-Template; "sudo ./install.sh" scheitert dort. Beide Wege dokumentiert, git als Voraussetzung ergaenzt, HTTPS-Clone als Normalfall. - Rollback: systemctl start kann kein Glob. journald-Reparatur: Instanzen danach neu starten, sonst bleibt das Journal leer. 254 Tests gruen. Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
This commit is contained in:
+134
-18
@@ -14,10 +14,46 @@ Verwandte Dokumente: [README](../README.md) · [Update](UPDATE.md) · [Debian-Ma
|
||||
| Python | 3.11+ (wegen `tomllib` aus der stdlib); kommt aus der Distribution |
|
||||
| Arbeitsspeicher | **mindestens 2 GB** für den produktiven Betrieb — siehe [Systemanforderungen](#systemanforderungen) |
|
||||
| Dateisystem | **ext4, xfs oder zfs**; `incoming/` **lokal**, kein CIFS/NFS — siehe [Dateisystem](#dateisystem-ext4-xfs-oder-zfs) |
|
||||
| Rechte | `root` (`sudo ./install.sh`) |
|
||||
| Rechte | `root` — als root direkt `./install.sh`, sonst `sudo ./install.sh` (s. [root oder sudo](#root-oder-sudo)) |
|
||||
| `git` | zum Klonen des Repos — **nicht** vorinstalliert, s. [Pakete, die fehlen können](#pakete-die-auf-einem-frischen-system-fehlen-können) |
|
||||
| Netz | apt-Zugriff für die System-Pakete, PyPI-Zugriff für die venv |
|
||||
| Repo | muss dauerhaft liegen bleiben — `update.sh` kopiert daraus (s. [UPDATE.md](UPDATE.md)) |
|
||||
|
||||
### Pakete, die auf einem frischen System fehlen können
|
||||
|
||||
Auf dem **Proxmox-Debian-Standard-Template** (12 **und** 13) fehlen zwei Dinge,
|
||||
die jede Anleitung stillschweigend voraussetzt — am frisch angelegten Container
|
||||
verifiziert:
|
||||
|
||||
| Fehlt | Folge | Abhilfe |
|
||||
|-------|-------|---------|
|
||||
| **`git`** | `git clone …` schlägt mit `git: command not found` fehl — und ohne Clone gibt es kein Repo, aus dem `install.sh` läuft | `apt install git` |
|
||||
| **`sudo`** | der überall dokumentierte Aufruf `sudo ./install.sh` schlägt mit `sudo: command not found` fehl | entweder `apt install sudo`, oder **einfach als `root` ohne `sudo` arbeiten** |
|
||||
|
||||
```bash
|
||||
apt update
|
||||
apt install -y git # zwingend
|
||||
apt install -y sudo # nur, wenn nicht als root gearbeitet wird
|
||||
```
|
||||
|
||||
### root oder sudo
|
||||
|
||||
Installer und Updater brauchen **root-Rechte** — *wie* man dahin kommt, ist
|
||||
ihnen gleich. Beide Wege sind gleichwertig:
|
||||
|
||||
```bash
|
||||
# (a) man ist bereits root — im frischen Container der Normalfall
|
||||
./install.sh
|
||||
|
||||
# (b) man arbeitet als normaler Benutzer und hat sudo
|
||||
sudo ./install.sh
|
||||
```
|
||||
|
||||
In dieser Doku steht durchgehend die Variante mit `sudo`, weil die meisten
|
||||
Systeme es haben. **Wer als `root` arbeitet, lässt das `sudo` bei jedem Befehl
|
||||
einfach weg** — das gilt für alle Kommandos in diesem und den übrigen
|
||||
Dokumenten. Ein fehlendes `sudo` ist kein Grund, es nachzuinstallieren.
|
||||
|
||||
Die System-Pakete installiert der Installer selbst. Die Liste steht als
|
||||
einzige Quelle in `lib/common.sh` (Funktion `pdf_ocr_apt_packages()`, zwischen
|
||||
den Marken `# --- BEGIN apt-packages` / `# --- END apt-packages`); `install.sh`
|
||||
@@ -174,14 +210,51 @@ System mehr RAM bekommt.
|
||||
## Installation
|
||||
|
||||
```bash
|
||||
git clone gitea@gitea.sonith.de:sonith_ug/pdf-ocr-hotfolder.git
|
||||
apt update && apt install -y git # fehlt im Proxmox-Standard-Template
|
||||
git clone https://gitea.sonith.de/sonith_ug/pdf-ocr-hotfolder.git
|
||||
cd pdf-ocr-hotfolder
|
||||
sudo ./install.sh
|
||||
sudo ./install.sh # als root: ./install.sh
|
||||
```
|
||||
|
||||
#### Welche Clone-URL?
|
||||
|
||||
| Variante | URL | Wann |
|
||||
|----------|-----|------|
|
||||
| **HTTPS** (Normalfall) | `https://gitea.sonith.de/sonith_ug/pdf-ocr-hotfolder.git` | braucht **keine** Credentials und funktioniert auf einem frischen Server sofort — der Weg, der im Installations-Test benutzt wurde |
|
||||
| **SSH** | `gitea@gitea.sonith.de:sonith_ug/pdf-ocr-hotfolder.git` | nur sinnvoll, wenn auf dem Zielsystem ein **Deploy-Key** hinterlegt ist (z.B. weil auch gepusht werden soll) |
|
||||
|
||||
> ⚠️ **Der SSH-User bei `gitea.sonith.de` heißt `gitea`, nicht `git`.**
|
||||
> `git@gitea.sonith.de:…` ist der Default anderer Git-Hoster und hier **falsch**
|
||||
> — der Clone scheitert dann mit `Permission denied (publickey)`.
|
||||
|
||||
`install.sh` ist **Installer und Instanz-Manager in einem** und idempotent —
|
||||
jeder weitere Aufruf überspringt, was schon steht.
|
||||
|
||||
### So sieht ein Erstlauf aus
|
||||
|
||||
Verifiziert auf frischen Debian-12- und Debian-13-Containern. Die Reihenfolge
|
||||
der Abfragen:
|
||||
|
||||
1. **LXC-Drop-in** — nur im Container: „systemd-Hardening-Drop-in für LXC
|
||||
installieren?" → **ja**, sonst scheitert der Start mit `226/NAMESPACE`
|
||||
([warum](#lxccontainer-error-226namespace)).
|
||||
2. **Ghostscript-Hinweis** — nur auf Debian 12 mit betroffener Version. Kein
|
||||
Abbruch: mit dem Default `pdfa_level = ""` ist die Installation
|
||||
unproblematisch ([Hintergrund](#ghostscript-bug-auf-debian-12)).
|
||||
3. **journald-Warnung** — nur, wenn `systemd-journald` nicht läuft. Typisch für
|
||||
Debian 13 in LXC auf Proxmox. Hier **abbrechen**, journald reparieren und neu
|
||||
anfangen — sonst hat der Dienst kein Log
|
||||
([Abhilfe](#debian-13-in-lxc-auf-proxmox-journald-scheitert-243credentials)).
|
||||
4. Dann die **fünf Fragen pro Instanz**: Instanz-Name → Basis-Pfad →
|
||||
Service-User → OCR-Sprachen → Original-Behandlung (Archiv/löschen/liegen
|
||||
lassen). Im Detail: [Die Abfragen pro Instanz](#die-abfragen-pro-instanz).
|
||||
5. Zum Schluss `Weitere Instanz anlegen? [j/N]:` — hier entsteht die zweite
|
||||
Instanz, ohne dass irgendetwas am Basis-Install noch einmal angefasst wird.
|
||||
|
||||
Danach läuft `pdf-ocr-hotfolder@<instanz>.service`. Gegenprobe: eine PDF nach
|
||||
`incoming/` kopieren und `journalctl -u pdf-ocr-hotfolder@<instanz> -f`
|
||||
mitlesen.
|
||||
|
||||
### Basis-Install vs. Instanz-Anlage
|
||||
|
||||
Der Installer unterscheidet zwei Ebenen:
|
||||
@@ -424,21 +497,40 @@ ocrmypdf-Version:
|
||||
|
||||
### Abhilfe
|
||||
|
||||
**Weg 1 — Ghostscript anheben** (empfohlen). Der Installer erkennt betroffene
|
||||
Versionen und bietet auf Debian 12 bookworm-backports an. Manuell:
|
||||
> 🚫 **Es gibt auf Debian 12 kein neueres Ghostscript.** `bookworm-backports`
|
||||
> führt **kein** Ghostscript-Paket — am Paketindex geprüft
|
||||
> (`bookworm-backports/main/binary-amd64`: 2606 Pakete, `ghostscript` nicht
|
||||
> darunter, `systemd`/`golang-go`/`linux-image-amd64` schon). Ältere Fassungen
|
||||
> dieser Anleitung und frühere Versionen des Installers haben genau das
|
||||
> empfohlen — der Rat konnte nie funktionieren.
|
||||
>
|
||||
> **Planungsaussage:** Wer auf Debian 12 **PDF/A in der schnellen Betriebsart**
|
||||
> (`skip_text = true`) braucht, hat dort **keinen Weg** — weder über Backports
|
||||
> noch sonst. Es bleibt: PDF/A aufgeben, `skip_text` aufgeben (Weg 2, kostet
|
||||
> Laufzeit) oder Debian 13. **Das gehört vor die Installation**, nicht in den
|
||||
> Moment, in dem der Preflight abbricht.
|
||||
|
||||
```bash
|
||||
echo 'deb http://deb.debian.org/debian bookworm-backports main' | \
|
||||
sudo tee /etc/apt/sources.list.d/bookworm-backports.list
|
||||
sudo apt update && sudo apt install -t bookworm-backports ghostscript
|
||||
```
|
||||
|
||||
Ab Ghostscript 10.02.1 ist alles in Ordnung; PDF/A kann dann eingeschaltet
|
||||
werden.
|
||||
**Weg 1 — `pdfa_level = ""` lassen** (Default, empfohlen). Ohne PDF/A-Ausgabe
|
||||
fasst ocrmypdf ≥ 17 Ghostscript gar nicht an; die betroffene Version ist dann
|
||||
völlig unproblematisch. Der Preis ist PDF/A — das Ergebnis ist eine normale
|
||||
durchsuchbare PDF. Für die übliche Anwendung (Scan wird durchsuchbar) reicht
|
||||
das.
|
||||
|
||||
**Weg 2 — `skip_text = false` setzen.** Dann wird vorhandener Text neu erkannt
|
||||
statt übersprungen, und die Bedingung greift nicht mehr. Das kostet Laufzeit bei
|
||||
PDFs, die bereits eine Textebene haben.
|
||||
statt übersprungen, und die Bedingung greift nicht mehr — PDF/A ist damit auch
|
||||
auf Debian 12 möglich. Das kostet Laufzeit bei PDFs, die bereits eine Textebene
|
||||
haben, und OCRt sie ein zweites Mal.
|
||||
|
||||
**Weg 3 — Distribution mit neuerem Ghostscript.** **Debian 13 liefert
|
||||
Ghostscript 10.05.1** und ist vom Bug nicht betroffen; dort ist PDF/A zusammen
|
||||
mit `skip_text = true` ohne Einschränkung nutzbar. Wer PDF/A verbindlich
|
||||
braucht, installiert von vornherein auf Debian 13.
|
||||
|
||||
| Ich brauche … | Debian 12 | Debian 13 |
|
||||
|---------------|-----------|-----------|
|
||||
| durchsuchbare PDF, kein PDF/A | ✅ Default (`pdfa_level = ""`) | ✅ |
|
||||
| PDF/A **und** `skip_text = true` | ❌ kein Weg | ✅ |
|
||||
| PDF/A mit `skip_text = false` | ✅ (langsamer) | ✅ |
|
||||
|
||||
---
|
||||
|
||||
@@ -762,6 +854,13 @@ Ist `systemd-journald.service` selbst `failed` (beobachtet mit
|
||||
`status=243/CREDENTIALS`), gibt es schlicht kein journal, in das geschrieben
|
||||
werden könnte.
|
||||
|
||||
Läuft journald dagegen `active (running)` und das Journal der Instanz ist
|
||||
trotzdem leer (`-- No entries --`), ist meist journald **erst nach dem Dienst**
|
||||
wieder hochgekommen: die Startmeldungen hatten in der Zwischenzeit kein Ziel und
|
||||
sind weg. `sudo systemctl restart 'pdf-ocr-hotfolder@*'` schreibt sie neu —
|
||||
siehe die Warnung im
|
||||
[nächsten Abschnitt](#debian-13-in-lxc-auf-proxmox-journald-scheitert-243credentials).
|
||||
|
||||
**Einordnung.** Der Dienst loggt seit v0.4.1 **ausschließlich** nach journald —
|
||||
es gibt bewusst kein eigenes Logfile und kein Logverzeichnis. Ein kaputtes
|
||||
journald ist damit ein blinder Fleck: jede Fehlersuche läuft ins Leere, und der
|
||||
@@ -843,9 +942,26 @@ sudo systemctl restart systemd-journald
|
||||
sudo journalctl --flush
|
||||
```
|
||||
|
||||
Danach `systemctl status systemd-journald` (muss `active (running)` sein) und
|
||||
`journalctl -u pdf-ocr-hotfolder@<instanz>` gegenprüfen. Für die anderen
|
||||
betroffenen Units gilt dasselbe Muster mit deren Unit-Namen.
|
||||
Danach `systemctl status systemd-journald` gegenprüfen — muss `active
|
||||
(running)` sein. Für die anderen betroffenen Units gilt dasselbe Muster mit
|
||||
deren Unit-Namen.
|
||||
|
||||
> ⚠️ **Jetzt die Instanzen einmal neu starten — sonst steht man vor einem
|
||||
> leeren Journal.** Wurde der Dienst gestartet, **während** journald tot war,
|
||||
> sind seine Startmeldungen unwiederbringlich weg: sie hatten kein Ziel. Nach
|
||||
> der Reparatur meldet `journalctl -u pdf-ocr-hotfolder@<instanz>` dann
|
||||
> `-- No entries --` — und das sieht exakt so aus wie ein gescheiterter
|
||||
> Reparaturversuch, obwohl journald längst wieder läuft. Der Neustart schreibt
|
||||
> die Startmeldungen neu ins frische Journal:
|
||||
>
|
||||
> ```bash
|
||||
> sudo systemctl restart 'pdf-ocr-hotfolder@*'
|
||||
> journalctl -u pdf-ocr-hotfolder@<instanz> -n 20
|
||||
> ```
|
||||
>
|
||||
> Erst wenn hier die Startmeldungen stehen, ist die Reparatur belegt. (`restart`
|
||||
> kann das Glob, weil die Units geladen sind — `start` nicht, siehe
|
||||
> [UPDATE.md](UPDATE.md#rollback).)
|
||||
|
||||
> **Der saubere Weg liegt host-seitig.** Das Drop-in kuriert das Symptom im
|
||||
> Container. Richtig behoben wird es auf dem Proxmox-Host: Update von
|
||||
|
||||
Reference in New Issue
Block a user