atendentepro 0.3.0__py3-none-any.whl → 0.5.2__py3-none-any.whl
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- atendentepro/README.md +651 -74
- atendentepro/__init__.py +17 -3
- atendentepro/agents/__init__.py +11 -0
- atendentepro/agents/answer.py +1 -2
- atendentepro/agents/escalation.py +510 -0
- atendentepro/agents/feedback.py +961 -0
- atendentepro/license.py +3 -3
- atendentepro/network.py +115 -15
- atendentepro/prompts/__init__.py +10 -0
- atendentepro/prompts/answer.py +2 -3
- atendentepro/prompts/escalation.py +190 -0
- atendentepro/prompts/feedback.py +232 -0
- {atendentepro-0.3.0.dist-info → atendentepro-0.5.2.dist-info}/METADATA +58 -44
- {atendentepro-0.3.0.dist-info → atendentepro-0.5.2.dist-info}/RECORD +18 -14
- {atendentepro-0.3.0.dist-info → atendentepro-0.5.2.dist-info}/licenses/LICENSE +3 -3
- {atendentepro-0.3.0.dist-info → atendentepro-0.5.2.dist-info}/WHEEL +0 -0
- {atendentepro-0.3.0.dist-info → atendentepro-0.5.2.dist-info}/entry_points.txt +0 -0
- {atendentepro-0.3.0.dist-info → atendentepro-0.5.2.dist-info}/top_level.txt +0 -0
atendentepro/license.py
CHANGED
|
@@ -77,7 +77,7 @@ class LicenseNotActivatedError(LicenseError):
|
|
|
77
77
|
"║ export ATENDENTEPRO_LICENSE_KEY='seu-token' ║\n"
|
|
78
78
|
"║ ║\n"
|
|
79
79
|
"║ Para obter um token, entre em contato: ║\n"
|
|
80
|
-
"║ 📧 contato@
|
|
80
|
+
"║ 📧 contato@monkai.com.br ║\n"
|
|
81
81
|
"║ ║\n"
|
|
82
82
|
"╚══════════════════════════════════════════════════════════════╝\n"
|
|
83
83
|
)
|
|
@@ -96,7 +96,7 @@ class LicenseExpiredError(LicenseError):
|
|
|
96
96
|
f"║ Sua licença expirou em: {expiration:<36}║\n"
|
|
97
97
|
f"║ ║\n"
|
|
98
98
|
f"║ Para renovar, entre em contato: ║\n"
|
|
99
|
-
f"║ 📧 contato@
|
|
99
|
+
f"║ 📧 contato@monkai.com.br ║\n"
|
|
100
100
|
f"║ ║\n"
|
|
101
101
|
f"╚══════════════════════════════════════════════════════════════╝\n"
|
|
102
102
|
)
|
|
@@ -115,7 +115,7 @@ class InvalidTokenError(LicenseError):
|
|
|
115
115
|
"║ O token fornecido não é válido. ║\n"
|
|
116
116
|
"║ ║\n"
|
|
117
117
|
"║ Verifique se o token está correto ou entre em contato: ║\n"
|
|
118
|
-
"║ 📧 contato@
|
|
118
|
+
"║ 📧 contato@monkai.com.br ║\n"
|
|
119
119
|
"║ ║\n"
|
|
120
120
|
"╚══════════════════════════════════════════════════════════════╝\n"
|
|
121
121
|
)
|
atendentepro/network.py
CHANGED
|
@@ -20,6 +20,8 @@ from atendentepro.agents import (
|
|
|
20
20
|
create_confirmation_agent,
|
|
21
21
|
create_usage_agent,
|
|
22
22
|
create_onboarding_agent,
|
|
23
|
+
create_escalation_agent,
|
|
24
|
+
create_feedback_agent,
|
|
23
25
|
TriageAgent,
|
|
24
26
|
FlowAgent,
|
|
25
27
|
InterviewAgent,
|
|
@@ -28,6 +30,8 @@ from atendentepro.agents import (
|
|
|
28
30
|
ConfirmationAgent,
|
|
29
31
|
UsageAgent,
|
|
30
32
|
OnboardingAgent,
|
|
33
|
+
EscalationAgent,
|
|
34
|
+
FeedbackAgent,
|
|
31
35
|
)
|
|
32
36
|
from atendentepro.guardrails import get_guardrails_for_agent, set_guardrails_client
|
|
33
37
|
from atendentepro.license import require_activation
|
|
@@ -60,6 +64,8 @@ class AgentNetwork:
|
|
|
60
64
|
confirmation: Optional[ConfirmationAgent] = None
|
|
61
65
|
usage: Optional[UsageAgent] = None
|
|
62
66
|
onboarding: Optional[OnboardingAgent] = None
|
|
67
|
+
escalation: Optional[EscalationAgent] = None
|
|
68
|
+
feedback: Optional[FeedbackAgent] = None
|
|
63
69
|
|
|
64
70
|
templates_root: Optional[Path] = None
|
|
65
71
|
current_client: str = "standard"
|
|
@@ -68,35 +74,67 @@ class AgentNetwork:
|
|
|
68
74
|
"""Get list of all configured agents."""
|
|
69
75
|
agents = []
|
|
70
76
|
for attr in ["triage", "flow", "interview", "answer", "knowledge",
|
|
71
|
-
"confirmation", "usage", "onboarding"]:
|
|
77
|
+
"confirmation", "usage", "onboarding", "escalation", "feedback"]:
|
|
72
78
|
agent = getattr(self, attr, None)
|
|
73
79
|
if agent:
|
|
74
80
|
agents.append(agent)
|
|
75
81
|
return agents
|
|
82
|
+
|
|
83
|
+
def add_escalation_to_all(self) -> None:
|
|
84
|
+
"""Add escalation agent as handoff to all other agents."""
|
|
85
|
+
if not self.escalation:
|
|
86
|
+
return
|
|
87
|
+
|
|
88
|
+
for agent in self.get_all_agents():
|
|
89
|
+
if agent != self.escalation and self.escalation not in agent.handoffs:
|
|
90
|
+
agent.handoffs.append(self.escalation)
|
|
91
|
+
|
|
92
|
+
def add_feedback_to_all(self) -> None:
|
|
93
|
+
"""Add feedback agent as handoff to all other agents."""
|
|
94
|
+
if not self.feedback:
|
|
95
|
+
return
|
|
96
|
+
|
|
97
|
+
for agent in self.get_all_agents():
|
|
98
|
+
if agent != self.feedback and self.feedback not in agent.handoffs:
|
|
99
|
+
agent.handoffs.append(self.feedback)
|
|
76
100
|
|
|
77
101
|
|
|
78
102
|
def create_standard_network(
|
|
79
103
|
templates_root: Path,
|
|
80
104
|
client: str = "standard",
|
|
81
105
|
include_onboarding: bool = False,
|
|
106
|
+
include_escalation: bool = True,
|
|
107
|
+
include_feedback: bool = True,
|
|
108
|
+
escalation_channels: str = "",
|
|
109
|
+
feedback_protocol_prefix: str = "TKT",
|
|
110
|
+
feedback_brand_color: str = "#4A90D9",
|
|
111
|
+
feedback_brand_name: str = "Atendimento",
|
|
82
112
|
custom_tools: Optional[Dict[str, List]] = None,
|
|
83
113
|
) -> AgentNetwork:
|
|
84
114
|
"""
|
|
85
115
|
Create a standard agent network with proper handoff configuration.
|
|
86
116
|
|
|
87
117
|
This creates the default network configuration with:
|
|
88
|
-
- Triage -> Flow, Confirmation, Knowledge, Usage
|
|
89
|
-
- Flow -> Interview, Triage
|
|
90
|
-
- Interview -> Answer
|
|
91
|
-
- Answer -> Triage,
|
|
92
|
-
- Confirmation -> Triage
|
|
93
|
-
- Knowledge -> Triage
|
|
94
|
-
- Usage -> Triage
|
|
118
|
+
- Triage -> Flow, Confirmation, Knowledge, Usage, Escalation, Feedback
|
|
119
|
+
- Flow -> Interview, Triage, Escalation, Feedback
|
|
120
|
+
- Interview -> Answer, Escalation, Feedback
|
|
121
|
+
- Answer -> Triage, Escalation, Feedback
|
|
122
|
+
- Confirmation -> Triage, Escalation, Feedback
|
|
123
|
+
- Knowledge -> Triage, Escalation, Feedback
|
|
124
|
+
- Usage -> Triage, Escalation, Feedback
|
|
125
|
+
- Escalation -> Triage
|
|
126
|
+
- Feedback -> Triage, Escalation
|
|
95
127
|
|
|
96
128
|
Args:
|
|
97
129
|
templates_root: Root directory for template configurations.
|
|
98
130
|
client: Client key to load configurations for.
|
|
99
131
|
include_onboarding: Whether to include the onboarding agent.
|
|
132
|
+
include_escalation: Whether to include the escalation agent (default True).
|
|
133
|
+
include_feedback: Whether to include the feedback agent (default True).
|
|
134
|
+
escalation_channels: Description of available escalation channels.
|
|
135
|
+
feedback_protocol_prefix: Prefix for ticket protocols (e.g., "SAC", "TKT").
|
|
136
|
+
feedback_brand_color: Brand color for feedback emails.
|
|
137
|
+
feedback_brand_name: Brand name for feedback emails.
|
|
100
138
|
custom_tools: Optional dict of custom tools by agent name.
|
|
101
139
|
|
|
102
140
|
Returns:
|
|
@@ -217,14 +255,72 @@ def create_standard_network(
|
|
|
217
255
|
guardrails=get_guardrails_for_agent("Usage Agent", templates_root),
|
|
218
256
|
)
|
|
219
257
|
|
|
258
|
+
# Create escalation agent if requested
|
|
259
|
+
escalation = None
|
|
260
|
+
if include_escalation:
|
|
261
|
+
escalation = create_escalation_agent(
|
|
262
|
+
escalation_channels=escalation_channels,
|
|
263
|
+
tools=tools.get("escalation", []),
|
|
264
|
+
guardrails=get_guardrails_for_agent("Escalation Agent", templates_root),
|
|
265
|
+
)
|
|
266
|
+
|
|
267
|
+
# Create feedback agent if requested
|
|
268
|
+
feedback = None
|
|
269
|
+
if include_feedback:
|
|
270
|
+
feedback = create_feedback_agent(
|
|
271
|
+
protocol_prefix=feedback_protocol_prefix,
|
|
272
|
+
email_brand_color=feedback_brand_color,
|
|
273
|
+
email_brand_name=feedback_brand_name,
|
|
274
|
+
tools=tools.get("feedback", []),
|
|
275
|
+
guardrails=get_guardrails_for_agent("Feedback Agent", templates_root),
|
|
276
|
+
)
|
|
277
|
+
|
|
220
278
|
# Configure handoffs
|
|
221
|
-
|
|
222
|
-
|
|
223
|
-
|
|
224
|
-
|
|
225
|
-
|
|
226
|
-
|
|
227
|
-
|
|
279
|
+
triage_handoffs = [flow, confirmation, knowledge, usage]
|
|
280
|
+
flow_handoffs = [interview, triage]
|
|
281
|
+
confirmation_handoffs = [triage]
|
|
282
|
+
knowledge_handoffs = [triage]
|
|
283
|
+
usage_handoffs = [triage]
|
|
284
|
+
interview_handoffs = [answer]
|
|
285
|
+
answer_handoffs = [triage] # Answer só volta para Triage (não faz sentido voltar para Interview)
|
|
286
|
+
escalation_handoffs = [triage]
|
|
287
|
+
feedback_handoffs = [triage]
|
|
288
|
+
|
|
289
|
+
# Add escalation to all agents if enabled
|
|
290
|
+
if escalation:
|
|
291
|
+
triage_handoffs.append(escalation)
|
|
292
|
+
flow_handoffs.append(escalation)
|
|
293
|
+
confirmation_handoffs.append(escalation)
|
|
294
|
+
knowledge_handoffs.append(escalation)
|
|
295
|
+
usage_handoffs.append(escalation)
|
|
296
|
+
interview_handoffs.append(escalation)
|
|
297
|
+
answer_handoffs.append(escalation)
|
|
298
|
+
if feedback:
|
|
299
|
+
feedback_handoffs.append(escalation)
|
|
300
|
+
|
|
301
|
+
# Add feedback to all agents if enabled
|
|
302
|
+
if feedback:
|
|
303
|
+
triage_handoffs.append(feedback)
|
|
304
|
+
flow_handoffs.append(feedback)
|
|
305
|
+
confirmation_handoffs.append(feedback)
|
|
306
|
+
knowledge_handoffs.append(feedback)
|
|
307
|
+
usage_handoffs.append(feedback)
|
|
308
|
+
interview_handoffs.append(feedback)
|
|
309
|
+
answer_handoffs.append(feedback)
|
|
310
|
+
if escalation:
|
|
311
|
+
escalation_handoffs.append(feedback)
|
|
312
|
+
|
|
313
|
+
triage.handoffs = triage_handoffs
|
|
314
|
+
flow.handoffs = flow_handoffs
|
|
315
|
+
confirmation.handoffs = confirmation_handoffs
|
|
316
|
+
knowledge.handoffs = knowledge_handoffs
|
|
317
|
+
usage.handoffs = usage_handoffs
|
|
318
|
+
interview.handoffs = interview_handoffs
|
|
319
|
+
answer.handoffs = answer_handoffs
|
|
320
|
+
if escalation:
|
|
321
|
+
escalation.handoffs = escalation_handoffs
|
|
322
|
+
if feedback:
|
|
323
|
+
feedback.handoffs = feedback_handoffs
|
|
228
324
|
|
|
229
325
|
network = AgentNetwork(
|
|
230
326
|
triage=triage,
|
|
@@ -234,6 +330,8 @@ def create_standard_network(
|
|
|
234
330
|
knowledge=knowledge,
|
|
235
331
|
confirmation=confirmation,
|
|
236
332
|
usage=usage,
|
|
333
|
+
escalation=escalation,
|
|
334
|
+
feedback=feedback,
|
|
237
335
|
templates_root=templates_root,
|
|
238
336
|
current_client=client,
|
|
239
337
|
)
|
|
@@ -309,6 +407,8 @@ def create_custom_network(
|
|
|
309
407
|
"confirmation": network.confirmation,
|
|
310
408
|
"usage": network.usage,
|
|
311
409
|
"onboarding": network.onboarding,
|
|
410
|
+
"escalation": network.escalation,
|
|
411
|
+
"feedback": network.feedback,
|
|
312
412
|
}
|
|
313
413
|
|
|
314
414
|
# Apply custom handoff configuration
|
atendentepro/prompts/__init__.py
CHANGED
|
@@ -8,6 +8,8 @@ from .answer import get_answer_prompt, AnswerPromptBuilder
|
|
|
8
8
|
from .knowledge import get_knowledge_prompt, KnowledgePromptBuilder
|
|
9
9
|
from .confirmation import get_confirmation_prompt, ConfirmationPromptBuilder
|
|
10
10
|
from .onboarding import get_onboarding_prompt, OnboardingPromptBuilder
|
|
11
|
+
from .escalation import get_escalation_prompt, EscalationPromptBuilder, ESCALATION_INTRO
|
|
12
|
+
from .feedback import get_feedback_prompt, FeedbackPromptBuilder, FEEDBACK_INTRO
|
|
11
13
|
|
|
12
14
|
__all__ = [
|
|
13
15
|
# Triage
|
|
@@ -31,5 +33,13 @@ __all__ = [
|
|
|
31
33
|
# Onboarding
|
|
32
34
|
"get_onboarding_prompt",
|
|
33
35
|
"OnboardingPromptBuilder",
|
|
36
|
+
# Escalation
|
|
37
|
+
"get_escalation_prompt",
|
|
38
|
+
"EscalationPromptBuilder",
|
|
39
|
+
"ESCALATION_INTRO",
|
|
40
|
+
# Feedback
|
|
41
|
+
"get_feedback_prompt",
|
|
42
|
+
"FeedbackPromptBuilder",
|
|
43
|
+
"FEEDBACK_INTRO",
|
|
34
44
|
]
|
|
35
45
|
|
atendentepro/prompts/answer.py
CHANGED
|
@@ -22,7 +22,6 @@ ANSWER_INTRO = """
|
|
|
22
22
|
Você é um agente de resposta especializado.
|
|
23
23
|
Você deverá responder à pergunta do usuário usando o template de resposta configurado.
|
|
24
24
|
Use as informações coletadas durante a entrevista para fornecer uma resposta precisa e útil.
|
|
25
|
-
Se precisar de mais informações, transfira para o interview_agent com orientações objetivas.
|
|
26
25
|
Sempre que concluir uma resposta válida ao usuário, assim que receber qualquer outra pergunta, transfira a conversa para o triage_agent.
|
|
27
26
|
Nas mensagens ao usuário, utilize linguagem natural e evite revelar processos internos, etapas de análise ou nomes de agentes.
|
|
28
27
|
"""
|
|
@@ -76,7 +75,7 @@ ANSWER_OUTPUT = """
|
|
|
76
75
|
1. Envie a mensagem final ao usuário.
|
|
77
76
|
2. Em seguida, com qualquer pergunta, transfira a conversa para o triage_agent.
|
|
78
77
|
- (Raciocínio interno) Se a resposta não estiver completa:
|
|
79
|
-
1.
|
|
78
|
+
1. Solicite as informações faltantes diretamente ao usuário de forma clara e objetiva.
|
|
80
79
|
- (Mensagem ao usuário) Resuma apenas o necessário, sem mencionar transferências, ferramentas ou processos internos.
|
|
81
80
|
"""
|
|
82
81
|
|
|
@@ -95,7 +94,7 @@ def get_answer_prompt(answer_template: str = "") -> str:
|
|
|
95
94
|
[ROUTE]
|
|
96
95
|
- (Raciocínio interno) Responder à pergunta do usuário usando o template de resposta como guia:
|
|
97
96
|
{answer_template}
|
|
98
|
-
- (Raciocínio interno) Identifique se todas as informações obrigatórias do template estão preenchidas. Se faltar algo,
|
|
97
|
+
- (Raciocínio interno) Identifique se todas as informações obrigatórias do template estão preenchidas. Se faltar algo, solicite diretamente ao usuário.
|
|
99
98
|
"""
|
|
100
99
|
|
|
101
100
|
return "\n".join([
|
|
@@ -0,0 +1,190 @@
|
|
|
1
|
+
# -*- coding: utf-8 -*-
|
|
2
|
+
"""Escalation Agent prompts."""
|
|
3
|
+
|
|
4
|
+
from __future__ import annotations
|
|
5
|
+
|
|
6
|
+
from dataclasses import dataclass
|
|
7
|
+
from typing import Optional
|
|
8
|
+
|
|
9
|
+
|
|
10
|
+
@dataclass
|
|
11
|
+
class EscalationPromptBuilder:
|
|
12
|
+
"""Builder for Escalation Agent prompts."""
|
|
13
|
+
|
|
14
|
+
escalation_triggers: str = ""
|
|
15
|
+
escalation_channels: str = ""
|
|
16
|
+
|
|
17
|
+
def build(self) -> str:
|
|
18
|
+
"""Build the complete escalation agent prompt."""
|
|
19
|
+
return get_escalation_prompt(
|
|
20
|
+
escalation_triggers=self.escalation_triggers,
|
|
21
|
+
escalation_channels=self.escalation_channels,
|
|
22
|
+
)
|
|
23
|
+
|
|
24
|
+
|
|
25
|
+
ESCALATION_INTRO = """
|
|
26
|
+
Você é o Agente de Escalação, responsável por transferir conversas para atendimento humano.
|
|
27
|
+
Sua função é garantir que o usuário receba o suporte adequado quando o sistema automatizado não consegue resolver.
|
|
28
|
+
"""
|
|
29
|
+
|
|
30
|
+
ESCALATION_MODULES = """
|
|
31
|
+
Deve seguir as seguintes etapas de forma sequencial (todas são raciocínio interno; não exponha nada ao usuário):
|
|
32
|
+
[READ] - [IDENTIFY] - [COLLECT] - [VERIFY] - [REGISTER] - [INFORM] - [OUTPUT]
|
|
33
|
+
"""
|
|
34
|
+
|
|
35
|
+
ESCALATION_READ = """
|
|
36
|
+
[READ]
|
|
37
|
+
- (Raciocínio interno) Leia cuidadosamente a mensagem do usuário e identifique o motivo da escalação.
|
|
38
|
+
- (Raciocínio interno) Verifique se é uma solicitação explícita ou se foi encaminhado por outro agente.
|
|
39
|
+
"""
|
|
40
|
+
|
|
41
|
+
ESCALATION_IDENTIFY = """
|
|
42
|
+
[IDENTIFY]
|
|
43
|
+
- (Raciocínio interno) Identifique o tipo de escalação necessária:
|
|
44
|
+
- Solicitação explícita do usuário ("quero falar com um humano")
|
|
45
|
+
- Tópico não coberto pelo sistema
|
|
46
|
+
- Frustração ou insatisfação do usuário
|
|
47
|
+
- Problema complexo que requer análise humana
|
|
48
|
+
- Questões jurídicas, financeiras ou críticas
|
|
49
|
+
"""
|
|
50
|
+
|
|
51
|
+
ESCALATION_COLLECT = """
|
|
52
|
+
[COLLECT]
|
|
53
|
+
- (Raciocínio interno) Colete as informações necessárias para a escalação:
|
|
54
|
+
- Nome do usuário (se ainda não coletado)
|
|
55
|
+
- Telefone ou email para contato
|
|
56
|
+
- Motivo resumido da escalação
|
|
57
|
+
- Nível de urgência (normal ou urgente)
|
|
58
|
+
"""
|
|
59
|
+
|
|
60
|
+
ESCALATION_VERIFY = """
|
|
61
|
+
[VERIFY]
|
|
62
|
+
- (Raciocínio interno) Verifique o horário de atendimento humano.
|
|
63
|
+
- (Raciocínio interno) Se estiver fora do horário, informe ao usuário e ofereça alternativas.
|
|
64
|
+
- (Raciocínio interno) Se estiver dentro do horário, prossiga com o registro.
|
|
65
|
+
"""
|
|
66
|
+
|
|
67
|
+
ESCALATION_REGISTER = """
|
|
68
|
+
[REGISTER]
|
|
69
|
+
- (Raciocínio interno) Utilize a ferramenta registrar_escalacao para criar o registro.
|
|
70
|
+
- (Raciocínio interno) Anote o número do protocolo gerado para informar ao usuário.
|
|
71
|
+
"""
|
|
72
|
+
|
|
73
|
+
ESCALATION_INFORM = """
|
|
74
|
+
[INFORM]
|
|
75
|
+
- (Raciocínio interno) Prepare a mensagem final com:
|
|
76
|
+
- Confirmação de que a escalação foi registrada
|
|
77
|
+
- Número do protocolo
|
|
78
|
+
- Canais de atendimento disponíveis
|
|
79
|
+
- Tempo estimado de espera (se aplicável)
|
|
80
|
+
"""
|
|
81
|
+
|
|
82
|
+
ESCALATION_OUTPUT = """
|
|
83
|
+
[OUTPUT]
|
|
84
|
+
- (Mensagem ao usuário) Informe que a solicitação de atendimento humano foi registrada.
|
|
85
|
+
- (Mensagem ao usuário) Forneça o protocolo e os canais de contato de forma clara.
|
|
86
|
+
- (Mensagem ao usuário) Seja empático e tranquilize o usuário sobre o atendimento.
|
|
87
|
+
"""
|
|
88
|
+
|
|
89
|
+
DEFAULT_ESCALATION_TRIGGERS = """
|
|
90
|
+
## Gatilhos de Escalação
|
|
91
|
+
|
|
92
|
+
### Solicitações Explícitas
|
|
93
|
+
- "quero falar com um humano"
|
|
94
|
+
- "atendente humano"
|
|
95
|
+
- "falar com uma pessoa"
|
|
96
|
+
- "transferir para atendente"
|
|
97
|
+
- "pessoa real"
|
|
98
|
+
|
|
99
|
+
### Frustração do Usuário
|
|
100
|
+
- "você não está me ajudando"
|
|
101
|
+
- "isso não resolve"
|
|
102
|
+
- "já tentei de tudo"
|
|
103
|
+
- "não funciona"
|
|
104
|
+
- "estou frustrado"
|
|
105
|
+
|
|
106
|
+
### Tópicos Não Cobertos
|
|
107
|
+
- Questões jurídicas
|
|
108
|
+
- Cancelamento de contrato
|
|
109
|
+
- Reclamações formais graves
|
|
110
|
+
- Processos administrativos
|
|
111
|
+
"""
|
|
112
|
+
|
|
113
|
+
|
|
114
|
+
def get_escalation_prompt(
|
|
115
|
+
escalation_triggers: str = "",
|
|
116
|
+
escalation_channels: str = "",
|
|
117
|
+
) -> str:
|
|
118
|
+
"""
|
|
119
|
+
Build the escalation agent prompt.
|
|
120
|
+
|
|
121
|
+
Args:
|
|
122
|
+
escalation_triggers: Custom triggers for escalation.
|
|
123
|
+
escalation_channels: Available channels (phone, email, chat).
|
|
124
|
+
|
|
125
|
+
Returns:
|
|
126
|
+
Complete escalation agent prompt.
|
|
127
|
+
"""
|
|
128
|
+
intro = f"""
|
|
129
|
+
{ESCALATION_INTRO}
|
|
130
|
+
|
|
131
|
+
## Seu Papel
|
|
132
|
+
|
|
133
|
+
Você ajuda os usuários que precisam de atendimento humano:
|
|
134
|
+
1. **Identificar** o motivo da escalação
|
|
135
|
+
2. **Coletar** informações de contato
|
|
136
|
+
3. **Verificar** disponibilidade de atendimento
|
|
137
|
+
4. **Registrar** a solicitação
|
|
138
|
+
5. **Informar** o protocolo e canais disponíveis
|
|
139
|
+
|
|
140
|
+
## Quando Escalar
|
|
141
|
+
|
|
142
|
+
- O usuário solicita explicitamente falar com um humano
|
|
143
|
+
- O tópico não é coberto pelo sistema automatizado
|
|
144
|
+
- O usuário demonstra frustração ou insatisfação
|
|
145
|
+
- O problema é complexo e requer análise humana
|
|
146
|
+
- Questões jurídicas, financeiras ou críticas
|
|
147
|
+
"""
|
|
148
|
+
|
|
149
|
+
triggers = escalation_triggers or DEFAULT_ESCALATION_TRIGGERS
|
|
150
|
+
|
|
151
|
+
channels_section = ""
|
|
152
|
+
if escalation_channels:
|
|
153
|
+
channels_section = f"""
|
|
154
|
+
## Canais Disponíveis
|
|
155
|
+
|
|
156
|
+
{escalation_channels}
|
|
157
|
+
"""
|
|
158
|
+
|
|
159
|
+
guidelines = """
|
|
160
|
+
## Diretrizes
|
|
161
|
+
|
|
162
|
+
- Seja empático e demonstre que entende a necessidade do usuário
|
|
163
|
+
- Nunca force o usuário a usar o sistema automatizado se ele quer um humano
|
|
164
|
+
- Colete apenas as informações essenciais para o contato
|
|
165
|
+
- Informe claramente o tempo estimado de resposta
|
|
166
|
+
- Se fora do horário, ofereça alternativas (callback, email, etc.)
|
|
167
|
+
|
|
168
|
+
## Tom de Voz
|
|
169
|
+
|
|
170
|
+
- Seja compreensivo e profissional
|
|
171
|
+
- Valide os sentimentos do usuário
|
|
172
|
+
- Transmita confiança de que o problema será resolvido
|
|
173
|
+
- Evite frases como "infelizmente" ou "não é possível"
|
|
174
|
+
"""
|
|
175
|
+
|
|
176
|
+
return "\n".join([
|
|
177
|
+
intro,
|
|
178
|
+
triggers,
|
|
179
|
+
channels_section,
|
|
180
|
+
guidelines,
|
|
181
|
+
ESCALATION_MODULES,
|
|
182
|
+
ESCALATION_READ,
|
|
183
|
+
ESCALATION_IDENTIFY,
|
|
184
|
+
ESCALATION_COLLECT,
|
|
185
|
+
ESCALATION_VERIFY,
|
|
186
|
+
ESCALATION_REGISTER,
|
|
187
|
+
ESCALATION_INFORM,
|
|
188
|
+
ESCALATION_OUTPUT,
|
|
189
|
+
])
|
|
190
|
+
|