gigafibre-fsm/docs/ARCHITECTURE.md
louispaulb 607ea54b5c refactor: reduce token count, DRY code, consolidate docs
Backend services:
- targo-hub: extract deepGetValue to helpers.js, DRY disconnect reasons
  lookup map, compact CAPABILITIES, consolidate vision.js prompts/schemas,
  extract dispatch scoring weights, trim section dividers across 9 files
- modem-bridge: extract getSession() helper (6 occurrences), resetIdleTimer(),
  consolidate DM query factory, fix duplicate username fill bug, trim headers
  (server.js -36%, tplink-session.js -47%, docker-compose.yml -57%)

Frontend:
- useWifiDiagnostic: extract THRESHOLDS const, split processDiagnostic into
  6 focused helpers (processOnlineStatus, processWanIPs, processRadios,
  processMeshNodes, processClients, checkRadioIssues)
- EquipmentDetail: merge duplicate ROLE_LABELS, remove verbose comments

Documentation (17 → 13 files, -1,400 lines):
- New consolidated README.md (architecture, services, dependencies, auth)
- Merge ECOSYSTEM-OVERVIEW into ARCHITECTURE.md
- Merge MIGRATION-PLAN + ARCHITECTURE-COMPARE + FIELD-GAP + CHANGELOG → MIGRATION.md
- Merge COMPETITIVE-ANALYSIS into PLATFORM-STRATEGY.md
- Update ROADMAP.md with current phase status
- Delete CONTEXT.md (absorbed into README)

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-04-13 08:39:58 -04:00

14 KiB

Gigafibre FSM -- Architecture

