Architecture kata · K—08

Competitor Price and Markdown Intelligence Platform

Architecture kata · design study on a fictional brief

Sector
Retail pricing
Technologies
Cloud Run, Playwright, Cloud Storage, Pub/Sub, BigQuery, Dataform, pgvector, Cloud Composer, Langfuse, Keycloak
Flow: a site registry gates collection; raw pages are stored, then parsed, matched in three tiers and turned into advice.
The design at a glance: the one-page, 30-minute live drawing.

In short

Collect competitor pages within legal limits, match them to 120,000 SKUs with measured precision, advise on markdown timing with evidence.

Problem

A mid-market apparel group sells in 25 countries online and through 900 stores. Merchandising sets prices and markdowns in spreadsheets fed by two external vendors. Their data arrives weekly, covers 30% of the assortment and is mapped to the group’s products by hand. Gross margin fell two points because markdowns started too late in some countries and too early in others. The CFO wants daily competitor prices for the full assortment. Legal insists on collection within each country’s law and the competitors’ terms, and on a human who can see why a recommendation was made.

Approach

Three constraints matter, and none is solved by “write a model”. Collection must stay within legal and politeness limits. Matching must reach a measured precision above 95% across 120,000 products. The decision must stay human. The design follows one order. No collection without a registry entry. Raw snapshots first. Parsing as a separate stage. Tiered matching, measured daily. Each recommendation carries its evidence in the same row.

Architecture

  • Site registry: robots rules, request rate, country legal status and selector version in one place. A worker does not start without an approved row.
  • Collection: Cloud Run Jobs with Playwright and HTTP workers that scale to zero overnight, and fixed egress addresses per country. Proxy rotation is out of scope.
  • Raw store: every page is kept as (site, URL, capture time) in locked Cloud Storage for five years.
  • Matching: deterministic rules, then embedding similarity with pgvector, then an LLM with structured output only in the grey zone. Low confidence goes to a human queue.
  • Warehouse and advice: BigQuery with Dataform layers, a daily price index, and a read-only API with no write path into the pricing system.
Architecture: a registry gates collection, raw pages are parsed in a separate stage, and three-tier matching feeds BigQuery.
Solution overview: from the site registry and the raw snapshot store through parsing, three-tier matching and BigQuery layers to a read-only API.Open full size (opens in new tab)

Why these components

Need Choice Why
Collection law and courtesy Site registry in Git and a BigQuery table Robots rules, rate, country legal status and selector version in one place; no worker starts without its row. Legal can stop a country without an engineer. A config file inside the worker cannot be audited.
Collector fleet Cloud Run Jobs with Playwright and HTTP workers Scales to zero when done, with one job and token bucket per site and country. An idle Kubernetes pool still bills; Cloud Functions are too limited for a browser. Plain HTTP stays the cheap path.
Fixed egress addresses Cloud NAT with a registered IP per country Legal needs to know which address we collect from. Proxy rotation counts as evading blocks and is out of scope. Each country gets a declared IP and an honest user agent.
Scheduling Cloud Composer, managed Airflow Daily plans, retries, re-parse campaigns and supplier files are classic orchestration. The DAGs stay portable.
Raw snapshot store Cloud Storage bronze with a five-year retention lock Reproducibility only comes from an untouched source, and the lock stops deletion even by admins. Raw HTML in BigQuery would be expensive and cannot be locked. The Archive class keeps five years affordable.
Events Pub/Sub Captured, parsed and matched events trigger the next stage instead of direct calls. Kafka would be too much here: no stream processing, no ordering need, a few tens of millions of small messages a day.
Parsing Cloud Run service with versioned selectors A stage separate from collection. When a selector breaks, snapshots are parsed again and the site is not visited again. Personal data such as review authors is dropped here and never reaches the bronze tables.
Matching Rules, Vertex embeddings with pgvector, Gemini in the grey zone, a human queue Rules and embeddings settle about 80% deterministically. The LLM sees only the grey zone, with a daily cap and 5% sampled review. pgvector is open and portable; Pinecone-style managed services add needless dependency.
Warehouse and transformation BigQuery EU and Dataform with bronze, silver and gold A partitioned, columnar warehouse for five years at 8 million rows a day. Running our own cluster would break the fixed budget. Dataform SQL lives in Git and stays compatible with dbt.
Index, elasticity and advice BigQuery ML and a SQL rule engine The daily run is deterministic: same input, same output. Rules draw the decision space and the model only ranks within it. A separate Vertex model service is unnecessary for a daily batch.
Serving and identity Intelligence API on Cloud Run, Keycloak A read-only API. No service account can write to the pricing system, so “advice only” is enforced by IAM. Keycloak gives open-source OpenID Connect and country roles.
Trend summary Gemini, weekly, with citations required Every sentence cites a raw snapshot and carries a “summary” label; uncited sentences are not produced. Golden, drift and injection tests run on every release.
LLM tracing and evaluation Langfuse on Cloud Run and Cloud SQL Every LLM call is traced with cost and output, and evaluation runs gate releases. The core is MIT-licensed. Managed tracing products would move data outside the perimeter.
Dashboard Looker Studio with BI Engine A free dashboard on gold, with the legal team’s collection audit view in the same place. Superset is the open alternative but needs one more service to run.

