CREATE TABLE IF NOT EXISTS calendars (
    id UUID PRIMARY KEY DEFAULT gen_random_uuid(),
    tenant_id UUID NOT NULL,
    name VARCHAR(200) NOT NULL,
    color VARCHAR(20) DEFAULT '#3B82F6',
    type VARCHAR(20) DEFAULT 'personal',
    owner_id UUID NOT NULL,
    ics_token VARCHAR(64),
    created_at TIMESTAMPTZ DEFAULT NOW(),
    updated_at TIMESTAMPTZ DEFAULT NOW(),
    deleted_at TIMESTAMPTZ
);
CREATE INDEX IF NOT EXISTS idx_calendars_tenant ON calendars(tenant_id) WHERE deleted_at IS NULL;

CREATE TABLE IF NOT EXISTS calendar_entries (
    id UUID PRIMARY KEY DEFAULT gen_random_uuid(),
    tenant_id UUID NOT NULL,
    calendar_id UUID REFERENCES calendars(id) ON DELETE CASCADE,
    entry_type VARCHAR(15) NOT NULL,
    subtype VARCHAR(20) DEFAULT 'normal',
    title VARCHAR(500) NOT NULL,
    description TEXT,
    start_at TIMESTAMPTZ,
    end_at TIMESTAMPTZ,
    all_day BOOLEAN DEFAULT false,
    location VARCHAR(500),
    due_date TIMESTAMPTZ,
    priority VARCHAR(10) DEFAULT 'medium',
    status VARCHAR(15) DEFAULT 'open',
    assigned_to UUID,
    reminder JSONB,
    recurrence JSONB,
    source_mail_id UUID,
    created_by UUID NOT NULL,
    created_at TIMESTAMPTZ DEFAULT NOW(),
    updated_at TIMESTAMPTZ DEFAULT NOW(),
    deleted_at TIMESTAMPTZ
);
CREATE INDEX IF NOT EXISTS idx_entries_tenant_cal ON calendar_entries(tenant_id, calendar_id) WHERE deleted_at IS NULL;
CREATE INDEX IF NOT EXISTS idx_entries_tenant_start ON calendar_entries(tenant_id, start_at) WHERE deleted_at IS NULL;
CREATE INDEX IF NOT EXISTS idx_entries_tenant_due ON calendar_entries(tenant_id, due_date) WHERE deleted_at IS NULL;
CREATE INDEX IF NOT EXISTS idx_entries_assigned ON calendar_entries(tenant_id, assigned_to, status) WHERE deleted_at IS NULL;

CREATE TABLE IF NOT EXISTS calendar_entry_links (
    id UUID PRIMARY KEY DEFAULT gen_random_uuid(),
    tenant_id UUID NOT NULL,
    entry_id UUID REFERENCES calendar_entries(id) ON DELETE CASCADE,
    entity_type VARCHAR(50) NOT NULL,
    entity_id UUID NOT NULL,
    deleted_at TIMESTAMPTZ,
    created_at TIMESTAMPTZ DEFAULT NOW(),
    updated_at TIMESTAMPTZ DEFAULT NOW()
);
CREATE INDEX IF NOT EXISTS idx_entry_links_entry ON calendar_entry_links(entry_id);

CREATE TABLE IF NOT EXISTS calendar_shares (
    id UUID PRIMARY KEY DEFAULT gen_random_uuid(),
    tenant_id UUID NOT NULL,
    calendar_id UUID REFERENCES calendars(id) ON DELETE CASCADE,
    user_id UUID,
    group_id UUID,
    permission VARCHAR(10) NOT NULL,
    deleted_at TIMESTAMPTZ,
    created_at TIMESTAMPTZ DEFAULT NOW(),
    updated_at TIMESTAMPTZ DEFAULT NOW()
);
CREATE INDEX IF NOT EXISTS idx_calendar_shares_cal ON calendar_shares(calendar_id);

CREATE TABLE IF NOT EXISTS user_calendar_visibility (
    user_id UUID NOT NULL,
    calendar_id UUID NOT NULL,
    tenant_id UUID NOT NULL,
    visible BOOLEAN DEFAULT true,
    PRIMARY KEY (user_id, calendar_id)
);

CREATE TABLE IF NOT EXISTS subtasks (
    id UUID PRIMARY KEY DEFAULT gen_random_uuid(),
    tenant_id UUID NOT NULL,
    entry_id UUID REFERENCES calendar_entries(id) ON DELETE CASCADE,
    title VARCHAR(500) NOT NULL,
    completed BOOLEAN DEFAULT false,
    deleted_at TIMESTAMPTZ,
    created_at TIMESTAMPTZ DEFAULT NOW(),
    updated_at TIMESTAMPTZ DEFAULT NOW()
);
CREATE INDEX IF NOT EXISTS idx_subtasks_entry ON subtasks(entry_id);

CREATE TABLE IF NOT EXISTS resources (
    id UUID PRIMARY KEY DEFAULT gen_random_uuid(),
    tenant_id UUID NOT NULL,
    name VARCHAR(200) NOT NULL,
    type VARCHAR(50) NOT NULL,
    deleted_at TIMESTAMPTZ,
    created_at TIMESTAMPTZ DEFAULT NOW(),
    updated_at TIMESTAMPTZ DEFAULT NOW()
);
CREATE INDEX IF NOT EXISTS idx_resources_tenant ON resources(tenant_id);

CREATE TABLE IF NOT EXISTS resource_bookings (
    id UUID PRIMARY KEY DEFAULT gen_random_uuid(),
    tenant_id UUID NOT NULL,
    resource_id UUID REFERENCES resources(id) ON DELETE CASCADE,
    entry_id UUID REFERENCES calendar_entries(id) ON DELETE CASCADE,
    start_at TIMESTAMPTZ NOT NULL,
    end_at TIMESTAMPTZ NOT NULL,
    deleted_at TIMESTAMPTZ,
    created_at TIMESTAMPTZ DEFAULT NOW(),
    updated_at TIMESTAMPTZ DEFAULT NOW()
);
CREATE INDEX IF NOT EXISTS idx_bookings_resource ON resource_bookings(resource_id);
CREATE INDEX IF NOT EXISTS idx_bookings_entry ON resource_bookings(entry_id);
