Como posso configurar meu firewall para trabalhar com o Docker?

1

Meu computador está hospedando um aplicativo na porta 1234 que nunca deve ser acessível a partir de nada além da minha máquina. No entanto, meu contêiner do Docker (que está executando o Apache) deve poder acessá-lo. Da mesma forma, meu contêiner do Docker está hospedando vários recursos em várias portas que, da mesma forma, devem estar acessíveis apenas no meu computador. Agora, isso é ainda mais complicado pelo fato de meu sistema usar uma ponte para essa rede específica:

NETWORK ID          NAME                DRIVER              SCOPE
4d4b5e752963        bridge              bridge              local               
c387eb42698a        project_default     bridge              local               
6818c0eb94bf        host                host                local               
f7e4ed6c05a2        none                null                local  

Essa ponte (irritantemente) sempre tem um ID gerado aleatoriamente que muda cada vez que eu reinicio minha configuração do Docker Compose:

br-c387eb42698a Link encap:Ethernet  HWaddr 02:42:29:95:fd:2c  
          inet addr:172.18.0.1  Bcast:0.0.0.0  Mask:255.255.0.0
          inet6 addr: fe80::42:29ff:fe95:fd2c/64 Scope:Link
          UP BROADCAST RUNNING MULTICAST  MTU:1500  Metric:1
          RX packets:405753 errors:0 dropped:0 overruns:0 frame:0
          TX packets:530699 errors:0 dropped:0 overruns:0 carrier:0
          collisions:0 txqueuelen:0 
          RX bytes:85147217 (85.1 MB)  TX bytes:75260996 (75.2 MB)

Em suma, preciso do seguinte:

  • Qualquer host em br-c387eb42698a (ou qualquer que seja o nome da rede) para acessar a porta 1234 em minha máquina local (convenientemente 172.18.0.1)
  • Minha máquina pode acessar qualquer porta em qualquer host dessa sub-rede. (padrão)
  • O mundo nunca poderá acessar qualquer porta da sub-rede ou porta 1234.

Idealmente, uma solução aqui funcionaria de um modo independente de IP, de modo que não dependesse da ponte estar na sub-rede 172.18.0.0/24 , nem quebraria ou permitiria vazamentos de dados se eu estivesse conectado a uma rede que por acaso contém a sub-rede 172.18.0.0/24 .

A coisa mais fácil que posso imaginar seria usar o nome da interface e configurar as regras do UFW em torno disso, mas não posso fazer isso, já que minha interface está mudando constantemente.

Como posso fazer isso? Embora eu prefira fazer isso em ufw puro (ou iptables , se necessário), estou aberto a soluções que envolvam a configuração do Docker para sempre atribuir um ID persistente (ou até mesmo um nome personalizado?) À interface de ponte.

    
por Kaz Wolfe 10.04.2017 / 22:34

2 respostas

3

Isso não é possível no UFW vanilla devido ao fato de que o nome da interface está em um estado constante de irreversibilidade. Para definir algo assim, uma rede definida manualmente deve ser criada. Em suma, pode-se usar as opções de driver do bridge do Docker em a configuração de composição para criar uma rede personalizada . Isso será parecido com:

networks:
    my_bridge:
        driver: bridge
        driver_opts:
            com.docker.network.bridge.name: my-bridge

A partir daqui, a configuração da ponte pode ser adicionada a cada serviço no arquivo de composição:

myimage:
    image: myimage:1.0
    ports:
        - "2580:2580"
    networks:
        - my_bridge

Então, na próxima partida do sistema Compose, a nova rede será criada com o nome próprio:

my-bridge Link encap:Ethernet  HWaddr 11:22:33:44:55:66  
      inet addr:172.18.0.1  Bcast:0.0.0.0  Mask:255.255.0.0
      inet6 addr: fe80::42:1122:3344:5566/64 Scope:Link
      UP BROADCAST RUNNING MULTICAST  MTU:1500  Metric:1
      RX packets:11 errors:0 dropped:0 overruns:0 frame:0
      TX packets:6 errors:0 dropped:0 overruns:0 carrier:0
      collisions:0 txqueuelen:0 
      RX bytes:788 (788.0 B)  TX bytes:695 (695.0 B)

A partir daí, adicionar regras UFW para permitir a conexão à porta 1234 é trivial:

ufw allow in on my-bridge from any to any port 1234

E, de repente, tudo funciona perfeitamente!

    
por Kaz Wolfe 10.04.2017 / 23:48
1

Para integrar a resposta aceita, você também pode usar um comando docker para criar a rede fora do docker-compose:

sudo docker network create -d bridge -o com.docker.network.bridge.name=my-bridge my_bridge

Depois disso, você pode inspecionar a emissão de redes

ip link show

Agora, nos seus arquivos de composição, você pode apenas redirecionar a rede padrão ou definir qualquer rede que você goste de remapear para a rede já existente

version: "3"
services:
  test:
    image: nginx:alpine
    ports:
      - "80:80"
networks:
  default:
    external:
      name: my_bridge
    
por Roberto Lo Giacco 05.06.2018 / 20:22