Docker - ASP.CORE 2.2 应用和SSH
Docker - ASP.CORE 2.2 application and SSH
我正在尝试配置我的 docker 容器,以便可以通过 ssh 进入它(该容器将在 Azure 上 运行)。我设法创建了一个图像,使用户能够通过 ssh 进入从该图像创建的容器,Dockerfile 看起来像这样(不是我的,我在互联网上找到的):
FROM mcr.microsoft.com/dotnet/core/sdk:2.2-stretch AS build
EXPOSE 2222
RUN apt-get update && apt-get install -y openssh-server
RUN mkdir /var/run/sshd
COPY sshd_config /etc/ssh
RUN echo 'root:Docker' | chpasswd
RUN sed -i 's/PermitRootLogin prohibit-password/PermitRootLogin yes/' /etc/ssh/sshd_config
RUN sed 's@session\s*required\s*pam_loginuid.so@session optional pam_loginuid.so@g' -i /etc/pam.d/sshd
ENV NOTVISIBLE "in users profile"
RUN echo "export VISIBLE=now" >> /etc/profile
CMD ["/usr/sbin/sshd", "-D"]
我正在使用 mcr.microsoft.com/dotnet/core/sdk:2.2-stretch
,因为这是我稍后 运行 应用程序所需要的。
有了上面的Dockerfile,我运行 docker build . -t ssh
。我可以确认可以按照以下说明通过 ssh 连接到从 ssh
图像创建的容器中:
docker run -d -p 0.0.0.0:2222:22 --name ssh ssh
ssh root@localhost -p 2222
我的应用程序的 Dockerfile:
FROM mcr.microsoft.com/dotnet/core/sdk:2.2-stretch AS build
WORKDIR /src
COPY ["Application.WebAPI/Application.WebAPI.csproj", "Application.WebAPI/"]
COPY ["Processing.Dependency/Processing.Dependency.csproj", "Processing.Dependency/"]
COPY ["Processing.QueryHandling/Processing.QueryHandling.csproj", "Processing.QueryHandling/"]
COPY ["Model.ViewModels/Model.ViewModels.csproj", "Model.ViewModels/"]
COPY ["Core.Infrastructure/Core.Infrastructure.csproj", "Core.Infrastructure/"]
COPY ["Model.Values/Model.Values.csproj", "Model.Values/"]
COPY ["Sql.Business/Sql.Business.csproj", "Sql.Business/"]
COPY ["Model.Events/Model.Events.csproj", "Model.Events/"]
COPY ["Model.Messages/Model.Messages.csproj", "Model.Messages/"]
COPY ["Model.Commands/Model.Commands.csproj", "Model.Commands/"]
COPY ["Sql.Common/Sql.Common.csproj", "Sql.Common/"]
COPY ["Model.Business/Model.Business.csproj", "Model.Business/"]
COPY ["Processing.MessageBus/Processing.MessageBus.csproj", "Processing.MessageBus/"]
COPY [".Processing.CommandHandling/Processing.CommandHandling.csproj", "Processing.CommandHandling/"]
COPY ["Processing.EventHandling/Processing.EventHandling.csproj", "Processing.EventHandling/"]
COPY ["Sql.System/Sql.System.csproj", "Sql.System/"]
COPY ["Application.Common/Application.Common.csproj", "Application.Common/"]
RUN dotnet restore "Application.WebAPI/Application.WebAPI.csproj"
COPY . .
WORKDIR "/src/Application.WebAPI"
RUN dotnet build "Application.WebAPI.csproj" -c Release -o /app
FROM build AS publish
RUN dotnet publish "Application.WebAPI.csproj" -c Release -o /app
FROM ssh AS final
WORKDIR /app
EXPOSE 80
EXPOSE 443
COPY --from=publish /app .
ENTRYPOINT ["dotnet", "Application.WebApi.dll"]
如您所见,我在最后阶段使用 ssh
图像作为基础图像。即使我能够通过 sshe 进入从 ssh
图像创建的容器,我也无法通过 ssh 进入从后者 Dockerfile 创建的容器。这是我使用的 docker-compose.yml 以便于启动容器:
version: '3.7'
services:
application.webapi:
image: application.webapi
container_name: webapi
ports:
- "0.0.0.0:5000:80"
- "0.0.0.0:2222:22"
build:
context: .
dockerfile: Application.WebAPI/Dockerfile
environment:
- ASPNETCORE_ENVIRONMENT=docker
当我 运行 docker exec -it webapi bash
并执行 service ssh status
时,我得到 [FAIL] sshd is not running ... failed!
- 但是当我执行 service ssh start
并尝试通过 ssh 进入它时容器,它的工作原理。不幸的是,这种方法是不可接受的,ssh 守护进程应该在启动时自行启动。
我尝试使用 debian 上可用的 cron 和其他东西,但它是一个精简版,那里没有 systemd - 我也不喜欢在精简版上安装数百个东西。
你知道这里可能出了什么问题吗?
您的最终映像中的启动命令定义存在冲突。请注意,CMD
不仅仅是 运行 图像中的命令,它定义了 启动命令 ,并且与 ENTRYPOINT
有复杂的交互(在简而言之:如果两者都存在,CMD
只是向 ENTRYPOINT
).
提供额外的参数
您可以在 Dockerfile 文档中看到 table 种可能性:https://docs.docker.com/engine/reference/builder/。此外,当您在不同层中混合和匹配 CMD
和 ENTRYPOINT
时,还有一个额外的并发症:
Note: If CMD is defined from the base image, setting ENTRYPOINT will reset CMD to an empty value. In this scenario, CMD must be defined in the current image to have a value.
据我所知,光靠层叠图片是得不到你想要的。您将需要在最终图像中创建一个启动脚本,其中包括 运行s sshd -D
和 运行s dotnet Application.WebApi.dll
。
我正在尝试配置我的 docker 容器,以便可以通过 ssh 进入它(该容器将在 Azure 上 运行)。我设法创建了一个图像,使用户能够通过 ssh 进入从该图像创建的容器,Dockerfile 看起来像这样(不是我的,我在互联网上找到的):
FROM mcr.microsoft.com/dotnet/core/sdk:2.2-stretch AS build
EXPOSE 2222
RUN apt-get update && apt-get install -y openssh-server
RUN mkdir /var/run/sshd
COPY sshd_config /etc/ssh
RUN echo 'root:Docker' | chpasswd
RUN sed -i 's/PermitRootLogin prohibit-password/PermitRootLogin yes/' /etc/ssh/sshd_config
RUN sed 's@session\s*required\s*pam_loginuid.so@session optional pam_loginuid.so@g' -i /etc/pam.d/sshd
ENV NOTVISIBLE "in users profile"
RUN echo "export VISIBLE=now" >> /etc/profile
CMD ["/usr/sbin/sshd", "-D"]
我正在使用 mcr.microsoft.com/dotnet/core/sdk:2.2-stretch
,因为这是我稍后 运行 应用程序所需要的。
有了上面的Dockerfile,我运行 docker build . -t ssh
。我可以确认可以按照以下说明通过 ssh 连接到从 ssh
图像创建的容器中:
docker run -d -p 0.0.0.0:2222:22 --name ssh ssh
ssh root@localhost -p 2222
我的应用程序的 Dockerfile:
FROM mcr.microsoft.com/dotnet/core/sdk:2.2-stretch AS build
WORKDIR /src
COPY ["Application.WebAPI/Application.WebAPI.csproj", "Application.WebAPI/"]
COPY ["Processing.Dependency/Processing.Dependency.csproj", "Processing.Dependency/"]
COPY ["Processing.QueryHandling/Processing.QueryHandling.csproj", "Processing.QueryHandling/"]
COPY ["Model.ViewModels/Model.ViewModels.csproj", "Model.ViewModels/"]
COPY ["Core.Infrastructure/Core.Infrastructure.csproj", "Core.Infrastructure/"]
COPY ["Model.Values/Model.Values.csproj", "Model.Values/"]
COPY ["Sql.Business/Sql.Business.csproj", "Sql.Business/"]
COPY ["Model.Events/Model.Events.csproj", "Model.Events/"]
COPY ["Model.Messages/Model.Messages.csproj", "Model.Messages/"]
COPY ["Model.Commands/Model.Commands.csproj", "Model.Commands/"]
COPY ["Sql.Common/Sql.Common.csproj", "Sql.Common/"]
COPY ["Model.Business/Model.Business.csproj", "Model.Business/"]
COPY ["Processing.MessageBus/Processing.MessageBus.csproj", "Processing.MessageBus/"]
COPY [".Processing.CommandHandling/Processing.CommandHandling.csproj", "Processing.CommandHandling/"]
COPY ["Processing.EventHandling/Processing.EventHandling.csproj", "Processing.EventHandling/"]
COPY ["Sql.System/Sql.System.csproj", "Sql.System/"]
COPY ["Application.Common/Application.Common.csproj", "Application.Common/"]
RUN dotnet restore "Application.WebAPI/Application.WebAPI.csproj"
COPY . .
WORKDIR "/src/Application.WebAPI"
RUN dotnet build "Application.WebAPI.csproj" -c Release -o /app
FROM build AS publish
RUN dotnet publish "Application.WebAPI.csproj" -c Release -o /app
FROM ssh AS final
WORKDIR /app
EXPOSE 80
EXPOSE 443
COPY --from=publish /app .
ENTRYPOINT ["dotnet", "Application.WebApi.dll"]
如您所见,我在最后阶段使用 ssh
图像作为基础图像。即使我能够通过 sshe 进入从 ssh
图像创建的容器,我也无法通过 ssh 进入从后者 Dockerfile 创建的容器。这是我使用的 docker-compose.yml 以便于启动容器:
version: '3.7'
services:
application.webapi:
image: application.webapi
container_name: webapi
ports:
- "0.0.0.0:5000:80"
- "0.0.0.0:2222:22"
build:
context: .
dockerfile: Application.WebAPI/Dockerfile
environment:
- ASPNETCORE_ENVIRONMENT=docker
当我 运行 docker exec -it webapi bash
并执行 service ssh status
时,我得到 [FAIL] sshd is not running ... failed!
- 但是当我执行 service ssh start
并尝试通过 ssh 进入它时容器,它的工作原理。不幸的是,这种方法是不可接受的,ssh 守护进程应该在启动时自行启动。
我尝试使用 debian 上可用的 cron 和其他东西,但它是一个精简版,那里没有 systemd - 我也不喜欢在精简版上安装数百个东西。
你知道这里可能出了什么问题吗?
您的最终映像中的启动命令定义存在冲突。请注意,CMD
不仅仅是 运行 图像中的命令,它定义了 启动命令 ,并且与 ENTRYPOINT
有复杂的交互(在简而言之:如果两者都存在,CMD
只是向 ENTRYPOINT
).
您可以在 Dockerfile 文档中看到 table 种可能性:https://docs.docker.com/engine/reference/builder/。此外,当您在不同层中混合和匹配 CMD
和 ENTRYPOINT
时,还有一个额外的并发症:
Note: If CMD is defined from the base image, setting ENTRYPOINT will reset CMD to an empty value. In this scenario, CMD must be defined in the current image to have a value.
据我所知,光靠层叠图片是得不到你想要的。您将需要在最终图像中创建一个启动脚本,其中包括 运行s sshd -D
和 运行s dotnet Application.WebApi.dll
。