Überlegung

Im letzten Beitrag zum Thema “Eigene Internetseite einfach gemacht, with extra steps” habe ich einen LXC-Container unter Proxmox aufgesetzt, dort Fernzugriff mit tailscale eingerichtet und Quartz, den static site generator for the elegant, installiert. Aber ein Haufen Fachbegriffe macht noch keinen Blog, daher geht es jetzt weiter mit dem Aufsetzen von Quartz, samt Screen (damit es im Hintergrund läuft), dem Synchronisieren der Websitendaten live aus dem Notizprogramm Obsidian heraus und natürlich dem Herzstück, ein Bastelskript um die ganzen Seiten hochzuladen (hot loading style).

Screen für Quartz

Der erste Schritt ist schnell getan, mit sudo apt install screen installiert man das Terminalfensterprogramm Screen und öffnet sich damit ein Fenster der Möglichkeiten. Denn jetzt wird Quartz im Hintergrund lauffähig.

Der Befehl…

npx quartz build --serve --verbose

… startet den Server in seiner geschwätzigen Variante (dank --verbose Parameter):

Der Server läuft dann sogleich unter localhost, ist aber auch unter der festgelegten IP-Adresse im lokalen Netz verfügbar, oder noch netter über die tailscale-IP-Adresse (plus Port 8080):

Das ist natürlich nur bedingt sinnvoll, denn es handelt sich nur um die Beispielseite. Der nächste Schritt ist die aktuelle Quartzkonfiguration in den Container zu verfrachten.

”Sync that thing!”

Da mir Netzwerkshares immer gerne Knoten im Knopf machen, werde ich die Synchronisierung mit dem wunderbaren Programm Syncthing probieren. Ich denke, dass ist hier die beste Variante, auch wenn es in meinem Fall zu einer verschachtelten Synchronisierung kommen wird, der Überordner wird nämlich bereits gesyncthingt und das produziert im besten Fall Redundanzen. Hier der neuronale Senf dazu:

Anmerkung zum Gebrauch und Einbinden von Sprachmodellsprech: Ich bin mir immer noch nicht sicher, wie ich mit den ChatGPT-Ausgaben umgehen soll, inhaltlich versuche ich so transparent wie möglich zu sein und gebe auch an wie ich zu welcher Entscheidung gekommen bin und mit welcher Grundlage. Rein vom Formalen her, weiß ich nicht inwiefern es sinnvoll ist Screenshots der Konversationen einzufügen. Als Text stört es halt dann doch, denn die ChatGPT-Chats sind, genau wie meine Seite, in Markdown formatiert und die Überschriften vom Chatbot werden dann auch als Artikelüberschriften hier gebracht, nicht optimal und braucht auch wieder Nachbearbeitung – daher zurzeit als Screenshots.

Wie auch immer, Syncthing wird’s werden und dazu verwenden wir die Paketquelle von Syncthing.

Zuerst die PGP keys hinzufügen:

sudo mkdir -p /etc/apt/keyrings
sudo curl -L -o /etc/apt/keyrings/syncthing-archive-keyring.gpg https://syncthing.net/release-key.gpg

Dann die stable Version hinzufügen zu den Paketquellen hinzufügen:

echo "deb [signed-by=/etc/apt/keyrings/syncthing-archive-keyring.gpg] https://apt.syncthing.net/ syncthing stable" | sudo tee /etc/apt/sources.list.d/syncthing.list

Und installieren:

sudo apt-get update
sudo apt-get install syncthing

Damit Syncthing auch nach dem Systemstart verfügbar ist (Usernamen anpassen nicht vergessen):

systemctl enable syncthing@quartzboxuser.service
systemctl start syncthing@quartzboxuser.service

Oder mit diesem Befehl:

systemctl --user enable syncthing.service
systemctl --user start syncthing.service

Ich konnte mich jedoch zuerst nicht einloggen, da das WebUI nur im headless Container selbst zu Verfügung stand. Man kann aber auch durch SSH durchlotsen:

ssh -L 8888:localhost:8384 quartzboxuser@192.168.0.90

Das legt den Zugriff auf den Port 8888 (war notwendig da der Standartport bereits belegt war durch die lokale Syncthing-Installation).

In Syncthing kann man dann den Port ändern, und Passwort festlegen nicht vergessen. Das schaut so aus:

Wichtig ist hierbei die IP-Adresse auf 0.0.0.0 plus gewünschten Port zu ändern, sonst kann man nicht von anderen Geräten aus zugreifen.

Syncthing Einrichten

Als nächsten Schritt werden wir Syncthing mit den bestehenden Geräten verbinden. Dazu klickt man im WebUI auf + Add Remote Device

… und fügt die ID des anderen Geräts ein. In meinem Fall ist das Syncthing auf der TrueNAS VM (Update: Wie weiter unten beschrieben, war das nicht zielführend, der Vollständigkeit halber lasse ich diese Schritte aber stehen). In der anderen Syncthing-Instanz muss man das noch bestätigen. Das sieht so aus:

Anschließend fügt man den gewünschten Ordner hinzu. Das ist in meinem Fall fast der gesamte Quartz-Ordner vom Laptop:

Eine Ausnahme stellt der Symlink mit dem content-Ordner dar, der funktioniert sowieso nicht im Container und ist nur im Weg:

Glücklicherweise kann man in Syncthing “Ignore Patterns” eingeben und so soll das aussehen:

Nach einem Rescan All zeigt der Ordner einen reduzierten Zustand, dank der Ignorierliste an:

Sollte also funktionieren. Dasselbe sollte man auch am besten gleich auf der anderen Maschine (also dem dem TrueNAS Share) machen:

Und am Laptop:

Sehr gut, aber jetzt muss ich ja noch den Websiten-Quell-Ordner hinzufügen und teilen:

Hier warnt Syncthing zwar wieder, dass es schon der Überordner geteilt wird, aber wir machen es trotzdem:

Und so schaut das Werkl aus:

Ménage à Sync

Hier zeigen sich dann die Grenzen meines naiven Ansatzes, einfach einmal wild drauf los Ordner miteinander zu synchronisieren, vor allem wenn es sich um schon geteilte Ordner handelt (der Ordner Obsidian wird geteilt und dann noch der Unterordner “martinfellner.at”, also die Notizen der Website).

Das erste Anzeichen eines Problems war dass, die letzten Screenshots beim lokalen Test nicht geladen wurden. Zuerst habe ich gedacht, dass dies am Screen liegen könnte.

Nach nochmaliger Überprüfung liegt es wohl nicht am Screen, sondern, dass die Strecke Laptop/Handy TrueNAS Quartzbox wohl nicht die schnellste in Punkto Synchronisierung ist.

Die nächste Überlegung die Synchronisierung etwas mehr “vermeshen”, sprich auch direkte Synchronisierung von Laptop/Handy auf Quartzbox einrichten, hat dann zu Problemen geführt.

Die zusätzlichen Geräte sind dabei und den Ordner habe ich jetzt in einer Art “Dreieckssyncbeziehung” zusammengeschaltet:

Die Live-Websiten-Aktualisierung hat zuerst viel schneller funktioniert, auch wenn es ein paar Sekunden braucht um Text auf die lokale Test-Website zu hieven und noch länger um auch Screenshots dabei zu haben.

Was die CPU-Auslastung des Containers betrifft, finde ich hält sich das einigermaßen in Grenzen. Der Websiten-Rebuild braucht in etwa eine halbe Sekunde…

… währenddessen die CPU etwa bei 35-45 Prozent liegt:

Das ist vollkommen in Ordnung meiner Meinung nach.

Doch das Problem: Es sind in diesem Testlauf bereits ein paar konfligierende Notizen entstanden. Zuerst habe ich noch gehofft, dass sich das noch “einrenkt”, aber letztendlich hat das Syncthing-Setup eine dringende Überarbeitung benötigt.

Der erste Schritt war den TrueNAS Speicher nicht mehr als eine Relaisstation zu verwenden und den Ordner public gar nicht mehr zu synchronisieren, denn dessen Inhalt ändert sich zu schnell und häufig, sodass es nach kurzer Zeit zu Konflikten kommt:

Und zu diesem Zeitpunkt war es schon zu spät, Syncthing hat die Hoffnung in diese beiden Ordner verloren…

… es waren die wild herumschwirrenden Public-HTML-Dateien die hier den Bahö verursacht haben..

… und auch beim Ordner für die Notizen der Website hat was nicht gepasst:

Das Syncthing-Knäuel entwirren

Es ist mir nichts anderes übrig geblieben, außer die Doppelsynchronisierung überall auszuschalten, denn die hat (ähnlich wie die alten verzögerungsbasierten Speicher) dazu geführt, dass die alten Versionen der Dateien wie Untote wieder zurücksynchronisiert wurden und dann auf einmal fünf Varianten der selben Notiz im Ordner herumgelungert haben.

Dafür muss man auf allen beteiligten Geräten beim Sync-Ordner Obsidian den Unterordner mit den Websitennotizen auf die Ignorierbank setzen, das sieht so aus:

Anschließend habe ich die geteilten Ordner neu erstellen müssen, aber dann hat es endlich funktioniert.

Die wichtigste Lehre daraus war, sich gut zu überlegen wie man synchronisiert. Ich habe zwischenzeitlich eine zirkuläre Synchronisierung zusammengebracht, sprich an einem Ende wurde eine Datei gelöscht, nur um von der anderen Seite gleich wieder zurücksynchronisiert zu werden. Keine gute Sache, aber zumindest habe ich etwas dabei gelernt.

Weitere Schritte

Der nächste Schritt ist das Skript, welches die neue Version auf die Website lädt. Das wird aber erst in einem der kommenden Beitrag geschehen. Und wer sich wundert, was es mit dieser “Not in Dosen” auf sich hat, findet hier einen Beitrag dazu. Die heutige Lektion hat auch einen eigenen “Today I Learned” Beitrag bekommen.