Kairo-Jinkendo/backend/migrations/002_auth_identity_tenant_actor.sql
Lars 564008be13
Some checks failed
Deploy Development / deploy (push) Successful in 38s
Test Suite / pytest-backend (push) Failing after 7s
Test Suite / k6 /api/health Baseline (push) Has been skipped
Test Suite / playwright-smoke (push) Has been skipped
Test Suite / lint-backend (push) Successful in 2s
Test Suite / compose-smoke (push) Has been skipped
AP0.2: Auth, Tenant, Actor Foundation mit Sessions, TenantContext und Tests.
Co-authored-by: Cursor <cursoragent@cursor.com>
2026-07-04 20:09:54 +02:00

82 lines
2.9 KiB
SQL

-- AP0.2: Auth, Identity, Tenant & Actor Foundation
CREATE EXTENSION IF NOT EXISTS pgcrypto;
CREATE TABLE users (
id UUID PRIMARY KEY DEFAULT gen_random_uuid(),
email VARCHAR(255) NOT NULL UNIQUE,
password_hash VARCHAR(255) NOT NULL,
display_name VARCHAR(255) NOT NULL,
portal_role VARCHAR(32) NOT NULL DEFAULT 'user'
CHECK (portal_role IN ('user', 'admin')),
is_active BOOLEAN NOT NULL DEFAULT TRUE,
created_at TIMESTAMPTZ NOT NULL DEFAULT NOW(),
updated_at TIMESTAMPTZ NOT NULL DEFAULT NOW()
);
CREATE TABLE tenants (
id UUID PRIMARY KEY DEFAULT gen_random_uuid(),
slug VARCHAR(64) NOT NULL UNIQUE,
name VARCHAR(255) NOT NULL,
is_active BOOLEAN NOT NULL DEFAULT TRUE,
created_at TIMESTAMPTZ NOT NULL DEFAULT NOW(),
updated_at TIMESTAMPTZ NOT NULL DEFAULT NOW()
);
CREATE TABLE tenant_memberships (
id UUID PRIMARY KEY DEFAULT gen_random_uuid(),
tenant_id UUID NOT NULL REFERENCES tenants(id) ON DELETE CASCADE,
user_id UUID NOT NULL REFERENCES users(id) ON DELETE CASCADE,
tenant_role VARCHAR(32) NOT NULL DEFAULT 'member'
CHECK (tenant_role IN ('owner', 'admin', 'member')),
is_active BOOLEAN NOT NULL DEFAULT TRUE,
created_at TIMESTAMPTZ NOT NULL DEFAULT NOW(),
UNIQUE (tenant_id, user_id)
);
CREATE INDEX idx_tenant_memberships_user ON tenant_memberships(user_id);
CREATE TABLE actors (
id UUID PRIMARY KEY DEFAULT gen_random_uuid(),
tenant_id UUID NOT NULL REFERENCES tenants(id) ON DELETE CASCADE,
actor_type VARCHAR(32) NOT NULL
CHECK (actor_type IN ('human', 'agent', 'working_group', 'external_system')),
name VARCHAR(255) NOT NULL,
user_id UUID NULL REFERENCES users(id) ON DELETE SET NULL,
is_active BOOLEAN NOT NULL DEFAULT TRUE,
created_at TIMESTAMPTZ NOT NULL DEFAULT NOW(),
CHECK (
(actor_type = 'human' AND user_id IS NOT NULL)
OR (actor_type <> 'human' AND user_id IS NULL)
)
);
CREATE UNIQUE INDEX idx_actors_human_user_tenant
ON actors(tenant_id, user_id)
WHERE actor_type = 'human';
CREATE INDEX idx_actors_tenant ON actors(tenant_id);
CREATE TABLE sessions (
id UUID PRIMARY KEY DEFAULT gen_random_uuid(),
token VARCHAR(128) NOT NULL UNIQUE,
user_id UUID NOT NULL REFERENCES users(id) ON DELETE CASCADE,
active_tenant_id UUID NULL REFERENCES tenants(id) ON DELETE SET NULL,
expires_at TIMESTAMPTZ NOT NULL,
created_at TIMESTAMPTZ NOT NULL DEFAULT NOW()
);
CREATE INDEX idx_sessions_token ON sessions(token);
CREATE INDEX idx_sessions_user_id ON sessions(user_id);
CREATE TABLE audit_log (
id UUID PRIMARY KEY DEFAULT gen_random_uuid(),
action VARCHAR(64) NOT NULL,
user_id UUID NULL REFERENCES users(id) ON DELETE SET NULL,
tenant_id UUID NULL REFERENCES tenants(id) ON DELETE SET NULL,
details JSONB NOT NULL DEFAULT '{}',
created_at TIMESTAMPTZ NOT NULL DEFAULT NOW()
);
CREATE INDEX idx_audit_log_created ON audit_log(created_at DESC);