Ein paar irrelevante Tutorials

Paperless NGX

Paperless NGX ist eine einfach zu bedienende Lösung zur Verwaltung von Dokumenten. Es kann PDF-Dateien, Office-Dokumente, Bilddateien und Mails verarbeiten.

Installation

Vorbereitung Docker

Zunächst wird eine Docker-Laufzeitumgebung benötigt. Ubuntu bringt eine Docker-Umgebung mit. Allerdings funktioniert diese mitgelieferte Umgebung oftmals und hier konkret mit den Paperless-Paketen nicht. Darum ist eine Installation von Docker auf der Grundlage der Docker-Dokumentation zuverlässiger (s. https://docs.docker.com/engine/install/ubuntu/). Das habe ich in dem Beitrag über Docker beschrieben.

Installation Paperless NGX mittel Docker-Compose-File

Wenn ich mich auf der SSH-Konsole des Servers angemeldet habe, dann bewege ich mich im Homeshare des angegebenen Users (also z.B. /home/andreas/). Hier erstelle ich einen Ordner paperless-nxg und wechsele dort hinein mit

mkdir paperless-nxg && cd paperless-ngx

Für Paperless NGX muss hier nun nur eine Datei docker-compose.yml angelegt werden mit

nano docker-compose.yml

mit folgendem Inhalt:

services:
broker:
image: docker.io/library/redis:8.4
restart: unless-stopped
volumes:
- redisdata:/data

db:
image: postgres:alpine
restart: unless-stopped
volumes:
- ./db:/var/lib/postgresql/data
environment:
POSTGRES_DB: paperless
POSTGRES_USER: paperless
POSTGRES_PASSWORD: paperless

webserver:
image: ghcr.io/paperless-ngx/paperless-ngx:2.19.1
restart: unless-stopped
depends_on:
- db
- broker
- gotenberg
- tika
ports:
- "8000:8000"
volumes:
- ./data:/usr/src/paperless/data
- ./media:/usr/src/paperless/media
- ./export:/usr/src/paperless/export
- ./consume:/usr/src/paperless/consume
environment:
PAPERLESS_URL: {Domain oder leer lassen}
PAPERLESS_TIME_ZONE: 'Europe/Berlin'
PAPERLESS_OCR_LANGUAGE: deu+eng
PAPERLESS_SECRET_KEY: 'echt komplexes, geheimes passwort wie z.B. 123456'
PAPERLESS_REDIS: redis://broker:6379
PAPERLESS_DBHOST: db
PAPERLESS_DBNAME: paperless
PAPERLESS_DBUSER: paperless
PAPERLESS_DBPASS: paperless
PAPERLESS_TIKA_ENABLED: 1
PAPERLESS_TIKA_GOTENBERG_ENDPOINT: http://gotenberg:3000
PAPERLESS_TIKA_ENDPOINT: http://tika:9998

gotenberg:
image: docker.io/gotenberg/gotenberg:8.24
restart: unless-stopped

# Beim Konvertieren von .eml-Files mit Gotenberg soll
# externer content wie z.B: tracking pixels oder javascript
# nicht mit konvertiert werden
command:
- "gotenberg"
- "--chromium-disable-javascript=true"
- "--chromium-allow-list=file:///tmp/.*"

tika:
image: docker.io/apache/tika:latest
restart: unless-stopped

volumes:
redisdata:

Hier wird zunächst Redis, die In-Memory-Komponente zur Beschleunigung der Datenbankzugriffe, definiert. Redis bekommt hier ein Volume data unter dem Namen redisdata im aktuellen Pfad zugewiesen. Dann wird die Datenbank postgres in der Version alpine mit dem persistenten Volume data definiert. Die Volume-Definition ist wichtig, damit nach einem Neustart des Servers bzw. Containers die Daten noch vorhanden sind. Die Credentials für die Datenbank werden in den Environment-Variablen für die Services db und webserver (natürlich identisch) definiert. Dann werden die Services tika und gotenberg definiert, damit Paperless-NGX Office-Formate und eMails verarbeiten kann. Hier ist im Service eine kleine Besonderheit eingebaut: Es werden chromium-Features genutzt, um Java-Script, Tracking-Pixel und andere unerwünschte externe Links auszuschließen. Die Restart-Policy "unless-stopped" sorgt dafür, dass die Container nach einem Reboot des Servers wieder gestartet werden, es sei denn, sie wurden vorher ausdrücklich gestoppt.

Paperless-NGX kann ich nun starten mit

docker compose up -d

Das System startet, was eine Weile dauert. Den Erfolg kann ich zwischendurch mit

docker ps

oder ausführlicher mit

docker logs paperless-nxg-webserver-1

ansehen. Wenn keine Fehler aufgetreten sind, dann sollte Paperless NGX starten und unter der eingetragenen Domain, so sie denn erreichbar ist oder unter der IP-Adresse des Servers mit der Portnummer 8000 angesprochen werden können.

Freigabe des Consume-Ordners für den Scanner

Damit direkt in das DMS gescannt werden kann, muss der Scanner Dateien im Consume-Ordner ablegen können. Wenn dazu das SMB-Protokoll genutzt werden soll, dann ist auf dem DMS-Server ein Samba-Server zu installieren und eine entsprechende Freigabe einzurichen. Die Freigabe wird in der Datei "/etc/samba/smb.conf" eingetragen:

   [paperless]
comment = Paperless Eingangsordner
path = /home/andreas/paperless-ngx/paperless-ngx/consume
browsable = yes
read only = no
guest ok = no

Nach jeder Änderung der smb.conf ist der Samba-Server neu zu starten:

sudo systemctl daemon-reload && sudo systemctl restart smbd

Nun ist der Consume-Ordner als Freigabe im Netz verfügbar. Verarbeitbare Dateien (Office-Dateien, Mails, Textdateien, Grafiken und natürlich PDF), die in diesen Ordner geschrieben werden, werden von Paperless-NGX verarbeitet.

Datensicherung

Mein DMS-Server, ein LXC auf einem Proxmox-Host, wird jede Nacht auf den Proxmox-Backup-Server gesichert und kann komplett zurück gesichert werden und es kann auch ein Filerestore vorgenommen werden. Da für den PBS eine Retentionregel nach dem Grandfather-Father-Son-Prinzip eingerichtet ist, kann jederzeit auf die Stände der letzten Tage und Wochen zurück gesichert werden. Zu dieser Retention-Regel habe ich in meinem Youtube-Video (s. hier: Video) einiges erklärt. 

Zur Offsite-Sicherung wird jeden Tag um 11:30 Uhr ein Export der Daten angestoßen und diese exportierten Daten dann um 12:00 Uhr verschlüsselt und inkrementell per duplicati auf einen entfernten Server übertragen. Ich habe duplicati in meiner Umgebung auf einem anderen Server installiert als den Paperless-NGX-Server. Darum muss ich dafür sorgen, dass dubplicati auf die Sicherungsdaten zugreifen kann (s.u.).

Das Exportverzeichnis ist ja mittels der oben aufgeführten docker-compose.yml persistent eingerichtet. Hier hinein werden per cronjob und exporter die Export-Dateien abgelegt werden. Dazu richte ich den Cronjob mit

sudo nano /etc/crontab

ein und ergänze die Systemdatei um folgenden Eintrag:

30 11   * * *   andreas docker exec paperless-webserver-1 document_exporter /usr/src/paperless/data/export

So wird jeden Tag um 11:30 Uhr ein Export angestoßen. Der Exporter legt dabei alle Dokumente im Ursprungsformat, ihre jeweiligen PDF-Repräsentationen und Webvorschaubilder, eine Datei namens manifest.json mit allen Metadaten sowie eine Datei metadata.json mit der Angabe der Versionsnummer von Paperless-NGX in dem angegebenen Verzeichnis ab.

iDieses Verzeichnis ist per Samba freigegeben. Dazu steht in der Datei "/etc/samba/smb.conf" des DMS-Servers:

   [export]
comment = Export von Paperless-NGX
path = /home/andreas/paperless-ngx/paperless-ngx/data/export
browsable = yes
read only = no
guest ok = no

Dieses Verzeichnis ist auf dem Server, auf dem Duplicati läuft, unter "/export" gemounted:


//10.10.0.110/export /export cifs vers=3.0,username=ichhalt,password=**********,uid=1000,gid=1000 0 0

In der Datei "docker-compose.yml" für Ducati ist dieses Verzeichnis als Volume eingetragen:

         volumes:
...
- /export:/dms-export

In Duplicati ist nun ein Sicherungsjob namens "dms", eingerichtet, der die Daten täglich um 12:00 Uhr incrementell und verschlüsselt in das Verzeichnis "/backup/dms" sichert. Das Verzeichnis "backup" ist in der Datei "docker-compose.yml" als Volume mit dem Ziel "/remote-backup" eingetragen.
Das Verzeichnis "/remote-backup" auf dem Duplicati-Server ist eine SMB-Freigabe auf einen vServer von Netcup, auf den per Wireguard-Tunnel zugegriffen wird, und die auf dem Duplicati-Server gemounted ist.  

Die nachfolgende Grafik veranschaulicht das Prinzip (hoffentlich):

Absicherung

Der Zugriff auf die Anwendung kann abgesichert werden, indem mittels Nginx Proxy Manager HTTPS-Zugriffe ermöglicht (und erzwungen) werden. Außerdem kann eine Zwei-Faktor-Authentifizierung mit Authelia oder Authentik realisiert werden. Wenn die Anwendung über das Internet zugänglich ist, dann sollte das auf jeden Fall gemacht werden.

Updates

Updates können bequem durch Aktualisierung Container durchgeführt werden. Dazu wechselt man zunächst auf der Linux-Konsole in den Ordner mit der entsprechenden YAML-Datei (docker-compose.yml).

cd /home/andreas/paperless-ngx

Dort setzt man den Befehl zum Stoppen des Containers ab:

docker-compose down

Dann pullt man die aktuelle Version:

docker-compose pull

Das funktioniert, wenn wir bei der Installation die Version "latest" vorgegeben haben. Danach muss die neue Version gestartet werden:

docker-compose up -d

Wenn das ohne Fehlermeldungen durchgelaufen ist, dann ist die Paperless NGX-Instanz aktualisiert.

Migration/Umzug

Für eine Migration oder einen Umzug müssen zunächst die Quell- und die Zielinstanz in der selben Version vorliegen. Ggf. ist zunächst ein Update durchzuführen. Dann wird von der Quellinstanz der Export durchgeführt:

docker exec -it paperless-webserver-1 document_exporter ../data/export

Die Daten liegen dann im Verzeichnis ../data/export (also z.B. "/home/andreas/paperless-ngx/data/export").

Zum Importieren müssen sie zunächst auf den Zielserver übertragen werden. Wenn sie in den oben genannten Ordner kopiert wurden, dann können sie nun mit dem Befehl

docker exec -it paperless-webserver-1 document_importer ../data/export

importiert werden. Dadurch wird die Datenbank überschrieben und alle Daten werden importiert. Der Name des betreffenden Containers (hier "paperless-webserver-1" genannt) muss natürlich passen. Er kann mit 

docker ps

ausgelesen werden.

Trouble Shooting

Wenn der Webserver nach einem Neustart des Servers nicht auf Port 8000 lauscht, dann hilft es, zunächst die Firewall des Server temporär zu deaktivieren und den Webserver neu zu starten. Danach kann die Firewall wieder aktiviert werden.