Skip to content
New issue

Have a question about this project? # for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “#”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? # to your account

.NET6 docker build stuck on dotnet restore #3338

Closed
Neo-Ciber94 opened this issue Dec 13, 2021 · 37 comments
Closed

.NET6 docker build stuck on dotnet restore #3338

Neo-Ciber94 opened this issue Dec 13, 2021 · 37 comments

Comments

@Neo-Ciber94
Copy link

Describe the Bug

I'm trying to create a docker image of a .NET 6 project, but is stuck during dotnet restore while using +12GB of RAM.

My project structure is:

- backend/
- frontend/

Where I just cd in the backend/ and run docker build .

enter image description here

This is the output of the console currently:

[+] Building 276.4s (15/19)
 => [internal] load .dockerignore                                                                                                           0.0s 
 => [internal] load build definition from Dockerfile.server                                                                                 0.0s 
 => [internal] load metadata for mcr.microsoft.com/dotnet/sdk:6.0                                                                           0.6s 
 => [internal] load metadata for mcr.microsoft.com/dotnet/aspnet:6.0                                                                        0.6s 
 => [stage-1 1/3] FROM mcr.microsoft.com/dotnet/aspnet:6.0@sha256:9ca180a6a0a0ec39209437e5e0986caf17b7d91473d9c34bb6191e47a7b500aa          0.0s 
 => [build-env 1/6] FROM mcr.microsoft.com/dotnet/sdk:6.0@sha256:ca4344774139fabfb58eed70381710c8912900d92cf879019d2eb52abc307102           0.0s 
 => [internal] load build context                                                                                                           0.2s 
 => => transferring context: 3.69kB                                                                                                         0.2s 
 => CACHED [stage-1 2/3] WORKDIR /app                                                                                                       0.0s 
 => CACHED [build-env 2/6] WORKDIR /app                                                                                                     0.0s 
 => CACHED [build-env 3/6] COPY *.csproj ./                                                                                                 0.0s 
 => [build-env 4/6] RUN dotnet restore                                                                                                    270.2s

My csproj:

<Project Sdk="Microsoft.NET.Sdk.Web">

  <PropertyGroup>
    <TargetFramework>net6.0</TargetFramework>
    <Nullable>enable</Nullable>
    <TreatWarningsAsErrors>true</TreatWarningsAsErrors>
    <GenerateDocumentationFile>true</GenerateDocumentationFile>
    <NoWarn>1701;1702;1705;1591;10102;</NoWarn>
    <DefaultItemExcludes>**\node_modules\**;$(DefaultItemExcludes)</DefaultItemExcludes>
  </PropertyGroup>

  <ItemGroup>
    <Watch Include="..\**\*.env" />
  </ItemGroup>

  <ItemGroup>
    <PackageReference Include="AutoMapper" Version="10.1.1" />
    <PackageReference Include="AutoMapper.Extensions.Microsoft.DependencyInjection" Version="8.1.1" />
    <PackageReference Include="BCrypt.Net-Next" Version="4.0.2" />
    <PackageReference Include="dotenv.net" Version="3.1.1" />
    <PackageReference Include="Microsoft.AspNetCore.Authentication.JwtBearer" Version="6.0.0" />
    <PackageReference Include="Microsoft.AspNetCore.JsonPatch" Version="6.0.0" />
    <PackageReference Include="Microsoft.EntityFrameworkCore" Version="6.0.0" />
    <PackageReference Include="Microsoft.EntityFrameworkCore.Design" Version="6.0.0">
      <IncludeAssets>runtime; build; native; contentfiles; analyzers; buildtransitive</IncludeAssets>
      <PrivateAssets>all</PrivateAssets>
    </PackageReference>
    <PackageReference Include="Microsoft.EntityFrameworkCore.InMemory" Version="6.0.0" />
    <PackageReference Include="Microsoft.EntityFrameworkCore.SqlServer" Version="6.0.0" />
    <PackageReference Include="Microsoft.AspNetCore.Authentication.Certificate" Version="5.0.12" />
    <PackageReference Include="Swashbuckle.AspNetCore" Version="6.2.3" />
  </ItemGroup>

</Project>

This is my Dockerfile:

