Generación de certificados autofirmados con la CLI de .NET

Hay diferentes maneras de crear y usar certificados autofirmados para escenarios de desarrollo y pruebas. En este artículo se describe el uso de certificados autofirmados con dotnet dev-certsy otras opciones como PowerShell y OpenSSL.

Después, puede validar que el certificado se cargará mediante un ejemplo como una aplicación ASP.NET Core hospedada en un contenedor.

Requisitos previos

Para dotnet dev-certs, asegúrese de que tiene instalada la versión adecuada de .NET:

En este ejemplo se necesita la versión Docker 17.06 o posterior del cliente Docker.

Preparación de la aplicación de ejemplo

En esta guía, usará una aplicación de ejemplo y realizará los cambios necesarios.

Compruebe que el Dockerfile de la aplicación de ejemplo usa .NET 8.

En función del sistema operativo host, es posible que tenga que actualizar el entorno de ejecución de ASP.NET. Por ejemplo, para tener como destino el entorno de ejecución de Windows adecuado, cambie mcr.microsoft.com/dotnet/aspnet:8.0-nanoservercore-2009 AS runtime a mcr.microsoft.com/dotnet/aspnet:8.0-windowsservercore-ltsc2022 AS runtime en el Dockerfile.

Por ejemplo, esto ayudará a probar los certificados en Windows:

# https://hub.docker.com/_/microsoft-dotnet
FROM mcr.microsoft.com/dotnet/sdk:8.0 AS build
WORKDIR /source

