Inspiration

In live selling, the first "mine" in the comments wins the item. In the Philippines, buyers who say "mine" and never pay even have a name: joy miners (PhilSTAR Life). The seller is left chasing an unpaid "mine" while the next buyer waits.

What it does

Hawker reads a live-sale chat in English, Pidgin or Taglish, turns each "mine" into a timed hold with its own PayPal invoice, and passes an unpaid hold to the next buyer.

  • The seller goes live anywhere and pins the stall link. Buyers claim on the stall, then pay on PayPal. A helper watches every hold on the desk.
  • Holds are granted in the order comments arrived, checked against the catalog, with 3:00 to pay in the demo and no partial payments.
  • A size whose units are all paid for is sold: there's no line to join, and anyone still waiting when the last one is paid for ends Passed, told why.
  • Hawker reads each invoice's status from PayPal. There is no mark-as-paid button and no seller override. When the timer runs out, Hawker asks PayPal first: a paid invoice can't be cancelled, and PayPal refuses with CANNOT_CANCEL_PAID_INVOICE.
  • The seller's ledger is built in AG Studio, with Hawker's own widgets and an agent that re-reads PayPal before it says who still owes.
  • Every other ending can be attempted live from the landing page, and is refused: 9 attempts, at PayPal and in the database.

How we built it

  • Reading. A regex fast path runs first. Anything it can't read goes to one model client: Groq qwen/qwen3.8-27b, failing over to Gemini gemini-3.5-flash-lite, with a timeout, retries and a log line per call. The model only proposes a parse; plain code commits holds in arrival order and answers anything unknown with a clarifying reply.
  • Settling. Each hold gets its own invoice through the PayPal Invoicing API (sandbox) with allow_partial_payment: false. Payment truth is a status read: open invoices are re-read every 8 seconds. At the deadline Hawker re-reads the invoice; PAID is never passed, and anything else is cancelled at PayPal and offered to the next buyer with a new invoice.
  • Guarding. A Postgres trigger makes an ended hold final; the only later write it allows is linking a passed hold to the next buyer's, once.
  • The ledger. AG Studio with Hawker's Invoice Pad theme, three custom widgets (Stamp filter, Two endings, Who owes now) in Studio's Compose menu, and Hawker's agent as the primary agent in Studio's agent framework. Its tools: who_owes_now re-reads each open invoice from PayPal, ledger_totals counts from the ledger rows, and add_breakdown_chart builds a chart in code. It hands other dashboard edits to Studio's lead agent, and Studio's built-in agents run on Hawker's model client.
  • Next.js 16, React 19, TypeScript, Tailwind 4, Neon Postgres, Render. 108 tests; CI runs lint, typecheck, tests and the build on every push.

Challenges we ran into

  • Sandbox webhooks never arrived in our testing, so Hawker never trusts them: payment truth is PayPal's status read, and PAID shows 8–13 seconds after the buyer pays.
  • A payment in the last seconds. We paid an invoice 1.4 seconds before its deadline. At expiry Hawker re-read the invoice, found it unpaid, cancelled it and stamped Passed; PayPal then refused the in-flight payment, and the invoice reads cancelled with nothing paid. Paid 12 seconds before the deadline, the copy ended Paid.
  • Free model tiers. Groq's free tier refuses a single turn above its per-minute window, and AG Studio's built-in agents send turns of 5,000–30,000 tokens, so long turns go to Gemini. A built-in agent on a small free model once reported a chart it never added, so the common dashboard action is a deterministic tool, and the agent may only claim a delegated change the lead agent reports.
  • Taglish. Groq once read "sakin na lang yung L po" as a question for the seller: no hold, the safe failure. It's now a case in the eval.

Accomplishments that we're proud of

  • The rule holds at three layers: code re-reads PayPal before it passes a hold, PayPal refuses to cancel a paid invoice, and the database refuses to change an ended hold. All nine forbidden endings are refused live, and anyone can press the button.
  • On 63 labelled comments, the regex path alone gets 25 right and misses 18 real claims; with the model the pipeline got 63 / 63, with 0 phantom claims (62 / 63 on an earlier run the same day, when Gemini read one bit of chatter as a question).

What we learned

PayPal is the authority on payment, so read its status rather than trust events or a seller's button. And the AI should propose while code commits: the model reads what a buyer meant; it never decides who gets an item.

What's next for Hawker

Reading TikTok, Facebook and Instagram Live comments directly, which needs each platform's approval; a pilot with a seller on live PayPal; and more than one store.

Built With

Share this project:

Updates

Submission history