How Do I configure Okteto with cert-manager and Google Cloud DNS?

How do I configure the Okteto wildcard certificate with cert-manager and Google Cloud DNS?

The recommended solution is to use Workload Identity. Make sure to enable Workload Identity for your cluster and then run the command show in the GKE docs for updating your node pools.

After that you need to create a Service Account in the same Google Cloud project as your GKE cluster. Give it the DNS Administrator role.

Bind the GCP Service Account you just created with the K8S Service Account of cert-manager. Replace the variables below with your own information.

gcloud iam service-accounts add-iam-policy-binding \
  ${GSA_NAME}@${GSA_PROJECT}.iam.gserviceaccount.com \
  --role roles/iam.workloadIdentityUser \
  --member "serviceAccount:${PROJECT_ID}.svc.id.goog[${RELEASE_NAMESPACE}/cert-manager]"

This command assigns the Workload Identity User role to the Kubernetes service account cert-manager in the ${RELEASE_NAMESPACE} namespace. By granting this role, the cert-manager Kubernetes service account can impersonate the Google Cloud service account that we just created. This enables cert-manager to securely authenticate and access Google Cloud resources using Workload Identity, without needing service account keys.

$RELEASE_NAMESPACE is the namespace where you installed cert-manager in.

After that create a values.yaml file with these options for your cert-manager Helm installation and apply it:

  extraArgs: [--issuer-ambient-credentials=true]
  serviceAccount:
    annotations:
      iam.gke.io/gcp-service-account: GSA_NAME@GSA_PROJECT.iam.gserviceaccount.com
helm upgrade cert-manager jetstack/cert-manager \
  --namespace cert-manager \
  --version ${LATEST_VERSION} \
  --values values.yaml

Once your cert-manager is configured this way, create the following Issuer in the okteto namespace:

apiVersion: cert-manager.io/v1
kind: Issuer
metadata:
  name: okteto-letsencrypt
spec:
  acme:
    server: https://acme-v02.api.letsencrypt.org/directory
    email:  "<<your-email>>"
    privateKeySecretRef:
      name: okteto-letsencrypt-acme
    solvers:
    - http01:
        ingress:
          serviceType: ClusterIP
          class: nginx
    - dns01:
        cloudDNS:
          project: "<<your-google-project-id>>"

and the following Certificate:

apiVersion: cert-manager.io/v1
kind: Certificate
metadata:
 name: okteto-letsencrypt
spec:
 secretName: okteto-letsencrypt
 duration: 8760h0m0s
 renewBefore: 600h0m0s # 25d
 issuerRef:
   name: okteto-letsencrypt
   kind: Issuer
 dnsNames:
   - "*.<<your-okteto-subdomain>>"

Now, add the following to your Okteto Helm configuration file to tell Okteto and NGINX to use your certificate:

wildcardCertificate:
  create: false
  name: okteto-letsencrypt

ingress-nginx:
  controller:
    extraArgs:
      default-ssl-certificate: $(POD_NAMESPACE)/okteto-letsencrypt

Finally, upgrade your Okteto installation for the new configuration to be applied.

For troubleshooting, you can check the cert manager logs, and the events associated to the resources Challenge , Order and CertificateRequest.