Meu notebook dizia conectado. O cliente do AWS Client VPN mostrava o estado verde, o endpoint registrava uma sessão e, mesmo assim, eu não conseguia abrir uma porta do MongoDB em uma instância EC2 numa sub-rede privada. Nada estava obviamente quebrado: o certificado era válido, o perfil vinha do console e o túnel carregava tráfego. O erro era meu, porque eu lia conectado como autorizado.

O login responde exatamente a uma pergunta: esta identidade pode estabelecer uma sessão? Tudo o que vem depois é decidido por regras separadas que nunca veem o seu certificado. Uma sessão que se autentica e um pacote que chega são dois sucessos diferentes, e a lacuna entre eles é onde vivem a maioria dos relatos do tipo a VPN está no ar, mas o host não é acessível.

As verificações abaixo são a ordem que uso agora.

O que uma sessão conectada realmente prova

Durante o handshake, o endpoint valida o certificado do cliente contra o seu trust store ou redireciona o navegador para o seu provedor de identidade quando o SAML está configurado. Se isso passar, o cliente recebe um endereço do CIDR de cliente do endpoint e o console mostra uma conexão ativa. Em nenhum momento dessa troca algo pergunta se você pode chegar a 10.0.4.17 na porta 27017.

A permissão para um destino é um objeto separado no endpoint. Cada fluxo é comparado às regras de autorização, e cada uma delas associa um CIDR de destino ao grupo a que a regra é concedida. Quando nenhuma regra cobre o destino, o endpoint aceita a sessão e descarta o tráfego. Não há banner, não há laço de reconexão e não há nada na interface do cliente que diga negado.

Compare a regra de autorização com o recurso, não com a VPC

Liste as regras e coloque-as ao lado do endereço que a instância realmente tem:

aws ec2 describe-client-vpn-authorization-rules \
  --client-vpn-endpoint-id cvpn-endpoint-0a1b2c3d4e5f6a7b8

A saída mostra um CIDR de destino e um ID de grupo por regra. Há duas falhas escondidas ali. A regra pode autorizar 10.0.0.0/16 enquanto a instância está numa VPC emparelhada em 10.1.0.0/16; a rota de peering existe, mas ninguém escreveu uma regra de autorização para o segundo intervalo. Ou a regra aponta para um grupo do diretório a que o usuário pertence no diretório, mas não no grupo que o endpoint avalia.

Escreva a regra mais estreita que cobre o destino, e adicione uma segunda só quando um segundo CIDR for realmente necessário. Uma regra ampla 0.0.0.0/0 de um início rápido funciona, e é por isso que ela sobrevive até a produção e esconde o modelo.

Duas tabelas de rotas decidem se o pacote se move

Uma rota do endpoint mapeia um CIDR de destino para uma das sub-redes com que o endpoint está associado. Isso é metade do caminho. A tabela de rotas da própria sub-rede ainda precisa saber como encaminhar o pacote, e isso importa no momento em que o destino está atrás de uma conexão de peering, de um gateway de trânsito ou de um intervalo local alcançável por um túnel site-to-site.

aws ec2 describe-client-vpn-routes \
  --client-vpn-endpoint-id cvpn-endpoint-0a1b2c3d4e5f6a7b8

Procure uma rota cujo destino corresponda ao CIDR do recurso e cujo alvo seja uma sub-rede associada. Se a rota faltar, adicione-a. Se estiver presente e o host continuar mudo, a lacuna está do lado da VPC, então compare com a tabela de rotas da sub-rede de associação.

Um ajuste do lado do cliente quebra o roteamento sem quebrar o túnel: um perfil que contém route-nopull. A diretiva manda um cliente baseado em OpenVPN ignorar as rotas que o servidor empurra, então a interface sobe só com o endereço do próprio endpoint e o destino simplesmente não tem rota. Verifique com ip route show no Linux ou netstat -rn no macOS se existe uma rota pela interface tun. Se não existir, remova route-nopull do perfil exportado e reconecte para que as rotas empurradas sejam aplicadas.

Os grupos de segurança não veem o endereço do seu cliente

Esta é a parte que eu errei por uma tarde inteira. Para um endpoint IPv4 associado a uma sub-rede, o serviço traduz o endereço de origem do cliente para o endereço da interface de rede do endpoint naquela sub-rede. O pacote que chega à instância não carrega o endereço que o seu cliente mostrava, então uma regra de grupo de segurança que permite o pool de clientes, digamos 172.16.0.0/22, não corresponde a nada.

Permita a porta a partir do grupo de segurança do endpoint, que está ligado à interface da associação, e não a partir do CIDR de cliente. Referenciar o grupo é mais durável do que gravar um endereço na mão, porque o endereço da interface não é seu para controlar. As ACLs de rede não guardam estado, então onde existem entradas personalizadas, tanto a direção de entrada quanto a de saída precisam permitir o fluxo.

Conecte-se também ao endereço privado da instância. Um IP público tira o pacote da VPC e o traz de volta por outro caminho, com outras regras, então um teste pelo endereço público não diz nada sobre o caminho privado.

Uma ordem de isolamento que para na primeira falha

Percorra estes pontos em ordem e pare onde um falhar. Cada passo descarta uma camada em vez de todas.

  1. Confirme qual identidade a sessão usou e qual grupo o endpoint avalia. Um certificado de um trust store não é o mesmo principal que uma asserção SAML do diretório.
  2. Confirme que uma regra de autorização cobre o CIDR do recurso para aquele grupo.
  3. Confirme que existe uma rota do endpoint e que ela aponta para uma sub-rede associada, e então que a tabela de rotas da sub-rede consegue encaminhar adiante.
  4. Confirme que o grupo de segurança permite a porta a partir da interface do endpoint e não do pool de clientes.
  5. Teste de dentro da VPC, com uma sessão SSM em outra instância na mesma sub-rede, para separar um problema de aplicação de um problema do caminho do cliente.

Quando os passos não são decisivos, esta tabela é o que me apoia:

SymptomLayer to inspect
Client shows connected, host times out, no byte growth on the interfaceAuthorization rule, then security group
Ping fails but a TCP connect to the port succeedsICMP is blocked; not an access failure
Tunnel reconnects every few minutesTwo machines sharing one client certificate
Works on one laptop, fails on anotherLocal profile has route-nopull or stale pushed routes

Dois detalhes da conta produzem sintomas que parecem falhas de permissão. Cada usuário precisa de um certificado de cliente distinto; compartilhar um entre duas máquinas faz as sessões se deslocarem mutuamente, e o resultado é um laço de reconexão em vez de uma negação. Quando um novo endpoint é criado, o console mostra um nome DNS que algumas versões do cliente só aceitam com o prefixo aleatório exibido na página do endpoint, então copie o nome completo em vez de reconstruí-lo.

Se o quinto passo travar você, puxe o log de conexões do endpoint e leia as entradas de autorização antes de mudar qualquer coisa. O log nomeia o destino verificado e a regra que correspondeu ou não, e isso reduz a pergunta de quatro camadas a uma única resposta.

Artigos relacionados