The Problem
A Vietnamese Facebook seller runs the day out of three tabs. Ads Manager for the campaigns. The Page inbox and comment threads for the customers. A spreadsheet for the orders. Nothing talks to anything else.
At 500 conversations a day across three Pages, that arrangement stops working. Comments under a boosted post go unanswered while staff are deep in the inbox. Order details get retyped into a spreadsheet, and a digit goes missing. Nobody can say which ad actually produced revenue, only which one produced clicks. And in Vietnamese social commerce, a five-minute reply is not a slow reply — it is a lost sale, because the customer already bought from whoever answered first.
The part that hurts quietly is the money. Orders ship COD across several carriers, each with its own portal, its own fee schedule and its own payout cycle. When a carrier remits less than the order was worth, there is no practical way to notice. The discrepancy just becomes the cost of doing business.
What It Does
One Inbox for Everything Facebook
Inbox messages, comments, livestream chat and ad conversations all land in the same place, tagged by where they came from. Staff get auto-assigned, conversations carry the customer's full order history, and permissions are role-based so a salesperson sees what they need and nothing more.
Changes propagate over ElectricSQL, so when one person opens a thread everyone else sees it instantly. No two staff answering the same customer.
An AI Assistant Your Team Trains
The assistant reads the conversation and drafts a reply in Vietnamese — product availability, pricing, shipping, order status. It handles the way people actually type: slang, teencode, regional phrasing.
Nothing sends on its own. A draft appears, your staff approves, edits or rejects it. Every edit is captured, and those corrections feed a learning loop that updates how the assistant answers next time. The team that uses it is the team that trains it, without writing a single scripted flow.
Orders and Delivery in One Path
An order created in a conversation goes to the carrier from the same screen — GHN, TMC Express or SSC.eco — and its tracking status comes back into the order record. Stock levels read live from the SSC warehouse, so what staff quote is what actually exists.
COD Reconciled Automatically
For every shipment, the platform holds three numbers: what the order was worth, what the carrier says it collected, and what it deducted in fees. When those disagree, the order is flagged. What used to be an invisible leak becomes a list you can act on.
Ads Tied to Actual Orders
Campaigns, posts and livestreams are managed in-platform, and conversion events are sent back to Facebook to bring CPA down. Because the conversation, the order and the ad all live in one database, campaign reporting shows revenue produced — not engagement.
Built for Vietnamese Addresses
Vietnam's move from three-level to two-level administrative addresses broke the address field in most systems. Ours maps old to new automatically, with a confidence score on every match, so orders keep flowing to the right place without manual correction.
Results
How It's Built
| Layer | Choice | Why |
|---|---|---|
| Frontend | TanStack Start + React 19 | Full-stack type safety with server-side rendering |
| Backend | Python + FastAPI | Async-first, for thousands of concurrent platform webhooks |
| AI pipeline | LangGraph + pgvector | Checkpointed agent graph; hybrid vector and keyword retrieval over the catalogue |
| Real-time | ElectricSQL | Postgres changes streamed to every connected client |
| Realtime fan-out | Elixir + Phoenix | Handles connection volume the API layer shouldn't |
| Queue | Redis + arq workers | Keeps LLM work off the request path |
| Database | PostgreSQL + Drizzle ORM | ACID for anything touching money; type-safe queries |
| Auth | BetterAuth | Multi-tenant orgs, roles and per-organization permission overrides |
| Hosting | Self-hosted, multi-region | Your data stays on infrastructure you control |

