Files
ai-operator/internal/handoff/detector.go
T

78 lines
2.9 KiB
Go
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
package handoff
import (
"strings"
"unicode"
)
type DetectionResult struct {
Requested bool
Confidence float64
MatchedPhrase string
Language string
ReasonCode string
NeedsClarification bool
}
var handoffPhrases = []string{
"соедините с оператором", "переведите на оператора", "хочу оператора", "нужен оператор",
"позовите оператора", "можно с человеком", "хочу поговорить с человеком", "соедините с человеком",
"переключите на оператора", "не хочу робота", "не хочу ии", "позовите живого человека",
"мне нужен специалист", "соедините с консультантом", "живой оператор", "консультант",
"операторға қосыңыз", "операторға қос", "адаммен сөйлескім келеді", "тірі оператор",
"маман керек", "кеңесші керек", "кеңесшімен сөйлесу", "адамға қосыңыз",
"жасанды интеллект керек емес", "роботпен сөйлеспеймін", "оператор керек",
"human operator", "connect me to operator", "transfer to operator", "speak to human", "live agent",
}
var ambiguousPhrases = []string{"оператор связи", "operator schedule", "call center operator schedule"}
func DetectHandoffRequest(text string, language string) DetectionResult {
n := normalize(text)
if n == "" {
return DetectionResult{Language: language, ReasonCode: "empty_input"}
}
for _, p := range ambiguousPhrases {
if strings.Contains(n, p) {
return DetectionResult{Language: language, MatchedPhrase: p, Confidence: 0.45, ReasonCode: "ambiguous", NeedsClarification: true}
}
}
for _, p := range handoffPhrases {
if strings.Contains(n, p) {
return DetectionResult{Requested: true, Confidence: 0.95, MatchedPhrase: p, Language: language, ReasonCode: "exact_phrase"}
}
}
if hasWord(n, "оператор") || hasWord(n, "operator") {
return DetectionResult{Requested: true, Confidence: 0.80, MatchedPhrase: "оператор", Language: language, ReasonCode: "keyword"}
}
return DetectionResult{Language: language, ReasonCode: "no_match"}
}
func normalize(s string) string {
s = strings.ToLower(strings.TrimSpace(s))
s = strings.ReplaceAll(s, "ё", "е")
var b strings.Builder
lastSpace := false
for _, r := range s {
if unicode.IsLetter(r) || unicode.IsDigit(r) {
b.WriteRune(r)
lastSpace = false
continue
}
if !lastSpace {
b.WriteRune(' ')
lastSpace = true
}
}
return strings.Join(strings.Fields(b.String()), " ")
}
func hasWord(text, word string) bool {
for _, f := range strings.Fields(text) {
if f == word {
return true
}
}
return false
}