# syntax=docker/dockerfile:1
FROM mcr.microsoft.com/dotnet/sdk:6.0 AS build-env
WORKDIR /app

ARG Config=Debug
ENV ASPNETCORE_URLS=http://*:5000

# Copy csproj and restore as distinct layers
COPY *.csproj ./
RUN dotnet restore

# Copy everything
COPY . .

# Publish
RUN dotnet publish -c ${Config} -o /app/publish

# Build runtime image
FROM mcr.microsoft.com/dotnet/aspnet:6.0
WORKDIR /app
COPY --from=build-env /app/publish .
ENTRYPOINT ["dotnet", "ISO810_ERP.dll"]

My net usage:
net usage

This is a pass result (1 hour) building:
enter image description here

Steps to Reproduce

Clone https://github.com/Neo-Ciber94/ISO810_ERP
And run cd backend && docker build -f Dockerfile.server .

Other Information

Output of docker version

Client:
Cloud integration: v1.0.22
Version: 20.10.11
API version: 1.41
Go version: go1.16.10
Git commit: dea9396
Built: Thu Nov 18 00:42:51 2021
OS/Arch: windows/amd64
Context: default
Experimental: true

Server: Docker Engine - Community
Engine:
Version: 20.10.11
API version: 1.41 (minimum version 1.12)
Go version: go1.16.9
Git commit: 847da18
Built: Thu Nov 18 00:35:39 2021
OS/Arch: linux/amd64
Experimental: false
containerd:
Version: 1.4.12
GitCommit: 7b11cfaabd73bb80907dd23182b9347b4245eb5d
runc:
Version: 1.0.2
GitCommit: v1.0.2-0-g52b36a2
docker-init:
Version: 0.19.0
GitCommit: de40ad0

Output of docker info

Client:
Context: default
Debug Mode: false
Plugins:
buildx: Docker Buildx (Docker Inc., v0.7.1)
compose: Docker Compose (Docker Inc., v2.2.1)
scan: Docker Scan (Docker Inc., 0.9.0)

Server:
Containers: 1
Running: 1
Paused: 0
Stopped: 0
Images: 2
Server Version: 20.10.11
Storage Driver: overlay2
Backing Filesystem: extfs
Supports d_type: true
Native Overlay Diff: true
userxattr: false
Logging Driver: json-file
Cgroup Driver: cgroupfs
Cgroup Version: 1
Plugins:
Volume: local
Network: bridge host ipvlan macvlan null overlay
Log: awslogs fluentd gcplogs gelf journald json-file local logentries splunk syslog
Swarm: inactive
Runtimes: io.containerd.runtime.v1.linux runc io.containerd.runc.v2
Default Runtime: runc
Init Binary: docker-init
containerd version: 7b11cfaabd73bb80907dd23182b9347b4245eb5d
runc version: v1.0.2-0-g52b36a2
init version: de40ad0
Security Options:
seccomp
Profile: default
Kernel Version: 5.10.16.3-microsoft-standard-WSL2
Operating System: Docker Desktop
OSType: linux
Architecture: x86_64
CPUs: 8
Total Memory: 12.39GiB
Name: docker-desktop
ID: U5CE:U4D3:OMG7:YPA5:TNN5:L6IO:CRVZ:CYE4:Y3TN:7WEM:KSQV:XTS6
Docker Root Dir: /var/lib/docker
Debug Mode: false
Registry: https://index.docker.io/v1/
Labels:
Experimental: false
Insecure Registries:
127.0.0.0/8
Live Restore Enabled: false

WARNING: No blkio throttle.read_bps_device support
WARNING: No blkio throttle.write_bps_device support
WARNING: No blkio throttle.read_iops_device support
WARNING: No blkio throttle.write_iops_device support

@mthalman
Copy link
Member

mthalman commented Dec 15, 2021

[Triage] The issue is with this part of the csproj:
https://github.com/Neo-Ciber94/ISO810_ERP/blob/8d9d8dae062245457b72b690cb61cb2db962af4d/backend/ISO810_ERP.csproj#L13

Because the project is being placed in a directory that is directly under the root of the container, this path causes a scan of the entire container's file system. This slows things down tremendously.

One way to workaround this is to not have the <Watch> items apply during a Docker restore/build. This could be done by setting an IsDockerBuild MSBuild property when running the dotnet restore and dotnet publish commands:

RUN dotnet restore /p:IsDockerBuild=true

And then modifying your project file to conditionally enable the <Watch> item if that property is not true:

<Watch Include="..\**\*.env" Condition=" '$(IsDockerBuild)' != 'true' " />

@Neo-Ciber94
Copy link
Author

[Triage] The issue is with this part of the csproj: https://github.com/Neo-Ciber94/ISO810_ERP/blob/8d9d8dae062245457b72b690cb61cb2db962af4d/backend/ISO810_ERP.csproj#L13

Because the project is being placed in a directory that is directly under the root of the container, this path causes a scan of the entire container's file system. This slows things down tremendously.

One way to workaround this is to not have the <Watch> items apply during a Docker restore/build. This could be done by setting an IsDockerBuild MSBuild property when running the dotnet restore and dotnet publish commands:

RUN dotnet restore /p:IsDockerBuild=true

And then modifying your project file to conditionally enable the <Watch> item if that property is not true:

<Watch Include="..\**\*.env" Condition=" '$(IsDockerBuild)' != 'true' " />

Thanks, that solved my issue, I used DOTNET_RUNNING_IN_CONTAINER instead:

<Watch Include="..\**\*.env" Condition="'$(DOTNET_RUNNING_IN_CONTAINER)' != 'true'" />

Repository owner moved this from Backlog to Done in .NET Docker Dec 20, 2021
@mthalman
Copy link
Member

I had considered the use of DOTNET_RUNNING_IN_CONTAINER as a solution as well. But I realized that that would prevent you from running scenarios where you do want to use dotnet watch in the context of a container. So if that's a scenario that you'd want to support, you'd have to introduce your own MSBuild property.

@NurulloSulaymonov
Copy link

NurulloSulaymonov commented Jan 18, 2023

Hello Above problem occured when I build .net 7 project on docker

image

@richlander
Copy link
Member

What is the problem? Is the build hanging at that point?

@MxD-js
Copy link

MxD-js commented Feb 3, 2023

Same issue as @NurulloSulaymonov, just get's stuck with .net 7

I enabled -v diag on dotnet restore but nothing happens,

image

It hangs then times out after a long delay.
image

@richlander
Copy link
Member

Any chance you are doing this on an Apple M1 machine?

@MxD-js
Copy link

MxD-js commented Feb 3, 2023

I am building this on a M1, but I issued a platform flag for linux/amd64 which this will ultimately will run on.

docker build --platform linux/amd64 -t sccenter_image_test .

@richlander
Copy link
Member

That's the problem. .NET doesn't support QEMU.

More context: #3848

@MxD-js
Copy link

MxD-js commented Feb 3, 2023

Thanks for linking the discussion however I am using the Workaround 1 as mentioned in the discussion. I added
--platform linux/amd64 to the build command, same result.

@andrekiba
Copy link

seems the problem is --platform linux/amd64, removing the option the build completes in few seconds... but on M1 is linux/arm64

@richlander
Copy link
Member

It looks like that worked with .NET 6 but not .NET 7. I'll have to update that.

@sairohith-vanna
Copy link

sairohith-vanna commented Feb 3, 2023

This happens to me only when I add --platform=linux/amd64 for build, on my M1 Pro machine. It just gets stuck restore. I need to deploy the app - which is .NET 7 based - to a Kubernetes cluster that has a couple of Linux nodes, hence need to generate an AMD64 build. Is there any workaround for .NET 7 or is it advisable to just step down to .NET 6? It's just a PoC app so downgrade shouldn't matter; but end of the day it must work for .NET 7 too.

@richlander
Copy link
Member

richlander commented Feb 3, 2023

You can use workaround 2 in the doc I linked to.

It is the same approach that was used at dotnet/aspnetcore#46306

@MxD-js
Copy link

MxD-js commented Feb 4, 2023

Hmm. I tried Workaround 2 and getting the same result. I removed the --platfrom linx/amd64 from the command line, but the process get's stuck on dotnet restore command. This is my Dockerfile

