package ai import ( "context" "time" "ai-operator/internal/media" ) type VoiceProvider interface { StartSession(ctx context.Context, config VoiceSessionConfig) error SendAudio(ctx context.Context, chunk media.AudioChunk) error SendToolResult(ctx context.Context, result ToolResult) error Close(ctx context.Context) error Events() <-chan VoiceEvent Stats() VoiceProviderStats } type VoiceSessionConfig struct { CallID string ProviderSessionID string Language string RegionCode string SystemPrompt string InputAudioFormat string OutputAudioFormat string InputSampleRate int OutputSampleRate int Metadata map[string]string } type VoiceEventType string const ( VoiceEventSessionStarted VoiceEventType = "session.started" VoiceEventSessionUpdated VoiceEventType = "session.updated" VoiceEventUserTranscriptDelta VoiceEventType = "user.transcript.delta" VoiceEventUserTranscriptDone VoiceEventType = "user.transcript.done" VoiceEventAssistantTranscriptDelta VoiceEventType = "assistant.transcript.delta" VoiceEventAssistantTranscriptDone VoiceEventType = "assistant.transcript.done" VoiceEventAssistantAudioDelta VoiceEventType = "assistant.audio.delta" VoiceEventAssistantAudioDone VoiceEventType = "assistant.audio.done" VoiceEventToolCall VoiceEventType = "tool.call" VoiceEventInterruption VoiceEventType = "interruption" VoiceEventRateLimitsUpdated VoiceEventType = "rate_limits.updated" VoiceEventError VoiceEventType = "error" VoiceEventClosed VoiceEventType = "closed" ) type VoiceEvent struct { Type VoiceEventType CallID string Text string Audio []byte ToolCall *ToolCall Error string Metadata map[string]any At time.Time } type ToolCall struct { ID string Name string Arguments map[string]any RawArguments string } type ToolResult struct { CallID string ToolCallID string Result any Error string } type VoiceProviderStats struct { InputAudioFrames int64 InputAudioBytes int64 OutputAudioFrames int64 OutputAudioBytes int64 EventsReceived int64 EventsSent int64 ToolCallsReceived int64 Errors int64 StartedAt *time.Time ClosedAt *time.Time }