No alternative text provided

πŸ” Secure Kubernetes Access with Teleport: No More Port-Forwarding Pain

I run oursi.net on a self-hosted Kubernetes cluster, and I manage everything through ArgoCD. But like many of you, I was getting tired of doing this every time I wanted to check my deployments:

1kubectl port-forward svc/argocd-server -n argocd 8080:8080

And then navigating to https://localhost:8080. Meh.

So I decided to deploy Teleport.

🧭 What is Teleport?

Teleport is a secure access platform β€” like a modern Bastion host on steroids. It gives you:

  • a web interface
  • CLI access
  • and zero trust authentication across SSH, Kubernetes, databases, and web apps

… all from a single login (including passkeys or OTP).

In my case, I wanted to use Teleport to securely expose internal services (like ArgoCD and Argo Workflows) without making them public.

πŸ› οΈ Installing Teleport via Helm + ArgoCD

I use GitOps, so everything goes through ArgoCD. The first step is to deploy the main teleport cluster.

1apiVersion: argoproj.io/v1alpha1
2kind: Application
3metadata:
4  name: teleport
5  namespace: argocd
6spec:
7  project: default
8  source:
9    repoURL: https://charts.releases.teleport.dev
10    chart: teleport-cluster
11    targetRevision: 17.5.1
12    helm:
13      values: |
14        clusterName: "teleport.oursi.net"
15        service:
16          type: ClusterIP
17        ingress:
18          enabled: false
19        proxyListenerMode: multiplex
20        acme: false
21        tls:
22          existingSecretName: teleport-tls-cert
23        operator:
24          enabled: true
25        persistence:
26          enabled: true
27          storageClassName: "local-path"
28          size: 10Gi
29        log:
30          level: INFO
31        resources:
32          limits:
33            cpu: 500m
34            memory: 512Mi
35          requests:
36            cpu: 250m
37            memory: 256Mi
38  destination:
39    server: https://kubernetes.default.svc
40    namespace: teleport-cluster
41  syncPolicy:
42    automated:
43      prune: true
44      selfHeal: true
45    syncOptions:
46      - CreateNamespace=true

πŸ” TLS with cert-manager

I created a TLS certificate using cert-manager and Let's Encrypt:

1apiVersion: cert-manager.io/v1
2kind: Certificate
3metadata:
4  name: teleport-tls-cert
5  namespace: teleport-cluster
6spec:
7  secretName: teleport-tls-cert
8  dnsNames:
9    - teleport.oursi.net
10    - "*.teleport.oursi.net"
11  issuerRef:
12    name: letsencrypt-issuer
13    kind: ClusterIssuer
14    group: cert-manager.io

This is the secret referenced in the Teleport cluster Helm chart.

🌐 Exposing Teleport with Traefik (IngressRouteTCP)

Teleport speaks native TLS over TCP. Regular Ingress didn’t work well, so I used IngressRouteTCP from Traefik:

1apiVersion: traefik.io/v1alpha1
2kind: IngressRouteTCP
3metadata:
4  name: teleport-tcp
5  namespace: teleport-cluster
6spec:
7  entryPoints:
8    - websecure
9  routes:
10    - match: HostSNI(`teleport.oursi.net`)
11      services:
12        - name: teleport
13          port: 443
14          nativeLB: true
15    - match: HostSNI(`argocd.teleport.oursi.net`)
16      services:
17        - name: teleport
18          port: 443
19          nativeLB: true
20    - match: HostSNI(`argowf.teleport.oursi.net`)
21      services:
22        - name: teleport
23          port: 443
24          nativeLB: true
25  tls:
26    passthrough: true

The only downside is that I must reference each new application's hostname here as well.

πŸ‘€ Creating a User with Teleport CRD

To create my teleport user, with admin access, I use this yaml:

1apiVersion: resources.teleport.dev/v2
2kind: TeleportUser
3metadata:
4  name: benoit
5  namespace: teleport-cluster
6spec:
7  roles:
8    - access
9    - editor

It will create the user, but you still need to set up a password for it. To do so, generate a password reset link:

1kubectl -n teleport-cluster exec -ti deployment/teleport-auth -- tctl users reset benoit

Follow the link and boom, you're in ✨

πŸ”Œ Installing the Kube Agent

Now to expose ArgoCD and Argo Workflows, I deployed the teleport-kube-agent.

First, create a join token:

1apiVersion: resources.teleport.dev/v2
2kind: TeleportProvisionToken
3metadata:
4  name: kubernetes-app-token
5  namespace: teleport-cluster
6spec:
7  roles: [App]
8  join_method: kubernetes
9  kubernetes:
10    type: in_cluster
11    allow:
12      - service_account: "teleport-cluster:teleport-agent"

Then install the Helm chart via ArgoCD:

1apiVersion: argoproj.io/v1alpha1
2kind: Application
3metadata:
4  name: teleport-agent
5  namespace: argocd
6spec:
7  project: default
8  source:
9    repoURL: https://charts.releases.teleport.dev
10    chart: teleport-kube-agent
11    targetRevision: 17.5.1
12    helm:
13      values: |
14        proxyAddr: "teleport.oursi.net:443"
15        roles: app
16        joinParams:
17          method: "kubernetes"
18          tokenName: "kubernetes-app-token"
19        apps:
20          - name: argocd
21            uri: "https://argocd-server.argocd.svc.cluster.local"
22            public_addr: argocd.teleport.oursi.net
23            insecure_skip_verify: true
24            rewrite:
25              redirect:
26                - argocd-server.argocd.svc.cluster.local
27          - name: argowf
28            uri: "https://argo-server.argo.svc.cluster.local:2746"
29            public_addr: argowf.teleport.oursi.net
30            insecure_skip_verify: true
31            rewrite:
32              redirect:
33                - argo-server.argo.svc.cluster.local
34  destination:
35    server: https://kubernetes.default.svc
36    namespace: teleport-cluster
37  syncPolicy:
38    automated:
39      prune: true
40      selfHeal: true
41    syncOptions:
42      - CreateNamespace=true

πŸŽ‰ Result

Now, I can go to:

https://argocd.teleport.oursi.net

https://argowf.teleport.oursi.net

… log in with passkeys, and enjoy secure access from anywhere πŸš€

Teleport abstracts the pain of port forwarding, secure tunneling, and multi-cluster auth into a slick interface. Highly recommend for anyone doing GitOps or running internal tools!

Secure Kubernetes Access with Teleport: No More Port-Forwarding Pain