dezembro 21, 2025
15 min de leitura

Perguntas para Entrevistas de Engenheiro Sênior de Confiabilidade de Sites: Guia Completo

interview
career-advice
job-search
Perguntas para Entrevistas de Engenheiro Sênior de Confiabilidade de Sites: Guia Completo
Milad Bonakdar

Milad Bonakdar

Autor

Domine conceitos avançados de SRE com perguntas abrangentes para entrevistas, cobrindo planejamento de capacidade, engenharia do caos, sistemas distribuídos, design de SLO, liderança em incidentes e práticas organizacionais de SRE para cargos seniores.


Introdução

Espera-se que os Engenheiros de Confiabilidade de Site (SREs) seniores projetem sistemas confiáveis em escala, liderem respostas a incidentes, promovam a cultura SRE e tomem decisões estratégicas sobre investimentos em confiabilidade. Essa função exige profundo conhecimento técnico, habilidades de liderança e a capacidade de equilibrar confiabilidade com a velocidade dos negócios.

Este guia abrangente aborda as principais perguntas de entrevistas para SREs seniores, com foco em conceitos avançados, design de sistemas e impacto organizacional. Cada pergunta inclui explicações detalhadas e exemplos práticos.


Design Avançado de SLO

1. Como você projeta SLIs e SLOs para um novo serviço com dados limitados?

Resposta: Projetar SLOs para novos serviços exige equilibrar ambição com capacidade de realização:

Abordagem:

1. Comece com o mapeamento da jornada do usuário:

# Identifique as jornadas críticas do usuário
user_journeys = {
    'search_product': {
        'steps': ['search_query', 'results_display', 'product_click'],
        'criticality': 'high',
        'expected_latency': '< 500ms'
    },
    'checkout': {
        'steps': ['add_to_cart', 'payment', 'confirmation'],
        'criticality': 'critical',
        'expected_latency': '< 2s'
    },
    'browse_recommendations': {
        'steps': ['load_page', 'fetch_recommendations'],
        'criticality': 'medium',
        'expected_latency': '< 1s'
    }
}

2. Defina SLIs com base na experiência do usuário:

# Especificação SLI
slis:
  availability:
    description: "Porcentagem de solicitações bem-sucedidas"
    measurement: "count(http_status < 500) / count(http_requests)"
    
  latency:
    description: "Latência de solicitação do percentil 95"
    measurement: "histogram_quantile(0.95, http_request_duration_seconds)"
    
  correctness:
    description: "Porcentagem de solicitações que retornam dados corretos"
    measurement: "count(validation_passed) / count(requests)"

3. Defina SLOs iniciais de forma conservadora:

def calculate_initial_slo(service_type, criticality):
    """
    Calcular SLO inicial com base nas características do serviço
    """
    base_slos = {
        'critical': {
            'availability': 0.999,  # 99,9%
            'latency_p95': 1.0,     # 1 segundo
            'latency_p99': 2.0      # 2 segundos
        },
        'high': {
            'availability': 0.995,  # 99,5%
            'latency_p95': 2.0,
            'latency_p99': 5.0
        },
        'medium': {
            'availability': 0.99,   # 99%
            'latency_p95': 5.0,
            'latency_p99': 10.0
        }
    }
    
    return base_slos.get(criticality, base_slos['medium'])

# Exemplo
checkout_slo = calculate_initial_slo('payment', 'critical')
print(f"Checkout SLO: {checkout_slo}")

4. Planeje a iteração:

  • Comece com uma janela de medição de 4 semanas
  • Revise o desempenho do SLO semanalmente
  • Ajuste com base no desempenho real e no feedback do usuário
  • Aperte os SLOs à medida que o sistema amadurece

5. Documente as premissas:

## Premissas do SLO (Inicial)

### Disponibilidade: 99,9%
- Assume: Confiabilidade padrão da infraestrutura de nuvem
- Orçamento de erro: 43 minutos/mês
- Revisão: Após 3 meses de dados

### Latência (p95): < 1s
- Assume: Consultas de banco de dados < 100ms
- Assume: Sem cálculos complexos
- Revisão: Se os padrões de consulta mudarem

