Skip to content

Merchant Portal β€” Rolling Plan ​

Created: 2026-03-29 Status: Active β€” merchant-venue association shipped; offers and consumer-app tether next Last Updated: 2026-04-22

"Can we create a smooth beaver?" β€” working title for the merchant monetization path. A beaver builds; smooth means the experience is friction-free for venue owners.


Overview ​

This document tracks the rolling implementation of the Lantern merchant portal across iterations. Each section records what shipped and what's next. The goal: let venue owners manage their presence, run promotions, and eventually see consumer-app analytics β€” all through the admin portal.


Shipped ​

Ad Placeholder Components βœ… ​

Commit de79322 (PR #321 / #322 merge to dev).

  • ChatOfferPill and FeedOfferCard renderers for the two missing placement types.
  • AdSlot routing component.
  • offerNormalizer utility.
  • Live preview section in OfferForm renders all 4 placements in real-time as merchants fill in fields.

Merchant Portal in Admin App β€” Phases 1 & 2 βœ… ​

Commits f800589, 5202f37 (Phase 1 + auth wiring).

  • checkMerchantRole() in apps/web/src/lib/auth.js and apps/admin/src/firebase.js, mirroring checkAdminRole().
  • isMerchant state alongside isAdmin in both App.jsx files.
  • PILOT_MODE gate (consumer) and admin access gate accept admin OR merchant.
  • Merchants sub-nav (admin app): expandable with Overview, Offers, Create Merchant sub-items.
  • Merchants see only Merchants section; admins get full nav including admin-only sub-items.

Merchant Create / Edit / Detail / Directory βœ… ​

Commits 19dadee, 89b9d5a, 35b57b1, 58a3db5.

  • Hardened merchant creation end-to-end (validation, error states).
  • MerchantDetail page with redirect after create.
  • All Merchants directory view (admin only).
  • Edit mode on MerchantDetail + PATCH update endpoint.

Merchant ↔ Venue Association βœ… ​

Commits d02ee1b through 4abe4d1 (19 commits).

  • New merchants/{merchantId} entity with m_* id; schema introduces stable identifier separate from user uid (#231 prep).
  • Six new /auth/admin/merchants/* endpoints (list, detail, associate, disassociate) + modified POST/PATCH merchant endpoints.
  • AdminVenuePicker component + functional Venues section on MerchantDetail.
  • MerchantsAll reshaped to query merchants collection directly.
  • Firestore rules: isMerchantOf() helper + merchants match + venues update rule.
  • Composite index for (status, createdAt) on merchants.
  • OpenAPI spec updated for all new/changed routes.
  • Design + plan docs committed before implementation.

Out of scope (deliberately) ​

These were explicitly deferred during design reviews and will not land in the merchant portal iterations tracked here. Each should get its own project plan when the time comes.

  • Multi-user per merchant (#231) β€” one user β†’ one merchant today; junction table approach needed.
  • Self-service merchant signup (#136) β€” admin-created only for now; claim workflow depends on #136.
  • Zero-knowledge encryption for merchant accounts β€” merchant auth intentionally uses standard Firebase email/password with no ZKE passphrase, because merchants need multi-device access and standard password recovery.
  • Food-court / sub-venue model β€” deliberate non-feature; complex venue hierarchy not planned.
  • Venue deletion flow β€” no delete endpoint today; stale references are a low-probability edge case.

Next candidates ​

Ordered by dependency and value. Items marked (unblocked) became unblocked when merchant-venue association shipped.

  1. Multi-user per merchant (#231) β€” junior items: merchantUsers junction collection, admin UI to add/remove users from a merchant, update isMerchantOf() to use junction. Depends on stable merchantId (now shipped).

  2. Venue onboarding β€” let merchants (or admins on their behalf) add a net-new venue that isn't in the existing OSM-sourced directory. Produces a venues doc with source: 'merchant', pending admin approval. Was "Path 2" from Q3 in the association design spec. Depends on venue association (now shipped).

  3. Merchant analytics read β€” /auth/admin/merchants/:merchantId/analytics pulling from BigQuery or the analytics-api. Depends on stable merchantId + venueId references (now shipped).

  4. Firestore rules: merchant self-read β€” let authenticated merchant users read their own merchants/{merchantId} doc (today only admins can). Unblocks a future merchant-facing portal outside the admin app.

  5. Offers UI β€” create/edit/delete β€” functional offer management in the admin app. AdSlot components and OfferForm exist; the gap is CRUD endpoints on offers collection and wiring the form to save. (unblocked β€” depends on stable merchantId, now shipped)

  6. Consumer-app tether β€” surface active offers in the consumer web app's venue view and dashboard. Depends on Offers UI (#5 above) and stable venue↔merchant references. (unblocked β€” venue association now shipped)


Deferred (longer-horizon) ​

  • Self-service merchant onboarding β€” public signup flow, invite link, email verification, admin approval step. Needs #136 complete first.
  • Merchant-facing dashboard (standalone) β€” break merchant experience out of the admin app into its own surface, or a deep-linked view. Currently merchants sign into the admin app; long-term that's awkward.
  • Offer scheduling and targeting β€” time-based activation, audience filters (proximity, gender, age). Post-MVP.
  • Revenue / billing β€” connecting offers to impressions/redemptions for billing purposes. Needs analytics pipeline first.

Built with VitePress