-- 186_tg_support.sql
-- Telegram support bridge: @MERAsupport_bot mirrors client DMs into a
-- support-group topic; an operator replies in-thread; the bot relays the
-- reply back to the client's private chat.
--
-- WHY:
--   No durable state existed for this flow. Two things are required to make
--   it work reliably:
--     1. A mapping from "message mirrored into the support topic" back to
--        "which client chat_id it came from" — this is how an operator's
--        reply (a Telegram reply-to a topic message) gets routed to the
--        right client. `topic_message_id` on tg_support_messages is that
--        routing key.
--     2. A durable long-polling offset (`tg_support_state`) so a worker
--        restart does not replay already-processed Telegram updates.
--
-- WHAT:
--   - tg_support_users     — one row per client Telegram private chat
--                             (chat_id is the Telegram chat id, stable per
--                             client, used directly as PK — no surrogate key
--                             needed).
--   - tg_support_messages  — full conversation log, both directions.
--   - tg_support_state     — singleton key/value store for worker offsets
--                             (e.g. key='last_update_id').
--
-- 152-FZ:
--   tg_support_users / tg_support_messages hold personal data (Telegram
--   username/name + free-text conversation content). ON DELETE CASCADE from
--   tg_support_users -> tg_support_messages makes client erasure a single
--   `DELETE FROM tg_support_users WHERE chat_id = :chat_id` statement, no
--   separate cleanup pass needed.
--
-- IDEMPOTENCY / SAFETY:
--   CREATE TABLE IF NOT EXISTS + CREATE INDEX IF NOT EXISTS throughout —
--   safe re-run. Purely additive: no existing table/view/column touched.
--
-- Dependencies: none (new standalone tables). Auto-applied on deploy via
-- _schema_migrations tracking (tradein-mvp/backend/data/sql convention).

BEGIN;

CREATE TABLE IF NOT EXISTS tg_support_users (
    chat_id       bigint PRIMARY KEY,
    username      text,
    first_name    text,
    last_name     text,
    language_code text,
    created_at    timestamptz NOT NULL DEFAULT now(),
    last_seen_at  timestamptz NOT NULL DEFAULT now(),
    is_blocked    boolean NOT NULL DEFAULT false
);

COMMENT ON TABLE tg_support_users IS '152-ФЗ: ПДн клиентов Telegram-поддержки (@MERAsupport_bot). Удаление клиента — DELETE FROM tg_support_users WHERE chat_id=...; ON DELETE CASCADE в tg_support_messages подчищает переписку одной операцией.';
COMMENT ON COLUMN tg_support_users.chat_id IS 'Telegram private chat id клиента (стабильный, используется как PK напрямую).';
COMMENT ON COLUMN tg_support_users.is_blocked IS 'true, если клиент заблокировал бота (Telegram 403 на отправку) — бот перестаёт пытаться слать сообщения.';

CREATE TABLE IF NOT EXISTS tg_support_messages (
    id               bigserial PRIMARY KEY,
    chat_id          bigint NOT NULL REFERENCES tg_support_users (chat_id) ON DELETE CASCADE,
    direction        text NOT NULL CHECK (direction IN ('in', 'out')),
    tg_message_id    bigint,
    topic_message_id bigint,
    kind             text NOT NULL,
    text_body        text,
    operator_tg_id   bigint,
    created_at       timestamptz NOT NULL DEFAULT now()
);

COMMENT ON TABLE tg_support_messages IS '152-ФЗ: полный лог переписки Telegram-поддержки (ПДн, содержимое сообщений). Каскадно удаляется вместе с tg_support_users по chat_id.';
COMMENT ON COLUMN tg_support_messages.direction IS '''in'' — сообщение от клиента боту; ''out'' — ответ бота/оператора клиенту.';
COMMENT ON COLUMN tg_support_messages.tg_message_id IS 'id сообщения в личном чате с клиентом (Telegram message_id в chat_id).';
COMMENT ON COLUMN tg_support_messages.topic_message_id IS 'id зеркала сообщения в support-топике группы — ключ маршрутизации: реплай оператора на это сообщение адресуется данному chat_id.';
COMMENT ON COLUMN tg_support_messages.kind IS 'text | photo | document | video | voice | other.';
COMMENT ON COLUMN tg_support_messages.text_body IS 'Текст сообщения или caption медиа; NULL для медиа без подписи.';
COMMENT ON COLUMN tg_support_messages.operator_tg_id IS 'Telegram user id оператора, ответившего в топике; заполняется только для direction=''out''.';

CREATE UNIQUE INDEX IF NOT EXISTS tg_support_messages_topic_message_id_uq
    ON tg_support_messages (topic_message_id)
    WHERE topic_message_id IS NOT NULL;

CREATE INDEX IF NOT EXISTS tg_support_messages_chat_id_created_at_idx
    ON tg_support_messages (chat_id, created_at DESC);

CREATE TABLE IF NOT EXISTS tg_support_state (
    key        text PRIMARY KEY,
    value      text NOT NULL,
    updated_at timestamptz NOT NULL DEFAULT now()
);

COMMENT ON TABLE tg_support_state IS 'Singleton key/value store для состояния Telegram-поддержки (например last_update_id для long-polling), переживает рестарт воркера.';
COMMENT ON COLUMN tg_support_state.key IS 'e.g. ''last_update_id''.';

COMMIT;
