Handlers | Adapter | Conceito
- Handlers | Adapter | Conceito
Adapter é um tipo de handler que tem só 1 função: Adaptar um evento em um comando.
- recebe um evento
- buscar dados adicionais para a criação do comando
- formata o comando
- envia o comando
Visão geral rápida
Um handler (manipulador) é uma função/rotina que responde a um evento (requisição, erro, sinal, timer, mensagem, etc.). O nome varia conforme o contexto: event handler, request handler, exception handler, signal handler, interrupt handler, callback, route handler, webhook handler, etc. Todos têm a mesma ideia: receber algo e reagir.
Principais tipos de handlers
1. Event handlers (manipuladores de eventos)
O que fazem: respondem a eventos assíncronos (click do usuário, input, mensagens do sistema, etc). Onde aparecem: front-end (DOM), frameworks reativos, sistemas de eventos (event-driven). Exemplo (JavaScript / navegador):
button.addEventListener('click', (e) => {
console.log('clicou!', e);
});
Quando usar: UI, pipelines assíncronos, pub/sub. Cuidados: evitar trabalho pesado no handler (bloqueio da UI); debounce/throttle quando necessário.
2. Request / Route handlers (manipuladores de requisição)
O que fazem: processam uma requisição (HTTP, RPC) e retornam uma resposta. Onde: servidores web (Express, Flask, Django, etc.). Exemplo (Node + Express):
app.get('/produtos/:id', (req, res) => {
const id = req.params.id;
res.json(getProduto(id));
});
Quando usar: lógica de endpoint, validação, autenticação, resposta. Boas práticas: separar validação/autorização/negócio; tratar erros e tempo limite; limpar recursos.
3. Callback handlers (callbacks)
O que fazem: rotina passada como argumento para executar quando algo terminar (I/O, timers). Onde: APIs assíncronas em muitas linguagens. Exemplo (Node fs):
fs.readFile('a.txt', (err, data) => {
if (err) throw err;
console.log(data.toString());
});
Cuidados: evitar “callback hell” — prefira Promises/async-await onde possível.
4. Filter / Middleware handlers
O que fazem: interceptam e modificam requests/responses em cadeia (pipeline). Onde: frameworks web (middleware), processamento de dados. Exemplo (Express):
app.use((req, res, next) => {
console.log(req.method, req.url);
next(); // passa pro próximo middleware/handler
});
Quando usar: autenticação, logging, CORS, rate-limiting. Cuidados: ordem importa; interromper corretamente quando necessário (res.end / next(err)).
5. Exception / Error handlers (tratamento de exceções)
O que fazem: capturam erros/exceções e tratam (log, resposta amigável, rollback). Onde: em quase toda aplicação. Exemplo (Python):
try:
x = 1/0
except ZeroDivisionError as e:
logger.error("Erro: %s", e)
# tratar/retornar mensagem ao usuário
Boas práticas: não engolir erros silently; logs suficientes; separar erros esperados de inesperados; em servidores, ter um handler global que converta exceções em respostas HTTP adequadas.
6. Signal handlers (sinais do SO)
O que fazem: respondem a sinais do sistema (SIGINT, SIGTERM) para shutdown gracioso, reload, etc. Onde: aplicações servidoras, processos long-lived. Exemplo (Python):
import signal, sys
def handler(signum, frame):
print('terminando...')
sys.exit(0)
signal.signal(signal.SIGINT, handler)
Quando usar: cleanup, flush de logs, encerramento ordenado.
7. Interrupt handlers / ISRs (em sistemas embarcados)
O que fazem: respondem a interrupções de hardware (timer, GPIO). Precisam ser rápidas e determinísticas. Onde: firmware, microcontroladores. Cuidados: não chamar funções lentas/complexas; usar filas/flags para trabalho pós-interrupt.
8. Message / Queue handlers (consumidores)
O que fazem: processam mensagens de filas (RabbitMQ, Kafka, SQS). Muitas vezes idempotentes. Onde: microservices, processamento assíncrono. Exemplo (pseudocódigo):
for msg in queue.consume():
process(msg)
msg.ack()
Boas práticas: retry/backoff, idempotência, dead-letter queues.
9. Webhook handlers
O que fazem: endpoints que recebem callbacks de serviços externos (Stripe, GitHub). Onde: integração com terceiros. Cuidados: verificar assinatura/secret; tratar replays; validar payloads; responder 200 rápido.
10. Cron / Scheduled handlers (tarefas agendadas)
O que fazem: executam trabalho periódico (backup, limpeza, relatórios). Onde: CRON, job schedulers, WP-Cron. Boas práticas: evitar sobreposição (locks), monitoramento, retries controlados.
11. File / Stream handlers
O que fazem: processam leitura/gravação de arquivos ou streams (logs, upload). Cuidados: tratamento de erros de I/O, encoding, flush, fecho de descriptors.
12. Authentication / Authorization handlers
O que fazem: verificam identidade e permissões (middleware ou específico por rota). Exemplo (Express + JWT):
function auth(req, res, next) {
const token = req.headers.authorization?.split(' ')[1];
// validar token...
next();
}
app.use('/private', auth);
Boas práticas: falhar fechado (deny by default), logging, revogação de tokens.
13. Logging / Telemetry handlers
O que fazem: capturam eventos/erros para envio a sistemas de observabilidade (ELK, Sentry). Cuidados: não logar dados sensíveis (PII, senhas), evitar logs excessivos que causem I/O bloqueante.
14. Command / CQRS handlers (comandos e queries)
O que fazem: em arquiteturas CQRS/ES, handlers processam comandos (que mudam estado) ou queries (leitura). Boas práticas: separar claramente side-effects e leitura, idempotência em comandos quando aplicável.
Como escolher/organizar handlers na aplicação
- Separa responsabilidades: validação → autorização → negócio → resposta (pipeline).
- Mantenha handlers pequenos e testáveis.
- Use middleware para preocupações transversais (logs, auth, CORS).
- Evite efeitos colaterais inesperados — documente o que cada handler altera.
- Idempotência: especialmente em webhooks e mensagens, para tolerância a retries.
- Timeouts e cancelamento: handlers devem respeitar limites e abortar trabalho caro quando solicitado.
- Segurança: sempre sanitize/valide entradas; verifique assinaturas em webhooks; use nonces em formulários; trate exposição de erros cuidadosamente.
Debugging e testes
- Unit tests para lógica do handler.
- Integration tests simulando requests/mensagens.
- Local queues / mocks para testar message handlers.
- Ferramentas de observability (tracing, logs estruturados, metrics) para produção.
- Simular condições de erro (timeouts, falta de DB, mensagens duplicadas).
Resumo: quando usar cada tipo (cheat-sheet rápido)
- UI → event handlers
- Endpoints HTTP → route/request handlers + middleware
- Erros → exception/error handlers
- Sistema/terminação → signal handlers
- Hardware → interrupt handlers/ISRs
- Mensageria → message/queue handlers
- Integração externa → webhook handlers
- Agendamento → cron/scheduled handlers