1. Service Map

                          ┌──────────────────┐
                          │   Authentik SSO   │
                          │  auth.targo.ca    │
                          └────────┬─────────┘
                                   │ forwardAuth
                                   ▼
                          ┌──────────────────┐
                          │     Traefik       │
                          │  :80 / :443       │
                          │  Let's Encrypt    │
                          └──┬───┬───┬───┬───┘
          ┌──────────────────┘   │   │   └───────────────────┐
          ▼                      ▼   ▼                       ▼
 ┌────────────────┐  ┌──────────────────┐  ┌──────────────────┐
 │  Ops App       │  │  ERPNext v16     │  │  targo-hub       │
 │  /ops/ (nginx) │  │  erp.gigafibre.ca│  │  msg.gigafibre.ca│
 └───────┬────────┘  └───────┬──────────┘  └──┬───┬───┬──────┘
         │ /api/* proxy      │                 │   │   │
         │ (token injected)  │                 │   │   │
         └───────────────────┘                 │   │   │
                                               │   │   │
          ┌────────────────────────────────────┘   │   └──────┐
          ▼                                        ▼          ▼
 ┌──────────────────┐                ┌────────────────┐  ┌─────────┐
 │  GenieACS NBI    │                │  Twilio API    │  │ Stripe  │
 │  10.5.2.115:7557 │                │  SMS + Voice   │  │ Payments│
 └───────┬──────────┘                └────────────────┘  └─────────┘
         │ CWMP (TR-069)
         ▼
 ┌──────────────────┐       ┌──────────────────┐
 │  CPE / ONT       │◀──────│  modem-bridge    │
 │  TP-Link XX230v  │ HTTPS │  :3301 (internal)│
 │  Raisecom HT803G │       │  Playwright      │
 └──────────────────┘       └──────────────────┘

Docker networks: proxy (Traefik-facing services), erpnext (ERPNext cluster + targo-hub).


2. Docker Containers

Host: 96.125.196.67 (Proxmox VM, Ubuntu 24.04). All services on one Docker host.

Container Image Port Network Purpose
ops-frontend nginx:alpine 80 proxy Ops SPA + ERPNext API proxy
targo-hub node:20-alpine 3300 proxy, erpnext API gateway: SSE, SMS, devices, dispatch
erpnext-frontend-1 frappe/erpnext 8080 erpnext ERPNext web + API
erpnext-backend frappe/erpnext 8000 erpnext Frappe worker
erpnext-db-1 postgres:16 5432 erpnext ERPNext + targo_cache DBs
modem-bridge node:20-slim+Chromium 3301 proxy Headless browser for ONU web GUI
oktopus-acs-1 oktopusp/acs 9292 oktopus USP/TR-369 controller
oktopus-mongo-1 mongo:7 27017 oktopus Oktopus datastore
fn-routr fonoster/routr-one -- fonoster VoIP SIP routing
fn-asterisk fonoster/asterisk -- fonoster PBX media server
fn-postgres postgres:16 -- fonoster Fonoster DB
authentik-* goauthentik -- authentik SSO provider (staff + client)
apps-www-gigafibre-1 nginx -- proxy Marketing website

3. Ops App (Quasar v2 / Vue 3 / Vite)

Served from /opt/ops-app/ via ops-frontend nginx at erp.gigafibre.ca/ops/.

Directory Structure

Directory Files Content
api/ 10 ERPNext CRUD, dispatch, offers, presets, SMS, traccar, OCR, auth, reports
components/ 23 .vue customer/, dispatch/, shared/, layout/
composables/ 41 Domain-specific reactive logic (see below)
modules/dispatch/components/ 13 Timeline, calendar, map, modals, context menus
pages/ 16 Routed page views
stores/ 2 Pinia: auth, dispatch
config/ 8 erpnext, nav, dispatch, ticket-config, hub, table-columns

Pages (16)

DashboardPage, ClientsPage, ClientDetailPage, TicketsPage, DispatchPage, EquipePage, NetworkPage, TelephonyPage, RapportsPage, SettingsPage, OcrPage, AgentFlowsPage, ReportARPage, ReportRevenuPage, ReportTaxesPage, ReportVentesPage

Composables (41) -- grouped by domain

Domain Composables
Scheduling useScheduler, useDragDrop, useBottomPanel, usePeriodNavigation, useAutoDispatch, useBestTech, useJobOffers, useAbsenceResize, useSelection, useUndo, useContextMenus, useTechManagement
Map / GPS useMap, useGpsTracking, useAddressSearch
Phone / SMS usePhone, useConversations
Data useClientData, useDeviceStatus, useSSE, useInlineEdit, useEquipmentActions, usePaymentActions, useSubscriptionActions, useSubscriptionGroups, useLegacySync, useCustomerNotes, usePermissions, usePermissionMatrix, useUserGroups
UI useHelpers, useFormatters, useStatusClasses, useDetailModal, useResourceFilter, useTagManagement, useUnifiedCreate, useScanner, useWifiDiagnostic, useWizardCatalog, useWizardPublish

4. Targo-Hub (Node.js)

Container targo-hub | msg.gigafibre.ca | Port 3300 | 40 modules in lib/

Modules (top 15 by size)

Module Lines Purpose
payments.js 1374 Stripe checkout, PPA cron, webhooks
network-intel.js 1221 Network topology, outage correlation
ai.js 719 Gemini AI integration (tool-calling)
acceptance.js 672 Service acceptance workflows
outage-monitor.js 601 Uptime-Kuma alerts
reports.js 572 Analytics and report generation
tech-mobile.js 562 Lightweight mobile page for technicians
devices.js 551 GenieACS proxy, device summary, poller
contracts.js 548 Contract generation
oktopus.js 545 TR-369/USP controller proxy
agent.js 529 AI SMS agent with tool-calling
conversation.js 499 Conversation persistence
voice-agent.js 457 Inbound voice IVR + WebSocket media
olt-snmp.js 419 OLT SNMP polling, ONU state tracking
checkout.js 399 Customer checkout / catalog API

Plus 25 smaller modules: server, twilio, pbx, dispatch, provision, auth, telephony, ical, modem-bridge, config, helpers, sse, email, otp, magic-link, traccar, vision, device-extractors, device-hosts, oktopus-mqtt, tech-absence-sms, address-search, email-templates, project-templates.

Endpoints -- grouped by domain

SSE / Real-time

Method Path Purpose
GET /sse?topics=... SSE stream (customer, conversations, sms-incoming)
POST /broadcast Push event to SSE clients

SMS / Voice / Telephony

Method Path Purpose
POST /send/sms Send SMS via Twilio
POST /webhook/twilio/sms-incoming Inbound SMS
POST /webhook/twilio/sms-status Delivery status
GET /voice/token Twilio voice JWT
POST /voice/twiml, /voice/status TwiML + call status
POST /voice/inbound, /voice/gather, /voice/connect-agent IVR voice agent
WS /voice/ws Twilio Media Streams (WebSocket)
POST /webhook/3cx/call-event 3CX call events
* /telephony/* Fonoster/Routr SIP CRUD

Devices / Network

Method Path Purpose
GET /devices/lookup?serial=X GenieACS device search (3 fallback strategies)
GET /devices/summary Fleet statistics
GET /devices/:id/hosts Connected clients + mesh mapping
POST /devices/:id/tasks Send task (reboot, refresh)
* /acs/* ACS config export
* /modem/* Proxy to modem-bridge
* /olt/* OLT SNMP stats, ONU lookup, registration
* /oktopus/* TR-369 USP proxy
* /network/* Network intelligence / topology

Dispatch / Scheduling -- /dispatch/* (CRUD, iCal token + feed)

Auth / Customer / Payments -- /auth/* (RBAC), /magic-link/*, /api/checkout|catalog|otp|order|address (customer flow), /payments/* + /webhook/stripe (Stripe + PPA cron), /accept/*, /contract/*

AI / Vision -- /ai/* (Gemini), /agent/* (SMS agent), /vision/barcodes|equipment, /conversations/*

Other -- /traccar/* (GPS), /provision/* (OLT), /reports/*, /t/:token (tech mobile), /webhook/kuma (outage), /health


5. Modem-Bridge (Playwright/Chromium)

Internal-only service on port 3301. Provides REST access to TP-Link ONU web GUIs via headless Chromium. Required because XX230v firmware uses GDPR-encrypted communication (RSA key exchange, AES session, encrypted JSON on /cgi_gdpr?9). Playwright lets the modem's own JavaScript handle all crypto natively rather than re-implementing the protocol.

Method Path Purpose
POST /session/login Authenticate to modem (ip, user, pass)
GET /session/list List active browser sessions
DELETE /session/:ip Close session
GET /modem/:ip/status Device status summary
GET /modem/:ip/dm/:oid Data manager GET
GET /modem/:ip/screenshot PNG screenshot (debug)

Constraints: ~450MB disk (node + Chromium), ~80MB idle + 150MB per session, 512MB Docker limit, sessions auto-expire after 5 min. Bearer token auth, private IP restriction, read-only operations only.


6. Secondary Apps

App Stack URL Purpose
Field App (apps/field/) Vue 3 / Quasar PWA -- Tech mobile: daily tasks, barcode scanner, device diagnostics, offline sync
Client Portal (apps/client/) Vue 3 / Quasar PWA client.gigafibre.ca Self-service: invoices, subscriptions, tickets, catalog. Auth via Authentik
Website (apps/website/) React / Vite / Tailwind www.gigafibre.ca Marketing: products, eligibility check, online ordering, FAQ

7. Data Model (ERPNext Doctypes)

Customer
  ├── Service Location (LOC-#####)
  │     ├── Address + GPS coordinates
  │     ├── OLT port, VLAN, network config
  │     ├── Service Equipment (EQP-#####)
  │     │     ├── Type: ONT / Router / Switch / AP / Decodeur
  │     │     ├── Serial + MAC + manage IP + firmware
  │     │     └── Status: Active / Inactive / En stock / Defectueux / Retourne
  │     └── Service Subscription (SUB-#####)
  │           ├── Plan: Internet / IPTV / VoIP / Bundle
  │           └── Status: pending → active → suspended → cancelled
  └── Sales Invoice → Payment Entry

Dispatch Job
  ├── Customer + Service Location
  ├── Dispatch Technician (assigned + assistants)
  ├── Dispatch Tag Link (tag + level 1-5 + required flag)
  ├── Schedule: date, time, duration, recurrence (RRULE)
  └── Equipment Items / Materials Used

Dispatch Technician
  ├── weekly_schedule (JSON), extra_shifts (JSON)
  └── Dispatch Tag Link (skill level per tag)

Custom fields on standard doctypes: Customer (stripe_id, is_commercial, ppa_enabled), Subscription (actual_price, service_location), Issue (linked dispatch jobs), Sales Invoice (QR code, portal link).


8. External Integrations

Service Purpose Connection
GenieACS (10.5.2.115) TR-069 CPE management NBI REST, LAN, no auth
Twilio SMS + voice REST API, Basic auth
Stripe Payments, checkout API + webhooks
Mapbox Maps, geocoding, routing JS SDK + Directions API
Gemini AI OCR, SMS agent, AI tools REST, Bearer token
Traccar GPS tech tracking REST API, Basic auth
3CX PBX Call history REST API poller (30s)
Fonoster/Routr SIP trunking Direct PostgreSQL
Authentik SSO (staff + client) Traefik forwardAuth + API
n8n Workflow automation HTTP webhooks
Uptime-Kuma Outage monitoring Webhook to targo-hub
Cloudflare DNS for gigafibre.ca REST API

9. Data Flows

Device Diagnostic

Ops App → EquipmentDetail.vue → GET /devices/lookup?serial=X
  → targo-hub → GenieACS NBI (3 fallback strategies) → summarizeDevice()
  → {interfaces, mesh, wifi, opticalStatus, ethernet}

GET /devices/:id/hosts?refresh
  → 2 tasks to CPE (connection_request) → read GenieACS cache
  → clientNodeMap: MAC → {nodeName, band, signal, speed}
  → UI: clients grouped by mesh node (basement, hallway, etc.)

Dispatch Auto-Assign

New job with required tags (e.g., Fibre level 3)
  → useAutoDispatch → useBestTech
  → Filter techs: tag level >= required, available in time slot
  → Sort: lowest adequate skill level first (preserve experts)
  → Assign → SSE broadcast → timeline updates

SMS Notification

Compose in ChatterPanel → POST /send/sms → targo-hub
  → Twilio API → delivery
  → /webhook/twilio/sms-status → SSE broadcast (conv:{token})
  → UI updates delivery status in thread

Inbound SMS → /webhook/twilio/sms-incoming
  → conversation.js (persist) → SSE broadcast (sms-incoming)
  → agent.js (optional AI auto-reply with tool-calling)

Customer Onboarding

Website → /api/address (eligibility check) → /api/catalog
  → /api/checkout (Stripe session) → /webhook/stripe (payment confirmed)
  → ERPNext: create Customer + Service Location + Subscription
  → /api/otp (SMS verification) → magic-link auth
  → provision.js: OLT pre-auth → GenieACS auto-provision on connect