Go-Backend (chi, pgx, golang-migrate) + React/TS-Frontend als PWA. Enthalten: Auth inkl. OIDC, Dateien mit Versionen und Papierkorb, Freigaben (Links + intern), WebDAV, Gruppenordner, Admin/Theming, Volltextsuche mit OCR, eigener PDF-Betrachter und WOPI-Office (Collabora/OnlyOffice). Nicht im Repo: deploy/.env (Sitzungsschlüssel, DB- und Admin-Passwort) sowie alle Daten- und Build-Verzeichnisse – siehe .gitignore. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
36 lines
1.9 KiB
SQL
36 lines
1.9 KiB
SQL
-- Gruppenordner: ein Ordner, der keinem einzelnen Konto gehört, sondern einer
|
||
-- Gruppe. Wer Mitglied ist, sieht ihn; wer die Gruppe verlässt, nicht mehr.
|
||
--
|
||
-- Ordner und Dateien gehören ab jetzt entweder einem Nutzer ODER einer Gruppe,
|
||
-- nie beidem und nie keinem. Deshalb wird owner_id nullbar und bekommt eine
|
||
-- CHECK-Bedingung als Gegengewicht – ohne die könnte ein Datensatz herrenlos
|
||
-- werden und wäre über keine Abfrage mehr erreichbar.
|
||
|
||
ALTER TABLE folders ALTER COLUMN owner_id DROP NOT NULL;
|
||
ALTER TABLE files ALTER COLUMN owner_id DROP NOT NULL;
|
||
|
||
ALTER TABLE folders ADD COLUMN group_id UUID REFERENCES groups(id) ON DELETE CASCADE;
|
||
ALTER TABLE files ADD COLUMN group_id UUID REFERENCES groups(id) ON DELETE CASCADE;
|
||
|
||
ALTER TABLE folders ADD CONSTRAINT folders_one_principal
|
||
CHECK (num_nonnulls(owner_id, group_id) = 1);
|
||
ALTER TABLE files ADD CONSTRAINT files_one_principal
|
||
CHECK (num_nonnulls(owner_id, group_id) = 1);
|
||
|
||
-- Gruppen bekommen ein eigenes Kontingent. Die Alternative – „zählt beim
|
||
-- Ersteller" – wäre für die Mitglieder nicht nachvollziehbar: Der Ordner wäre
|
||
-- plötzlich voll, weil jemand anders privat etwas hochgeladen hat.
|
||
ALTER TABLE groups ADD COLUMN quota_bytes BIGINT NOT NULL DEFAULT 10737418240;
|
||
|
||
-- Die bestehende UNIQUE (owner_id, parent_id, name) greift für Gruppenordner
|
||
-- nicht: In SQL kollidiert NULL nicht mit NULL, zwei Gruppenordner gleichen
|
||
-- Namens rutschten also durch.
|
||
CREATE UNIQUE INDEX idx_folders_group_name ON folders (group_id, parent_id, name)
|
||
WHERE group_id IS NOT NULL AND parent_id IS NOT NULL;
|
||
-- Auf oberster Ebene ist parent_id NULL, das braucht einen eigenen Index.
|
||
CREATE UNIQUE INDEX idx_folders_group_root_name ON folders (group_id, name)
|
||
WHERE group_id IS NOT NULL AND parent_id IS NULL;
|
||
|
||
CREATE INDEX idx_folders_group ON folders (group_id) WHERE group_id IS NOT NULL;
|
||
CREATE INDEX idx_files_group ON files (group_id) WHERE group_id IS NOT NULL;
|