0Pricing
AI Agents · Aula

Tratamento de formatos de arquivo: CSV, JSON e TXT

Módulo csv, json.load/dump e codificação segura de texto para ferramentas de agentes.

Tratamento de formatos de arquivo: CSV, JSON e TXT é uma aula grátis de AI Agents no CoddyKit. Esta é a aula 3 de 4. Você pode ler a aula completa abaixo gratuitamente — depois pratica ao vivo no navegador com um editor de código integrado e um tutor de IA 24/7. Faz parte do caminho de aprendizado de AI Agents, e seu progresso é sincronizado entre a web e o app CoddyKit. O curso de AI Agents inclui 4 aulas no total.

Os três formatos de arquivo mais comuns para agentes

Os agentes leem e gravam constantemente três formatos de arquivo: CSV para dados tabulares, JSON para objetos estruturados e texto simples para registros, instruções e relatórios. Cada formato tem requisitos de análise, casos-limite e boas práticas diferentes. O Python oferece excelente suporte integrado para os três.

import csv
import json
from pathlib import Path

# Detect format from extension
def read_data_file(file_path):
    path = Path(file_path)
    if path.suffix == '.csv':
        return read_csv(path)
    elif path.suffix == '.json':
        return read_json(path)
    elif path.suffix == '.txt':
        return path.read_text(encoding='utf-8')
    else:
        raise ValueError(f'Unsupported format: {path.suffix}')

csv.reader — Análise básica de CSV

csv.reader analisa um arquivo CSV linha por linha, retornando cada linha como uma lista de cadeias de caracteres. Ele lida corretamente com campos entre aspas, vírgulas incorporadas e quebras de linha dentro de valores entre aspas — ao contrário da divisão manual por vírgulas, que falha em casos-limite.

import csv

with open('sales.csv', 'w', newline='') as f:
    f.write('product,qty,price\nWidget,3,9.99\nGadget,1,19.99\n')

with open('sales.csv', 'r', encoding='utf-8', newline='') as f:
    reader = csv.reader(f)
    header = next(reader)
    print('Columns:', header)

    for row in reader:
        product = row[0]
        quantity = int(row[1])
        price = float(row[2])
        print(f'{product}: {quantity} units at ${price}')

csv.DictReader — Linha como dicionário

csv.DictReader lê cada linha como um OrderedDict (ou como um dicionário comum no Python 3.8 ou posterior), usando os cabeçalhos das colunas como chaves. Isso é muito mais fácil de usar que a indexação posicional — seu código continua legível mesmo que as colunas sejam reordenadas.

import csv

with open('employees.csv', 'w', newline='') as f:
    f.write('name,department,salary\nAlice,Eng,95000\nBob,Sales,70000\n')

with open('employees.csv', 'r', encoding='utf-8', newline='') as f:
    reader = csv.DictReader(f)
    print('Fields:', reader.fieldnames)

    total_salary = 0
    for row in reader:
        name = row['name']
        department = row['department']
        salary = float(row['salary'])
        total_salary += salary
        print(f'{name} ({department}): ${salary:,.2f}')

    print(f'Total payroll: ${total_salary:,.2f}')

csv.writer e DictWriter — Gravando CSV

Use csv.writer para gravar linhas como listas ou csv.DictWriter para gravar linhas como dicionários. Sempre passe newline='' ao abrir o arquivo — o módulo csv lida sozinho com as terminações de linha para evitar quebras de linha duplicadas no Windows.

import csv

results = [
    {'task_id': 'T001', 'status': 'completed', 'duration_s': 12.5},
    {'task_id': 'T002', 'status': 'failed', 'duration_s': 3.1},
    {'task_id': 'T003', 'status': 'completed', 'duration_s': 45.8},
]

fieldnames = ['task_id', 'status', 'duration_s']

with open('task_results.csv', 'w', newline='', encoding='utf-8') as f:
    writer = csv.DictWriter(f, fieldnames=fieldnames)
    writer.writeheader()  # write column names
    writer.writerows(results)

print('Wrote task_results.csv')

json.load() e json.dump() — E/S de arquivos

Use json.load(file) para analisar um arquivo JSON e json.dump(obj, file) para gravá-lo. Essas funções trabalham com objetos de arquivo. Use json.loads(string) e json.dumps(obj) para cadeias de caracteres. Sempre use indent=2 para obter uma saída legível.

import json

with open('config.json', 'w', encoding='utf-8') as f:
    json.dump({'api_url': 'https://api.example.com', 'timeout': 15}, f)

with open('config.json', 'r', encoding='utf-8') as f:
    config = json.load(f)

print('API URL:', config.get('api_url'))
print('Timeout:', config.get('timeout', 30))

output_data = {
    'run_id': 'abc123',
    'items': [1, 2, 3],
    'meta': {'agent': 'v2', 'model': 'gpt-4o'}
}

with open('output.json', 'w', encoding='utf-8') as f:
    json.dump(
        output_data, f,
        indent=2,
        ensure_ascii=False
    )
