feat(whatsapp): send routes through configured backend - #226
Conversation
Replace the UI mock with protected backend delivery so route sends use production WhatsApp results. Co-authored-by: Cursor <cursoragent@cursor.com>
Give dispatchers clear delivery results with failed driver names and actionable error details. Co-authored-by: Cursor <cursoragent@cursor.com>
Keep export copy and dispatcher-facing send outcomes verified through the browser flow. Co-authored-by: Cursor <cursoragent@cursor.com>
Restore the prior send flow while retaining the Export Routes copy update. Co-authored-by: Cursor <cursoragent@cursor.com>
|
@markboenigk This PR removes the mock data and replaces it with a real call to WhatsApp along with a quick wording change in the UI that Kirill mentioned on Friday. I thought about adding more UI regarding a success/failure popup based on if WhatsApp sent the routes successfully or not to the drivers, but I decided to leave that for a future PR. |
|
@markboenigk I do want to bring up a possible issue flagged by my agent regarding WhatsApp's policy: WhatsApp's 24-hour session / template rule. The backend sends a free-form type: "text" message. WhatsApp Cloud API only allows free-form text inside an open 24-hour customer-service window; outside it, you must use a pre-approved message template. So unsolicited route sends to drivers who haven't recently messaged the business number will be rejected by Graph API and surface as status: "failed". This is a backend/platform constraint, not something this PR introduces, but it will block "cold" sends in production. This could be a problem for production, I believe we need to get a template approved by WhatsApp in order to be able to cold send these messages to drivers. |
Review: send routes through configured backendGood change overall — the secret handling checks out (server-only, Error info is discarded on non-OK responses (medium) Ambiguous "failed" on malformed-but-2xx response (medium) No retry/backoff or timeout (low) Unbounded concurrent fan-out (low) Worth confirming intentional Nice to have: Test coverage is solid (success, backend-500/network/malformed-response failures, missing-env-var rejection, empty-batch) — matches what's described in the PR body. I also reran the checks marked "not rerun after final reversion" ( Nothing here blocks on security grounds — the secret is well-isolated. The error-swallowing and missing-retry points are the ones I'd want addressed before this carries real driver traffic at volume. |
Address PR review by logging failures, retrying transient errors, capping concurrency, treating 2xx without message IDs as sent, and sending a readable stop list instead of raw JSON. Co-authored-by: Cursor <cursoragent@cursor.com>
Co-authored-by: Cursor <cursoragent@cursor.com>
|
Hey @markboenigk, I went ahead and addressed the error handling concerns and formatted the message to match the template I sent over on Slack, although, I think we should discuss this more before sending the template for approval to Meta. |
Avoid duplicate driver messages when a 5xx follows an upstream-accepted WhatsApp POST. Co-authored-by: Cursor <cursoragent@cursor.com>
Summary
Motivation
Changes
to/messagerequest per route to the configured backend, attach the send-secret header, and map returned WhatsApp message IDs to per-route results.Export JSONtoExport Routes, simplify the method description, and update the export modal subtitle.WHATSAPP_SEND_ROUTE_SECRETas a runtime App Hosting secret.Validation
Frontend
npm --prefix app/ui run typechecknpm --prefix app/ui run format:checknpm --prefix app/ui run test -- src/tests/whatsappClient.test.ts src/tests/formatRouteMessage.test.ts— 12 tests passednpm --prefix app/ui run test -- src/tests/exportMethodModal.test.ts— 2 tests passednpm --prefix app/ui run lint- cleannpm --prefix app/ui run test- passednpm --prefix app/ui run test:e2e— Playwright Chromium unavailable locallynpm --prefix app/ui run build— not run in this updatenpm --prefix app/mobile run lint— mobile package unchangednpm --prefix app/mobile run typecheck— mobile package unchangedBackend
Risk
WHATSAPP_SEND_ROUTE_SECRETvalue. Missing runtime configuration prevents sends rather than exposing the secret to the client.Rollout and Recovery
High-Signal PR Checklist