【问题标题】:No node_modules folder after npm install inside Docker在 Docker 中安装 npm 后没有 node_modules 文件夹
【发布时间】:2020-02-27 00:38:14
【问题描述】:

最近几天,我试图在 Google Cloud App Engine 服务上部署 asp.net core 3.1 应用程序。我认为,我已经很接近了,但目前我在安装 npm 包时遇到了问题。 通常,我在我的 Razor 页面应用程序中将 node_modules 文件夹作为静态文件提供,所以我的 Startup.cs 类中有这样一段代码:

app.UseStaticFiles(new StaticFileOptions
{
  FileProvider = new PhysicalFileProvider(Path.Combine(Directory.GetCurrentDirectory(), "node_modules")),
  RequestPath = "/node_modules"
});

Google 云目前不支持 .net core 3.1,因此部署应用程序的唯一方法是将其部署为 Docker 映像。 所以这是我的 Dockerfile:

FROM mcr.microsoft.com/dotnet/core/sdk:3.1 AS build
WORKDIR /source

# copy csproj and restore as distinct layers
COPY myApp/myApp.csproj myApp/
COPY myApp.DataAccess/myApp.DataAccess.csproj myApp.DataAccess/
COPY myApp.Model/myApp.Model.csproj myApp.Model/
RUN dotnet restore myApp/myApp.csproj

# copy and build app and libraries
COPY myApp/ myApp/
COPY myApp.DataAccess/ myApp.DataAccess/
COPY myApp.Model/ myApp.Model/
WORKDIR /source/myApp
RUN dotnet build -c release

FROM build AS publish
RUN dotnet publish -c release --no-build -o /app

# npm libs
FROM node:10
WORKDIR /app
COPY myApp/package.json .
COPY myApp/package-lock.json .
RUN npm install
RUN npm root

# final stage/image
FROM mcr.microsoft.com/dotnet/core/aspnet:3.1 AS runtime
WORKDIR /app
COPY --from=publish /app .
ENTRYPOINT ["dotnet", "myApp.dll"]

docker构建成功,但是当我尝试运行容器时出现这样的异常:

System.IO.DirectoryNotFoundException: /app/node_modules/
   at Microsoft.Extensions.FileProviders.PhysicalFileProvider..ctor(String root, ExclusionFilters filters)
   at Microsoft.Extensions.FileProviders.PhysicalFileProvider..ctor(String root)
   at UniCableApp.Startup.Configure(IApplicationBuilder app, IWebHostEnvironment env, RoleManager`1 roleManager, UserManager`1 userManager) in /source/UniCableApp/Startup.cs:line 113

我使用以下方法创建了已停止容器的图像:

docker commit <id> <snapshot name>

之后我可以通过以下方式检查图像:

docker run -ti --entrypoint=sh<snapshot name>

并且 /app 目录下没有 node_modules 文件夹。 正如我所说,我是 Docker 世界的新手,所以也许有人可以帮助我解决这个问题?

【问题讨论】:

    标签: c# docker npm .net-core gcloud


    【解决方案1】:

    您正在从publish 图像|层复制/app,并有效地忽略了您在FROM: node 层中执行的 NPM 安装。

    FROM: node 需要 COPY --from=publish /app . 也可以命名该层。

    然后runtime 层也需要COPY --from=2 /app . 或者您决定调用node 层。

    您可能需要使用/app/ ./(终止/)来确保副本是递归的。

    我不确定您是否应该包含package-lock.json 文件。我认为您将其包含在内是正确的,但这可能会妨碍软件包的安装。不知道。

    你可以确认/app/node_modules被添加并结转,方法是在每一层添加以下内容,然后在构建图像时检查输出:

    RUN ls -ld /app
    

    NB Google Cloud Platform 的计算服务非常适合 Microsoft 的运行时,包括 .NET Core。我不清楚你所说的不受支持是什么意思。

    更新:重现

    我对你的例子做了一个更简单的复制来展示它的工作原理:

    FROM mcr.microsoft.com/dotnet/core/sdk:3.1 AS build
    WORKDIR /app
    
    COPY app/app.csproj ./
    RUN dotnet restore ./app.csproj
    
    COPY app/ app/
    RUN dotnet build
    
    FROM build AS publish
    WORKDIR /app
    
    COPY --from=build /app .
    RUN ls -l /app
    
    RUN dotnet publish
    
    FROM node:10 as node
    WORKDIR /app
    COPY --from=publish /app .
    RUN ls -l /app
    
    COPY app/package.json .
    RUN npm install
    RUN npm root
    
    FROM mcr.microsoft.com/dotnet/core/aspnet:3.1 AS runtime
    WORKDIR /app
    
    COPY --from=node /app .
    RUN ls -l /app
    
    ENTRYPOINT ["dotnet", "myApp.dll"]
    

    还有:

    docker build --tag=60424677 --file=Dockerfile --no-cache .
    

    产量(为清楚起见进行了编辑):

    Sending build context to Docker daemon  6.144kB
    Step 1/23 : FROM mcr.microsoft.com/dotnet/core/sdk:3.1 AS build
    ...
    Step 7/23 : FROM build AS publish
    Step 9/23 : COPY --from=build /app .
    Step 10/23 : RUN ls -l /app
    drwxr-xr-x 2 root root 4096 Feb 27 20:50 app
    -rw-r--r-- 1 root root  178 Feb 27 20:41 app.csproj
    drwxr-xr-x 4 root root 4096 Feb 27 20:50 bin
    drwxr-xr-x 4 root root 4096 Feb 27 20:50 obj
    ...
    Step 12/23 : FROM node:10 as node
    Step 14/23 : COPY --from=publish /app .
    Step 15/23 : RUN ls -l /app
    drwxr-xr-x 2 root root 4096 Feb 27 20:50 app
    -rw-r--r-- 1 root root  178 Feb 27 20:41 app.csproj
    drwxr-xr-x 3 root root 4096 Feb 27 20:51 bin
    drwxr-xr-x 3 root root 4096 Feb 27 20:50 obj
    ...
    Step 19/23 : FROM mcr.microsoft.com/dotnet/core/aspnet:3.1 AS runtime
    Step 21/23 : COPY --from=node /app .
    Step 22/23 : RUN ls -l /app
    drwxr-xr-x 2 root root 4096 Feb 27 20:50 app
    -rw-r--r-- 1 root root  178 Feb 27 20:41 app.csproj
    drwxr-xr-x 3 root root 4096 Feb 27 20:51 bin
    drwxr-xr-x 3 root root 4096 Feb 27 20:51 node_modules
    drwxr-xr-x 3 root root 4096 Feb 27 20:50 obj
    -rw-r--r-- 1 root root  345 Feb 27 20:51 package-lock.json
    -rw-r--r-- 1 root root  270 Feb 27 20:51 package.json
    ...
    Successfully built 43ba6f8577e5
    Successfully tagged 60424677:latest
    

    【讨论】:

    • 哦,现在我明白了。我一下班回来,我会检查你的提示。
    • 如果是 Google Cloud 和 .NET Core。我的意思是,使用 Visual Studio 和 Google Cloud 扩展部署 .net 核心应用程序有一种更简单的方法,但目前 .net 核心的最后支持版本是 2.1。
    • 啊哈!感谢您的澄清
    猜你喜欢
    • 2013-12-24
    • 1970-01-01
    • 2016-11-23
    • 1970-01-01
    • 2020-07-25
    • 2017-01-01
    • 1970-01-01
    • 2021-11-09
    • 2016-03-25
    相关资源
    最近更新 更多