print('Written output.json')

Lidando com erros de decodificação de JSON

Arquivos JSON malformados são comuns nos fluxos de processamento de agentes — gravações incompletas, downloads truncados ou problemas de codificação. Sempre envolva json.load() em um bloco try/except e forneça mensagens de erro claras que incluam o caminho do arquivo para facilitar a depuração.

import json
from pathlib import Path

def safe_load_json(file_path):
    path = Path(file_path)
    try:
        with open(path, 'r', encoding='utf-8') as f:
            return json.load(f)
    except json.JSONDecodeError as e:
        print(f'Invalid JSON in {path}: line {e.lineno}, col {e.colno}')
        print(f'  Error: {e.msg}')
        # Show the problem area
        content = path.read_text(encoding='utf-8')
        lines = content.split('\n')
        if e.lineno <= len(lines):
            print(f'  Content: {lines[e.lineno-1][:80]}')
        return None
    except FileNotFoundError:
        print(f'File not found: {path}')
        return None

# --- demo ---
Path('good.json').write_text('{"model": "gpt-4o"}', encoding='utf-8')
Path('bad.json').write_text('{"model": "gpt-4o", }', encoding='utf-8')

print('Loading good.json:', safe_load_json('good.json'))
print('Loading bad.json:', safe_load_json('bad.json'))

Lendo o formato JSONL (linhas JSON)

Muitas APIs de IA e fluxos de dados usam JSONL (linhas JSON) — um objeto JSON por linha. Esse formato permite o processamento em fluxo e é fácil de processar linha a linha sem carregar o arquivo inteiro na memória. Cada linha é um objeto JSON completo e independente.

import json

with open('events.jsonl', 'w', encoding='utf-8') as f:
    f.write('{"event": "start"}\n{"event": "stop"}\nnot json\n')

results = []
with open('events.jsonl', 'r', encoding='utf-8') as f:
    for line_num, line in enumerate(f, 1):
        line = line.strip()
        if not line:
            continue
        try:
            event = json.loads(line)
            results.append(event)
        except json.JSONDecodeError as e:
            print(f'Bad JSON on line {line_num}: {e}')

print(f'Loaded {len(results)} events')

with open('output.jsonl', 'w', encoding='utf-8') as f:
    for record in results:
        f.write(json.dumps(record, ensure_ascii=False) + '\n')

Lendo arquivos de texto simples

O texto simples é o formato mais básico — usado em registros, instruções, relatórios e arquivos de configuração. Leia o arquivo inteiro com .read() ou processe-o linha a linha. Para arquivos grandes, sempre use a abordagem linha a linha para manter constante o uso de memória.

from pathlib import Path

Path('system_prompt.txt').write_text('You are a helpful agent.', encoding='utf-8')
with open('agent.log', 'w', encoding='utf-8') as f:
    f.write('INFO: boot\nERROR: disk full\nCRITICAL: crash\nINFO: recovered\n')

prompt = Path('system_prompt.txt').read_text(encoding='utf-8')
print(f'Prompt length: {len(prompt)} characters')

error_lines = []
with open('agent.log', 'r', encoding='utf-8') as f:
    for line in f:
        line = line.rstrip()
        if not line:
            continue
        if 'ERROR' in line or 'CRITICAL' in line:
            error_lines.append(line)

print(f'Found {len(error_lines)} error lines')

with open('summary.txt', 'w', encoding='utf-8') as f:
    f.write('Agent Run Summary\n')
    f.write('=' * 40 + '\n')
    for error in error_lines[:10]:
        f.write(f'  {error}\n')
print('Summary written')

Lidando com BOM (marca de ordem dos bytes)

Arquivos exportados do Excel ou de ferramentas do Windows geralmente começam com um BOM (marca de ordem dos bytes) — um caractere invisível \ufeff. Se não for tratado, ele corrompe o nome do primeiro campo durante a análise de CSV. Use encoding='utf-8-sig' para removê-lo automaticamente.

import csv

with open('windows_export.csv', 'wb') as f:
    f.write('name,email,age\nAlice,alice@x.com,30\n'.encode('utf-8'))
with open('file.txt', 'wb') as f:
    f.write(b'\xef\xbb\xbfhello')

with open('windows_export.csv', 'r', encoding='utf-8') as f:
    reader = csv.DictReader(f)
    first = next(reader)
    print(list(first.keys()))

with open('windows_export.csv', 'r', encoding='utf-8-sig') as f:
    reader = csv.DictReader(f)
    first = next(reader)
    print(list(first.keys()))

content = open('file.txt', 'rb').read()
if content.startswith(b'\xef\xbb\xbf'):
    content = content[3:]
text = content.decode('utf-8')
print('Decoded:', text)

Lidando com erros de codificação

Ao ler arquivos de fontes desconhecidas, erros de codificação são comuns. O parâmetro errors de open() controla o que acontece: 'replace' substitui caracteres inválidos por ?, 'ignore' os descarta e 'backslashreplace' os transforma em sequências de escape. Para uma validação rigorosa, use 'strict' (o padrão).

