Handbuch auf MkDocs-Basis, mit Bildschirmfotos aus dem Programm
26 Kapitel in vier Teilen, in der Reihenfolge, in der man sie braucht: erst sichern, dann Dateien holen, dann ganze Maschinen wiederherstellen, dahinter der Nachschlagteil. Gebaut wird mit MkDocs + Material. Bewusst ohne Netzabhaengigkeiten: keine Schriften vom CDN (font: false), Volltextsuche mit deutschem Stemming liegt neben den Seiten. Im Notfall steht vielleicht das halbe Netz - dann nuetzt eine Doku im Internet nichts. handbuch/bauen.sh baut handbuch/site/ handbuch/bauen.sh ansehen Vorschau auf 127.0.0.1:8000 install.sh nimmt das gebaute Handbuch mit nach /usr/share/doc/pvesnap/handbuch/ - falls es vorliegt. Auf dem Host selbst wird nichts gebaut, mkdocs gehoert nicht auf einen Hypervisor. Die 28 Bildschirmfotos sind nicht abfotografiert, sondern erzeugt: Der echte Programmcode laeuft in einem Pseudo-Terminal gegen einen erfundenen Proxmox-Host (Attrappen fuer pvesh, perl und rbd), pyte baut den Bildschirm nach, heraus faellt ein SVG. Damit stimmen sie garantiert mit dem Programm ueberein, sind reproduzierbar und enthalten keine echten Daten. Die Werkstatt dafuer liegt unter handbuch/werkstatt/ samt LIESMICH.md. Nebenbei: die Schlussmeldung von install.sh warb noch mit --exchange, das mit dem eingebauten Austauschlaufwerk weggefallen ist. Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
This commit is contained in:
co-authored by
Claude Opus 5
parent
c484596702
commit
59e7224297
@@ -0,0 +1,139 @@
|
||||
# Die Bildschirmfoto-Werkstatt
|
||||
|
||||
Die Bilder im Handbuch sind keine abfotografierten Terminals, sondern werden
|
||||
erzeugt — aus dem **echten** Programmcode, gegen einen erfundenen Proxmox-Host.
|
||||
|
||||
```bash
|
||||
./aufnehmen.sh # alle Bilder neu
|
||||
./aufnehmen.sh explorer # nur die, deren Name "explorer" enthält
|
||||
```
|
||||
|
||||
Ergebnis: `handbuch/docs/bilder/*.svg`
|
||||
|
||||
Das hat drei Gründe:
|
||||
|
||||
* **Sie stimmen.** Es läuft wirklich `pvesnap/recovery_ui.py`, nicht eine
|
||||
Nachbildung. Ändert sich die Tastenleiste, ändert sich das Bild.
|
||||
* **Sie sind reproduzierbar.** Derselbe Aufruf ergibt dasselbe Bild — gleiche
|
||||
Daten, gleiche Uhrzeiten, gleiche Snapshot-Namen.
|
||||
* **Kein echter Host wird angefasst.** Weder Daten noch Namen aus einer echten
|
||||
Umgebung landen im Handbuch.
|
||||
|
||||
---
|
||||
|
||||
## Wie es funktioniert
|
||||
|
||||
```
|
||||
scenes.py Liste aller Aufnahmen: Name, Szene, Tastenfolge, Titel
|
||||
└─ probe.py startet eine Szene in einem Pseudo-Terminal
|
||||
└─ stage.sh hängt die Kulisse an die richtigen Pfade (Namensraum)
|
||||
└─ run.py biegt die Pfade im Programmcode um und ruft die Oberfläche auf
|
||||
└─ pvesnap/… der echte Programmcode
|
||||
└─ shot.py baut den Bildschirm nach und schreibt ihn als SVG
|
||||
```
|
||||
|
||||
### `demo.py` — die Kulisse
|
||||
|
||||
Baut unter `werkstatt/demo/` ein erfundenes Rechenzentrum auf: zwei Nodes, zehn
|
||||
Gäste, ein paar hundert Snapshots, zwei laufende Wiederherstellungen, drei
|
||||
Austauschlaufwerke und einen Dateibaum für den Explorer.
|
||||
|
||||
Ein **fester Zeitpunkt** (`NOW`) sorgt dafür, dass zwei Aufnahmen derselben
|
||||
Liste gleich aussehen — sonst würde die Beschreibung im Handbuch nicht mehr
|
||||
zum Bild passen.
|
||||
|
||||
### `bin/pvesh`, `bin/perl`, `bin/rbd` — die Attrappen
|
||||
|
||||
pvesnap spricht mit Proxmox über genau drei Programme. Alle drei liegen hier als
|
||||
kleine Python-Skripte, die aus `demo/state.json` antworten. Sie stehen im `PATH`
|
||||
vor den echten.
|
||||
|
||||
Nichts davon verändert etwas — die schreibenden Aufrufe geben brav eine UPID
|
||||
zurück und tun sonst nichts.
|
||||
|
||||
### `run.py` — die Pfade umbiegen
|
||||
|
||||
Setzt vor dem Start die Konstanten um, die sonst auf einen echten Host zeigen:
|
||||
|
||||
```python
|
||||
recovery.REGISTRY = demo/lib/recovery.json
|
||||
transfer.INDEX = demo/lib/transfer/index.json
|
||||
transfer.CONF_ROOT = demo/pve/nodes
|
||||
```
|
||||
|
||||
Der Programmcode selbst wird nicht angefasst. Die Bilder zeigen also wirklich
|
||||
das, was auf dem Host auch zu sehen ist.
|
||||
|
||||
### `stage.sh` — die Pfade, die im Bild stehen
|
||||
|
||||
Der Explorer zeigt Pfade an. Im Handbuch sollen das die Pfade eines echten
|
||||
Hosts sein (`/run/pvesnap/mnt/…`, `/root`, `/etc/pvesnap.conf`) und nicht die
|
||||
Arbeitsverzeichnisse dieser Werkstatt.
|
||||
|
||||
Deshalb läuft jede Aufnahme in einem eigenen **Mount-Namensraum**
|
||||
(`unshare -r -m`): Dort dürfen wir uns die Pfade hinbiegen, ohne am System
|
||||
etwas zu verändern. `/etc` bekommt eine Overlay-Schicht, damit die
|
||||
Konfiguration dort liegt, wo sie hingehört.
|
||||
|
||||
### `shot.py` — der Bildschirmnachbau
|
||||
|
||||
Startet das Programm in einem Pseudo-Terminal fester Größe (118 × 32), spielt
|
||||
Tastendrücke ein, lässt [pyte](https://pypi.org/project/pyte/) den Bildschirm
|
||||
nachbilden und schreibt das Ergebnis als SVG.
|
||||
|
||||
Zwei Feinheiten, die Zeit gekostet haben:
|
||||
|
||||
**`textLength` auf jedem Textstück.** Das SVG bettet keine Schrift ein — es
|
||||
soll ja klein bleiben und offline funktionieren. Damit das Zeichenraster
|
||||
trotzdem in jedem Browser sitzt, wird jede Zeichenkette fest vermessen.
|
||||
|
||||
**`NCURSES_NO_UTF8_ACS=1`.** ncurses zeichnet Rahmen sonst über den
|
||||
Ersatzzeichensatz (`ESC ( 0`). pyte ignoriert das im UTF-8-Betrieb, und aus den
|
||||
Linien würden Buchstaben (`lqqqk` statt `┌───┐`). Mit der Variablen liefert
|
||||
ncurses echte Unicode-Rahmenzeichen.
|
||||
|
||||
---
|
||||
|
||||
## Eine Szene nachsehen
|
||||
|
||||
Zum Ausprobieren, ohne ein Bild zu schreiben — gibt den Bildschirm als Text aus:
|
||||
|
||||
```bash
|
||||
../.venv/bin/python probe.py recovery
|
||||
../.venv/bin/python probe.py recovery enter p
|
||||
COLS=140 ROWS=40 ../.venv/bin/python probe.py explorer ab ab enter
|
||||
```
|
||||
|
||||
Tastennamen: `ab auf links rechts enter tab esc space f2 f3 f5 f7 f9`,
|
||||
alles andere wird als Zeichen geschickt.
|
||||
|
||||
Verfügbare Szenen stehen in `run.py` unter `SZENEN`.
|
||||
|
||||
---
|
||||
|
||||
## Eine Aufnahme hinzufügen
|
||||
|
||||
In `scenes.py` eine Zeile ergänzen:
|
||||
|
||||
```python
|
||||
("recovery-neuerkram", "recovery", ["enter", "p"],
|
||||
"root@pve1 — pvesnap-recovery"),
|
||||
```
|
||||
|
||||
Fünftes Feld optional: Wartezeit in Sekunden, für Bildschirme, hinter denen
|
||||
noch etwas arbeitet (sonst hält der Nachbau den letzten Stand fest, während im
|
||||
Hintergrund noch ein Proxmox-Task läuft).
|
||||
|
||||
Braucht es dafür eine neue Szene, kommt sie in `run.py` dazu.
|
||||
|
||||
---
|
||||
|
||||
## Wenn etwas nicht klappt
|
||||
|
||||
| Symptom | Ursache |
|
||||
|---|---|
|
||||
| Bild ist leer oder zeigt einen Traceback | `scenes.py` meldet das selbst — mit `probe.py` nachsehen |
|
||||
| Rahmen bestehen aus `lqqqk` | `NCURSES_NO_UTF8_ACS=1` fehlt in `probe.umgebung()` |
|
||||
| Pfade zeigen ins Scratchpad | `unshare -r` ging nicht; `aufnehmen.sh` prüft das vorher |
|
||||
| Pfeiltasten bewegen nichts | Es muss `\x1bOB` sein, nicht `\x1b[B` — curses schaltet auf den Anwendungsmodus |
|
||||
| Ein Bildschirm hängt bei „bitte warten" | Eine Antwort der Attrappe fehlt; mit `log_level=DEBUG` sieht man den Aufruf |
|
||||
Reference in New Issue
Block a user