Running dotnetCore 2.2
I have a clr.dll dependency in my .Logic library. This clr.dll calls unmanaged.dll that I cannot load as a dependency and instead have to just copy do the bin like this.
<PropertyGroup>
<TargetFramework>netcoreapp2.2</TargetFramework>
</PropertyGroup>
<ItemGroup>
<ProjectReference Include="..\myApp.Models\myApp.Models.csproj" />
</ItemGroup>
<ItemGroup>
<Reference Include="CLR">
<HintPath>..\Dependencies\NonNuget\CLR.dll</HintPath>
</Reference>
</ItemGroup>
<ItemGroup>
<None Update="unmanaged.dll">
<CopyToOutputDirectory>Always</CopyToOutputDirectory>
</None>
</ItemGroup>
</Project>
my docker file looks like this:
#Depending on the operating system of the host machines(s) that will build or run the containers, the image specified in the FROM statement may need to be changed.
#For more information, please see https://aka.ms/containercompat
FROM microsoft/dotnet:2.2-aspnetcore-runtime-nanoserver-1803 AS base
WORKDIR /app
EXPOSE 80
EXPOSE 443
FROM microsoft/dotnet:2.2-sdk-nanoserver-1803 AS build
WORKDIR /src
COPY ["myApp.Api/myApp.Api.csproj", "myApp.Api/"]
COPY ["myApp.logic/myApp.logic.csproj", "myApp.logic/"]
COPY ["myApp.Models/myApp.Models.csproj", "myApp.Models/"]
RUN dotnet restore "myApp.Api/myApp.Api.csproj"
COPY . .
WORKDIR "/src/myApp.Api"
RUN dotnet build "myApp.Api.csproj" -c Release -o /app
FROM build AS publish
RUN dotnet publish "myApp.Api.csproj" -c Release -o /app
FROM base AS final
WORKDIR /app
COPY --from=publish /app .
ENTRYPOINT ["dotnet", "myApp.Api.dll"]
**When I run the api outside docker it works fine. **
When I create a docker image and run the api I end up with
System.DllNotFoundException: Unable to load DLL 'unmanaged.dll'
I assumed the file was somehow not being included in my docker image but when i run docker exec -it myapp I can see the file is present
146 appsettings.Development.json
105 appsettings.json
**3,426,680 unmanaged.dll**
239,429 myApp.Api.deps.json
13,824 myApp.Api.dll
2,696 myApp.Api.pdb
252 myApp.Api.runtimeconfig.dev.json
224 myApp.Api.runtimeconfig.json
1,188 myApp.logic.deps.json
5,120 myApp.logic.dll
632 myApp.logic.pdb
1,459 myApp.Models.deps.json
4,608 myApp.Models.dll
708 myApp.Models.pdb
**5,120 clr.dll**
I could really use some advice as I am very new to docker and not sure where to go from here.
Related
I have a small .Net Core 7 MVC project that i'm trying to run on Docker. Actually, the running part works but it looks like the wwwroot folder is only partially published. I'm using npm and webpack to generate the javascript and css files necessary and they seem to be present because the url to the generated javascript files and css files work.
But the rest of the files in a wwwroot subfolder, like images, are not published. It's a PWA and the serviceworker works. A "offline.html" in the wwwroot folder works. So files directly in wwwroot are published, along with the "dist" folder generated by npm/webpack. But other subfolders are not published
Below you can find a bit of configuration. I got to this configuration by multiple tutorials so maybe there is a piece of config that contradicts another piece but i don't see it
My Dockerfile:
WORKDIR /app
EXPOSE 80
EXPOSE 443
FROM mcr.microsoft.com/dotnet/sdk:7.0 AS build
WORKDIR /src
COPY ["MyProject/MyProject.csproj", "MyProject/"]
RUN dotnet restore "MyProject/MyProject.csproj"
COPY . .
WORKDIR "/src/MyProject"
RUN dotnet build "MyProject.csproj" -c Release -o /app/build
FROM build AS publish
RUN dotnet publish "MyProject.csproj" -c Release -o /app/publish
WORKDIR /app/publish
FROM base AS final
WORKDIR /app
COPY --from=publish /app/publish .
ENTRYPOINT ["dotnet", "MyProject.dll"]
My csproj
<Project Sdk="Microsoft.NET.Sdk.Web">
<PropertyGroup>
<TargetFramework>net7.0</TargetFramework>
<Nullable>enable</Nullable>
<ImplicitUsings>enable</ImplicitUsings>
<DockerDefaultTargetOS>Linux</DockerDefaultTargetOS>
<IsPackable>false</IsPackable>
<MpaRoot>npm\</MpaRoot>
<WWWRoot>wwwroot\</WWWRoot>
<DefaultItemExcludes>$(DefaultItemExcludes);$(MpaRoot)node_modules\**</DefaultItemExcludes>
</PropertyGroup>
<!--<ItemGroup>
<Content Include="npm\src\css\site.css" />
</ItemGroup>-->
<ItemGroup>
<PackageReference Include="Dapper" Version="2.0.123" />
<PackageReference Include="Microsoft.AspNetCore.Diagnostics.EntityFrameworkCore" Version="7.0.2" />
<PackageReference Include="Microsoft.AspNetCore.Identity.EntityFrameworkCore" Version="7.0.2" />
<PackageReference Include="Microsoft.AspNetCore.Identity.UI" Version="7.0.2" />
<PackageReference Include="Microsoft.EntityFrameworkCore.SqlServer" Version="7.0.2" />
<PackageReference Include="Microsoft.EntityFrameworkCore.Tools" Version="7.0.2">
<PrivateAssets>all</PrivateAssets>
<IncludeAssets>runtime; build; native; contentfiles; analyzers; buildtransitive</IncludeAssets>
</PackageReference>
<PackageReference Include="Microsoft.VisualStudio.Web.CodeGeneration.Design" Version="7.0.3" />
</ItemGroup>
<ItemGroup>
<PackageReference Include="Microsoft.AspNetCore.SpaServices.Extensions" Version="7.0.2" />
</ItemGroup>
<ItemGroup>
<!-- Don't publish the MPA source files, but do show them in the project files list -->
<Content Remove="$(MpaRoot)**" />
<None Remove="$(MpaRoot)**" />
<None Include="$(MpaRoot)**" Exclude="$(MpaRoot)node_modules\**" />
</ItemGroup>
</Project>
In my program.cs I added app.UseStaticFiles() before app.UseRouting().
i found a similar post before i posted my question but i just couldn't see the difference. Then i spotted the differences in the folders. This docker file doesn't use '/app/build' and 'app/release' in the build and publish commands
FROM mcr.microsoft.com/dotnet/aspnet:7.0 AS base
WORKDIR /app
EXPOSE 80
EXPOSE 443
FROM mcr.microsoft.com/dotnet/sdk:7.0 AS build
WORKDIR /src
COPY ["MyProject/MyProject.csproj", "MyProject/"]
RUN dotnet restore "MyProject/MyProject.csproj"
COPY . ./
RUN dotnet build "/src/MyProject/MyProject.csproj" -c Release -o /app
FROM build AS publish
RUN dotnet publish "/src/MyProject/MyProject.csproj" -c Release -o /app
FROM base AS final
WORKDIR /app
COPY --from=publish /app .
ENTRYPOINT ["dotnet", "MyProject.dll"]
Instead of copying to "build" and "publish" folders, everything is done inside the /app folder. I'm guessing the wwwroot isn't copied form one folder to the other at some point. But that is just guessing. I'm sure someone can explain it.
So, in short. With this dockerfile everything works but I don't know why
I have a .NET 6 Console project that includes 2 binaries as linked files:
<ItemGroup>
<None Include="..\HFMath\bin\HFMath.dll" Link="HFMath.dll">
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
</None>
<None Include="..\HFMath\bin\libHFMath.so" Link="libHFMath.so">
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
</None>
</ItemGroup>
I need to deploy it as a docker container. The Dockerfile scaffolded by Visual Studio is
FROM mcr.microsoft.com/dotnet/runtime:6.0 AS base
WORKDIR /app
FROM mcr.microsoft.com/dotnet/sdk:6.0 AS build
WORKDIR /src
COPY ["ConsoleApp1/ConsoleApp1.csproj", "ConsoleApp1/"]
RUN dotnet restore "ConsoleApp1/ConsoleApp1.csproj"
COPY . .
WORKDIR "/src/ConsoleApp1"
RUN dotnet build "ConsoleApp1.csproj" -c Release -o /app/build
FROM build AS publish
RUN dotnet publish "ConsoleApp1.csproj" -c Release -o /app/publish
FROM base AS final
WORKDIR /app
COPY --from=publish /app/publish .
ENTRYPOINT ["dotnet", "ConsoleApp1.dll"]
when I run docker build, I get the following error:
#15 1.054 Determining projects to restore...
#15 1.322 All projects are up-to-date for restore.
#15 2.552 /usr/share/dotnet/sdk/6.0.100/Microsoft.Common.CurrentVersion.targets(5100,5): error MSB3030: Could not copy the file "/src/HFMath/bin/libHFMath.so" because it was not found. [/src/ConsoleApp1/ConsoleApp1.csproj]
#15 2.552 /usr/share/dotnet/sdk/6.0.100/Microsoft.Common.CurrentVersion.targets(5100,5): error MSB3030: Could not copy the file "/src/HFMath/bin/HFMath.dll" because it was not found. [/src/ConsoleApp1/ConsoleApp1.csproj]
#15 2.556
#15 2.556 Build FAILED.
I know that docker doesn't support symlinks, but I still need to build the image.
How do I fix this (without changing the .NET project)?
Problem
If you have auto generated the Dockerfile using Visual Studio, it will also have created a .dockerignore file (usually in the .sln folder). That file will contain an entry to exclude **/bin from the build context.
This means when the COPY . . executes, it is ignoring the files in any bin folder
Solution
Find and edit the .dockerignore file.
Add the line !HFMath/bin/ - this will tell Docker to NOT ignore the HFMath/bin folder
Run your docker build command again
I have got a problem while creating docker image on my .Net core web api application. Thats the docker image generated by VS docker support:
FROM mcr.microsoft.com/dotnet/core/aspnet:2.2-stretch-slim AS base
WORKDIR /app
EXPOSE 80
FROM mcr.microsoft.com/dotnet/core/sdk:2.2-stretch AS build
WORKDIR /src
COPY ["src/appname.Api/appname.Api.csproj", "src/appname.Api/"]
COPY ["src/appname.Data/appname.Data.csproj", "src/appname.Data/"]
COPY ["src/Eappname.Models/appname.Models.csproj", "src/appname.Models/"]
RUN dotnet restore "src/appname.Api/appname.Api.csproj"
COPY . .
WORKDIR "/src/src/appname.Api"
RUN dotnet build "appname.Api.csproj" -c Release -o /app
FROM build AS publish
RUN dotnet publish "appname.Api.csproj" -c Release -o /app
FROM base AS final
WORKDIR /app
COPY --from=publish /app .
ENTRYPOINT ["dotnet", "appname.Api.dll"]
Unfortunettly I use Azure Artifacts Feed package inside my app and this image does not work. I made a little research and try to use credential provider with nuget config file. Just like below:
FROM mcr.microsoft.com/dotnet/core/aspnet:2.2-stretch-slim AS base
WORKDIR /app
EXPOSE 80
EXPOSE 443
FROM mcr.microsoft.com/dotnet/core/sdk:2.2-stretch AS build
WORKDIR /src
COPY NuGet.Config ./
COPY ["src/appname.Api/appname.Api.csproj", "src/appname.Api/"]
COPY ["src/appname.Data/appname.Data.csproj", "src/appname.Data/"]
COPY ["src/appname.Models/appname.Models.csproj", "src/appname.Models/"]
RUN dotnet restore --configfile NuGet.Config "src/appname.Api/appname.Api.csproj"
COPY . .
WORKDIR "/src/src/appname.Api"
RUN dotnet build "appname.Api.csproj" -c Release -o /app
FROM build AS publish
RUN dotnet publish "appname.Api.csproj" -c Release -o /app
FROM base AS final
WORKDIR /app
COPY --from=publish /app .
ENTRYPOINT ["dotnet", "appname.Api.dll"]
and also added Nuget.Config:
<?xml version="1.0" encoding="utf-8"?>
<configuration>
<packageSources>
<add key="nuget.org" value="https://api.nuget.org/v3/index.json" protocolVersion="3" />
<add key="BredasVSTS" value="https://pkgs.dev.azure.com/feed/nuget/v3/index.json" />
</packageSources>
<packageSourceCredentials>
<BredasVSTS>
<add key="Username" value="<usernameWithEmail>" />
<add key="ClearTextPassword" value="<token>" />
</BredasVSTS>
</packageSourceCredentials>
</configuration>
Now I made a little progress because I am able to pass step 11 - dotnet restore. Unfortunettly in step 14- dotnet build I get the following error:
/bin/sh: 2: cd: can't cd to *Undefined*
Any ideas how can I solve this problem?
error: /bin/sh: 2: cd: can't cd to Undefined
According to the error MSB3073: The command "cd "undefined"", it seems you are using the command line or build event cd $(SolutionDir) in your xxx.Api project.
When you build the project file .csproj without solution file .sln with dockerfile, it could not get the value of $(SolutionDir), which is based on the .sln file.
So, you will get the error "cd "undefined", to resolve this issue you can try to replace all $(SolutionDir) with $(ProjectDir)..\ in your project file.
As test, I create a sample with build event:
CD $(SolutionDir)
Then I got the same error:
To resolve this issue, I have replaced $(SolutionDir) with $(ProjectDir)..\, then build it, it works fine:
Check the this thread for some more details.
Hope this helps.
The setup
In my solution folder, I have this file/folder-structure
Source
docker-compose.yml
.dockerignore
paths.json
Webproject
//All web-project files (including DockerFile)
AnotherWebproject
//All web-project files (including DockerFile)
In my Visual Studio project, I've added the paths.json as a linked file and to include it in my image, I've set my csproj file (don't know if this is necessary...)
<Project Sdk="Microsoft.NET.Sdk.Web">
<PropertyGroup>
<TargetFramework>netcoreapp3.0</TargetFramework>
<AspNetCoreHostingModel>InProcess</AspNetCoreHostingModel>
<DockerDefaultTargetOS>Windows</DockerDefaultTargetOS>
<UserSecretsId>8bcf6be2-9d06-4667-89f6-38f25af5dfbc</UserSecretsId>
<DockerComposeProjectPath>..\docker-compose.dcproj</DockerComposeProjectPath>
</PropertyGroup>
<ItemGroup>
<Content Include="..\paths.json" Link="paths.json">
<CopyToOutputDirectory>Always</CopyToOutputDirectory>
<CopyToPublishDirectory>Always</CopyToPublishDirectory>
</Content>
</ItemGroup>
...
</Project>
And my Dockerfile to:
FROM mcr.microsoft.com/dotnet/core/aspnet:3.0-nanoserver-1803 AS base
WORKDIR /app
EXPOSE 80
EXPOSE 443
FROM mcr.microsoft.com/dotnet/core/sdk:3.0-nanoserver-1803 AS base
WORKDIR /src
COPY ["Webproject/Webproject.csproj", "Webproject/"]
COPY "paths.json" "paths.json"
RUN dotnet restore "Webproject/Webproject.csproj"
COPY . .
WORKDIR "/src/Webproject"
RUN dotnet build "Webproject.csproj" -c Release -o /app
FROM build AS publish
RUN dotnet publish "Webproject.csproj" -c Release -o /app
FROM base AS final
WORKDIR /app
COPY --from=publish /app .
ENTRYPOINT ["dotnet", "Webproject.dll"]
To use the file in my application, I use:
public static IWebHostBuilder CreateWebHostBuilder(string[] args) =>
WebHost.CreateDefaultBuilder(args)
.ConfigureAppConfiguration((context, config) =>
{
var environment = context.HostingEnvironment;
var folder = Path.Combine(environment.ContentRootPath);
config.AddJsonFile(Path.Combine(folder, "paths.json"), false);
})
.UseStartup<Startup>();
I even tried to exclude it in my .dockerignore file:
!paths.json
FYI... I'm using also a docker-compose project
The error
When starting up the application, I have this error:
System.IO.FileNotFoundException: 'The configuration file 'paths.json' was not found and is not optional. The physical path is 'C:\app\paths.json'.'
The question
I tried a lot of different paths in the Dockerfile to include it, but it doesn't seem to work. Can anyone help me with setting the correct path?
Also, I searched if it is possible to list all the files (to check if it's copied to the correct path), but it doesn't seem possible?
Not sure your full dockerfile content and dockerfile path, try following steps below:
Folder Structure
Source
Dockerfile
paths.json
Webproject
Dockerfile
FROM mcr.microsoft.com/dotnet/core/aspnet:2.2-stretch-slim AS base
WORKDIR /app
EXPOSE 80
EXPOSE 443
FROM mcr.microsoft.com/dotnet/core/sdk:2.2-stretch AS build
WORKDIR /src
COPY ["DockerFileCopy/DockerFileCopy.csproj", "DockerFileCopy/"]
RUN dotnet restore "DockerFileCopy/DockerFileCopy.csproj"
COPY . .
WORKDIR "/src/DockerFileCopy"
RUN dotnet build "DockerFileCopy.csproj" -c Release -o /app
FROM build AS publish
RUN dotnet publish "DockerFileCopy.csproj" -c Release -o /app
FROM base AS final
WORKDIR /app
COPY --from=publish /app .
ENTRYPOINT ["dotnet", "DockerFileCopy.dll"]
There is no need to copy the paths.json in docker command, the RUN dotnet build and RUN dotnet publish will not copy this file to the published folder
We use link file to copy the paths.json, the .csproj content
<Project Sdk="Microsoft.NET.Sdk.Web">
<PropertyGroup>
<TargetFramework>netcoreapp2.2</TargetFramework>
<AspNetCoreHostingModel>InProcess</AspNetCoreHostingModel>
<UserSecretsId>2594cc66-3d1a-487b-a93c-99e0cf9975ef</UserSecretsId>
<DockerDefaultTargetOS>Linux</DockerDefaultTargetOS>
<DockerfileContext>.</DockerfileContext>
</PropertyGroup>
<ItemGroup>
<Content Include="..\paths.json" Link="paths.json">
<CopyToOutputDirectory>Always</CopyToOutputDirectory>
<CopyToPublishDirectory>Always</CopyToPublishDirectory>
</Content>
</ItemGroup>
<ItemGroup>
<PackageReference Include="Microsoft.AspNetCore.App" />
<PackageReference Include="Microsoft.AspNetCore.Razor.Design" Version="2.2.0" PrivateAssets="All" />
<PackageReference Include="Microsoft.VisualStudio.Azure.Containers.Tools.Targets" Version="1.7.9" />
</ItemGroup>
</Project>
Build the image in the Source folder by command like docker build -t dockerfilecopy .
I am trying to get include a swagger.json file into my docker image.
I am using aspnet core 2.2
When I run my app locally it picks up the swagger.json file sitting in wwwroot.
when I create my docker image and run it, swagger starts but won't find the .json so it just errors out. I am very new to docker.
I should note it also didn't find a test.gif file I dropped into wwwroot either.
Am I missing something in the docker file?
I definitely want to include the .json file in my image.
dockerfile:
FROM microsoft/dotnet:2.2-aspnetcore-runtime AS base
WORKDIR /app
EXPOSE 80
EXPOSE 443
FROM microsoft/dotnet:2.2-sdk AS build
WORKDIR /src
COPY ["myApp.Api/myApp.Api.csproj", "myApp.Api/"]
COPY ["myApp.logic/myApp.logic.csproj", "myApp.logic/"]
COPY ["myApp.Models/myApp.Models.csproj", "myApp.Models/"]
RUN dotnet restore "myApp.Api/myApp.Api.csproj"
COPY . .
WORKDIR "/src/myApp.Api"
RUN dotnet build "myApp.Api.csproj" -c Release -o /app
FROM build AS publish
RUN dotnet publish "myApp.Api.csproj" -c Release -o /app
FROM base AS final
WORKDIR /app
COPY --from=publish /app .
ENTRYPOINT ["dotnet", "myApp.Api.dll"]
csproj file:
<PropertyGroup>
<TargetFramework>netcoreapp2.2</TargetFramework>
<AspNetCoreHostingModel>InProcess</AspNetCoreHostingModel>
<DockerDefaultTargetOS>Linux</DockerDefaultTargetOS>
<UserSecretsId></UserSecretsId>
</PropertyGroup>
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|AnyCPU'">
<DocumentationFile></DocumentationFile>
</PropertyGroup>
<ItemGroup>
<PackageReference Include="Microsoft.AspNetCore.App" />
<PackageReference Include="Microsoft.AspNetCore.Razor.Design" Version="2.2.0" PrivateAssets="All" />
<PackageReference Include="Microsoft.VisualStudio.Azure.Containers.Tools.Targets" Version="1.0.2105168" />
<PackageReference Include="Swashbuckle.AspNetCore" Version="4.0.1" />
</ItemGroup>
<ItemGroup>
<ProjectReference Include="..\myApp.logic\myApp.logic.csproj" />
</ItemGroup>
<ItemGroup>
<Content Update="wwwroot\swagger.json">
<CopyToOutputDirectory>Always</CopyToOutputDirectory>
</Content>
</ItemGroup>
</Project>
docker command
docker run -it -p 5001:80 myapp:latest
In my case, the solution was renaming subfolders and files to lowercase because paths are case sensitive with the Docker image.