MSPs / operators
Sell CCaaS seats with tenant isolation and a sync screen instead of SSH.
Seat product · ESL control plane
A configurable contact-center and hosted PBX product: PostgreSQL is the source of truth, NestJS is the decision layer, and FreeSWITCH executes via ESL — with three keys: super-admin, tenant admin and agent.
Built for operators, MSPs and CCaaS product teams who need to sell seats without SSH into XML for every extension.
Operators who sell contact-center seats without a control plane typically hit:
One platform: Tenant admin saves objects → PostgreSQL → FreeSWITCH Sync (dialplan/SIP) → agent registers SIP.js → preview next lead → originate → disposition
Agents register from the browser when an extension is linked. Originate can also go through the API. Live events flow ESL → Nest → Socket.IO so screens move without a refresh.
SIP.js over WSS to FreeSWITCH; NestJS ESL for originate and events. Carrier path selectable in the quote builder.
flowchart TB
subgraph ui [Vue 3 SPA]
SA[Super-admin]
TA[Tenant admin]
AG[Agent workspace]
end
API[NestJS /api/v1 JWT RBAC]
PG[(PostgreSQL tenants PBX campaigns)]
FS[FreeSWITCH ESL]
SA --> API
TA --> API
AG --> API
API --> PG
API --> FS
FS --> AG
This product is a productized delivery of the documented engineering case study — evidence stays on this page so you do not have to guess what was shipped.




Full case study with video and FAQ →
Configure this scope & send RFQ →
Sell CCaaS seats with tenant isolation and a sync screen instead of SSH.
Own NestJS + Vue + FreeSWITCH — not Genesys or Five9 seats.
Super-admin, tenant admin and agent on one login.
Live channels, reports groups and campaign assignment in the SPA.
| Traditional setup | This product direction |
|---|---|
| SSH into FreeSWITCH XML | Admin UI writes PostgreSQL; Sync pushes dialplan/SIP |
| One office-PC password | JWT + RolesGuard; agents never see Tenants or Sync |
| Campaign CSV next to the PBX | Leads and campaigns on the same rail as extensions |
| Silent SIP failure | Banner: ask admin to link an extension |
Designed to let operators sell seats without snowflake XML per tenant. Case-study screens are a quiet lab capture — zeros are not a published SLA. Runtime is agent preview dial, not a claimed server-side predictive engine.
Estimates are scope-based planning figures — not binding quotes. Taxes, carrier deposits, DIDs and third-party AI usage are scoped in discovery.
No. You own NestJS, Vue, PostgreSQL and FreeSWITCH. UnifiedPBX.in is not a public CCaaS tenant login.
No. Asterisk 22 UnifiedPBX is a different product (Next.js + AMI/ARI). This CCaaS path is Vue 3 + ESL + SIP.js.
Campaign types include inbound, outbound and blended. Runtime in this build is agent preview: next lead, then SIP.js or originate. A backend auto-dialer worker is scoped separately.
Yes. Super-admin owns tenants; tenant admin owns PBX and campaigns; agents get the workspace. Isolation is tenant-scoped APIs plus FreeSWITCH directory variables.
Yes. BYOC, own SIP, Twilio, Telnyx and Sinch are in the quote builder.
Yes. SIP.js registers over WSS when an extension is linked to the user.
Managed VPS, your AWS/GCP/Azure account, or on-prem — selectable in the estimator.
CRM pop / webhook is an optional requirement in the quote builder; discovery confirms APIs.