docker - правильно работать в PowerShell, но не в Visual Studio - PullRequest
0 голосов
/ 01 апреля 2020

У меня есть обратный прокси (nginx) в одном контейнере и. net core api в другом контейнере. При запуске docker -композиция и docker -композиция в PowerShell это работает как ожидалось. API доступен только через обратный прокси (на http://localhost: 80 ).

Я настроил docker -композицию с Visual Studio и при работе в Visual Studio с тот же dockerfiles, docker -compose.yml, docker -compose.override.yml это не работает. Я не получаю сообщение об ошибке, и оба контейнера запускаются. Но при попытке доступа к API через обратный прокси я получаю следующую ошибку в docker журналах обратного прокси

2020/04/01 15:49:30 [error] 6#6: *8 connect() failed (111: Connection refused) while 
connecting to upstream, client: 172.20.0.1, server: , request: "GET /api/health HTTP/1.1", 
upstream: "http://172.20.0.2:5000/api/health", host: "localhost"
172.20.0.1 - - [01/Apr/2020:15:49:30 +0000] "GET /api/health HTTP/1.1" 502 559 "-" 
"Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) 
Chrome/80.0.3987.149 Safari/537.36"

Это моя структура папок:

  • . ...
  • RestApi (папка папки проекта)
    • Dockerfile
  • docker -compose.yml
  • docker -compose.override.yml
  • ReverseProxy (папка)
    • Dockerfile
    • nginx .conf
  • ...

Вот файлы, которые я использую:

Dockerfile для. net core api:

FROM mcr.microsoft.com/dotnet/core/aspnet:2.1-stretch-slim AS base
WORKDIR /app

FROM mcr.microsoft.com/dotnet/core/sdk:2.1-stretch AS build
WORKDIR /src
COPY ["RestApi/RestApi.csproj", "RestApi/"]
COPY ["Services/Services.csproj", "Services/"]
COPY ["DataServices/DataServices.csproj", "DataServices/"]
COPY ["Entities/Entities.csproj", "Entities/"]
RUN dotnet restore "RestApi/RestApi.csproj"
COPY . .
WORKDIR "/src/RestApi"
RUN dotnet build "RestApi.csproj" -c Release -o /app/build

FROM build AS publish
RUN dotnet publish "RestApi.csproj" -c Release -o /app/publish

FROM base AS final
WORKDIR /app
COPY --from=publish /app/publish .

ENV ASPNETCORE_URLS http://+:5000
EXPOSE 5000

ENTRYPOINT ["dotnet", "RestApi.dll"]

Dockerfile для обратный прокси:

FROM nginx
COPY nginx.conf /etc/nginx/nginx.conf

файл ngingx conf обратный прокси:

worker_processes 4;

events { worker_connections 1024; }

http {
    sendfile on;

    upstream app_servers {
        server restapi:5000;
    }

    server {
        listen 80;

        location / {
            proxy_pass         http://app_servers;
            proxy_redirect     off;
            proxy_set_header   Host $host;
            proxy_set_header   X-Real-IP $remote_addr;
            proxy_set_header   X-Forwarded-For $proxy_add_x_forwarded_for;
            proxy_set_header   X-Forwarded-Host $server_name;
        }
    }
}

docker -compose.yml:

version: '3.7'
services:
  restapi:
    build:
      context: .
      dockerfile: RestApi/Dockerfile
    container_name: restapi
    image: restapi:latest
    expose:
      - "5000"
  reverseproxy:
    build:
      context: ./ReverseProxy
      dockerfile: Dockerfile
    container_name: reverseproxy
    image: reverseproxy:latest
    ports:
      - "80:80"
    links :
      - restapi

docker -compose.override.yml:

version: '3.7'

services:
  restapi:
    volumes:
      - ${USERPROFILE}/.aws:/root/.aws
    environment:
      - ASPNETCORE_ENVIRONMENT=Development
      - AWS_REGION=eu-west-3
      - AWS_PROFILE=default

И вот что Visual Studio делает из файла при запуске:

services:
  restapi:
    build:
      context: D:\Repositories\dank\dank\api\RestApi
      dockerfile: RestApi/Dockerfile
      labels:
        com.microsoft.created-by: visual-studio
        com.microsoft.visual-studio.project-name: RestApi
      target: base
    container_name: restapi
    entrypoint: tail -f /dev/null
    environment:
      ASPNETCORE_ENVIRONMENT: Development
      AWS_PROFILE: default
      AWS_REGION: eu-west-3
      DOTNET_USE_POLLING_FILE_WATCHER: '1'
      NUGET_FALLBACK_PACKAGES: ''
    expose:
    - '5000'
    image: restapi:dev
    labels:
      com.microsoft.visualstudio.debuggee.arguments: ' --additionalProbingPath /root/.nuget/packages  "bin/Debug/netcoreapp2.1/RestApi.dll"'
      com.microsoft.visualstudio.debuggee.killprogram: /bin/sh -c "if PID=$$(pidof
        dotnet); then kill $$PID; fi"
      com.microsoft.visualstudio.debuggee.program: dotnet
      com.microsoft.visualstudio.debuggee.workingdirectory: /app
    tty: true
    volumes:
    - D:\Repositories\dank\dank\api\RestApi\RestApi:/app:rw
    - C:\Users\Gebruiker\vsdbg\vs2017u5:/remote_debugger:rw
    - C:\Users\Gebruiker\AppData\Roaming\ASP.NET\Https:/root/.aspnet/https:ro
    - C:\Users\Gebruiker\.aws:/root/.aws:rw
    - C:\Users\Gebruiker\AppData\Roaming\Microsoft\UserSecrets:/root/.microsoft/usersecrets:ro
    - C:\Users\Gebruiker\.nuget\packages:/root/.nuget/packages:ro
    - D:\Repositories\dank\dank\api\RestApi:/src:rw
  reverseproxy:
    build:
      context: D:\Repositories\dank\dank\api\RestApi\ReverseProxy
      dockerfile: Dockerfile
    container_name: reverseproxy
    image: reverseproxy:latest
    links:
    - restapi
    ports:
    - published: 80
      target: 80
