Product Search — the N-source sweep
Requires: web fetching. The retailer ladder escalates to a browser when a site blocks plain fetches, so a Playwright MCP server (or any browser-automation tool) makes the sweep far more reliable. Without one, record blocked sites as BLOCKED and widen the retailer list instead.
Born from a real failure: "nothing matches" declared after two retailers; the pushed-back sweep of fourteen found real candidates. This skill exists so the first pass is the rigorous one.
1. Pin the spec before searching
- Split hard constraints (dimensions with tolerance, budget ceiling, must-have features, safety certs for baby gear) from soft preferences (style, material, color). Write both down first; the hard set decides pass/fail, the soft set ranks.
- Pull the user's actual context, not the aspirational version: if they keep a
notes file of real measurements and standing constraints (a
MEASUREMENTS.mdorCONSTRAINTS.md: owned pieces, style registry), read it before inventing numbers.
2. The retailer ladder
- Floor: 8 retailers checked before any verdict. Default list, adjusted per category: Amazon, Target, Wayfair, IKEA, West Elm, CB2, Crate & Barrel, Article, AllModern, Pottery Barn (swap in category specialists — e.g. babylist/Carter's-tier for baby gear, REI-tier for outdoor).
- Escalation per site: WebFetch → Playwright (
browser_navigate+browser_evaluate) when fetch is blocked → record as BLOCKED and move on. Known bot-blockers needing Playwright or worse: Wayfair, RH, CB2. - Wide sweeps go to parallel subagents (2–3 retailers each, returning candidates as structured rows) — never a long serial crawl with no findings surfaced.
- Track every retailer's outcome:
candidates / none-fit / blocked.
3. Verify before shortlisting
- Dimensions come from the actual product page (spec table), never a category listing or search snippet; note price, variant, and stock state.
- A candidate without verified dimensions doesn't make the table. Convert units once, carefully; compare against the tolerance, not the nominal number.
4. The verdict
- Lead with the move: best candidate first — one sentence, price, why it fits.
- Then the shortlist table: retailer · product · dims vs. constraint · price · link.
- Then the coverage log: N retailers checked, who blocked, who had nothing.
- "No match exists" is only sayable with the full coverage log attached — and even then it's "checked N, none fit; nearest misses were A (off by x″) and B (over budget by $y)", which gives the user something to relax rather than a dead end.