### Dependências
- Disponibilidade da API externa: 99,95%
- Disponibilidade do banco de dados: 99,99%

Raridade: Comum
Dificuldade: Difícil


2. Como você lida com SLOs conflitantes entre diferentes segmentos de usuários?

Resposta: Diferentes segmentos de usuários geralmente têm diferentes necessidades de confiabilidade:

Estratégia: SLOs de vários níveis

class SLOTier:
    def __init__(self, name, availability, latency_p95, latency_p99):
        self.name = name
        self.availability = availability
        self.latency_p95 = latency_p95
        self.latency_p99 = latency_p99
        self.error_budget = 1 - availability

# Defina os níveis
tiers = {
    'premium': SLOTier(
        name='Premium',
        availability=0.9999,  # 99,99% - 4,3 min/mês
        latency_p95=0.5,
        latency_p99=1.0
    ),
    'standard': SLOTier(
        name='Standard',
        availability=0.999,   # 99,9% - 43 min/mês
        latency_p95=1.0,
        latency_p99=2.0
    ),
    'free': SLOTier(
        name='Free',
        availability=0.99,    # 99% - 7,2 horas/mês
        latency_p95=2.0,
        latency_p99=5.0
    )
}

# Rota as solicitações com base no nível
def get_user_tier(user_id):
    # Consulte o nível de assinatura do usuário
    return user_subscription_tier(user_id)

def apply_slo_policy(user_id, request):
    tier = get_user_tier(user_id)
    slo = tiers[tier]
    
    # Aplique políticas específicas de nível
    request.timeout = slo.latency_p99
    request.priority = tier  # Para priorização de fila
    request.retry_budget = calculate_retry_budget(slo.error_budget)
    
    return request

Implementação com Roteamento de Tráfego:

# Exemplo do Kubernetes: Implantações separadas por nível
apiVersion: apps/v1
kind: Deployment
metadata:
  name: api-premium
spec:
  replicas: 10
  template:
    spec:
      containers:
      - name: api
        resources:
          requests:
            cpu: "2"
            memory: "4Gi"
          limits:
            cpu: "4"
            memory: "8Gi"
      priorityClassName: high-priority
---
apiVersion: apps/v1
kind: Deployment
metadata:
  name: api-standard
spec:
  replicas: 5
  template:
    spec:
      containers:
      - name: api
        resources:
          requests:
            cpu: "1"
            memory: "2Gi"

Monitoramento por nível:

# Disponibilidade por nível
sum(rate(http_requests_total{status!~"5.."}[5m])) by (tier)
/
sum(rate(http_requests_total[5m])) by (tier)

# Latência por nível
histogram_quantile(0.95,
  rate(http_request_duration_seconds_bucket[5m])
) by (tier)

Raridade: Incomum
Dificuldade: Difícil


Planejamento de Capacidade

3. Descreva seu processo de planejamento de capacidade para um serviço em rápido crescimento.

Resposta: O planejamento de capacidade garante que os recursos atendam à demanda, otimizando os custos:

Estrutura de Planejamento de Capacidade:

Loading diagram...

1. Medir a linha de base:

import pandas as pd
import numpy as np
from sklearn.linear_model import LinearRegression

