Quiz: Spring Cloud e Microservices
Teste seus conhecimentos sobre arquitetura de microservices e Spring Cloud.
30 questões - Clique em cada pergunta para revelar a resposta.
Questões 1-10: Arquitetura de Microservices
Questão 1: Qual a diferença entre monólito e microservices?
Resposta:
| Monólito | Microservices |
|---|---|
| Uma única aplicação | Serviços independentes |
| Um banco de dados | DB por serviço |
| Deploy global | Deploy independente |
| Escalabilidade global | Escalabilidade por serviço |
| Simples no início | Complexo no início |
| Forte acoplamento | Baixo acoplamento |
Questão 2: Quando escolher uma arquitetura de microservices?
Resposta:
- Equipe grande (múltiplas equipes)
- Necessidade de escalabilidade diferenciada
- Tecnologias diferentes por serviço
- Deploys frequentes e independentes
- Tolerância a falhas por serviço
Evite para: equipes pequenas, protótipos, aplicações simples.
Questão 3: O que é Service Discovery?
Resposta: Mecanismo que permite aos serviços se encontrarem dinamicamente sem configuração estática de endereços IP.
Service A: "Onde está o Service B?"
↓
Eureka Server: "Service B está em 192.168.1.10:8081 e 192.168.1.11:8081"
↓
Service A chama Service B
Questão 4: O que é um API Gateway?
Resposta: Ponto de entrada único para todos os microservices:
- Roteamento para os serviços
- Autenticação centralizada
- Rate limiting
- Load balancing
- Logging/Monitoring
Cliente → API Gateway → Service A
→ Service B
→ Service C
Questão 5: O que é um Circuit Breaker?
Resposta: Padrão de resiliência que "corta" as chamadas para um serviço com falha:
Estados:
CLOSED → Chamadas normais
OPEN → Chamadas bloqueadas (fallback)
HALF_OPEN → Teste de recuperação
Evita cascata de falhas.
Questão 6: O que é o padrão Saga?
Resposta: Gerenciamento de transações distribuídas via uma sequência de transações locais com compensações:
Order → Payment → Inventory → Shipping
↓ (falha)
Compensação: reembolsar
Cada serviço gerencia sua transação e pode desfazer (compensar) se necessário.
Questão 7: O que é CQRS?
Resposta: Command Query Responsibility Segregation - separa operações de leitura e escrita:
Comandos (Write) → Command Service → Write DB
Consultas (Read) → Query Service → Read DB (otimizado)
Permite otimizar cada lado independentemente.
Questão 8: O que é Event Sourcing?
Resposta: Armazenar todos os eventos ao invés do estado atual:
Events:
1. UserCreated {id: 1, name: "John"}
2. UserEmailChanged {id: 1, email: "john@new.com"}
3. UserDeleted {id: 1}
Estado = replay de todos os eventos
Vantagens: auditoria completa, reconstrução de estado, event replay.
Questão 9: Quais são os 12 fatores de uma aplicação cloud-native?
Resposta:
- Codebase: um repositório, múltiplos deploys
- Dependencies: declaradas e isoladas
- Config: no ambiente
- Backing services: tratados como recursos anexados
- Build, release, run: etapas estritamente separadas
- Processes: stateless
- Port binding: auto-contido
- Concurrency: escala horizontal
- Disposability: start/stop rápidos
- Dev/prod parity: ambientes similares
- Logs: fluxo de eventos
- Admin processes: tarefas pontuais
Questão 10: Como gerenciar a comunicação entre serviços?
Resposta:
| Tipo | Protocolo | Uso |
|---|---|---|
| Síncrono | REST/gRPC | Resposta imediata necessária |
| Assíncrono | RabbitMQ/Kafka | Desacoplamento, eventos |
Prefira assíncrono sempre que possível para resiliência.
Questões 11-20: Spring Cloud
Questão 11: Como configurar o Eureka Server?
Resposta:
@SpringBootApplication
@EnableEurekaServer
public class EurekaServerApplication { }
server:
port: 8761
eureka:
client:
register-with-eureka: false
fetch-registry: false
Questão 12: Como registrar um serviço no Eureka?
Resposta:
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-netflix-eureka-client</artifactId>
</dependency>
spring:
application:
name: user-service
eureka:
client:
service-url:
defaultZone: http://localhost:8761/eureka/
Questão 13: Como chamar outro serviço com RestTemplate e load balancing?
Resposta:
@Bean
@LoadBalanced
public RestTemplate restTemplate() {
return new RestTemplate();
}
@Service
public class OrderService {
private final RestTemplate restTemplate;
public User getUser(Long id) {
// Usa o nome do serviço, não a URL
return restTemplate.getForObject(
"http://user-service/api/users/" + id, User.class);
}
}
Questão 14: Como usar OpenFeign para chamadas entre serviços?
Resposta:
@EnableFeignClients
@SpringBootApplication
public class OrderApplication { }
@FeignClient(name = "user-service")
public interface UserClient {
@GetMapping("/api/users/{id}")
User getUser(@PathVariable Long id);
}
@Service
public class OrderService {
private final UserClient userClient;
public Order createOrder(OrderRequest req) {
User user = userClient.getUser(req.getUserId());
// ...
}
}
Questão 15: Como configurar o Spring Cloud Config Server?
Resposta:
@SpringBootApplication
@EnableConfigServer
public class ConfigServerApplication { }
server:
port: 8888
spring:
cloud:
config:
server:
git:
uri: https://github.com/org/config-repo
default-label: main
Questão 16: Como um serviço cliente usa o Config Server?
Resposta:
# bootstrap.yml
spring:
application:
name: user-service
cloud:
config:
uri: http://localhost:8888
O serviço busca user-service.yml do Config Server.
Questão 17: Como configurar o Spring Cloud Gateway?
Resposta:
spring:
cloud:
gateway:
routes:
- id: user-service
uri: lb://user-service
predicates:
- Path=/api/users/**
filters:
- StripPrefix=1
- id: order-service
uri: lb://order-service
predicates:
- Path=/api/orders/**
- Method=GET,POST
Questão 18: Como adicionar um filtro global no Gateway?
Resposta:
@Component
public class LoggingFilter implements GlobalFilter, Ordered {
@Override
public Mono<Void> filter(ServerWebExchange exchange, GatewayFilterChain chain) {
log.info("Request: {} {}",
exchange.getRequest().getMethod(),
exchange.getRequest().getPath());
return chain.filter(exchange).then(Mono.fromRunnable(() -> {
log.info("Response: {}",
exchange.getResponse().getStatusCode());
}));
}
@Override
public int getOrder() {
return -1;
}
}
Questão 19: Como configurar o Resilience4j Circuit Breaker?
Resposta:
resilience4j:
circuitbreaker:
instances:
userService:
slidingWindowSize: 10
failureRateThreshold: 50
waitDurationInOpenState: 10000
permittedNumberOfCallsInHalfOpenState: 3
@CircuitBreaker(name = "userService", fallbackMethod = "fallback")
public User getUser(Long id) {
return userClient.getUser(id);
}
public User fallback(Long id, Exception ex) {
return new User(id, "Fallback User", "N/A");
}
Questão 20: Como configurar retry com Resilience4j?
Resposta:
resilience4j:
retry:
instances:
userService:
maxAttempts: 3
waitDuration: 1000
enableExponentialBackoff: true
exponentialBackoffMultiplier: 2
@Retry(name = "userService")
@CircuitBreaker(name = "userService", fallbackMethod = "fallback")
public User getUser(Long id) {
return userClient.getUser(id);
}
Questões 21-30: Padrões Avançados
Questão 21: Como implementar um fallback com Feign?
Resposta:
@FeignClient(name = "user-service", fallbackFactory = UserClientFallback.class)
public interface UserClient {
@GetMapping("/api/users/{id}")
User getUser(@PathVariable Long id);
}
@Component
public class UserClientFallback implements FallbackFactory<UserClient> {
@Override
public UserClient create(Throwable cause) {
return id -> new User(id, "Fallback", "N/A");
}
}
Questão 22: Como implementar rate limiting no Gateway?
Resposta:
spring:
cloud:
gateway:
routes:
- id: api-route
uri: lb://api-service
predicates:
- Path=/api/**
filters:
- name: RequestRateLimiter
args:
redis-rate-limiter.replenishRate: 10
redis-rate-limiter.burstCapacity: 20
key-resolver: "#{@userKeyResolver}"
@Bean
public KeyResolver userKeyResolver() {
return exchange -> Mono.just(
exchange.getRequest().getRemoteAddress().getHostName()
);
}
Questão 23: Como atualizar a configuração em tempo real?
Resposta:
@RefreshScope
@RestController
public class ConfigController {
@Value("${app.message}")
private String message;
@GetMapping("/message")
public String getMessage() {
return message;
}
}
# Disparar o refresh
curl -X POST http://localhost:8080/actuator/refresh
Ou com Spring Cloud Bus para propagar para todos os serviços.
Questão 24: Como rastrear requisições distribuídas?
Resposta: Com Micrometer Tracing (ex-Sleuth) + Zipkin:
<dependency>
<groupId>io.micrometer</groupId>
<artifactId>micrometer-tracing-bridge-brave</artifactId>
</dependency>
<dependency>
<groupId>io.zipkin.reporter2</groupId>
<artifactId>zipkin-reporter-brave</artifactId>
</dependency>
management:
tracing:
sampling:
probability: 1.0
zipkin:
tracing:
endpoint: http://zipkin:9411/api/v2/spans
Cada requisição tem um traceId único propagado entre os serviços.
Questão 25: Como proteger as comunicações entre serviços?
Resposta:
- mTLS: certificados mútuos
- JWT propagation: token passado entre serviços
- Service mesh: Istio, Linkerd
- Network policies: Kubernetes
// JWT propagation com Feign
@Configuration
public class FeignConfig {
@Bean
public RequestInterceptor authInterceptor() {
return template -> {
String token = SecurityContextHolder.getContext()
.getAuthentication().getCredentials().toString();
template.header("Authorization", "Bearer " + token);
};
}
}
Questão 26: Como gerenciar secrets em microservices?
Resposta:
- Spring Cloud Config com criptografia
- Vault (HashiCorp)
- Kubernetes Secrets
- AWS Secrets Manager / Azure Key Vault
# Config Server com criptografia
spring:
cloud:
config:
server:
encrypt:
enabled: true
encrypt:
key: ${ENCRYPT_KEY}
Questão 27: Como gerenciar versões de API?
Resposta:
- URL versioning:
/api/v1/users - Header versioning:
Accept: application/vnd.api.v1+json - Query param:
/api/users?version=1
@RestController
@RequestMapping("/api/v1/users")
public class UserControllerV1 { }
@RestController
@RequestMapping("/api/v2/users")
public class UserControllerV2 { }
Questão 28: Como fazer deploy de microservices com Kubernetes?
Resposta:
# deployment.yaml
apiVersion: apps/v1
kind: Deployment
metadata:
name: user-service
spec:
replicas: 3
selector:
matchLabels:
app: user-service
template:
metadata:
labels:
app: user-service
spec:
containers:
- name: user-service
image: user-service:1.0
ports:
- containerPort: 8080
env:
- name: EUREKA_SERVER
value: "http://eureka:8761/eureka"
---
apiVersion: v1
kind: Service
metadata:
name: user-service
spec:
selector:
app: user-service
ports:
- port: 80
targetPort: 8080
Questão 29: Como monitorar microservices?
Resposta:
- Métricas: Prometheus + Grafana
- Logs: ELK Stack (Elasticsearch, Logstash, Kibana)
- Traces: Zipkin / Jaeger
- Alertas: Prometheus Alertmanager
Dashboard centralizado com:
- Latência por serviço
- Taxa de erro
- Throughput
- Dependências
Questão 30: Quais são as boas práticas de microservices?
Resposta:
- Bounded context: um serviço = um domínio de negócio
- Database per service: sem DB compartilhado
- API contracts: OpenAPI/Swagger
- Idempotência: operações repetíveis sem efeito colateral
- Healthchecks: Actuator para cada serviço
- Circuit breakers: proteção contra falhas
- Comunicação assíncrona: preferir sempre que possível
- Centralized logging: correlação por traceId
- Infrastructure as Code: Terraform, Helm
- Feature flags: deploy progressivo
Pontuação
| Pontuação | Nível |
|---|---|
| 27-30 | Excelente - Microservices dominados |
| 21-26 | Bom - Algumas revisões |
| 15-20 | Médio - Releia os capítulos |
| Menos de 15 | Precisa revisar |