ARG ARCH=amd64
ARG TAG=7.0-bullseye-slim-$ARCH
FROM mcr.microsoft.com/dotnet/aspnet:$TAG AS base
#####################
#PUPPETEER RECIPE
#####################
RUN apt-get update && apt-get -f install && apt-get -y install wget gnupg2 apt-utils
RUN wget -q -O - https://dl.google.com/linux/linux_signing_key.pub | apt-key add -
RUN echo 'deb [arch=amd64] http://dl.google.com/linux/chrome/deb/ stable main' >> /etc/apt/sources.list
RUN apt-get update \
&& apt-get install -y google-chrome-stable --no-install-recommends --allow-downgrades fonts-ipafont-gothic fonts-wqy-zenhei fonts-thai-tlwg fonts-kacst fonts-freefont-ttf
######################
#END PUPPETEER RECIPE
######################
ENV PUPPETEER_EXECUTABLE_PATH "/usr/bin/google-chrome-stable"
WORKDIR /app
EXPOSE 80
EXPOSE 443


FROM mcr.microsoft.com/dotnet/sdk:$TAG AS build
WORKDIR /src
COPY ["sccenter_puppeteer_sharp/sccenter_puppeteer_sharp.csproj", "sccenter_puppeteer_sharp/"]
RUN dotnet restore -v diag "sccenter_puppeteer_sharp/sccenter_puppeteer_sharp.csproj"
COPY . .
WORKDIR "/src/sccenter_puppeteer_sharp"
RUN dotnet build "sccenter_puppeteer_sharp.csproj" -c Release -o /app/build

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

FROM base AS final
WORKDIR /app
COPY --from=publish /app/publish .
ENTRYPOINT ["dotnet", "sccenter_puppeteer_sharp.dll"]

image

@richlander
Copy link
Member

I think I gave some bad advice, sadly. I'll get back to you on Monday with clearer guidance. I misunderstood an aspect of how Docker works.

@richlander
Copy link
Member

FYI: #4388 (comment)

@richlander
Copy link
Member

@douglasg14b
Copy link

This seems to be an ongoing problem, why is the issue closed?

@vmandic
Copy link

vmandic commented May 4, 2023

+1 same issue here on Apple M1, dotnet7.0 SDK, trying to build and run on Apple M1 (+ I need single file, self contained and cant use bullseye-slim, doing all of this to test TieredPGO=true and other JIT optimizations).

I get to bypass some problems by specifying the RID as osx.12-arm64 but I cant get the project to start, all I get when I try to start my exe in container is:

/bin/sh: 1: ./MyApp: Exec format error

My images (dockerfile is) are:

FROM mcr.microsoft.com/dotnet/sdk:7.0 AS build
...
FROM mcr.microsoft.com/dotnet/runtime-deps:7.0-alpine
...
ENTRYPOINT exec ./MyApp

Other combinations just get stuck at dotnet restore forever. Specifying docker --platform does not help out. This is really frustrating as I was hoping to get this solved when moving from netcoreapp3.1 and this has not moved an inch for supporting Apple M1. For all docker ops I have to switch to a spare Win x64 to do the related work.

@douglasg14b
Copy link

douglasg14b commented May 7, 2023

@vmandic Your issue is different I think, and is because .Net SDK < 7.0.3 build environment has some issues on apple silicon and a problem with QEMU. Specifically it will hang on restore.

The solution is to wait for .Net SDK v 7.0.3 to be released, or to target .Net 8 Preview in your Dockerfile mcr.microsoft.com/dotnet/nightly/sdk:8.0-preview. The SDK verison in the final app/image doesn't matter afaik as long as it's equal to or higher than the SDK version your project builds with.

Relevant blog post:

https://devblogs.microsoft.com/dotnet/improving-multiplatform-container-support/

There is unfortunately a whole rash of closed github issues that only link to closed github issues to track the problem....

@Maclay74
Copy link

Maclay74 commented Jun 1, 2023

@vmandic Your issue is different I think, and is because .Net SDK < 7.0.3 build environment has some issues on apple silicon and a problem with QEMU. Specifically it will hang on restore.

The solution is to wait for .Net SDK v 7.0.3 to be released, or to target .Net 8 Preview in your Dockerfile mcr.microsoft.com/dotnet/nightly/sdk:8.0-preview. The SDK verison in the final app/image doesn't matter afaik as long as it's equal to or higher than the SDK version your project builds with.