class CapacityPlanner:
    def __init__(self, metrics_data):
        self.data = pd.DataFrame(metrics_data)
    
    def analyze_trends(self, metric_name, days=30):
        """Analisar tendências históricas"""
        metric_data = self.data[metric_name].tail(days * 24)  # Dados por hora
        
        # Calcular taxa de crescimento
        start_value = metric_data.iloc[0]
        end_value = metric_data.iloc[-1]
        growth_rate = ((end_value - start_value) / start_value) * 100
        
        # Identificar o pico de uso
        peak_value = metric_data.max()
        peak_time = metric_data.idxmax()
        
        # Calcular percentis
        p50 = metric_data.quantile(0.50)
        p95 = metric_data.quantile(0.95)
        p99 = metric_data.quantile(0.99)
        
        return {
            'growth_rate': growth_rate,
            'peak_value': peak_value,
            'peak_time': peak_time,
            'p50': p50,
            'p95': p95,
            'p99': p99
        }
    
    def forecast_capacity(self, metric_name, months_ahead=3):
        """Prever necessidades futuras de capacidade"""
        # Preparar dados
        df = self.data[[metric_name]].reset_index()
        df['days'] = (df.index / 24).astype(int)  # Converter horas em dias
        
        # Treinar modelo
        X = df[['days']].values
        y = df[metric_name].values
        
        model = LinearRegression()
        model.fit(X, y)
        
        # Prever
        future_days = np.array([[df['days'].max() + (30 * months_ahead)]])
        forecast = model.predict(future_days)[0]
        
        # Adicionar margem de segurança (20%)
        forecast_with_margin = forecast * 1.2
        
        return {
            'forecast': forecast,
            'with_margin': forecast_with_margin,
            'current': y[-1],
            'growth_factor': forecast / y[-1]
        }
    
    def calculate_resource_needs(self, requests_per_second, 
                                 requests_per_instance=100,
                                 headroom=0.3):
        """Calcular instâncias necessárias"""
        # Capacidade base
        base_instances = np.ceil(requests_per_second / requests_per_instance)
        
        # Adicionar margem de segurança para picos e manutenção
        total_instances = np.ceil(base_instances * (1 + headroom))
        
        return {
            'base_instances': int(base_instances),
            'total_instances': int(total_instances),
            'headroom_instances': int(total_instances - base_instances)
        }

# Exemplo de uso
metrics = {
    'requests_per_second': [100, 105, 110, 115, 120, ...],  # Dados históricos
    'cpu_usage': [45, 48, 50, 52, 55, ...],
    'memory_usage': [60, 62, 65, 67, 70, ...]
}

planner = CapacityPlanner(metrics)

# Analisar tendências
trends = planner.analyze_trends('requests_per_second', days=30)
print(f"Taxa de crescimento: {trends['growth_rate']:.2f}%")
print(f"Pico de RPS: {trends['peak_value']}")

# Prever capacidade
forecast = planner.forecast_capacity('requests_per_second', months_ahead=3)
print(f"RPS previsto em 3 meses: {forecast['forecast']:.0f}")
print(f"Com margem de segurança: {forecast['with_margin']:.0f}")

# Calcular necessidades de recursos
resources = planner.calculate_resource_needs(
    requests_per_second=forecast['with_margin'],
    requests_per_instance=100,
    headroom=0.3
)
print(f"Instâncias necessárias: {resources['total_instances']}")

2. Considere os impulsionadores de crescimento:

  • Taxa de crescimento do usuário
  • Lançamentos de recursos
  • Padrões sazonais
  • Campanhas de marketing
  • Expansão geográfica

3. Planeje a margem de segurança:

  • N+1: Sobreviva a uma falha de instância
  • N+2: Sobreviva a duas falhas ou uma interrupção de zona
  • Picos de tráfego: 2-3x a capacidade normal
  • Janelas de manutenção: 20-30% de sobrecarga

4. Otimização de custos:

def optimize_instance_mix(workload_profile):
    """
    Otimizar tipos de instância para custo
    """
    # Combinação de tipos de instância
    instance_types = {
        'on_demand': {
            'cost_per_hour': 0.10,
            'reliability': 1.0,
            'percentage': 0.3  # 30% sob demanda para linha de base
        },
        'spot': {
            'cost_per_hour': 0.03,
            'reliability': 0.95,
            'percentage': 0.5  # 50% spot para economia de custos
        },
        'reserved': {
            'cost_per_hour': 0.06,
            'reliability': 1.0,
            'percentage': 0.2  # 20% reservado para carga previsível
        }
    }
    
    total_instances = workload_profile['total_instances']
    
    allocation = {}
    for instance_type, config in instance_types.items():
        count = int(total_instances * config['percentage'])
        allocation[instance_type] = {
            'count': count,
            'monthly_cost': count * config['cost_per_hour'] * 730
        }
    
    return allocation

