File size: 3,670 Bytes
faf41ff
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
# utils.py

import pandas as pd
import re
import os
import requests
import matplotlib.font_manager as fm
from pydantic import BaseModel, Field, ConfigDict
from typing import List, Tuple, Optional
from fpdf import FPDF
from datetime import datetime

# --- MODELOS PYDANTIC ---
class Historico(BaseModel):
    entradas: List[Tuple[str, str]] = []

    def adicionar(self, pergunta: str, resposta: str):
        if pergunta and resposta:
            self.entradas.append((pergunta, resposta))

# --- FUNÇÕES DE PROCESSAMENTO DE TEXTO E DADOS ---
def descricao_colunas(df: pd.DataFrame) -> str:
    descricao = "\n".join([f"`{col}`: {str(df[col].dtype)}" for col in df.columns])
    return "Colunas do DataFrame:\n" + descricao

def limpar_codigo_pandas(codigo: str) -> str:
    codigo = re.sub(r'```(?:python)?\n?', '', codigo)
    codigo = re.sub(r'```', '', codigo)
    linhas = [linha.strip() for linha in codigo.split('\n') if linha.strip()]
    codigo_filtrado = [l for l in linhas if not (l.startswith('#') or 'resposta:' in l.lower())]
    return codigo_filtrado[-1] if codigo_filtrado else ""

# --- LÓGICA DE PREPARAÇÃO DE FONTES ---
FONT_PATH = ""
def setup_font():
    global FONT_PATH
    FONT_NAME_TO_FIND = "DejaVu Sans"
    try:
        FONT_PATH = fm.findfont(FONT_NAME_TO_FIND, fallback_to_default=True)
        if not os.path.exists(FONT_PATH): raise FileNotFoundError
        print(f"✅ Fonte encontrada localmente: {FONT_PATH}")
    except Exception:
        print(f"⚠️ Fonte '{FONT_NAME_TO_FIND}' não encontrada. Baixando alternativa (Roboto)...")
        FONT_FILE_NAME = "Roboto-Regular.ttf"
        FONT_URL = "https://github.com/google/fonts/raw/main/ofl/roboto/Roboto-Regular.ttf"
        if not os.path.exists(FONT_FILE_NAME):
            try:
                response = requests.get(FONT_URL)
                response.raise_for_status()
                with open(FONT_FILE_NAME, "wb") as f: f.write(response.content)
                FONT_PATH = FONT_FILE_NAME
                print(f"✅ Fonte alternativa baixada!")
            except Exception as e:
                print(f"❌ FALHA CRÍTICA ao baixar fonte: {e}")
                FONT_PATH = ""
        else:
            FONT_PATH = FONT_FILE_NAME
            print(f"✅ Fonte alternativa já existe.")
    return FONT_PATH

# --- GERAÇÃO DE PDF ---
def gerar_pdf_report(historico: Historico, font_path: str):
    if not historico or not historico.entradas:
        print("⚠️ Tentativa de gerar PDF com histórico vazio.")
        return None
    if not font_path or not os.path.exists(font_path):
        print(f"❌ Erro ao gerar PDF: Arquivo da fonte não encontrado em '{font_path}'.")
        return None

    try:
        timestamp = datetime.now().strftime("%Y%m%d_%H%M%S")
        caminho_pdf = f"relatorio_consultas_{timestamp}.pdf"
        pdf = FPDF()
        pdf.add_page()
        pdf.add_font('CustomFont', '', font_path, uni=True)
        pdf.set_font('CustomFont', '', 16)
        pdf.cell(0, 10, "Relatório de Consultas ao CSV", ln=True, align="C")
        pdf.ln(10)

        for i, (pergunta, resposta) in enumerate(historico.entradas, 1):
            pdf.set_font('CustomFont', '', 12)
            pdf.multi_cell(0, 8, f"Pergunta {i}: {pergunta}")
            pdf.ln(2)
            pdf.set_font('CustomFont', '', 10)
            pdf.multi_cell(0, 6, f"Resposta: {resposta}")
            pdf.ln(8)
            pdf.cell(0, 0, '', 'T'); pdf.ln(8)

        pdf.output(caminho_pdf)
        print(f"✅ PDF gerado: {caminho_pdf}")
        return caminho_pdf
    except Exception as e:
        print(f"❌ Erro crítico ao gerar PDF: {e}")
        return None