mirror of
https://dev.azure.com/globalhealthx/EMR/_git/helix-engage-server
synced 2026-04-11 18:08:16 +00:00
- CallEventsService orchestrates: Exotel webhook → lead lookup → AI enrichment → WebSocket push - CallEventsGateway (Socket.IO /call-events namespace) with agent room registration and disposition handling - EnrichedCallEvent/DispositionPayload types for frontend contract - Disposition flow: creates Call record, updates lead status, logs lead activity - Wired ExotelController to forward answered/ended events to CallEventsService - forwardRef used to resolve circular dependency between gateway and service Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
31 lines
1.1 KiB
TypeScript
31 lines
1.1 KiB
TypeScript
import { Controller, Post, Body, Logger, HttpCode } from '@nestjs/common';
|
|
import { ExotelService } from './exotel.service';
|
|
import { CallEventsService } from '../call-events/call-events.service';
|
|
import type { ExotelWebhookPayload } from './exotel.types';
|
|
|
|
@Controller('webhooks/exotel')
|
|
export class ExotelController {
|
|
private readonly logger = new Logger(ExotelController.name);
|
|
|
|
constructor(
|
|
private readonly exotelService: ExotelService,
|
|
private readonly callEventsService: CallEventsService,
|
|
) {}
|
|
|
|
@Post('call-status')
|
|
@HttpCode(200)
|
|
async handleCallStatus(@Body() payload: ExotelWebhookPayload) {
|
|
this.logger.log(`Received Exotel webhook: ${payload.event_details?.event_type}`);
|
|
|
|
const callEvent = this.exotelService.parseWebhook(payload);
|
|
|
|
if (callEvent.eventType === 'answered') {
|
|
await this.callEventsService.handleIncomingCall(callEvent);
|
|
} else if (callEvent.eventType === 'ended') {
|
|
await this.callEventsService.handleCallEnded(callEvent);
|
|
}
|
|
|
|
return { status: 'received' };
|
|
}
|
|
}
|