Raridade: Muito Comum
Dificuldade: Difícil


Engenharia do Caos

4. Como você implementa a engenharia do caos em produção?

Resposta: A engenharia do caos testa proativamente a resiliência do sistema, injetando falhas:

Princípios da Engenharia do Caos:

  1. Construa uma hipótese em torno do estado estável
  2. Varie eventos do mundo real
  3. Execute experimentos em produção
  4. Automatize experimentos
  5. Minimize o raio de explosão

Implementação:

# Estrutura de experimento de caos
from dataclasses import dataclass
from enum import Enum
import random
import time

class ExperimentStatus(Enum):
    PLANNED = "planejado"
    RUNNING = "em_execução"
    COMPLETED = "concluído"
    ABORTED = "abortado"

@dataclass
class ChaosExperiment:
    name: str
    hypothesis: str
    blast_radius: float  # Porcentagem do tráfego afetado
    duration_seconds: int
    rollback_criteria: dict
    
    def __post_init__(self):
        self.status = ExperimentStatus.PLANNED
        self.metrics_before = {}
        self.metrics_during = {}
        self.metrics_after = {}

class ChaosRunner:
    def __init__(self, monitoring_client):
        self.monitoring = monitoring_client
        self.experiments = []
    
    def run_experiment(self, experiment: ChaosExperiment):
        """Executar experimento de caos com verificações de segurança"""
        print(f"Iniciando experimento: {experiment.name}")
        
        # 1. Medir a linha de base
        experiment.metrics_before = self.measure_metrics()
        print(f"Métricas de linha de base: {experiment.metrics_before}")
        
        # 2. Verificar se o sistema está saudável
        if not self.is_system_healthy(experiment.metrics_before):
            print("Sistema não saudável, abortando o experimento")
            return False
        
        # 3. Injetar falha
        experiment.status = ExperimentStatus.RUNNING
        failure_injection = self.inject_failure(experiment)
        
        try:
            # 4. Monitorar durante o experimento
            start_time = time.time()
            while time.time() - start_time < experiment.duration_seconds:
                experiment.metrics_during = self.measure_metrics()
                
                # Verificar critérios de reversão
                if self.should_rollback(experiment):
                    print("Critérios de reversão atendidos, interrompendo o experimento")
                    self.rollback(failure_injection)
                    experiment.status = ExperimentStatus.ABORTED
                    return False
                
                time.sleep(10)  # Verificar a cada 10 segundos
            
            # 5. Reverter a injeção de falha
            self.rollback(failure_injection)
            
            # 6. Medir a recuperação
            time.sleep(60)  # Aguardar a estabilização do sistema
            experiment.metrics_after = self.measure_metrics()
            
            # 7. Analisar os resultados
            experiment.status = ExperimentStatus.COMPLETED
            return self.analyze_results(experiment)
            
        except Exception as e:
            print(f"Experimento falhou: {e}")
            self.rollback(failure_injection)
            experiment.status = ExperimentStatus.ABORTED
            return False
    
    def inject_failure(self, experiment):
        """Injetar tipo de falha específico"""
        # A implementação depende do tipo de falha
        pass
    
    def measure_metrics(self):
        """Medir as principais métricas do sistema"""
        return {
            'error_rate': self.monitoring.get_error_rate(),
            'latency_p95': self.monitoring.get_latency_p95(),
            'requests_per_second': self.monitoring.get_rps(),
            'availability': self.monitoring.get_availability()
        }
    
    def is_system_healthy(self, metrics):
        """Verificar se o sistema atende aos SLOs"""
        return (
            metrics['error_rate'] < 0.01 and  # < 1% de erros
            metrics['latency_p95'] < 1.0 and  # < 1s de latência
            metrics['availability'] > 0.999   # > 99,9% disponível
        )
    
    def should_rollback(self, experiment):
        """Verificar se o experimento deve ser abortado"""
        current = experiment.metrics_during
        criteria = experiment.rollback_criteria
        
        return (
            current['error_rate'] > criteria.get('max_error_rate', 0.05) or
            current['latency_p95'] > criteria.get('max_latency', 5.0) or
            current['availability'] < criteria.get('min_availability', 0.99)
        )
    
    def rollback(self, failure_injection):
        """Remover a injeção de falha"""
        print("Revertendo a injeção de falha")
        # A implementação depende do tipo de falha
    
    def analyze_results(self, experiment):
        """Analisar os resultados do experimento"""
        before = experiment.metrics_before
        during = experiment.metrics_during
        after = experiment.metrics_after
        
        print(f"\nResultados do Experimento: {experiment.name}")
        print(f"Hipótese: {experiment.hypothesis}")
        print(f"\nMétricas:")
        print(f"  Antes: {before}")
        print(f"  Durante: {during}")
        print(f"  Depois: {after}")
        
        # Determinar se a hipótese foi validada
        hypothesis_validated = (
            during['availability'] >= experiment.rollback_criteria['min_availability']
        )
        
        return hypothesis_validated

