nc-app-purge: Reste deinstallierter Nextcloud-Apps entfernen

Ein Kommandozeilenwerkzeug, das Tabellen, Einstellungen, Hintergrundjobs und appdata entfernter Nextcloud-Apps findet, sie über die Migrationen der Apps zuordnet und mit einem wiederherstellbaren Backup löscht.

Das Problem

occ app:remove löscht den Code einer Nextcloud-App und sonst nichts. Ihre Tabellen, Einstellungen, Migrationseinträge, Hintergrundjobs und ihr appdata-Ordner bleiben.

Issue #5539, "Detect / Delete App Data", ist seit Juni 2017 offen und hat 250 Reaktionen. Nutzer beschreiben, wie sie Tabellen von Hand löschen. Ein zweiter Anwendungsfall ist das Zurücksetzen einer App, deren Einstellungen sie kaputt machen: Neu installieren hilft nicht, weil die alte Konfiguration bleibt. Polls hat dafür ein eigenes occ polls:db:purge, das nur diese eine App abdeckt und nur funktioniert, solange sie installiert ist.

Nextcloud 35 hat occ db:schema:check eingeführt. Die ausführliche Ausgabe führt Tabellen, die sich keiner App zuordnen lassen, als "(unknown app)", und der Hilfetext sagt selbst, dass "occ app:remove only deletes its code, not its tables or config". Im Oktober 2026 beschrieb ein Nutzer genau diese Ausgabe im Issue und wünschte sich "a program to delete tables and related data for all (unknown app) tables". Ein bestehendes Projekt dafür habe ich nicht gefunden.

Wie nc-app-purge arbeitet

nc-app-purge ist ein PHP-Skript, das Nextcloud wie occ im eigenen Prozess startet und dessen Datenbankverbindung nutzt. SQLite, MariaDB und PostgreSQL funktionieren damit gleichermaßen.

Um Tabellen Apps zuzuordnen, spielt es die Migrationen von Core und von jeder App, deren Code vorhanden ist, in ein Schema im Speicher ein und merkt sich, welche App welche Tabelle angelegt hat. Das ist der Ansatz von db:schema:check; es läuft nur changeSchema(), geschrieben wird nichts. Tabellen installierter Apps kommen deshalb nie in Frage.

Eine entfernte App hat keinen Code mehr. Für sie lädt das Werkzeug den Code über Nextclouds Installer aus dem App Store, der Zertifikat und Signatur prüft, spielt die Migrationen ein, um die genaue Tabellenliste zu bekommen, und löscht den Code wieder. Die App wird nie aktiviert. Apps, die nicht im App Store sind, lassen sich nur über den Tabellennamen zuordnen; solche Tabellen löscht es nur mit --by-name.

Außerdem entfernt es die Zeilen der App in appconfig, preferences, migrations und notifications, ihre Hintergrundjobs und ihren appdata-Ordner. Vorher schreibt es ein Backup (Tabellendefinitionen, Zeilen als JSON Lines, Kopie von appdata), das nc-app-purge restore zurückspielt. Aktivierte und mit Nextcloud ausgelieferte Apps lehnt es ab. Für das Zurücksetzen bereinigt man eine deaktivierte App; beim nächsten Aktivieren installiert Nextcloud sie neu.

Beispiel

Der Scan aus einem CI-Lauf gegen Nextcloud 35.0.2 auf PostgreSQL, nach occ app:remove deck und mit einer Test-App, die es im App Store nicht gibt:

Nextcloud 35.0.2.2 (pgsql, table prefix oc_)

APP       STATUS   TABLES  ROWS  CONFIG  PREFS  MIGR  JOBS  NOTIF  APPDATA
deck      removed  0+10?   30    4       2      16    4     0      26 B
ghostapp  removed  0+1?    1     1       0      1     0     0      -

Ohne Code passen die zehn Deck-Tabellen nur über den Namen (+10?). purge deck lädt Deck 1.19.2, ordnet alle zehn Tabellen über die Migrationen zu und listet dann, was es löscht: zehn Tabellen, vier Konfigurationswerte, zwei Benutzereinstellungen, 16 Migrationseinträge, vier Hintergrundjobs und den appdata-Ordner.

Tests

Der Integrationstest läuft in GitHub Actions gegen echtes Nextcloud 35 (SQLite, MariaDB, PostgreSQL), 34 (SQLite, MariaDB) und 33 (PostgreSQL). Er installiert Deck, legt über die Deck-API Boards an, ergänzt Konfiguration, eine Benutzereinstellung, eine appdata-Datei und eine Fake-App mit Binärspalte und ruft occ app:remove auf. Danach prüft er, dass nach dem Download jede Deck-Tabelle zugeordnet ist, ein Trockenlauf nichts ändert, aktivierte Apps abgelehnt werden, nach dem Bereinigen nichts übrig ist und db:schema:check die Tabellen nicht mehr meldet, das Restore Boards, Konfiguration, appdata und Binärdaten zurückbringt und eine Neuinstallation leer startet.

Lokal liefen nur die Unit-Tests; alle Tests gegen Nextcloud laufen im CI.

Grenzen

Nur Nextcloud 33 bis 35. Die genaue Zuordnung braucht den Code der App, auf der Platte, per --source oder aus dem App Store für die laufende Version; sonst bleibt nur der Namensabgleich. Der Download führt die Migrationsklassen der App aus, mit demselben Vertrauen wie eine Installation. Aktivitätseinträge oder Freigaben, die andere Apps über die entfernte App speichern, bleiben unberührt. Object Storage und Oracle sind ungetestet. Restore braucht denselben Datenbanktyp und dasselbe Tabellenpräfix. Vorher ein Datenbank-Backup machen.

Der Code steht unter MIT-Lizenz: github.com/Jwrede/nc-app-purge.