Ligação de porta do contêiner do Windows no Windows Server 2016 não está funcionando

5

Estou executando um Windows Container em um host do Windows (Windows Server 2016 TP4) .

O contêiner deve executar internamente um servidor IIS na porta 80 e eu também quero vincular a porta 80 ao host , para que eu possa acessá-lo via IP host / URL.

Eu segui as instruções da Microsoft em

Eu tentei a abordagem via Powershell e Docker e, em ambos os casos, a ligação de porta para o host não funciona.

========================= Abordagem de Powershell ================= =========

Implantando o host do contêiner no sistema existente (Windows Server 2016 TP4)

PS C:> wget -uri https://aka.ms/tp4/Install-ContainerHost -OutFile C:\Install-ContainerHost.ps1

PS C:> powershell.exe -NoProfile C:\Install-ContainerHost.ps1

Querying status of Windows feature: Containers...
Feature Containers is already enabled.
Waiting for Hyper-V Management...
Networking is already configured.  Confirming configuration...
Getting Container OS image (NanoServer) version 10.0.10586.0 from OneGet (this may take a few minutes)...
Container base image install complete.  Querying container images...
OS image (NanoServer) is already installed.
The following images are present on this machine:
    ContainerImage (Name = 'NanoServer') [Publisher = 'CN=Microsoft', Version = '10.0.10586.0']
    ContainerImage (Name = 'WindowsServerCore') [Publisher = 'CN=Microsoft', Version = '10.0.10586.0']

Docker is already installed.
Stopping Docker...
Starting Docker...
Tagging new base image (8572198a60f1)...
Base image is now tagged:
nanoserver          10.0.10586.0        8572198a60f1        5 months ago        0 B
nanoserver          latest              8572198a60f1        5 months ago        0 B
Script complete!

Preparando a imagem e o contêiner que executam o IIS (com base na imagem WindowsServerCore)

Estas são as etapas exatas descritas na documentação da Microsoft, no link . Eu crio um container do WindowsServerCore, instalo o IIS nele e faço uma nova imagem dele, que eu posso reutilizar depois.

PS C:> Get-ContainerImage

Name              Publisher    Version      IsOSImage
----              ---------    -------      ---------
NanoServer        CN=Microsoft 10.0.10586.0 True
WindowsServerCore CN=Microsoft 10.0.10586.0 True


PS C:\> New-Container -Name TP4Demo -ContainerImageName WindowsServerCore -SwitchName "Virtual Switch"

Name    State Uptime   ParentImageName
----    ----- ------   ---------------
TP4Demo Off   00:00:00 WindowsServerCore


PS C:\> Get-Container

Name    State Uptime   ParentImageName
----    ----- ------   ---------------
TP4Demo Off   00:00:00 WindowsServerCore


PS C:\> Start-Container -Name TP4Demo

PS C:\> Enter-PSSession -ContainerName TP4Demo -RunAsAdministrator
[TP4Demo]: PS C:\Windows\system32> Install-WindowsFeature web-server

