Sensory profiles
Up to three taste identities — e.g. Gas / Fuel bombs, Evening knock-out, Sweet tropics — each defined across aroma, flavour, effect, texture, potency and priority weights. A completeness ring unlocks matching at 60%.
Sensory sommelier for cannabis
A private-by-design tasting room. Instead of “indica / sativa / hybrid” reductionism, SŌMA lets a member build a personal sensory profile — aromas, flavours, effects — then scans any dispensary menu and ranks every strain against that taste with a deterministic, fully explainable match engine.
Every dispensary menu sorts flower by legacy taxonomy (indica / sativa / hybrid) and marketing copy (“euphoric, uplifting, creative”) — categories that don’t actually describe what a person’s palate wants tonight.
SŌMA borrows its language from wine and perfumery instead. Members describe how they want a flower to smell, taste and feel, and the app finds the ones that match — on any menu, with a written verdict for every result. Discover, experience, evolve.
Up to three taste identities — e.g. Gas / Fuel bombs, Evening knock-out, Sweet tropics — each defined across aroma, flavour, effect, texture, potency and priority weights. A completeness ring unlocks matching at 60%.
A deterministic scoring engine reading the same sensory vocabulary as the questionnaire, catalog and audit log. No black-box ML — every match ships a per-sense breakdown and a written verdict.
Paste a dispensary menu as text — a deterministic parser pulls out grower, THC, price and weight — and get a ranked #1 / #2 / #3 board plus the full list, each row expandable into the analysis, with a compare-two side-by-side view.
A virtual fourth profile that mixes two or three real ones with a bias slider and a bridge mode (min-across-worlds, so only strains strong in every world survive). Solves “I want both moods tonight.”
An editorial catalog of 895 curated strains — sommelier-style curator notes, lineage, market aliases and a sensory family taxonomy (all in the language the engine reads from), with hand-drawn poster art for the headline strains.
A member’s shelf of tried and wishlisted flowers, plus a two-strain compare view that decomposes match scores by profile and by sense.
“Candied tropical nose over a creamy gelato base; a soft, rounded evening lean. A near-perfect fit for your Sweet tropics profile.”
Engine, questionnaire and strain data all draw from one canonical
vocabulary object (VOCAB_VERSION), so a score is always
reproducible from stored inputs — audit rows survive vocab migrations
by pivoting on the version.
Every visitor gets a signed anonymous UUID cookie; profile, history and audit log accumulate under it. Registering just sets username + password hash on the same row. HMAC session tokens validate in-process so a DB blip never silently logs a member out.
First paint started in “did it freeze?” territory. Fix: cache the assembled catalog (hundreds of thousands of comparisons no longer paid per cold start), trim the per-card payload sharply, paginate to 40 cards with IntersectionObserver infinite scroll, and add an instant skeleton.
Every gold surface is pure CSS — no image assets: masked hollow-ring borders, sculpted medallion rings with a debossed cream well, star-shine glints, and a 42% frosted card that lets the embossed leaf backdrop show through. All theme-aware.
Gilded champagne-gold and frosted-cream cards on an embossed cannabis-leaf backdrop. Display in Fraunces (a high-contrast antiqua), UI in Inter. Every microcopy line reads like a sommelier note, not a marketing bullet — sensory-family gradients shift per strain territory (gas-og, garlic-funk, citrus-haze…).
Next.js 15 (App Router · React 19 · Server Components) with TypeScript and Tailwind. Prisma over PostgreSQL (Supabase); custom scrypt + HMAC-cookie auth (no auth library). OpenAI is optional — it only rewrites the written verdicts and infers off-catalog strain names; it never touches the scores. Tested with Node’s built-in test runner plus a stress harness that guards against “the illusion of intelligence.”
◆ ◆ ◆
SŌMA is live — step into the tasting room.