Índice
- Sección primera (básico):
- Docker en Windows. Apartado I: Instalar WSL2 (y Docker).
- Docker en Windows. Apartado II: Instalar Docker en Windows 11.
- Sección segunda (avanzado):
- Docker en Windows. Apartado III: Confianza entre entornos.
- Docker en Windows. Apartado IV: Configurar conexión entre Docker Windows y Docker WSL.
- Docker en Windows. Apartado V: Instalar Portainer en el entorno WSL.
- Docker en Windows. Apartado VI: Apuntes.
Con este artículo empezamos la sección avanzada. Además, este apartado lo dividiremos en dos partes: la primera para la creación un certificado CA; y, la segunda para la creación de los certificados TLS que necesitaremos.
Apartado III. Confianza entre entornos
¿Para qué necesitamos tener un certificado de una CA?
Vamos a conectar el docker de Windows con el docker de WSL, para lo cual al tener que realizar la conexión por dominio/IP necesitamos que ambas virtualizaciones confíen entre ellas... lo que no s obliga a tener certificados firmados por una CA. Aquí tenemos dos opciones: pagamos o no pagamos. Para esta sección de Docker nos interesa el aprendizaje de crear la CA y utilizarla.
Primera parte: Crear una CA (Autoridad Certificadora) para usos internos
Descargar e instalar OpenSSL
Descarga el instalador de OpenSSL Win32OpenSSL de slproweb. Este instalador es un empaquetado por un tercero, si necesitas el código de OpenSSL sin empaquetar tienes los enlaces al final del artículo. Sea cual sea la opción que tomes debe instalarlo antes de continuar.
Configurar OpenSSL
Abre una consola Powershell.
Lo primero que haremos es añadir la ruta del ejecutable al path:
[Environment]::SetEnvironmentVariable("PATH", "$env:PATH;C:\Program Files\OpenSSL-Win64\bin", [EnvironmentVariableTarget]::Machine)
Asegúrate de haber realizado la instalación en la ruta indicada, o, en caso de que difiera actualiza los datos de la variable de entorno.
Una vez hecho esto debemos reiniciar la consola para que surta efecto.
Ubicación sugerida para los certificados
Normalmente la instalación de Docker crea todas las carpetas necesarias, pero, si no existiera lo correcto es crear la siguiente carpeta C:\ProgramData\certs
:
New-Item -ItemType Directory -Force -Path "C:\ProgramData\certs"
Generar los certificados utilizando OpenSSL
Antes de continuar: Recuerda que debes poner especial cuidado en la salvaguarda de las contraseñas, ficheros llave y certificados.
Generar la Llave y el Certificado de la CA (Autoridad Certificadora)
Para que un certificado actúe como CA, debe tener la extensión Basic Constraints
con CA:TRUE
.
Nos situamos en el directorio:
cd "C:\ProgramData\certs"
Crea un archivo llamado ca.cnf
con el siguiente contenido:
[ req ]
distinguished_name = req_distinguished_name
x509_extensions = v3_ca
prompt = no
[ req_distinguished_name ]
C = ES
ST = Comunitat Valenciana
L = Valencia
O = EMPRESA
OU = UNIDAD EMPRESARIAL
CN = Mi CA para Docker
[ v3_ca ]
subjectKeyIdentifier = hash
authorityKeyIdentifier = keyid:always,issuer
basicConstraints = critical, CA:TRUE
keyUsage = critical, digitalSignature, cRLSign, keyCertSign
Ajusta los campos C (Country), ST (State or Province), L (Locality), O (Organization), OU (Organizational Unit) y CN (Common Name) según tus necesidades.
Es importante utilizar un CN que nos permita tener una buena descripción de su cometido, por ejemplo un CN conveniente para este caso sería ca-$($env:COMPUTERNAME)-$($env:USERNAME)
. Al final del artículo hemos añadido información relevante para su correcta definición.
Genera el certificado llave:
openssl genrsa -aes256 -out ca-key.pem 4096
Te pedirá una contraseña para la clave de la CA. Esta contraseña es necesaria para firmar otros certificados. Como es habitual, guárdatela en tu Keepass o similar.
Genera el certificado (te pedirá la contraseña que has introducido en la llave):
openssl req -new -x509 -days 3650 -key ca-key.pem -sha256 -out ca.pem -config ca.cnf
Ahora para confirmar que es correcto, lanza el siguiente comando:
openssl x509 -in ca.pem -text -noout | Select-String "CA"
En el resultado tendrás que ver que basicConstraints
está como critical
y con CA:TRUE
.
Configurar los permisos de los archivos para WSL
Para ello entramos en una terminal Powershell en modo "Administrador" e introducimos:
wsl -d ubuntu
Ahora nos situamos en el directorio certs
:
cd /mnt/c/ProgramData/certs
Ahora limpiamos los archivos sobrantes:
rm *.csr *.cnf *.srl
Por último, vamos a cambiar los permisos:
chmod -v 0400 ca-key.pem
chmod -v 0444 ca.pem
¿Porqué hemos cambiado los permisos desde la terminal de Ubuntu?
Por dos razones:
- Es más simple que con Powershell.
- Nos aseguramos que tenemos acceso a los archivos en el disco
C:
de Windows desde el entorno WSL.
Evidentemente, puedes optar por cambiar los permisos desde Powershell.
Segunda parte: Configuración de la comunicación interna de los entornos
Debes tener un certificado CA antes de continuar.
Generar certificados TLS
Antes de configurar Docker tanto en Windows como WSL necesitas generar los certificados TLS. Estos certificados asegurarán la comunicación entre el cliente Docker y el daemon Docker. Necesitarás una Autoridad Certificadora (CA), el cual ya lo habrás preparado anteriormente.
Normalmente la instalación de Docker crea todas las carpetas necesarias, pero, si no existiera lo correcto es crear la carpeta C:\ProgramData\docker\certs
para los certificados:
New-Item -ItemType Directory -Force -Path "C:\ProgramData\docker\certs"
Nos situamos en el directorio:
cd "C:\ProgramData\docker\certs"
Generar los certificados utilizando OpenSSL
Es necesario que tengas un certificado de una CA para realizar los siguientes pasos como se indicó en el anterior apartado.
Si ha seguido las indicaciones del documento, tendrás en la carpeta C:\ProgramData\certs
el certificado CA ya creado. Créate el enlace en una variable para acceder rápidamente a ellos:
$caPem = "C:\ProgramData\certs\ca.pem"
$caKeyPem = "C:\ProgramData\certs\ca-key.pem"
Generar Clave y Certificado del Servidor para Docker en Windows
En este paso tendremos en cuenta que debemos configurarlo para que escuche a través de localhost.
openssl genrsa -out win-server-key.pem 4096
openssl req -subj "/CN=localhost" -sha256 -new -key win-server-key.pem -out win-server.csr
Consultamos el nombre de nuestro equipo lanzando el comando:
hostname
Ahora creamos el archivo extfile-win.cnf con el siguiente contenido utilizando el resultado de hostname
(sustituyendo xNAMEx
):
subjectAltName = DNS:localhost,IP:127.0.0.1,IP:::1,DNS:xNAMEx,DNS:wsl2docker.local
extendedKeyUsage = serverAuth
Como es lógico, cambiamos el DNS indicado (xNAMEx) por el nombre de tu máquina, y, además introducimos un nuevo DNS que será utilizado para “conectar” el entorno Windows y WSL sin necesidad de depender de una IP (esto nos permite que el certificado continúe siendo válido incluso si nos cambia la IP).
Ahora firma la CSR del servidor de Windows con tu CA:
$caPem = "C:\ProgramData\certs\ca.pem"
$caKeyPem = "C:\ProgramData\certs\ca-key.pem"
Copy-Item -Path $caPem "C:\ProgramData\docker\certs\ca.pem"
openssl x509 -req -days 3650 -sha256 -in win-server.csr -CA ca.pem -CAkey $caKeyPem -CAcreateserial -out win-server-cert.pem -extfile extfile-win.cnf
(te pedirá la contraseña de tu llave).
Generar Clave y Certificado del Servidor para Docker en WSL2
Seguimos los mismos pasos para el de WSL2:
openssl genrsa -out wsl-server-key.pem 4096
openssl req -subj "/CN=localhost" -sha256 -new -key wsl-server-key.pem -out wsl-server.csr
Creamos el archivo configuración de extensiones extfile-wsl.cnf:
subjectAltName = DNS:localhost,IP:127.0.0.1,IP:::1,DNS:wsl2docker.local
extendedKeyUsage = serverAuth
Firmamos el CSR del servidor de WSL2 con el CA:
openssl x509 -req -days 3650 -sha256 -in wsl-server.csr -CA ca.pem -CAkey $caKeyPem -CAcreateserial -out wsl-server-cert.pem -extfile extfile-wsl.cnf
(te pedirá la contraseña de tu llave).
Generar Clave y Certificado del Cliente (para docker CLI)
Los mismos pasos:
openssl genrsa -out client-key.pem 4096
openssl req -subj "/CN=client" -new -key client-key.pem -out client.csr
Creamos el archivo de configuración de extensiones extfile-client.cnf:
extendedKeyUsage = clientAuth
Y firmamos el CSR:
openssl x509 -req -days 3650 -sha256 -in client.csr -CA ca.pem -CAkey $caKeyPem -CAcreateserial -out client-cert.pem -extfile extfile-client.cnf
(te pedirá la contraseña de tu llave).
Configurar los permisos de los archivos
Aprovechamos que tenemos instalado WSL y terminamos de configurar los archivos desde la terminal de Ubuntu. Para ello entramos en una terminal powershell en modo "Administrador" e introducimos:
wsl -d ubuntu
Ahora nos situamos en el directorio apropiado (certs de Docker):
cd /mnt/c/ProgramData/docker/certs
Limpiamos los archivos sobrantes:
rm *.csr *.cnf *.srl
Cambiamos los permisos:
chmod -v 0400 *-key.pem client-key.pem
chmod -v 0444 *-cert.pem client-cert.pem
Salimos de la shell de Ubuntu:
exit
Y cerramos la consola con permisos Administrador que hemos abierto.
Configurar Docker en Windows para utilizar los certificados TLS
Recordemos lo que tenemos. Los archivos resultantes se dividen en:
- Clave CA o certificadora: archivos
ca.pem
yca-key.pem
. Estos archivos debes guardarlos offline en un lugar seguro. - Claves para el cliente docker:
ca.pem
,client-cert.pem
yclient-key.pem
.
En cuanto a las claves para el cliente, terminarán siendo colocadas en otros directorios (pero esto lo veremos después): en WSL, en la carpeta ~/.docker/
y en windows en la carpeta %USERPROFILE%\.docker\
. Vamos a ello.
Copiar las claves TLS a la carpeta de usuario
Primero, nos aseguramos de que los certificados de cliente (ca.pem
, client-cert.pem
, client-key.pem
) están en %USERPROFILE%\.docker\
con el nombre adecuado. En la terminal de Powershell:
$userProfile = $env:USERPROFILE
$dockerDir = Join-Path $userProfile ".docker"
If (-not (Test-Path $dockerDir)) { New-Item -Path $dockerDir -ItemType Directory }
Copy-Item "$caPem" -Destination (Join-Path $dockerDir "ca.pem")
Copy-Item "C:\ProgramData\Docker\certs\client-cert.pem" -Destination (Join-Path $dockerDir "cert.pem")
Copy-Item "C:\ProgramData\Docker\certs\client-key.pem" -Destination (Join-Path $dockerDir "key.pem")
Configuración del demonio
Utiliza Notepad++ (o el editor que prefieras) para crear el archivo:
C:\ProgramData\docker\config\daemon.json
con el contenido:
{
"hosts": ["tcp://0.0.0.0:2375", "npipe://"],
"tlsverify": true,
"tlscacert": "C:\\ProgramData\\docker\\certs\\ca.pem",
"tlscert": "C:\\ProgramData\\docker\\certs\\win-server-cert.pem",
"tlskey": "C:\\ProgramData\\docker\\certs\\win-server-key.pem"
}
Configurar un contexto para Windows
Necesitaremos utilizar “contextos” de Docker, para entre otros, conectar sin problemas desde VSCode a Docker, o desde el otro entorno.
Pero, primero verificamos que no tenemos el contexto ya creado con anterioridad:
docker context ls
(Nota: Si lo tienes deberías borrarlo, utiliza el comando docker context rm NombreContexto -f
.)
Ahora, crea el contexto con el nombre “windows” para Windows:
docker context create windows --docker "host=tcp://localhost:2375,ca=$userProfile\.docker\ca.pem,cert=$userProfile\.docker\cert.pem,key=$userProfile\.docker\key.pem"
Verifica que se ha creado correctamente:
docker context inspect windows
Y actívalo:
docker context use windows
Apuntes
Para crear una CA hay que tener en cuenta las siguientes normativas o estándares:
- Formato y estructura. X.509 implementado vía RFC 5280: https://datatracker.ietf.org/doc/html/rfc5280
- Certificados web (SSL/TLS): https://cabforum.org/working-groups/server/baseline-requirements/about/
- Validez legal, reglamento UE eIDAS y leyes nacionales BOE
- Funcionamiento interno, Declaración de Prácticas de Certificación de cada CA específica, por lo que debe buscar la DPC que puede afectarle para documentarse. Como ejemplo enlazamos la normativa de la FNMT (emisión de certificados oficiales en España) en su web de la Sede Electrónica de la Real Casa de la Moneda; y, al BOE con la disposición para la expedición de DNI y certificados digitales
Enlaces
- OpenSSL
- GitHub de OpenSSL
- Empaquetado para Windows por Shining Light Productions
Siguiente artículo:
- Docker en Windows. Apartado IV: Configurar conexión entre Docker Windows y Docker WSL.
Top comments (0)