I have an Azure pipeline
that does a dotnet restore
, a dotnet build
, and a dotnet publish
.
Originally, we published the artifact to an Azure App Service
.
We would like to switch to Docker
. Therefore, we started creating a Dockerfile
and a Docker@2 task
in our pipeline that builds the image and pushes it to our Azure Container Registry
.
In most examples I find, within the Dockerfile
, you have to do a dotnet restore
, a dotnet build
, and a dotnet publish
.
But if I’m already doing this in my Azure pipeline
, can’t I just copy-paste my artifact from the pipeline to the Docker image?
Similar to this question: Pass artifact to Docker task in Azure DevOps And this one: Build Docker with artifacts in Azure DevOps Pipeline
I tried to do it this way at the end of my pipeline:
- task: Docker@2
inputs:
containerRegistry: '$(containerRegistry)'
repository: '$(imageRepository)'
command: 'buildAndPush'
Dockerfile: '**/Dockerfile'
buildContext: '$(Build.ArtifactStagingDirectory)'
tags: |
$(Build.BuildId)
And, my Dockerfile
, which is at the root of my project:
FROM mcr.microsoft.com/dotnet/aspnet:8.0
COPY . App/
WORKDIR /App
EXPOSE 80
EXPOSE 443
ENTRYPOINT ["dotnet", "MyApplication.dll"]
The image is correctly created and published to my Azure Container Registry
, but when I try to run the image on Docker Desktop
, it tells me that the SDK is not available on the machine. Here is the error :
The command could not be loaded, possibly because:
- You intended to execute a .NET application: The application 'MyApplication.dll' does not exist.
- You intended to execute a .NET SDK command: No .NET SDKs were found.
When I'm in a local env, under the /bin/Debug...
I have a MyApplication.dll
. So I tried to generate the image from the sdk
instead:
FROM mcr.microsoft.com/dotnet/sdk:8.0
But now the error is even stranger:
Could not execute because the specified command or file was not found. Possible reasons for this include:
- You misspelled a built-in dotnet command.
- You intended to execute a .NET program, but dotnet-MyApplication.dll does not exist.
- You intended to run a global tool, but a dotnet-prefixed executable with this name could not be found on the PATH.
I think that I should stick to the aspnet
image.
I have two questions then: did I simply not copy (COPY . App/
) to the right place in the Dockerfile
, or is there something missing in my Dockerfile
to import the SDK?
Is it possible to use the artifact generated by my Azure Pipeline to build a Docker image?
Below is the sample I attempt on my side, and it can work as expected. You can reference it to try to re-configure your pipeline and ensure all the required artifact files have been copied into the container.
FROM mcr.microsoft.com/dotnet/aspnet:8.0
WORKDIR /app
EXPOSE 80
EXPOSE 443
COPY . .
RUN dotnet myApp.dll
ENTRYPOINT ["dotnet", "myApp.dll"]
# azure-pipelines.yml
pool:
vmImage: ubuntu-latest
steps:
- task: DotNetCoreCLI@2
displayName: 'dotnet restore'
inputs:
command: restore
projects: myApp.sln
vstsFeed: 'myFeed'
- task: DotNetCoreCLI@2
displayName: 'dotnet build'
inputs:
projects: myApp.sln
arguments: '--no-restore -c Release'
- task: DotNetCoreCLI@2
displayName: 'dotnet publish'
inputs:
command: publish
publishWebProjects: false
projects: myApp.sln
arguments: '--no-build -c Release -o "$(Build.ArtifactStagingDirectory)"'
zipAfterPublish: false
modifyOutputPath: false
- task: CopyFiles@2
displayName: 'Copy Dockerfile'
inputs:
SourceFolder: '$(Build.SourcesDirectory)'
Contents: '**/Dockerfile'
TargetFolder: '$(Build.ArtifactStagingDirectory)'
- task: Docker@2
displayName: 'Build and Push image'
inputs:
containerRegistry: myDockerConnection
repository: myApp
Dockerfile: '**/Dockerfile'
buildContext: '$(Build.ArtifactStagingDirectory)'
tags: |
$(Build.BuildId)
latest