The project structure is irrelevant, you’d just be building the host project and deploying/copying the results in the Docker container. You don’t make the decision of how many host projects you have when you Dockerize your App, it’s based on whether you’ve split your solution into multiple host projects in which case each host project would be a separate Docker container and deployment unit.
I looked through your repos but didn’t see any dockerfile for a project used the 3 projects approach.
I’m posting what I came up with in-case anyone else finds this post:
FROM microsoft/dotnet:sdk AS build-env
RUN curl -sL https://deb.nodesource.com/setup_10.x | bash - \
&& apt-get install -y gnupg nodejs
# Copy csproj and restore as distinct layers
COPY ./ProjectName/ProjectName.csproj ./ProjectName/ProjectName.csproj
COPY ./ProjectName/package.json ./ProjectName/package.json
COPY ./ProjectName/npm-shrinkwrap.json ./ProjectName/npm-shrinkwrap.json
COPY ./ProjectName.ServiceInterface/ProjectName.ServiceInterface.csproj ./ProjectName.ServiceInterface/ProjectName.ServiceInterface.csproj
COPY ./ProjectName.ServiceModel/ProjectName.ServiceModel.csproj ./ProjectName.ServiceModel/ProjectName.ServiceModel.csproj
RUN dotnet restore ./ProjectName/ProjectName.csproj
RUN dotnet restore ./ProjectName.ServiceInterface/ProjectName.ServiceInterface.csproj
RUN dotnet restore ./ProjectName.ServiceModel/ProjectName.ServiceModel.csproj
RUN cd ProjectName && npm i && cd ..
# Copy everything else and build
COPY ./ProjectName ./ProjectName
COPY ./ProjectName.ServiceInterface/ ./ProjectName.ServiceInterface
COPY ./ProjectName.ServiceModel/ ./ProjectName.ServiceModel
RUN cd ProjectName && npx ng build --prod && cd ..
RUN dotnet publish ./ProjectName/ProjectName.csproj -c Release -o out
# Build runtime image
COPY --from=build-env /app/ProjectName/out .
ENTRYPOINT ["dotnet", "ProjectName.dll"]
One little gotcha is that this must be in root of solution as docker build process doesn’t have access to parent directories.
The issue I found was image takes long time to build so I build dependencies with just the dependency files first so it caches them unless dependency files changes.
Slowest part is probably the npm modules downloading and angular cli building. I think it makes sense maybe to have this in it’s own image but then I think serverside rendering would be impossible. I am still researching the best way to arrange containers.
It uses the sdk image to build project and then uses that output in the production image.
If anyone has any suggestions or improvements please share.
Not sure why you’re copying the projects individually, you just need to copy the sources folder, run publish on the host project and copy the published output to a new ASP.NET Runtime Docker Image. If you run npm run publish (assuming you’re using one of our SPA templates) before creating the Docker image it will generate a production npm client build so you can avoid doing it within the DockerFile.
Here are our DockerFile’s for multi-project solutions:
I did it that way so dependencies get cached, I am not exactly sure how the CI build scripts will work, haven’t got to that stage yet so just guessing atm. If it lets me run publish on a post commit hook and then build image from that then it will be better to do like you say. I thought it might need everything to happen in the docker build so I did it that way, I’ll edit it when I get to that stage. Thanks for the links, all the examples I saw were copying proj file first for dependency reason so I was expecting a docker file referencing all proj files which is what threw me when looking at repo.