# copy csproj and restore as distinct layers
COPY *.sln .
COPY aspnetapp/*.csproj ./aspnetapp/
RUN dotnet restore -r win-x64

# copy everything else and build app
COPY aspnetapp/. ./aspnetapp/
WORKDIR /source/aspnetapp
RUN dotnet publish -c release -o /app -r win-x64 --self-contained false --no-restore

# final stage/image
FROM mcr.microsoft.com/dotnet/aspnet:8.0-windowsservercore-ltsc2022 AS runtime
WORKDIR /app
COPY --from=build /app ./
ENTRYPOINT ["aspnetapp"]

Si se van a probar los certificados en Linux, puede usar el Dockerfile existente.

Asegúrese de que aspnetapp.csproj incluye la plataforma de destino adecuada:

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

  <PropertyGroup>
    <TargetFramework>net8.0</TargetFramework>
    <!--Other Properties-->
  </PropertyGroup>

</Project>

Nota

Si quiere usar parámetros dotnet publish para recortar la implementación, asegúrese de que se incluyan las dependencias adecuadas para admitir los certificados SSL. Actualice el archivo dotnet-docker\samples\aspnetapp\aspnetapp.csproj para asegurarse de que los ensamblados adecuados están incluidos en el contenedor. Como referencia, compruebe cómo actualizar el archivo .csproj para admitir certificados SSL al usar el recorte para las implementaciones independientes.

Asegúrese de que apunta a la aplicación de ejemplo.

cd .\dotnet-docker\samples\aspnetapp

Cree el contenedor para realizar las pruebas localmente.

docker build -t aspnetapp:my-sample -f Dockerfile .

Creación de un certificado autofirmado

Puede crear un certificado autofirmado:

Con dotnet dev-certs

Puede usar dotnet dev-certs para trabajar con certificados autofirmados.

dotnet dev-certs https -ep $env:USERPROFILE\.aspnet\https\aspnetapp.pfx -p crypticpassword
dotnet dev-certs https --trust

Nota

El nombre del certificado, en este caso aspnetapp.pfx debe coincidir con el nombre del ensamblado del proyecto. crypticpassword se usa como sustituto de una contraseña que elija. Si la consola devuelve "Ya hay un certificado HTTPS válido.", ya existe un certificado de confianza en el almacén. Se puede exportar mediante la consola de MMC.

Configure los secretos de la aplicación para el certificado:

dotnet user-secrets -p aspnetapp\aspnetapp.csproj init
dotnet user-secrets -p aspnetapp\aspnetapp.csproj set "Kestrel:Certificates:Development:Password" "crypticpassword"

Nota

Nota: La contraseña debe coincidir con la contraseña usada para el certificado.

Ejecute la imagen de contenedor con ASP.NET Core configurado para HTTPS:

docker run --rm -it -p 8000:80 -p 8001:443 -e ASPNETCORE_URLS="https://+;http://+" -e ASPNETCORE_HTTPS_PORT=8001 -e ASPNETCORE_ENVIRONMENT=Development -v $env:APPDATA\microsoft\UserSecrets\:C:\Users\ContainerUser\AppData\Roaming\microsoft\UserSecrets -v $env:USERPROFILE\.aspnet\https:C:\Users\ContainerUser\AppData\Roaming\ASP.NET\Https mcr.microsoft.com/dotnet/samples:aspnetapp

Una vez que se inicie la aplicación, vaya a https://localhost:8001 en el explorador web.

Limpieza

Si los secretos y certificados no están en uso, asegúrese de limpiarlos.

dotnet user-secrets remove "Kestrel:Certificates:Development:Password" -p aspnetapp\aspnetapp.csproj
dotnet dev-certs https --clean

Con PowerShell

Puede usar PowerShell para generar certificados autofirmados. El cliente PKI se puede usar para generar un certificado autofirmado.

$cert = New-SelfSignedCertificate -DnsName @("contoso.com", "www.contoso.com") -CertStoreLocation "cert:\LocalMachine\My"

El certificado se generará, pero se debe colocar en un almacén de certificados para realizar las pruebas en un explorador.

$certKeyPath = "c:\certs\contoso.com.pfx"
$password = ConvertTo-SecureString 'password' -AsPlainText -Force
$cert | Export-PfxCertificate -FilePath $certKeyPath -Password $password
$rootCert = $(Import-PfxCertificate -FilePath $certKeyPath -CertStoreLocation 'Cert:\LocalMachine\Root' -Password $password)

En este momento, los certificados deben ser visibles desde un complemento MMC.

Puede ejecutar el contenedor de ejemplo en el Subsistema de Windows para Linux (WSL):

docker run --rm -it -p 8000:80 -p 8001:443 -e ASPNETCORE_URLS="https://+;http://+" -e ASPNETCORE_HTTPS_PORT=8001 -e ASPNETCORE_ENVIRONMENT=Development -e ASPNETCORE_Kestrel__Certificates__Default__Password="password" -e ASPNETCORE_Kestrel__Certificates__Default__Path=/https/contoso.com.pfx -v /c/certs:/https/ mcr.microsoft.com/dotnet/samples:aspnetapp

Nota:

Tenga en cuenta que, con el montaje del volumen, la ruta de acceso del archivo se podría controlar de otra manera en función del host. Por ejemplo, en WSL se podría reemplazar /c/certs por /mnt/c/certs.

Si usa el contenedor compilado anteriormente para Windows, el comando run tendría el siguiente aspecto:

docker run --rm -it -p 8000:80 -p 8001:443 -e ASPNETCORE_URLS="https://+;http://+" -e ASPNETCORE_HTTPS_PORT=8001 -e ASPNETCORE_ENVIRONMENT=Development -e ASPNETCORE_Kestrel__Certificates__Default__Password="password" -e ASPNETCORE_Kestrel__Certificates__Default__Path=c:\https\contoso.com.pfx -v c:\certs:C:\https aspnetapp:my-sample

Una vez que la aplicación esté activa, vaya a contoso.com:8001 en un explorador.

Asegúrese de que las entradas del host se actualizan para que contoso.com responda en la dirección IP adecuada (por ejemplo, 127.0.0.1). Si no se reconoce el certificado, asegúrese de que el certificado que se carga con el contenedor también sea de confianza en el host y de que existan entradas SAN/DNS adecuadas para contoso.com.

Limpieza

$cert | Remove-Item
Get-ChildItem $certKeyPath | Remove-Item
$rootCert | Remove-item

Con OpenSSL

Puede usar OpenSSL para crear certificados autofirmados. En este ejemplo se usará WSL / Ubuntu y un shell de bash con OpenSSL.

Este comando genera un archivo .crt y un .key.

PARENT="contoso.com"
openssl req \
-x509 \
-newkey rsa:4096 \
-sha256 \
-days 365 \
-nodes \
-keyout $PARENT.key \
-out $PARENT.crt \
-subj "/CN=${PARENT}" \
-extensions v3_ca \
-extensions v3_req \
-config <( \
  echo '[req]'; \
  echo 'default_bits= 4096'; \
  echo 'distinguished_name=req'; \
  echo 'x509_extension = v3_ca'; \
  echo 'req_extensions = v3_req'; \
  echo '[v3_req]'; \
  echo 'basicConstraints = CA:FALSE'; \
  echo 'keyUsage = nonRepudiation, digitalSignature, keyEncipherment'; \
  echo 'subjectAltName = @alt_names'; \
  echo '[ alt_names ]'; \
  echo "DNS.1 = www.${PARENT}"; \
  echo "DNS.2 = ${PARENT}"; \
  echo '[ v3_ca ]'; \
  echo 'subjectKeyIdentifier=hash'; \
  echo 'authorityKeyIdentifier=keyid:always,issuer'; \
  echo 'basicConstraints = critical, CA:TRUE, pathlen:0'; \
  echo 'keyUsage = critical, cRLSign, keyCertSign'; \
  echo 'extendedKeyUsage = serverAuth, clientAuth')

openssl x509 -noout -text -in $PARENT.crt

Para obtener un archivo .pfx, use el comando siguiente:

openssl pkcs12 -export -out $PARENT.pfx -inkey $PARENT.key -in $PARENT.crt

Nota:

A partir de .NET 5, Kestrel puede tomar archivos .crt y.key codificados con PEM además de archivos .pfx con una contraseña.

En función del sistema operativo del host, el certificado tendrá que ser de confianza. En un host de Linux, la "confianza" en el certificado es diferente y depende de la distribución.

Para los fines de esta guía, este es un ejemplo de Windows con PowerShell:

Import-Certificate -FilePath $certKeyPath -CertStoreLocation 'Cert:\LocalMachine\Root'

Ejecute el ejemplo con el siguiente comando en WSL:

docker run --rm -it -p 8000:80 -p 8001:443 -e ASPNETCORE_URLS="https://+;http://+" -e ASPNETCORE_HTTPS_PORT=8001 -e ASPNETCORE_ENVIRONMENT=Development -e ASPNETCORE_Kestrel__Certificates__Default__Path=/https/contoso.com.crt -e ASPNETCORE_Kestrel__Certificates__Default__KeyPath=/https/contoso.com.key -v /c/path/to/certs:/https/ mcr.microsoft.com/dotnet/samples:aspnetapp

Nota:

En WSL, la ruta de montaje del volumen puede cambiar en función de la configuración.

En PowerShell, ejecute el siguiente comando:

docker run --rm -it -p 8000:80 -p 8001:443 -e ASPNETCORE_URLS="https://+;http://+" -e ASPNETCORE_HTTPS_PORT=8001 -e ASPNETCORE_ENVIRONMENT=Development -e ASPNETCORE_Kestrel__Certificates__Default__Path=c:\https\contoso.com.crt -e ASPNETCORE_Kestrel__Certificates__Default__KeyPath=c:\https\contoso.com.key -v c:\certs:C:\https aspnetapp:my-sample

Una vez que la aplicación esté activa, vaya a contoso.com:8001 en un explorador.

Asegúrese de que las entradas del host se actualizan para que contoso.com responda en la dirección IP adecuada (por ejemplo, 127.0.0.1). Si no se reconoce el certificado, asegúrese de que el certificado que se carga con el contenedor también sea de confianza en el host y de que existan entradas SAN/DNS adecuadas para contoso.com.

Limpieza

Asegúrese de limpiar los certificados autofirmados una vez que se hayan realizado las pruebas.

Get-ChildItem $certKeyPath | Remove-Item

Consulte también