version: '3.7'

1 Ответ

0 голосов
/ 01 апреля 2020

Читая официальную документацию: https://docs.microsoft.com/en-us/visualstudio/containers/container-build?view=vs-2019#debugging

Я увидел, что они размещают свои порты наверху док-файла. При этом он работает в visual studio, и порт 5000 правильно отображается в моем контейнере api и доступен обратному прокси-серверу.

Это мой текущий докер-файл с изменениями:

FROM mcr.microsoft.com/dotnet/core/aspnet:2.1-stretch-slim AS base
WORKDIR /app

ENV ASPNETCORE_URLS http://+:5000
EXPOSE 5000

FROM mcr.microsoft.com/dotnet/core/sdk:2.1-stretch AS build
WORKDIR /src
COPY ["RestApi/RestApi.csproj", "RestApi/"]
COPY ["Services/Services.csproj", "Services/"]
COPY ["DataServices/DataServices.csproj", "DataServices/"]
COPY ["Entities/Entities.csproj", "Entities/"]
RUN dotnet restore "RestApi/RestApi.csproj"
COPY . .
WORKDIR "/src/RestApi"
RUN dotnet build "RestApi.csproj" -c Release -o /app/build

FROM build AS publish
RUN dotnet publish "RestApi.csproj" -c Release -o /app/publish

FROM base AS final
WORKDIR /app
COPY --from=publish /app/publish .

ENTRYPOINT ["dotnet", "RestApi.dll"]

Причина, по которой это работает (из документации):

При сборке в конфигурации отладки Visual Studio выполняет несколько оптимизаций, помогающих повысить производительность процесса сборки для контейнерных проектов. Процесс сборки для контейнерных приложений не так прост, как простое выполнение шагов, описанных в Dockerfile. Сборка в контейнере происходит намного медленнее, чем сборка на локальной машине. Итак, когда вы встраиваете в конфигурацию Debug, Visual Studio фактически строит ваши проекты на локальном компьютере, а затем разделяет выходную папку с контейнером, используя монтирование тома. Сборка с включенной оптимизацией называется сборкой в ​​быстром режиме.

В быстром режиме Visual Studio вызывает сборку docker с аргументом, который указывает Docker на сборку только базовой стадии. , Visual Studio обрабатывает остальную часть процесса независимо от содержимого файла Dockerfile. Поэтому, когда вы модифицируете свой Dockerfile, например, для настройки среды контейнера или установки дополнительных зависимостей, вы должны поместить свои изменения на первом этапе. Любые пользовательские шаги, помещенные в сборку, публикацию sh или финальные этапы Dockerfile, не будут выполняться.

...