# Exemplo de experimento
experiment = ChaosExperiment(
    name="Teste de Failover do Banco de Dados",
    hypothesis="O sistema permanece disponível durante o failover do banco de dados",
    blast_radius=0.1,  # 10% do tráfego
    duration_seconds=300,  # 5 minutos
    rollback_criteria={
        'max_error_rate': 0.05,
        'max_latency': 5.0,
        'min_availability': 0.99
    }
)

Experimentos de Caos Comuns:

1. Latência de Rede:

# Usando tc (traffic control) para adicionar latência
tc qdisc add dev eth0 root netem delay 100ms 20ms

# Reverter
tc qdisc del dev eth0 root

2. Falha de Pod (Kubernetes):

# Matar pods aleatórios
kubectl delete pod -l app=myapp --random=1

# Usando Chaos Mesh
kubectl apply -f - <<EOF
apiVersion: chaos-mesh.org/v1alpha1
kind: PodChaos
metadata:
  name: pod-failure
spec:
  action: pod-failure
  mode: one
  selector:
    namespaces:
      - production
    labelSelectors:
      app: myapp
  duration: "30s"
EOF

3. Esgotamento de Recursos:

# Estresse de CPU
stress-ng --cpu 4 --timeout 60s

# Estresse de memória
stress-ng --vm 2 --vm-bytes 2G --timeout 60s

Raridade: Comum
Dificuldade: Difícil


Liderança de Incidentes

5. Como você lidera um incidente de alta gravidade desde a detecção até o post-mortem?

Resposta: SREs seniores geralmente atuam como comandantes de incidentes para interrupções críticas:

Estrutura de Comando de Incidentes:

Loading diagram...

Responsabilidades do Comandante de Incidentes:

1. Resposta Inicial (0-5 minutos):

## Checklist do Comandante de Incidentes