Success Restart Needed Exit Code      Feature Result
------- -------------- ---------      --------------
True    No             Success        {Common HTTP Features, Default Document, D...


[TP4Demo]: PS C:\Windows\system32> exit
PS C:\> Stop-Container -Name TP4Demo

PS C:\> New-ContainerImage -ContainerName TP4Demo -Name WindowsServerCoreIIS -Publisher Demo -Version 1.0

Name                 Publisher Version IsOSImage
----                 --------- ------- ---------
WindowsServerCoreIIS CN=Demo   1.0.0.0 False


PS C:\> Remove-Container -Name TP4Demo -Force

Agora eu tenho um contêiner do IIS pronto que eu vinculo ao "Virtual Switch".

PS C:\> New-Container -Name IIS -ContainerImageName WindowsServerCoreIIS -SwitchName "Virtual Switch"

Name State Uptime   ParentImageName
---- ----- ------   ---------------
IIS  Off   00:00:00 WindowsServerCoreIIS


PS C:\> Start-Container -Name IIS

PS C:\> Invoke-Command -ContainerName IIS {ipconfig}

Windows IP Configuration

Ethernet adapter vEthernet (Virtual Switch-30179F35-A9BD-4231-B264-BDD2994BD956-0):

   Connection-specific DNS Suffix  . :
   Link-local IPv6 Address . . . . . : fe80::24f4:c726:ed9b:e603%28
   IPv4 Address. . . . . . . . . . . : 172.16.0.2
   Subnet Mask . . . . . . . . . . . : 255.240.0.0
   Default Gateway . . . . . . . . . : 172.16.0.1

Adicionando o mapeamento de porta e a regra de firewall:

PS C:\> if (!(Get-NetNatStaticMapping | where {$_.ExternalPort -eq 80})) {Add-NetNatStaticMapping -NatName "ContainerNat" -Protocol TCP -ExternalIPAddress 0.0.0.0 -InternalIPAddress 172.16.0.2 -InternalPort 80 -ExternalPort 80}

PS C:\> if (!(Get-NetFirewallRule | where {$_.Name -eq "TCP80"})) {New-NetFirewallRule -Name "TCP80" -DisplayName "HTTP on TCP/80" -Protocol tcp -LocalPort 80 -Action Allow -Enabled True}

Agora que adicionei o mapeamento de porta (e a regra de firewall), conseguirei alcançar o IIS por meio de meu host. (Só para ter certeza, eu desativei o firewall no host completamente).

Mas a ligação da porta do host não funciona. Não consigo acessar o IIS por meio dos IPs de host e da porta associada por meio do link nem link ou link

PS C:\> wget http://10.10.0.79:80/
wget : Unable to connect to the remote server
At line:1 char:1
+ wget http://10.10.0.79:80/
+ ~~~~~~~~~~~~~~~~~~~~~~~~~~
    + CategoryInfo          : InvalidOperation: (System.Net.HttpWebRequest:HttpWebRequest) [Invoke-WebRequest], WebException
    + FullyQualifiedErrorId : WebCmdletWebResponseException,Microsoft.PowerShell.Commands.InvokeWebRequestCommand

PS C:\> wget http://172.16.0.1:80/
wget : Unable to connect to the remote server
At line:1 char:1
+ wget http://172.16.0.1:80/
+ ~~~~~~~~~~~~~~~~~~~~~~~~~~
    + CategoryInfo          : InvalidOperation: (System.Net.HttpWebRequest:HttpWebRequest) [Invoke-WebRequest], WebException
    + FullyQualifiedErrorId : WebCmdletWebResponseException,Microsoft.PowerShell.Commands.InvokeWebRequestCommand

Eu só posso acessar a página padrão do IIS por meio do IP do contêiner ( link ).

========================= Abordagem do Docker ================= =========

E esta é a minha abordagem usando o Docker para gerenciar o contêiner:

C:\> docker run --name iisbase -it windowsservercore cmd
C:\> powershell.exe Install-WindowsFeature web-server
C:\> exit
PS C:\Windows\system32> docker commit iisbase windowsservercoreiis
64271b60a1c4af29ce37ebcee45b00d824883eb67c717d4cee765d9f696867bb
C:\> powershell.exe "if(!(Get-NetFirewallRule | where {$_.Name -eq 'TCP80'})) { New-NetFirewallRule -Name 'TCP80' -DisplayName 'HTTP on TCP/80' -Protocol tcp -LocalPort 80 -Action Allow -Enabled True }"
C:\> docker run --name iisdemo -it -p 80:80 windowsservercoreiis cmd

No final, só consigo acessar o IIS por meio do IP do contêiner, não por meio do IP do host.

Estou usando o Docker versão 1.10.0-dev, build 18c9fe0.

    
por Mathias Conradt 25.03.2016 / 14:25

2 respostas

1

Parece ser um problema com o Windows Server TP4.

Stefan Scherer da equipe do Docker respondeu ao meu problema relatado: link

I can reproduce the problems of @mathiasconradt. Played with the voting-app last week with TP4, I have the same workaround: Opening firewall ports on the host, opening the web server url with container's IP addresses. Can't wait to test the voting-app on TP5.

Esperando por TP5 ... enquanto isso eu uso o Apache httpd no host para lidar com o encaminhamento de porta.

    
por 28.03.2016 / 21:50
0

Nota: Finalmente, este é um bug no Windows Server 2016 TP4 que causa o comportamento descrito abaixo (veja os comentários). Mesmo que o Docker Daemon esteja supostamente instalado, o cliente parece ser usado com todas as limitações descritas abaixo. Este bug pode ser corrigido no futuro TP5.

Esta é uma limitação da implementação do Docker no Windows, onde você não pode se conectar ao contêiner através do host.

Esta é a resposta para esta mesma pergunta no relatório de erros # 15740: exposição da porta no windows =? :

The reason you're having this, is because on Linux, the docker daemon (and your containers) run on the Linux machine itself, so "localhost" is also the host that the container is running on, and the ports are mapped to.

On Windows (and OS X), the docker daemon, and your containers cannot run natively, so only the docker client is running on your Windows machine, but the daemon (and your containers) run in a VirtualBox Virtual Machine, that runs Linux.

To connect to the container, you must connect to the IP-address of the virtual machine, not of your Windows computer.

This is all described in the Windows installation documentation, found here; http://docs.docker.com/installation/windows/.

The Virtual Machine is described in this section;
http://docs.docker.com/installation/windows/#learn-the-key-concepts-before-installing

And an explanation on how to map ports, and connect to them is explained here;
http://docs.docker.com/installation/windows/#container-port-redirection

I'm going to close this issue, because this is not a bug, and explained in the documentation. I hope the above explanation helps you.

    
por 27.03.2016 / 17:14