Relevant blog post:

https://devblogs.microsoft.com/dotnet/improving-multiplatform-container-support/

There is unfortunately a whole rash of closed github issues that only link to closed github issues to track the problem....

I tried with 8.0 preview, still hangs on dotnet restore.

FROM mcr.microsoft.com/dotnet/nightly/sdk:8.0.100-preview.6-bookworm-slim-amd64 AS build

# Install make
RUN apt-get update && \
    apt-get install -y make build-essential libc6-dev

# Run building script
ENTRYPOINT [ "/backend/entrypoint.sh" ]

Also tried mcr.microsoft.com/dotnet/nightly/sdk:7.0.302-bullseye-slim-amd64 no luck, still hangs on restore.

But mcr.microsoft.com/dotnet/nightly/sdk:6.0-bullseye-slim-amd64 works though.

@vernou
Copy link

vernou commented Sep 3, 2023

I have the same problem on Windows 10 Pro.
Maybe a dedicated ticket to .NET7 (and .NET8?) is needed.

@vernou
Copy link

vernou commented Sep 3, 2023

I add in the Dockerfile the instruction WORKDIR and now the restore work.
Without, I think the command restore is executed at the root and this provoke the issue.

@nicholasyin
Copy link

+1 why was this closed as there's no clear solution to the 'restore hanging' issue.

@tjhorner
Copy link

tjhorner commented Oct 12, 2023

Can a maintainer please re-open this issue? It's still occurring, even in the .NET 8 release candidate image.

@lbussell
Copy link
Contributor

[Triage] This issue is about disabling dotnet Watch for Docker builds and was resolved with #3338 (comment). If you are having restore issues in scenarios unrelated to dotnet watch, please open a new issue with detailed repro steps.

@nicholasyin @tjhorner

@unseensenpai
Copy link

Still got problem about restoring nugets on .net 7 in linux/alpine docker system.

@MichaelSimons
Copy link
Member

Still got problem about restoring nugets on .net 7 in linux/alpine docker system.

Does your scenario involve dornet-watch? If not please open a new issue with steps to reproduce the issue. TIA.

@MattMckenzy
Copy link

I add in the Dockerfile the instruction WORKDIR and now the restore work. Without, I think the command restore is executed at the root and this provoke the issue.

I was also getting stuck on dotnet restore with .NET 8. This fixed it immediately, thanks for your comment!

@lbanchero
Copy link

lbanchero commented Dec 28, 2023

I add in the Dockerfile the instruction WORKDIR and now the restore work. Without, I think the command restore is executed at the root and this provoke the issue.

I was also getting stuck on dotnet restore with .NET 8. This fixed it immediately, thanks for your comment!

@MattMckenzy Do you have a working example? Tried different configurations of Dockerfile and none of them seems to work.

@kurt-mueller-osumc
Copy link

@lbanchero and @sairohith-vanna, I'm on an apple macbook and and I have to add the following environment variable in my Dockerfile when I'm running rosetta emulation:

ENV DOTNET_EnableWriteXorExecute=0

This works for me but makes the container a bit less responsive.

See here for the full Dockerfile definition:
https://github.com/kurt-mueller-osumc/dotnet-amd64/blob/main/Dockerfile#L4C1-L4C35

@gregoryb
Copy link

None of the suggested fixes work here. With the environment variables, the build crashes.

Any sample with WORKDIR. ?

@richlander
Copy link
Member

Any sample with WORKDIR. ?

Can you elaborate on the question?

@gregoryb
Copy link

In a previous comment, it was mentioned that adding the WORKDIR instruction solved the problem.
It doesn't solve the problem in my case. Maybe I missed something.

dotnet 8

@richlander
Copy link
Member

Yes. That's this issue: dotnet/sdk#38050

@keifgwinn
Copy link

if you're getting this issue with M-chip Mac's, then this is what solved it for me, adding the --platform$BUILDPLATFORM command to ensure that it got the right processor type

# Base image
FROM --platform=$BUILDPLATFORM mcr.microsoft.com/dotnet/sdk:8.0 AS base

# for free to join this conversation on GitHub. Already have an account? # to comment
Projects
Status: Done
Development

No branches or pull requests