Docker

Creando un contenedor de Docker para una aplicación ASP.NET Core

En este artículo, veremos cómo ejecutar una aplicación ASP.NET Core en contenedores de Docker.

  1. Crear proyecto para una aplicación ASP.NET Core Web API
  2. Crear archivo Dockerfile
  3. Ejecución del contenedor
  4. Detener contenedor
  5. Limpiar recursos

Crear proyecto para una aplicación ASP.NET Core Web API

Creamos una Web API con ASP.NET Core y la llamamos «SampleWebApi», usamos .NET 7.

Crear archivo Dockerfile

Dockerfile es un archivo de texto plano que contiene una serie de instrucciones que se utilizan para construir una imagen de Docker.

Para crear Dockerfile, añadimos compatibilidad con Docker como muestra la imagen:

y elegimos Windows o Linux cuando se solicite elegir el sistema operativo. Esto crea un archivo denominado Dockerfile en el directorio que contiene el archivo .csproj 

Abrimos este archivo «Dockerfile» y vemos lo siguiente:

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 ["SampleWebApi.csproj", "."]
RUN dotnet restore "./SampleWebApi.csproj"
COPY . .
WORKDIR "/src/."
RUN dotnet build "SampleWebApi.csproj" -c Release -o /app/build

FROM build AS publish
RUN dotnet publish "SampleWebApi.csproj" -c Release -o /app/publish /p:UseAppHost=false

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

Este Dockerfile contiene las instrucciones para construir una imagen Docker para una aplicación de ASP.NET Core en .NET 7. Se compone de etapas, las etapas en el Dockerfile se definen usando la instrucción «FROM» y cada etapa puede tener su propio conjunto de instrucciones adicionales para construir la imagen final.

Aquí hay algunas instrucciones comunes que se encuentran en los Dockerfiles:

  1. FROM: Esta es la primera línea de cualquier Dockerfile y especifica la imagen base que se utilizará para construir la nueva imagen.
  2. COPY: Esta instrucción copia archivos desde el host al contenedor.
  3. WORKDIR: Esta instrucción establece el directorio de trabajo en el contenedor donde se ejecutarán las siguientes instrucciones.
  4. RUN: Esta instrucción ejecuta comandos en el contenedor durante la construcción de la imagen.
  5. EXPOSE: Esta instrucción especifica los puertos que se expondrán en el contenedor.
  6. CMD: Esta instrucción especifica el comando que se ejecutará cuando se inicie el contenedor.
  7. ENTRYPOINT: Esta instrucción especifica el comando que se ejecutará cuando se inicie el contenedor, pero también permite que se pasen argumentos al contenedor.
  8. ENV: Esta instrucción establece variables de entorno en el contenedor.

Aquí hay un desglose de lo que hace cada etapa:

1. base: esta etapa comienza con la imagen base mcr.microsoft.com/dotnet/aspnet:7.0 y establece el directorio de trabajo en /app. También expone los puertos 80 y 443, que la aplicación usará para escuchar las solicitudes entrantes.

FROM mcr.microsoft.com/dotnet/aspnet:7.0 AS base
WORKDIR /app
EXPOSE 80
EXPOSE 443

2. build: esta etapa comienza con la imagen base mcr.microsoft.com/dotnet/sdk:7.0 y establece el directorio de trabajo en /src. Luego copia el archivo SampleWebApi.csproj en el contenedor y restaura las dependencias necesarias. Después de eso, copia el resto de los archivos del proyecto en el contenedor y establece el directorio de trabajo en /src/SampleWebApi. Finalmente, compila el proyecto en modo de Release y envía el resultado a /app/build.

FROM mcr.microsoft.com/dotnet/sdk:7.0 AS build
WORKDIR /src
COPY ["SampleWebApi.csproj", "."]
RUN dotnet restore "./SampleWebApi.csproj"
COPY . .
WORKDIR "/src/."
RUN dotnet build "SampleWebApi.csproj" -c Release -o /app/build

3. publish: esta etapa utiliza la salida de la etapa de compilación anterior como su imagen base. Establece el directorio de trabajo en /app y publica el proyecto en modo de publicación en /app/publish. El argumento /p:UseAppHost=false se usa para evitar la generación de un host de aplicación predeterminado, ya que esto no es necesario en un entorno en contenedores.

FROM build AS publish
RUN dotnet publish "SampleWebApi.csproj" -c Release -o /app/publish /p:UseAppHost=false

4. final: esta etapa comienza con la etapa «base» como su imagen base y establece el directorio de trabajo en /app. Luego copia el resultado de la etapa de publicación en el contenedor. Finalmente, establece el punto de entrada para el contenedor en dotnet SampleWebApi.dll, que es el comando que iniciará la aplicación.

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

Crear una imagen de Docker a partir de un Dockerfile

Ejecutamos el siguiente comando docker build para construir una imagen Docker.

Desglosemos el comando:

-t aspnetapp: Esta opción especifica el nombre de la imagen que se creará. En este caso, el nombre de la imagen será «aspnetapp».

-f Dockerfile: Esta opción especifica el archivo Dockerfile que se utilizará para construir la imagen. En este caso, el archivo se llama «Dockerfile».

.: El punto final especifica el directorio del contexto de construcción. Es decir, es el directorio donde se buscará el archivo Dockerfile y cualquier otro archivo que se deba copiar al contenedor. En este caso, el punto significa que el Dockerfile y cualquier otro archivo necesario se encuentran en el directorio actual.

docker build -t aspnetapp -f Dockerfile .

Ejecución del contenedor

Ejecutamos el ejemplo en Docker con el comando docker run inicia un nuevo contenedor Docker con el nombre aspnetcore_sample, ejecutando una aplicación ASP.NET Core en el puerto 80 dentro del contenedor, que está asignado al puerto 5000 en la máquina anfitriona.

docker run -it --rm -p 5000:80 --name aspnetcore_sample aspnetapp

Desglosemos el comando:

docker run inicia un nuevo contenedor basado en la imagen especificada.
-it adjunta una terminal al contenedor y lo hace interactivo.
–rm elimina el contenedor automáticamente después de que sale.
-p 5000:80 asigna el puerto 80 dentro del contenedor al puerto 5000 en la máquina host.
–name aspnetcore_sample asigna un nombre al contenedor.
aspnetapp es el nombre de la imagen de Docker que se usará para el contenedor.

En general, este comando es útil para activar rápidamente una aplicación ASP.NET Core en contenedor a la que se puede acceder desde la máquina host a través de un navegador web o una herramienta como curl.

Vamos a http://localhost:5000/weatherforecast en un explorador para probar la aplicación:

Detener contenedor

Detenemos el contenedor «aspnetcore_sample» en ejecución con el comando docker stop, primero podemos listar contenedores en ejecución docker container ls para comprobar que se está ejecutando:

docker container ls
docker stop aspnetcore_sample

docker rm aspnetcore_sample

Limpiar recursos

Eliminamos contenedor «aspnetcore_sample» con el comando docker rm, previamente debe ser detenido.

docker rm aspnetcore_sample

Eliminamos image Docker «aspnetapp» con el comando docker rmi:

docker rmi aspnetapp

Leer más

Introducción a Docker y contenedores

Comandos de Docker