from pathlib import Path

def read_with_fallback(file_path):
    path = Path(file_path)

    # Try UTF-8 first
    try:
        return path.read_text(encoding='utf-8')
    except UnicodeDecodeError:
        pass

    # Try Latin-1 (handles most European files)
    try:
        return path.read_text(encoding='latin-1')
    except UnicodeDecodeError:
        pass

    # Last resort: replace bad characters
    text = path.read_text(encoding='utf-8', errors='replace')
    print(f'Warning: {path.name} had encoding errors (chars replaced)')
    return text

# --- demo ---
Path('notes_utf8.txt').write_text('Notes: café, naïve, résumé', encoding='utf-8')
text = read_with_fallback('notes_utf8.txt')
print(f'Read {len(text)} chars: {text!r}')

Lidando com arquivos CSV malformados

Arquivos CSV do mundo real apresentam problemas: vírgulas extras, campos ausentes, uso inconsistente de aspas ou delimitadores mistos. Use as opções quoting e error_bad_lines e envolva a análise das linhas em try/except para ignorar linhas inválidas de forma controlada.

import csv

with open('messy_data.csv', 'w', newline='') as f:
    f.write('name,email,score\nAlice,alice@x.com,88\nBob,,90\nCarol,carol@x.com,notanumber\n')

valid_rows = []
error_count = 0

with open('messy_data.csv', 'r', encoding='utf-8', newline='') as f:
    reader = csv.DictReader(f)
    expected_fields = {'name', 'email', 'score'}

    for line_num, row in enumerate(reader, start=2):
        try:
            if not all(row.get(f, '').strip() for f in expected_fields):
                raise ValueError(f'Missing required field in row {line_num}')
            score = float(row['score'])
            valid_rows.append({
                'name': row['name'].strip(),
                'email': row['email'].strip().lower(),
                'score': score
            })
        except (ValueError, KeyError) as e:
            error_count += 1
            print(f'Skipping row {line_num}: {e}')

print(f'Valid: {len(valid_rows)}, Errors: {error_count}')

Verificação rápida: CSV DictReader vs reader

Teste sua compreensão das opções de análise de CSV.

Recapitulação do tratamento de formatos de arquivo

Agora você consegue analisar e gravar todos os principais formatos de arquivo usados por agentes:

  • CSV: use csv.DictReader para linhas em dicionários e csv.DictWriter para a saída; sempre use newline='' ao abrir
  • JSON: use json.load(f) para analisar e json.dump(obj, f, indent=2) para gravar; capture JSONDecodeError
  • JSONL: leia e analise cada linha com json.loads(line); excelente para dados em fluxo
  • Texto simples: use .read() para arquivos pequenos e iteração por linha para arquivos grandes
  • BOM: use encoding='utf-8-sig' para arquivos exportados pelo Windows
  • Erros de codificação: tente UTF-8, use latin-1 como alternativa ou use errors='replace'

Perguntas Frequentes

A aula “Tratamento de formatos de arquivo: CSV, JSON e TXT” é grátis?

Sim — o texto completo de “Tratamento de formatos de arquivo: CSV, JSON e TXT” é grátis para ler aqui na web. Para praticá-la interativamente (um editor de código integrado e um tutor de IA 24/7) e desbloquear o restante do curso de AI Agents, atualize para CoddyKit PRO. O curso de AI Agents inclui 4 aulas no total.

O que vou aprender em “Tratamento de formatos de arquivo: CSV, JSON e TXT”?

Módulo csv, json.load/dump e codificação segura de texto para ferramentas de agentes. Você pratica AI Agents com código prático que executa diretamente no navegador, e um tutor de IA 24/7 responde suas dúvidas enquanto trabalha na aula.

Preciso ter experiência prévia para começar AI Agents?

Nenhuma experiência prévia é necessária. AI Agents no CoddyKit é estruturado para alunos iniciantes até avançados, então você pode começar aqui ou desde o início e aprender no seu ritmo. Esta é a aula 3 de 4.

Quanto tempo leva a aula “Tratamento de formatos de arquivo: CSV, JSON e TXT”?

A maioria das aulas CoddyKit leva cerca de 5–10 minutos. Cada uma é compacta e interativa, então você faz progresso constante e retoma exatamente de onde parou entre web e app.

Posso escrever e executar código nesta aula de AI Agents?

Sim. Cada aula de AI Agents inclui um editor de código integrado, então você escreve e executa código real direto no navegador e recebe feedback de IA instantaneamente — nenhuma configuração local necessária.

Todas as aulas deste curso

  1. Lendo e escrevendo arquivos no contexto de agentes
  2. Percurso de diretórios e descoberta de arquivos
  3. Tratamento de formatos de arquivo: CSV, JSON e TXT
  4. Operações seguras com arquivos e tratamento de erros
← Voltar para AI Agents