← Back to case studies

20+ franchise brands on one platform

Case Study — Broom

Version: 3.0

Status: Approved

Last updated: 2026-07-06

Type: Prior production system (narrative documentation, source not in this repository)


Overview

Broom is a white-label ride-hailing platform (Brasil Machine instance) powering regional mobility brands across Brazil. A single codebase serves 20+ franchise operators with passenger and driver mobile apps, an operations panel, WhatsApp booking, and multi-gateway payments.

Role: Lead engineer — GraphQL API, mobile app architecture, WhatsApp integration, multi-tenant data model.

Production: api.broom.magicsoft.com.br, painel.broom.magicsoft.site


Business Problem

Regional urban mobility brands (taxi, mototaxi, app-based transport) need on-demand ride services, but building a complete platform — passenger and driver apps, operations panel, payments, notifications — is expensive and slow. Each city or franchise wants its own brand, support channels, and pricing rules without maintaining a separate codebase per operation.


Requirements

CategoryRequirement
White-labelPer-franchise branding, credentials, and pricing
MobilePassenger and driver React Native apps (iOS/Android)
OperationsAdmin panel: franchises, drivers, call center, live metrics
BookingApp, WhatsApp, and call-center channels
PaymentsStripe, Mercado Pago, PayPal, PIX per franchise
MatchingDriver-passenger matching with push and WhatsApp notification
Real-timeLive dashboard: revenue, rides, online drivers

Architecture

Broom uses a multi-app monorepo with a central GraphQL API and React Native + web clients.

ComponentResponsibility
api_machineGraphQL API, webhooks, cron matching and cancellation
passenger_machinePassenger app: map, request, history, wallet
driver_machineDriver app: rides, meter, financials, vehicle
painel_machineAdmin: franchises, drivers, call center, metrics

System Diagram


Technology Stack

LayerTechnology
BackendNode.js, TypeScript, Express, Apollo Server, type-graphql, Prisma 4
MobileReact Native 0.69, Apollo Client, React Navigation
AdminReact 18, PrimeReact, Mapbox GL, Chart.js
DatabasePostgreSQL
Auth / PushFirebase Auth, Firebase Messaging, Notifee
MapsGoogle Maps, Mapbox, Azure Geocoding, Nominatim fallback
PaymentsStripe, Mercado Pago, PayPal, PIX
MessagingWhatsApp Business API, Evolution API, OpenAI gpt-4o-mini
StorageContabo Spaces (S3-compatible)
Jobsnode-cron (matching, cancellation, driver heartbeat)

Key Features

  1. Franchise multi-tenancy — Branding, API keys, payment credentials, Firebase, WhatsApp per franchise
  2. Ride lifecycleAWAITACCEPTED_DRIVERON_ROUTEEMBARKATIONCOMPLETED
  3. WhatsApp booking — Legacy numbered flow + AI intent layer (request_ride, become_driver)
  4. WhatsApp-only driversuse_whatsapp: true with periodic location updates
  5. Call center — Operators create bookings via GraphQL with map address selection
  6. Live dashboard — Revenue, rides, cancellations, online drivers in real time
  7. Dynamic pricing — Base fare + km + minute + peak hour multipliers per franchise/region

Engineering Challenges

Operational multi-tenancy

Each franchise requires Firebase project, payment gateways, WhatsApp instance, and map API keys — dozens of credential fields per tenant.

Driver matching

20-second cron polling instead of event-driven architecture; radius logic (max_meters_request_drivers) with multi-channel notification.

Dual WhatsApp systems

Legacy numbered flow and new AI layer running in parallel during incremental migration.

Drivers without app

WhatsApp-only channel requires periodic location requests instead of continuous GPS.

Geocoding fragmentation

Fallback chain across Google, Mapbox, Azure, and OpenStreetMap for cost and regional availability.


Trade-offs

DecisionChosenAlternativeRationale
API styleGraphQLRESTFlexible queries for mobile apps with varied data needs
MatchingCron polling (20s)Event-driven (Redis/SQS)Simpler ops for current volume; known scale limit
MobileReact NativeNative Swift/KotlinSingle codebase for 20+ brands
WhatsAppDual flow during migrationBig-bang rewriteZero downtime for active franchises
Money storageInteger centsDecimalAvoid floating-point display bugs
Tenant configSingle Franchise modelConfig serviceFaster white-label onboarding

Security

ControlImplementation
AuthenticationFirebase Auth (Google, Apple, email)
API authorizationGraphQL context with franchise + role
Tenant isolationFranchise ID on all operational queries
Payment webhooksSignature verification per gateway
Credential storagePer-franchise env fields; not in client bundles
Admin accessRole flags (is_callcenter, franchise admin)

Performance

AreaApproach
GraphQLField-level resolvers; DataLoader patterns where applied
Matching cron20s interval; configurable driver search radius
Push notificationsFirebase FCM for instant driver alerts
DashboardAggregated queries against PostgreSQL; live refresh
File storageS3-compatible object storage for franchise assets

Scalability

DimensionStrategy
FranchisesShared API; franchise-scoped data and credentials
RidesHorizontal API scaling; stateless GraphQL handlers
MatchingCron bottleneck at high volume — documented migration path to queue
Mobile usersFirebase handles auth scale; CDN for static assets
StorageS3-compatible bucket per environment

Deployment

ComponentURLPlatform
APIapi.broom.magicsoft.com.brCapRover / Docker
Admin panelpainel.broom.magicsoft.siteCapRover / Docker
Mobile appsApp Store / Play StorePer-franchise branded builds
Franchises20+ brandsShared codebase, per-franchise config

Brands include Seu Motorista, ATA MOBI, Bora Lá, MotoboyLeva, Vai de Mob, among others.


Lessons Learned

  1. White-label needs a generous data model — Per-franchise credentials and branding from day one prevent per-client forks.
  2. WhatsApp is a product channel — Booking, registration, and driver operation via chat extend reach beyond the app.
  3. Simple cron works to a point — Polling-based matching is operational but event-driven scales better at volume.
  4. Incremental migration creates visible debt — Two WhatsApp flows coexist; plan deprecation explicitly.
  5. Cents everywhere — Integer money in schema requires discipline across the entire stack.

Screenshots

ScreenLocationDescription
Live dashboardpainel → DashboardRevenue, rides, online drivers
Franchise configpainel → FranchisesBranding, credentials, regions
Active rides mappainel → MonitorReal-time ride tracking
Driver managementpainel → DriversApproval, plans, financials

_Screenshots available on request during technical interviews._


Roadmap (at handoff)

PhaseItemStatus
v1.0App + panel + matchingShipped
v1.5WhatsApp bookingShipped
v2.0AI intent layer on WhatsAppShipped
v2.5Deprecate legacy WhatsApp flowIn progress
v3.0Event-driven matchingPlanned

Relation to NovaDesk

Concepts from Broom that inform NovaDesk:

  • Multi-tenancy by franchise/organization (Auth tenants, HelpDesk workspaces)
  • Well-defined lifecycle states (tickets, SLA)
  • Cron/workers for periodic tasks (Notification Service)
  • Operations panel with live metrics (Analytics Dashboard)
  • Multi-channel integration (chat, email, notifications)