- CallerContextService: added invalidateCache(leadId) method
- CallerResolutionController: POST /api/caller/invalidate-context
endpoint — frontend calls after appointment mutations to bust
stale AI context cache
Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
The build() method previously fetched Lead and Appointments in parallel.
When the input patientId was empty (outbound dial, first-time linkage),
the appointments query was skipped even though the Lead record in the DB
had a valid patientId. Now fetches Lead first, reads its patientId, then
fetches appointments/calls/activities in parallel with the correct ID.
Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
- CallerContextService: fetches lead profile, appointments, call history,
activities in parallel. Caches in Redis (5 min TTL). Renders as
human-readable KB section — no UUIDs exposed to the LLM.
- Caller resolution controller: prewarms context cache on resolve
(fire-and-forget) so the AI stream has a cache hit.
- AI chat stream: injects caller context into system prompt KB instead
of raw Lead ID. LLM answers patient questions from context, no tool
calls needed for current caller data.
- Eliminates UUID hallucination: LLM never sees leadId or patientId,
can't pass wrong ID to wrong tool parameter.
Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
Audited all 23 sidecar create-mutation call sites; 7 were missing the
top-level data.name field that the platform uses as record title:
- caller-resolution.service.ts createPatient — full name from first/last
- maint.controller.ts createPatient (backfill-lead-patient-links) — same
- widget.service.ts createPatient (chat path + booking path) — full name
- widget.service.ts createAppointment — "<Patient> — <date>"
- worklist/missed-queue.service.ts createCall — "Missed — <phone>"
- rules-engine/actions/escalate.action.ts createPerformanceAlert —
"<agent>: <message> (<value>)"
- supervisor/agent-history.service.ts createAgentEvent / createAgentSession
Cosmetic only — the app fetches fullName/agentName for display, so
end users never saw "Untitled". Fixes platform-side admin browsing.
Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
Return empty IDs for unrecognized numbers instead of creating lead+patient.
Per PRD: 'System will not identify the patient — no summary shown.'
Records are created when agent books appointment or logs enquiry.
Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
- POST /api/caller/invalidate — clears Redis cache for a phone number
- WorklistController: resolves agent name from login cache (avoids currentUser query)
- AuthController: caches agent name in Redis during login (keyed by token suffix)
- WorklistModule: imports AuthModule (forwardRef for circular dep)
Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>