Distributed Tracing - C-Suite
Este documento descreve o sistema de distributed tracing implementado para o ecossistema C-Suite.
Visão Geral
O módulo common/common_tracing.py fornece suporte a distributed tracing usando OpenTelemetry, permitindo rastrear requests através de múltiplos serviços e visualizar o fluxo completo de uma decisão.
Características
- ✅ Suporte a múltiplos backends (Jaeger, OTLP, AWS X-Ray)
- ✅ Instrumentação automática de FastAPI
- ✅ Instrumentação de HTTPX (chamadas HTTP)
- ✅ Instrumentação de SQLAlchemy (queries de banco)
- ✅ Context propagation entre serviços
- ✅ Sampling configurável
- ✅ Integração com métricas Prometheus
Configuração
Variáveis de Ambiente
# Habilitar tracing
TRACING_ENABLED=true
# Nome do serviço
TRACING_SERVICE_NAME=csuite-app
# Backend (jaeger, otlp, xray)
TRACING_BACKEND=jaeger
# Jaeger configuration
JAEGER_AGENT_HOST=localhost
JAEGER_AGENT_PORT=6831
JAEGER_ENDPOINT=http://localhost:14268/api/traces
# OTLP configuration
OTLP_ENDPOINT=http://localhost:4317
OTLP_INSECURE=true
# Sampling rate (0.0 a 1.0)
TRACING_SAMPLE_RATE=1.0
# Propagators (tracecontext, b3)
TRACING_PROPAGATORS=tracecontext,b3
# Versão do serviço
SERVICE_VERSION=1.0.0
# Ambiente
ENVIRONMENT=production
Uso
Setup Básico
from common.common_tracing import setup_tracing, instrument_fastapi
from fastapi import FastAPI
app = FastAPI()
# Setup tracing
setup_tracing(service_name="my-service")
# Instrumentar FastAPI automaticamente
instrument_fastapi(app)
Criar Spans Manualmente
from common.common_tracing import trace_span, get_tracer
# Usando context manager
with trace_span("database_query", {"table": "users", "operation": "select"}):
# Seu código aqui
result = db.query(User).all()
# Usando decorator
from common.common_tracing import trace_function
@trace_function(attributes={"component": "api"})
def my_function():
pass
Adicionar Atributos e Eventos
from common.common_tracing import add_trace_attributes, add_trace_event, add_trace_error
# Adicionar atributos ao span atual
add_trace_attributes(
user_id="123",
org_id=1,
operation="create_policy"
)
# Adicionar evento
add_trace_event("policy_created", {"policy_id": "min_margin"})
# Registrar erro
try:
risky_operation()
except Exception as e:
add_trace_error(e, {"context": "policy_creation"})
raise
Propagação de Context
from common.common_tracing import get_trace_context
import httpx
# Obter headers de trace context
headers = get_trace_context()
# Enviar em requisição HTTP
response = httpx.get("http://other-service/api", headers=headers)
Backends Suportados
Jaeger
TRACING_BACKEND=jaeger
JAEGER_AGENT_HOST=jaeger-agent
JAEGER_AGENT_PORT=6831
JAEGER_ENDPOINT=http://jaeger:14268/api/traces
OTLP (OpenTelemetry Protocol)
TRACING_BACKEND=otlp
OTLP_ENDPOINT=http://otel-collector:4317
OTLP_INSECURE=true
AWS X-Ray
Para AWS X-Ray, use o exporter OTLP com endpoint do X-Ray:
TRACING_BACKEND=otlp
OTLP_ENDPOINT=http://localhost:2000
Instrumentação Automática
O módulo instrumenta automaticamente:
- FastAPI: Todas as requests/responses
- HTTPX: Chamadas HTTP assíncronas
- SQLAlchemy: Queries de banco de dados
Visualização
Jaeger UI
Acesse o Jaeger UI em http://localhost:16686 para visualizar traces.
Grafana
Integre traces com métricas no Grafana usando o plugin de tracing.
Dependências
Adicione ao requirements.txt:
opentelemetry-api==1.21.0
opentelemetry-sdk==1.21.0
opentelemetry-exporter-jaeger-thrift==1.21.0
opentelemetry-exporter-otlp-proto-grpc==1.21.0
opentelemetry-instrumentation-fastapi==0.42b0
opentelemetry-instrumentation-httpx==0.42b0
opentelemetry-instrumentation-sqlalchemy==0.42b0
Exemplo Completo
from fastapi import FastAPI
from common.common_tracing import setup_tracing, instrument_fastapi, trace_span
from common.common_db_pool import get_db_session
app = FastAPI()
# Setup tracing
setup_tracing(service_name="csuite-api")
instrument_fastapi(app)
@app.get("/policies/{org_id}")
async def get_policies(org_id: int):
with trace_span("get_policies", {"org_id": org_id}):
session = get_db_session("csuite")
policies = session.query(Policy).filter_by(org_id=org_id).all()
return {"policies": policies}
Troubleshooting
Traces não aparecem
- Verifique se
TRACING_ENABLED=true - Verifique conectividade com o backend (Jaeger/OTLP)
- Verifique logs para erros de exportação
Performance
- Use sampling (
TRACING_SAMPLE_RATE) em produção - Configure batch export para reduzir overhead