Installation
Zwei Teile, die unabhängig voneinander laufen: der Client auf deinem Rechner und — nur wenn du mehrere Geräte abgleichen willst — der Sync-Server.
Fertige Apps
Für Windows und Android gibt es gebaute Fassungen auf der Downloadseite — ohne Store, ohne Konto, mit veröffentlichten Prüfsummen. Dort steht auch, wie man sie nachrechnet und was Windows und Android beim ersten Start melden.
Einmal installiert, aktualisiert sich tessera selbst: Die App sieht beim Start nach, ob es eine neue Fassung gibt, und setzt sie auf Knopfdruck ein. Was dabei geprüft wird und wie man es abschaltet, steht unter Updates. Selbst gebaute Fassungen suchen nie nach Updates.
Client selbst bauen
Wer lieber selbst baut, braucht das Flutter-SDK. Windows ist die Referenzplattform; Android baut auch unter Windows, iOS braucht einen Mac.
cd app
flutter pub get
flutter test # 892 Tests, gut zwanzig Sekunden
flutter run -d windows
Für den Windows-Build braucht es die C++-Toolchain von
Visual Studio. Ohne sie bricht flutter build
windows mit Unable to find suitable Visual Studio
toolchain ab. Tests und Analyse laufen auch ohne sie.
winget install --id Microsoft.VisualStudio.2022.BuildTools --override "--quiet --wait --add Microsoft.VisualStudio.Workload.VCTools --includeRecommended"
Danach muss flutter doctor den Punkt „Visual Studio“ grün
melden.
Android bauen
flutter devices
flutter run -d <gerät>
Ein Release-Paket zum Weitergeben braucht einen eigenen
Signaturschlüssel — mit dem Debug-Schlüssel gebaute Pakete lassen sich
später nicht aktualisieren und sind nicht vertrauenswürdig. Wie das
eingerichtet wird, steht in docs/distribution.md im
Quelltext.
Ohne Server benutzen
Wer nur einen Rechner hat — oder erst einmal schauen will —, richtet keinen Server ein. Die Einrichtung bietet unter dem Formular Ohne Server nutzen an; nach einer Rückfrage, die sagt, was dabei fehlt, ist der Client sofort einsatzbereit. Hosts, Snippets und Schlüssel liegen dann ausschließlich in der lokalen Datenbank dieses Geräts.
Kein Abgleich heißt auch: kein zweites Gerät, keine Geräteliste und kein Wiederherstellungscode. Geht dieses Gerät verloren, sind die Daten weg.
Der Sync lässt sich jederzeit später dazuschalten — über Abgleich einrichten im Menü, in den Einstellungen oder in der Fußzeile der Hostliste. Die bestehenden Daten werden dabei verschlüsselt hochgeladen; verloren geht nichts. Was dabei genau passiert, steht unter Ohne Server.
Server
Node 22 oder neuer und eine MariaDB. Für die Entwicklung reicht der mitgelieferte Container, im Produktivbetrieb läuft der Dienst unter systemd hinter nginx — ohne Docker.
cd server
npm ci
npm run db:up # MariaDB 11.8 auf Port 3307
npm test # 242 Tests
npm run dev
sudo ./deploy/install.sh
Das Skript ist idempotent und tut Folgendes:
- legt den Systembenutzer
tesseraan, - spiegelt
server/nach/opt/tesseraund ruftnpm ci --omit=devauf, - erzeugt beim ersten Lauf
/etc/tessera/envmit frischem JWT-Geheimnis, Registrierungstoken und Datenbankpasswort, - legt Datenbank und Datenbankbenutzer an, sofern MariaDB lokal läuft,
- installiert die systemd-Unit und startet den Dienst.
npm ci, nie npm install.
Das Lockfile ist verbindlich. Ein install auf dem Server
kann eine andere Version ziehen als die, gegen die getestet wurde.
Konfiguration
Alles steht in /etc/tessera/env, Rechte
0640 root:tessera. Die wichtigsten Schalter:
| Variable | Bedeutung |
|---|---|
TESSERA_HOST / TESSERA_PORT | Bindeadresse. Vorgabe 127.0.0.1:3000 — der Dienst gehört hinter den Reverse Proxy, nicht ins Netz. |
TESSERA_DB_* | Zugang zur MariaDB samt Poolgröße. |
TESSERA_JWT_SECRET | Signaturgeheimnis der Access-Tokens. Wird beim ersten Lauf erzeugt. |
TESSERA_REGISTRATION_TOKEN | Ist es gesetzt, braucht POST /account den Header X-Registration-Token. So bleibt der Server privat. |
TESSERA_TRUST_PROXY | Muss true sein, wenn nginx davor steht — sonst sieht das Rate Limit nur die Proxy-Adresse. |
nginx und TLS
Die mitgelieferte Konfiguration steht in
deploy/nginx-tessera.conf. Sie bringt zwei Dinge mit, die
über ein reines Weiterreichen hinausgehen: gestaffelte Ratenlimits
(streng auf /auth, /pairing und
/recovery, großzügiger auf dem Rest) und ein größeres
Körperlimit ausschließlich für /vault/rotate, weil dort
der gesamte neu verschlüsselte Vault in einem Aufruf ankommt.
sudo certbot --nginx -d sync.example.org
Nimm für den Sync-Server einen eigenen Hostnamen.
Diese Webseite und die API sollten nicht auf demselben Namen liegen
— die API antwortet auf / und würde sich sonst mit den
statischen Dateien in die Quere kommen.
Erstes Gerät verbinden
- In den Einstellungen des Clients die Server-URL eintragen.
- Ist ein Registrierungstoken gesetzt, dieses angeben. Es steht in
/etc/tessera/env. - Der Client erzeugt Konto und Geräteschlüssel, wrappt den Vault Key für sich und lädt ihn hoch.
- Den Wiederherstellungscode aufschreiben. Er erscheint genau einmal. Ohne ihn und ohne ein zweites gekoppeltes Gerät ist der Vault verloren — das ist keine Drohung, sondern die Konsequenz daraus, dass der Server nichts entschlüsseln kann.
Weitere Geräte kommen über die Kopplung dazu, nicht über eine zweite Registrierung.
Läuft es?
systemctl status tessera
curl -s https://sync.example.org/healthz
# {"status":"ok"}
journalctl -u tessera -n 50 --no-pager
/healthz gibt bewusst keine Zahl über Konten oder
Datensätze zurück. Ein Statusendpunkt, der verrät, wie viel auf dem
Server liegt, ist ein Endpunkt für Neugierige.