-- Full-text search infrastructure for /api/cauta and /achizitii/cauta.
-- Uses 'simple' config + unaccent for diacritic-insensitive matching, since RO
-- doesn't have a built-in PG text search config and we don't want stemming bias.
--
-- Idempotent: safe to re-run.

BEGIN;

-- Ensure unaccent extension
CREATE EXTENSION IF NOT EXISTS unaccent;

-- Wrap unaccent as IMMUTABLE so it can be used in expression indexes / generated cols.
-- Safe because we don't reload the unaccent dictionary at runtime.
CREATE OR REPLACE FUNCTION seap.immutable_unaccent(text) RETURNS text
LANGUAGE sql IMMUTABLE PARALLEL SAFE STRICT
AS $$ SELECT public.unaccent('public.unaccent', $1) $$;

-- Plain (non-generated) tsvector column populated by trigger.
ALTER TABLE seap.announcements ADD COLUMN IF NOT EXISTS search_tsv tsvector;

CREATE OR REPLACE FUNCTION seap.update_search_tsv() RETURNS trigger
LANGUAGE plpgsql AS $$
BEGIN
  NEW.search_tsv :=
    setweight(to_tsvector('simple', seap.immutable_unaccent(coalesce(NEW.title, ''))), 'A') ||
    setweight(to_tsvector('simple', seap.immutable_unaccent(coalesce(NEW.description, ''))), 'B') ||
    setweight(to_tsvector('simple', seap.immutable_unaccent(coalesce(NEW.authority_name, ''))), 'C') ||
    setweight(to_tsvector('simple', seap.immutable_unaccent(coalesce(NEW.supplier_name, ''))), 'C') ||
    setweight(to_tsvector('simple', seap.immutable_unaccent(coalesce(NEW.cpv_name_ro, ''))), 'D') ||
    setweight(to_tsvector('simple', seap.immutable_unaccent(coalesce(NEW.cpv_name, ''))), 'D');
  RETURN NEW;
END $$;

DROP TRIGGER IF EXISTS trg_announcements_search_tsv ON seap.announcements;
CREATE TRIGGER trg_announcements_search_tsv
  BEFORE INSERT OR UPDATE OF title, description, authority_name, supplier_name, cpv_name_ro, cpv_name
  ON seap.announcements
  FOR EACH ROW EXECUTE FUNCTION seap.update_search_tsv();

CREATE INDEX IF NOT EXISTS idx_ann_search_tsv ON seap.announcements USING gin(search_tsv);

-- Title-only trgm for "starts-with" or substring autocompletes
CREATE INDEX IF NOT EXISTS idx_ann_title_trgm
  ON seap.announcements USING gin(title gin_trgm_ops);

COMMIT;

-- Backfill existing rows (run outside the transaction). Long-running on 642K
-- rows but does NOT block reads.
UPDATE seap.announcements
SET search_tsv =
  setweight(to_tsvector('simple', seap.immutable_unaccent(coalesce(title, ''))), 'A') ||
  setweight(to_tsvector('simple', seap.immutable_unaccent(coalesce(description, ''))), 'B') ||
  setweight(to_tsvector('simple', seap.immutable_unaccent(coalesce(authority_name, ''))), 'C') ||
  setweight(to_tsvector('simple', seap.immutable_unaccent(coalesce(supplier_name, ''))), 'C') ||
  setweight(to_tsvector('simple', seap.immutable_unaccent(coalesce(cpv_name_ro, ''))), 'D') ||
  setweight(to_tsvector('simple', seap.immutable_unaccent(coalesce(cpv_name, ''))), 'D')
WHERE search_tsv IS NULL;