Decisions and trade-offs

  • Raw first, parse separately. Five-year reproducibility needs an untouched source. A price from three years ago is proven by opening the locked object and parsing it again with that day’s selector version. A lost collection day is never filled from history; it shows as missing. The cost is storage.
  • LLM only in the matching grey zone. The kata sizes this at about 20% of items. Asking an LLM for all 120,000 products against 60 competitors would break the budget and make precision impossible to measure. The daily production run uses no LLM. Precision is measured daily against a golden sample. Below 95% in a country, the threshold rises the same day: I give up recall, never precision.
  • Advice, not action. A recommendation is a table row that carries its evidence: competitor, date, observed price, raw snapshot and fired rule. The only output is an export file that a person uploads. No service account can write prices, so the rule lives in IAM, not in a policy text. Each applied recommendation is measured four weeks later to calibrate confidence.
  • The registry comes before collection, and blocks are respected. A 403, a 429 or a captcha stops work for that site. Its registry status changes and a ticket goes to legal. No proxy rotation, no captcha solving, no IP switching. The cost is coverage: the site shows as missing in the index and the coverage metric drops.
  • A fixed budget with hard caps. Collection runs on jobs that scale to zero overnight. The kata’s arithmetic comes to about 9,000 USD a month against a 15,000 budget. The LLM has a daily call cap, BigQuery a byte quota per project. Overruns stop the work and raise an alert; the bill does not grow. Browser-heavy sites are the main threat to that number.
  • Keep the two old suppliers for twelve months. Their data covers about 30% of the scope. Comparing it with our index is an independent check of precision, and it is the only history for the elasticity model’s early years. The cost is paying for both feeds for a year.
Flow: six hops from competitor page to advice, each reproducible from the one before; the LLM only judges the grey zone.
Six hops from a competitor page to an advisory markdown. Precision is measured, the LLM is confined to the grey zone, and a recommendation never writes to the pricing system.Open full size (opens in new tab)

What I would revisit

  • Legal approval per site. Which sites and countries did legal really approve? If a site’s terms ban automated access, it stays out of the registry and coverage drops.
  • Browser share. I assumed 20% of pages need a browser. At 40%, collection cost doubles and becomes the largest item.
  • Human review capacity. I assumed 1,500 decisions a day. If the real number is lower, thresholds go up and precision is protected over coverage.
  • Reviews and social listings. Their legal risk is higher than price pages. If they are not truly needed, I would drop them from scope.

Outcome notes (design assumptions, not measurements)

This is a design exercise, not a running scraper or pricing system. The output is a four-page diagram set, a one-page whiteboard version and a 16-page Turkish PDF with a line-by-line budget. Precision and share figures are targets and assumptions from the brief.

Sources

  • Architecture PDF (Turkish, 16 pages).
  • draw.io diagrams (English labels): four-page set and a one-page 30-minute version.

Real projects on this topic

  1. P—01

    Completed

    Featured

    Enterprise Data Warehouse Migration to Google BigQuery

    80 TB warehouse moved from SQL Server and a 15-node Cloudera cluster to BigQuery: $550K annual savings, 75% lower infrastructure cost, 7x faster workflows.

    • Data platform
    • Data quality
    • Analytics-ready data
    • Orchestration
    • Cloud

    Role

    Design and lead · Senior Data Engineering & Data Architecture Group Manager

  2. P—02

    Completed

    Featured

    GA4 Analytics Modernization: Gold Layer, Streaming and Anomaly Detection

    GA4 analytics rebuilt on BigQuery with a Gold e-commerce model and drift checks: monthly cost $9K to $3K, heaviest queries 46 minutes to 8 seconds.

    • Analytics-ready data
    • Decision support
    • Data quality
    • Data observability
    • Cloud

    Role

    Program lead · Data Solution Architect

Decisions: projects, katas and publications

About the katas

Write to me about a similar design problem.