Update app.py
Browse files
app.py
CHANGED
|
@@ -28,12 +28,12 @@ GEMINI_API_URL = f"https://generativelanguage.googleapis.com/v1beta/models/gemin
|
|
| 28 |
CONFIG = {
|
| 29 |
"max_retry_attempts": 3,
|
| 30 |
"retry_delay": 5,
|
| 31 |
-
"timeout": 30,
|
| 32 |
"temperatura": 0.2,
|
| 33 |
"max_tokens": 12882
|
| 34 |
}
|
| 35 |
|
| 36 |
-
rate_limiter = RateLimiter(max_calls=100, period=60)
|
| 37 |
|
| 38 |
DICAS_OAB_MELHORADO = {
|
| 39 |
"Endereçamento": "Em relações de consumo, prefira o foro do domicílio do autor (Art. 101, I, CDC). Exemplo: 'Excelentíssimo Senhor Juiz de Direito da Vara Cível da Comarca de [Cidade do Autor]'.",
|
|
@@ -183,7 +183,7 @@ def estruturar_prompt_analise(caso, peticao, modo_treinamento=False):
|
|
| 183 |
3. Pontos Positivos (Liste pelo menos 3 aspectos bem executados com justificativa legal detalhada, incluindo artigos, súmulas ou precedentes aplicáveis)
|
| 184 |
4. Pontos a Melhorar (Liste todos os problemas encontrados em ordem de gravidade, com explicação detalhada, base legal e impacto na nota)
|
| 185 |
5. Análise Específica dos Requisitos:
|
| 186 |
-
-
|
| 187 |
- Qualificação das partes (Art. 319, II, CPC)
|
| 188 |
- Fatos e fundamentos jurídicos (Art. 319, III, CPC; Art. 186, CC)
|
| 189 |
- Pedidos com especificações (Art. 319, IV, CPC)
|
|
@@ -300,35 +300,40 @@ def chamar_api(prompt):
|
|
| 300 |
except Exception as e:
|
| 301 |
return f"❌ Erro inesperado: {str(e)}"
|
| 302 |
|
| 303 |
-
def
|
|
|
|
| 304 |
if not caso.strip():
|
| 305 |
-
return "⚠️ Forneça o caso da banca."
|
| 306 |
if peticao_arquivo is not None:
|
|
|
|
| 307 |
peticao_conteudo = process_file(peticao_arquivo)
|
| 308 |
if peticao_conteudo.startswith("❌") or peticao_conteudo.startswith("⚠️"):
|
| 309 |
-
return peticao_conteudo
|
| 310 |
else:
|
| 311 |
peticao_conteudo = peticao_texto or ""
|
| 312 |
if not peticao_conteudo.strip():
|
| 313 |
-
return "⚠️ Forneça uma petição."
|
| 314 |
|
|
|
|
| 315 |
problemas = validar_peticao_basica(peticao_conteudo)
|
| 316 |
aviso_validacao = f"### Validação Inicial\n\n" + "\n".join(problemas) + "\n\n" if problemas else ""
|
| 317 |
|
| 318 |
cache_key = f"{caso[:50]}|{peticao_conteudo[:50]}|{modo_treinamento}"
|
| 319 |
if cache_key in CORRECAO_CACHE:
|
| 320 |
-
return aviso_validacao + CORRECAO_CACHE[cache_key]
|
| 321 |
|
|
|
|
| 322 |
prompt_analise = estruturar_prompt_analise(caso, peticao_conteudo, modo_treinamento)
|
| 323 |
analise = chamar_api(prompt_analise)
|
| 324 |
if "❌" in analise or "⏱️" in analise:
|
| 325 |
-
return aviso_validacao + analise
|
| 326 |
analise_formatada = formatar_correcao(analise)
|
| 327 |
|
|
|
|
| 328 |
prompt_peticao = estruturar_prompt_peticao_corrigida(caso, peticao_conteudo)
|
| 329 |
peticao_corrigida = chamar_api(prompt_peticao)
|
| 330 |
if "❌" in peticao_corrigida or "⏱️" in peticao_corrigida:
|
| 331 |
-
return aviso_validacao + analise_formatada + "\n\n" + peticao_corrigida
|
| 332 |
|
| 333 |
peticao_corrigida = pos_corrigir_peticao(peticao_corrigida)
|
| 334 |
|
|
@@ -342,7 +347,7 @@ def corrigir_peticao(caso, peticao_texto=None, peticao_arquivo=None, modo_treina
|
|
| 342 |
if len(HISTORICO) > 10:
|
| 343 |
HISTORICO.pop(0)
|
| 344 |
CORRECAO_CACHE[cache_key] = analise_formatada
|
| 345 |
-
return aviso_validacao + analise_formatada
|
| 346 |
|
| 347 |
def formatar_correcao(texto):
|
| 348 |
linhas = texto.split('\n')
|
|
@@ -367,7 +372,7 @@ def formatar_correcao(texto):
|
|
| 367 |
if "Nota Final" in texto_formatado:
|
| 368 |
import re
|
| 369 |
nota_pattern = r"### Nota Final.*?(\d+[.,]\d+|\d+)"
|
| 370 |
-
match = re.search(nota_pattern,
|
| 371 |
if match:
|
| 372 |
nota = match.group(1)
|
| 373 |
texto_formatado = texto_formatado.replace(f"### ⭐ Nota Final\n\n{nota}", f"### ⭐ Nota Final: {nota}/10\n\n")
|
|
@@ -507,7 +512,6 @@ def interface_gradio():
|
|
| 507 |
gr.Markdown("# 📝 Corretor Avançado de Petições Iniciais (Critérios OAB)")
|
| 508 |
gr.Markdown("⚠️ Nota: Devido a limites da API, pode haver atrasos ou erros em muitas requisições rápidas.")
|
| 509 |
|
| 510 |
-
# Campo de status adicionado logo no início
|
| 511 |
estado_processamento = gr.Textbox(label="Status do Processamento", value="Aguardando...", interactive=False)
|
| 512 |
|
| 513 |
with gr.Row():
|
|
@@ -593,52 +597,16 @@ def interface_gradio():
|
|
| 593 |
outputs=historico_output
|
| 594 |
)
|
| 595 |
|
| 596 |
-
# Configuração do botão de correção
|
| 597 |
btn_texto.click(
|
| 598 |
-
fn=
|
| 599 |
-
inputs=[caso_input, peticao_texto, modo_treinamento],
|
| 600 |
-
outputs=[resultado_output, estado_processamento]
|
| 601 |
-
_js="""() => {
|
| 602 |
-
let btn = document.querySelector('button[id*="btn_texto"]');
|
| 603 |
-
btn.disabled = true;
|
| 604 |
-
btn.innerText = '⏳ Corrigindo...';
|
| 605 |
-
document.querySelector('#estado_processamento textarea').value = '⏳ Processando sua petição...';
|
| 606 |
-
return [];
|
| 607 |
-
}"""
|
| 608 |
-
).then(
|
| 609 |
-
fn=lambda x: (x, "✅ Correção concluída!"),
|
| 610 |
-
inputs=[resultado_output],
|
| 611 |
-
outputs=[resultado_output, estado_processamento],
|
| 612 |
-
_js="""() => {
|
| 613 |
-
let btn = document.querySelector('button[id*="btn_texto"]');
|
| 614 |
-
btn.disabled = false;
|
| 615 |
-
btn.innerText = '🔍 Corrigir Petição (Texto)';
|
| 616 |
-
return [];
|
| 617 |
-
}"""
|
| 618 |
)
|
| 619 |
-
|
| 620 |
-
# Configuração do botão de correção de arquivo com feedback
|
| 621 |
btn_arquivo.click(
|
| 622 |
-
fn=
|
| 623 |
-
inputs=[caso_input, peticao_arquivo, modo_treinamento],
|
| 624 |
-
outputs=[resultado_output, estado_processamento]
|
| 625 |
-
_js="""() => {
|
| 626 |
-
let btn = document.querySelector('button[id*="btn_arquivo"]');
|
| 627 |
-
btn.disabled = true;
|
| 628 |
-
btn.innerText = '⏳ Corrigindo...';
|
| 629 |
-
document.querySelector('#estado_processamento textarea').value = '⏳ Processando seu arquivo...';
|
| 630 |
-
return [];
|
| 631 |
-
}"""
|
| 632 |
-
).then(
|
| 633 |
-
fn=lambda x: (x, "✅ Correção concluída!"),
|
| 634 |
-
inputs=[resultado_output],
|
| 635 |
-
outputs=[resultado_output, estado_processamento],
|
| 636 |
-
_js="""() => {
|
| 637 |
-
let btn = document.querySelector('button[id*="btn_arquivo"]');
|
| 638 |
-
btn.disabled = false;
|
| 639 |
-
btn.innerText = '🔍 Corrigir Petição (Arquivo)';
|
| 640 |
-
return [];
|
| 641 |
-
}"""
|
| 642 |
)
|
| 643 |
|
| 644 |
clear_btn.click(
|
|
|
|
| 28 |
CONFIG = {
|
| 29 |
"max_retry_attempts": 3,
|
| 30 |
"retry_delay": 5,
|
| 31 |
+
"timeout": 30,
|
| 32 |
"temperatura": 0.2,
|
| 33 |
"max_tokens": 12882
|
| 34 |
}
|
| 35 |
|
| 36 |
+
rate_limiter = RateLimiter(max_calls=100, period=60)
|
| 37 |
|
| 38 |
DICAS_OAB_MELHORADO = {
|
| 39 |
"Endereçamento": "Em relações de consumo, prefira o foro do domicílio do autor (Art. 101, I, CDC). Exemplo: 'Excelentíssimo Senhor Juiz de Direito da Vara Cível da Comarca de [Cidade do Autor]'.",
|
|
|
|
| 183 |
3. Pontos Positivos (Liste pelo menos 3 aspectos bem executados com justificativa legal detalhada, incluindo artigos, súmulas ou precedentes aplicáveis)
|
| 184 |
4. Pontos a Melhorar (Liste todos os problemas encontrados em ordem de gravidade, com explicação detalhada, base legal e impacto na nota)
|
| 185 |
5. Análise Específica dos Requisitos:
|
| 186 |
+
- Endereçamento e qualificação do juízo (Art. 319, I, CPC; Art. 101, I, CDC se aplicável)
|
| 187 |
- Qualificação das partes (Art. 319, II, CPC)
|
| 188 |
- Fatos e fundamentos jurídicos (Art. 319, III, CPC; Art. 186, CC)
|
| 189 |
- Pedidos com especificações (Art. 319, IV, CPC)
|
|
|
|
| 300 |
except Exception as e:
|
| 301 |
return f"❌ Erro inesperado: {str(e)}"
|
| 302 |
|
| 303 |
+
def corrigir_peticao_com_progresso(caso, peticao_texto=None, peticao_arquivo=None, modo_treinamento=False):
|
| 304 |
+
# Função wrapper para fornecer feedback de progresso
|
| 305 |
if not caso.strip():
|
| 306 |
+
return "⚠️ Forneça o caso da banca.", "⚠️ Erro: Caso não fornecido."
|
| 307 |
if peticao_arquivo is not None:
|
| 308 |
+
yield "", "⏳ Processando arquivo..."
|
| 309 |
peticao_conteudo = process_file(peticao_arquivo)
|
| 310 |
if peticao_conteudo.startswith("❌") or peticao_conteudo.startswith("⚠️"):
|
| 311 |
+
return peticao_conteudo, "⚠️ Erro no processamento do arquivo."
|
| 312 |
else:
|
| 313 |
peticao_conteudo = peticao_texto or ""
|
| 314 |
if not peticao_conteudo.strip():
|
| 315 |
+
return "⚠️ Forneça uma petição.", "⚠️ Erro: Petição não fornecida."
|
| 316 |
|
| 317 |
+
yield "", "⏳ Validando petição..."
|
| 318 |
problemas = validar_peticao_basica(peticao_conteudo)
|
| 319 |
aviso_validacao = f"### Validação Inicial\n\n" + "\n".join(problemas) + "\n\n" if problemas else ""
|
| 320 |
|
| 321 |
cache_key = f"{caso[:50]}|{peticao_conteudo[:50]}|{modo_treinamento}"
|
| 322 |
if cache_key in CORRECAO_CACHE:
|
| 323 |
+
return aviso_validacao + CORRECAO_CACHE[cache_key], "✅ Resultado recuperado do cache."
|
| 324 |
|
| 325 |
+
yield "", "⏳ Analisando petição com a API..."
|
| 326 |
prompt_analise = estruturar_prompt_analise(caso, peticao_conteudo, modo_treinamento)
|
| 327 |
analise = chamar_api(prompt_analise)
|
| 328 |
if "❌" in analise or "⏱️" in analise:
|
| 329 |
+
return aviso_validacao + analise, "⚠️ Erro na análise da API."
|
| 330 |
analise_formatada = formatar_correcao(analise)
|
| 331 |
|
| 332 |
+
yield "", "⏳ Gerando petição corrigida..."
|
| 333 |
prompt_peticao = estruturar_prompt_peticao_corrigida(caso, peticao_conteudo)
|
| 334 |
peticao_corrigida = chamar_api(prompt_peticao)
|
| 335 |
if "❌" in peticao_corrigida or "⏱️" in peticao_corrigida:
|
| 336 |
+
return aviso_validacao + analise_formatada + "\n\n" + peticao_corrigida, "⚠️ Erro ao gerar petição corrigida."
|
| 337 |
|
| 338 |
peticao_corrigida = pos_corrigir_peticao(peticao_corrigida)
|
| 339 |
|
|
|
|
| 347 |
if len(HISTORICO) > 10:
|
| 348 |
HISTORICO.pop(0)
|
| 349 |
CORRECAO_CACHE[cache_key] = analise_formatada
|
| 350 |
+
return aviso_validacao + analise_formatada, "✅ Correção concluída!"
|
| 351 |
|
| 352 |
def formatar_correcao(texto):
|
| 353 |
linhas = texto.split('\n')
|
|
|
|
| 372 |
if "Nota Final" in texto_formatado:
|
| 373 |
import re
|
| 374 |
nota_pattern = r"### Nota Final.*?(\d+[.,]\d+|\d+)"
|
| 375 |
+
match = re.search(nota_pattern, texto_formatada, re.DOTALL)
|
| 376 |
if match:
|
| 377 |
nota = match.group(1)
|
| 378 |
texto_formatado = texto_formatado.replace(f"### ⭐ Nota Final\n\n{nota}", f"### ⭐ Nota Final: {nota}/10\n\n")
|
|
|
|
| 512 |
gr.Markdown("# 📝 Corretor Avançado de Petições Iniciais (Critérios OAB)")
|
| 513 |
gr.Markdown("⚠️ Nota: Devido a limites da API, pode haver atrasos ou erros em muitas requisições rápidas.")
|
| 514 |
|
|
|
|
| 515 |
estado_processamento = gr.Textbox(label="Status do Processamento", value="Aguardando...", interactive=False)
|
| 516 |
|
| 517 |
with gr.Row():
|
|
|
|
| 597 |
outputs=historico_output
|
| 598 |
)
|
| 599 |
|
| 600 |
+
# Configuração do botão de correção com progresso
|
| 601 |
btn_texto.click(
|
| 602 |
+
fn=corrigir_peticao_com_progresso,
|
| 603 |
+
inputs=[caso_input, peticao_texto, peticao_arquivo, modo_treinamento],
|
| 604 |
+
outputs=[resultado_output, estado_processamento]
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 605 |
)
|
|
|
|
|
|
|
| 606 |
btn_arquivo.click(
|
| 607 |
+
fn=corrigir_peticao_com_progresso,
|
| 608 |
+
inputs=[caso_input, peticao_texto, peticao_arquivo, modo_treinamento],
|
| 609 |
+
outputs=[resultado_output, estado_processamento]
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 610 |
)
|
| 611 |
|
| 612 |
clear_btn.click(
|