In this article I will talk about how to create trust between a Container (Ubuntu) and external resources. In this example the external resource is an API hosted on an IIS that encrypts the traffic with a self singed certificate. Here the scenario in a picture:
As you can see, I run my container in an Azure Kubernetes cluster, so this obviously also works in a Kubernetes cluster.
I did all the openssl steps on an ubuntu machine. Step 6 would probably be different on a Windows Machine.
1. Create a Certificate Authority to sign your certificates.
openssl genrsa -out myRootCA.key 4096
openssl req -x509 -new -nodes -key myRootCA.key -days 3650 -out myRootCA.pem
openssl pkcs12 -export -inkey myRootCA.key -in myRootCA.pem -out myRootCA.pfx
2. Create a key for your certificate
openssl genrsa -out myTLS.key 2048
3. Create a config file (newcfg.cnf)
touch newcfg.cnf
4. Edit the file and save it
gedit newcfg.cnf
[req]
distinguished_name = req_distinguished_name
req_extensions = v3_req
prompt = no
[req_distinguished_name]
C = DE
ST = HH
L = Hamburg
O = Obungi GmbH
OU = test
CN = *.yourfirst.domain
[v3_req]
keyUsage = keyEncipherment, dataEncipherment
extendedKeyUsage = serverAuth
subjectAltName = @alt_names
[alt_names]
DNS.1 = *.yourfirst.domain
DNS.2 = *.yoursecond.domain
5. Create a certificate signing request
openssl req -new -out myTLS.csr -key myTLS.key -config newcfg.cnf
6. Sign the certificate
openssl x509 -req -days 365 -CA myRootCA.pem -CAkey myRootCA.key -CAcreateserial -extensions SAN -extfile <(cat /etc/ssl/openssl.cnf <(printf „\n[SAN]\nsubjectAltName=DNS:*.yourfirst.domain,DNS:*.yoursecond.domain“)) -in myTLS.csr -out myTLS.crt
The “-extensions SAN -extfile <(cat /etc/ssl/openssl.cnf <(printf „\n[SAN]\nsubjectAltName=DNS:*.yourfirst.domain,DNS:*.yoursecond.domain“))” part ensures that the subjectAlterativeNames are being kept in the singed certificate. Otherwhise you will get a irreversable error in Google Chrome.
7. Convert the Certificate to PFX to be able to import it into Windows
openssl pkcs12 -export -out myTLS.pfx -inkey myTLS.key -in myTLS.crt
8. Import the TLS certificate to your IIS Server
Win + r -> mmc.exe
File -> Add/Remove Snap-In
Certificates -> Add
Computer Account
Local Computer
Finish -> Ok
Certificates -> Personal -> Certificates -> Right klick -> All Tasks -> Import
Follow the steps in the wizard to import the certificate.
9. Add a https binding to the api on the IIS via the IIS Manager
10. Convert the CA certificate to CRT to be able to import it into Ubuntu
openssl pkcs12 -in myRootCA.pfx -clcerts -nokeys -out myRootCA.crt
11. Add the CA Certificate to your Containers and update the certificate store
Copy the RootCA certificate to the level where your Dockerfile is.
Example Dockerfile:
FROM microsoft/dotnet:2.1-aspnetcore-runtime AS base
WORKDIR /app
EXPOSE 80
FROM microsoft/dotnet:2.1-sdk AS build
WORKDIR /src
COPY [„RandumnumberNET/RandumnumberNET.csproj“, „RandumnumberNET/“]
RUN dotnet restore „RandumnumberNET/RandumnumberNET.csproj“
COPY . .
WORKDIR „/src/RandumnumberNET“
RUN dotnet build „RandumnumberNET.csproj“ -c Release -o /app
FROM build AS publish
RUN dotnet publish „RandumnumberNET.csproj“ -c Release -o /app
# This is where the certificate gets imported
RUN apt-get update && apt-get install -y curl && apt-get install -y ca-certificates
COPY ./myRootCa.crt /usr/local/share/ca-certificates/myRootCa.crt
RUN update-ca-certificates
FROM base AS final
WORKDIR /app
COPY –from=publish /app .
ENTRYPOINT [„dotnet“, „RandumnumberNET.dll“]
That’s it.
Now you just have to build the image and run it where ever you want to. In my case I push it to my container registry and update the pods in my Kubernetes cluster.