### Ações Imediatas
- [ ] Reconhecer o incidente
- [ ] Avaliar a gravidade (SEV-1, SEV-2, SEV-3)
- [ ] Criar canal de incidente (#incident-AAAA-MM-DD-NNN)
- [ ] Acionar as equipes apropriadas
- [ ] Designar funções:
  - [ ] Líder Técnico
  - [ ] Líder de Comunicações
  - [ ] Escriba (documentar a linha do tempo)

### Avaliação de Gravidade
**SEV-1 (Crítico):**
- Interrupção completa do serviço
- Perda de dados
- Violação de segurança
- > 50% dos usuários afetados

**SEV-2 (Alto):**
- Interrupção parcial
- Desempenho degradado
- 10-50% dos usuários afetados

**SEV-3 (Médio):**
- Degradação menor
- < 10% dos usuários afetados
- Solução alternativa disponível

2. Fase de Investigação:

class IncidentCommander:
    def __init__(self, incident_id):
        self.incident_id = incident_id
        self.timeline = []
        self.status_updates = []
        self.action_items = []
    
    def coordinate_investigation(self):
        """Coordenar a investigação técnica"""
        # Rastreamentos de investigação paralelos
        tracks = {
            'recent_changes': self.check_recent_deployments(),
            'infrastructure': self.check_infrastructure_health(),
            'dependencies': self.check_external_dependencies(),
            'metrics': self.analyze_metrics_anomalies()
        }
        
        return tracks
    
    def make_decision(self, options, deadline_minutes=5):
        """Tomar decisão com tempo limitado"""
        print(f"Decisão necessária em {deadline_minutes} minutos")
        print(f"Opções: {options}")
        
        # Coletar informações dos líderes técnicos
        # Tomar decisão com base em:
        # - Impacto no usuário
        # - Risco de cada opção
        # - Tempo para implementar
        # - Reversibilidade
        
        return selected_option
    
    def communicate_status(self, interval_minutes=15):
        """Atualizações regulares de status"""
        update = {
            'timestamp': datetime.now(),
            'status': self.get_current_status(),
            'impact': self.assess_user_impact(),
            'eta': self.estimate_resolution_time(),
            'next_update': datetime.now() + timedelta(minutes=interval_minutes)
        }
        
        # Enviar para as partes interessadas
        self.send_status_update(update)
        self.status_updates.append(update)
    
    def log_timeline_event(self, event, timestamp=None):
        """Documentar a linha do tempo do incidente"""
        self.timeline.append({
            'timestamp': timestamp or datetime.now(),
            'event': event,
            'logged_by': self.get_current_user()
        })

3. Estratégias de Mitigação:

def evaluate_mitigation_options():
    """Avaliar e priorizar opções de mitigação"""
    options = [
        {
            'action': 'Reverter implantação',
            'time_to_implement': 5,  # minutos
            'risk': 'low',
            'effectiveness': 'high',
            'reversible': True
        },
        {
            'action': 'Aumentar a escala dos recursos',
            'time_to_implement': 2,
            'risk': 'low',
            'effectiveness': 'medium',
            'reversible': True
        },
        {
            'action': 'Desativar o recurso',
            'time_to_implement': 1,
            'risk': 'low',
            'effectiveness': 'high',
            'reversible': True
        },
        {
            'action': 'Failover do banco de dados',
            'time_to_implement': 10,
            'risk': 'medium',
            'effectiveness': 'high',
            'reversible': False
        }
    ]
    
    # Classificar por: baixo risco, alta eficácia, implementação rápida
    sorted_options = sorted(
        options,
        key=lambda x: (
            x['risk'] == 'low',
            x['effectiveness'] == 'high',
            -x['time_to_implement']
        ),
        reverse=True
    )
    
    return sorted_options

4. Post-mortem (Sem Culpa):

# Post-mortem do Incidente: Interrupção da API

**Data:** 2024-11-25  
**Duração:** 45 minutos  
**Gravidade:** SEV-1  
**Comandante do Incidente:** Alice  
**Líder Técnico:** Bob

## Resumo Executivo
Interrupção completa da API afetando todos os usuários devido ao esgotamento do pool de conexões do banco de dados.

## Impacto
- **Usuários afetados:** 100% (todos os usuários)
- **Duração:** 45 minutos
- **Impacto na receita:** ~$50.000
- **Impacto no SLO:** Consumiu 75% do orçamento de erro mensal

## Causa Raiz
Pool de conexões do banco de dados esgotado devido ao vazamento de conexão no novo recurso implantado 2 horas antes do incidente.

## Linha do Tempo
| Hora  | Evento                                             |
|-------|----------------------------------------------------|
| 14:00 | Implantação da v2.5.0                              |
| 15:45 | Primeiros alertas para aumento da latência        |
| 15:50 | Interrupção completa da API                        |
| 15:52 | Incidente declarado (SEV-1)                        |
| 15:55 | Banco de dados identificado como gargalo          |
| 16:05 | Decisão de reverter a implantação                 |
| 16:15 | Reversão concluída                                 |
| 16:20 | Serviço em recuperação                             |
| 16:35 | Recuperação total confirmada                       |

## O Que Deu Certo
- Detecção rápida (5 minutos a partir do primeiro sintoma)
- Estrutura de comando de incidente clara
- Decisão rápida de reverter
- Boa comunicação com as partes interessadas

## O Que Deu Errado
- Vazamento de conexão não detectado nos testes
- Sem monitoramento do pool de conexões
- Implantação durante o horário de pico

## Itens de Ação
| Ação                                     | Proprietário | Data de Vencimento | Status |
|------------------------------------------|------------|-------------------|--------|
| Adicionar monitoramento do pool de conexões | Alice      | 2024-12-01        | Aberto |
| Implementar detecção de vazamento de conexão nos testes | Bob        | 2024-12-05        | Aberto |
| Atualizar política de implantação (evitar horários de pico) | Charlie    | 2024-11-30        | Aberto |
| Adicionar disjuntor para conexões de banco de dados | David      | 2024-12-10        | Aberto |

## Lições Aprendidas
- Lacunas de monitoramento podem ocultar problemas críticos
- O tempo de implantação é importante
- Necessidade de melhor teste de integração para vazamentos de recursos

Raridade: Muito Comum
Dificuldade: Difícil


Confiabilidade de Sistemas Distribuídos

6. Como você garante a confiabilidade em uma arquitetura de microsserviços distribuídos?

Resposta: Sistemas distribuídos introduzem desafios únicos de confiabilidade:

Padrões Chave:

1. Service Mesh para Resiliência:

# Exemplo do Istio: Disjuntor e tentativas
apiVersion: networking.istio.io/v1beta1
kind: DestinationRule
metadata:
  name: api-service
spec:
  host: api-service
  trafficPolicy:
    connectionPool:
      tcp:
        maxConnections: 100
      http:
        http1MaxPendingRequests: 50
        http2MaxRequests: 100
        maxRequestsPerConnection: 2
    outlierDetection:
      consecutiveErrors: 5
      interval: 30s
      baseEjectionTime: 30s
      maxEjectionPercent: 50
      minHealthPercent: 40
    loadBalancer:
      simple: LEAST_REQUEST
---
apiVersion: networking.istio.io/v1beta1
kind: VirtualService
metadata:
  name: api-service
spec:
  hosts:
  - api-service
  http:
  - retries:
      attempts: 3
      perTryTimeout: 2s
      retryOn: 5xx,reset,connect-failure,refused-stream
    timeout: 10s
    route:
    - destination:
        host: api-service

2. Rastreamento Distribuído:

from opentelemetry import trace
from opentelemetry.exporter.jaeger.thrift import JaegerExporter
from opentelemetry.sdk.trace import TracerProvider
from opentelemetry.sdk.trace.export import BatchSpanProcessor
from opentelemetry.instrumentation.requests import RequestsInstrumentor

# Configurar rastreamento
trace.set_tracer_provider(TracerProvider())
jaeger_exporter = JaegerExporter(
    agent_host_name="jaeger",
    agent_port=6831,
)
trace.get_tracer_provider().add_span_processor(
    BatchSpanProcessor(jaeger_exporter)
)

# Instrumentar a biblioteca de solicitações
RequestsInstrumentor().instrument()

# Usar no código
tracer = trace.get_tracer(__name__)

def process_order(order_id):
    with tracer.start_as_current_span("process_order") as span:
        span.set_attribute("order.id", order_id)
        
        # Chamar o serviço de pagamento
        with tracer.start_as_current_span("call_payment_service"):
            payment_result = call_payment_service(order_id)
        
        # Chamar o serviço de inventário
        with tracer.start_as_current_span("call_inventory_service"):
            inventory_result = call_inventory_service(
Newsletter subscription

Dicas de carreira semanais que realmente funcionam

Receba as últimas ideias diretamente na sua caixa de entrada

Crie um Currículo que Te Contrate 60% Mais Rápido

Em minutos, crie um currículo personalizado e compatível com ATS comprovado para conseguir 6 vezes mais entrevistas.

Crie um currículo melhor

Compartilhar esta publicação

Faça Seus 6 Segundos Contarem

Os recrutadores escaneiam currículos por uma média de apenas 6 a 7 segundos. Nossos modelos comprovados são projetados para capturar atenção instantaneamente e mantê-los lendo.