# ADR-0012: PostgreSQL full-text search before a dedicated search engine - **Status:** Accepted - **Date:** 2026-08-11 ## Context Search is a headline feature of a storefront, and reaching for Elasticsearch or OpenSearch is the reflex. It is also a second datastore to run, secure, back up and keep in sync — for a catalog that starts at a few hundred products. ## Decision Start with PostgreSQL full-text search plus `pg_trgm` for fuzzy matching and typo tolerance, behind a `SearchProvider` interface owned by `SearchModule`. The module is marked EXTRACTION CANDIDATE and reads the catalog only through public services, so it holds no privileged coupling. ## Consequences One datastore, no sync pipeline, no index drift, and search results that are transactionally consistent with the catalog. This is genuinely adequate below roughly 50k products with straightforward faceting. The limits are known and will eventually bind: no relevance tuning to speak of, no learning-to-rank, weak multilingual analysis for Vietnamese. When they do, the provider interface is the seam — swapping in OpenSearch changes one implementation, not every listing page. ## Alternatives considered Elasticsearch/OpenSearch from day one — rejected as premature infrastructure. A hosted service (Algolia, Typesense Cloud) — a reasonable future option; deferred because it adds per-record cost and a sync pipeline before there is a search-quality problem to solve.