Access a tailnet device from your Kubernetes cluster
Last validated:
You can make a tailnet device accessible to your Kubernetes cluster workloads by creating an egress proxy. This is useful for accessing databases, internal tools, or other services hosted on devices in your tailnet.
Your cluster workloads access the tailnet device using a Kubernetes Service name, like any other in-cluster Kubernetes Service.
Prerequisites
Before you begin, make sure you have the following:
- Install the Tailscale Kubernetes Operator.
- A device connected to your tailnet that you want to access.
- An egress
ProxyGroup. Refer to the following section for an example.
Create an egress ProxyGroup
Create a ProxyGroup with spec.type set to egress:
apiVersion: tailscale.com/v1alpha1
kind: ProxyGroup
metadata:
name: egress-proxies
spec:
type: egress
replicas: 2
Refer to high availability for production configuration options.
Create an egress Kubernetes Service
Create a Kubernetes ExternalName Service that references the ProxyGroup and the tailnet device:
apiVersion: v1
kind: Service
metadata:
name: my-tailnet-device
annotations:
tailscale.com/tailnet-fqdn: "<device-name>.<tailnet>.ts.net"
tailscale.com/proxy-group: "egress-proxies"
spec:
type: ExternalName
externalName: placeholder
ports:
- port: 80
protocol: TCP
name: http
The operator overwrites the externalName field. The value of tailscale.com/tailnet-fqdn must be the full MagicDNS name of the device, not just the hostname. Set spec.ports to match the ports exposed by the target device.
You can also use this pattern to access a Tailscale Service (a stable VIP on your tailnet). The configuration is identical: set tailscale.com/tailnet-fqdn to the Tailscale Service's MagicDNS name.
You can also target a device by its Tailscale IP address using tailscale.com/tailnet-ip. The value can be a tailnet IPv4 or IPv6 address, or an address exposed by a Tailscale subnet router. Only one of tailscale.com/tailnet-fqdn or tailscale.com/tailnet-ip can be set on a Kubernetes Service. Tailscale recommends using the MagicDNS name, as the proxy automatically updates if the IP address changes.
The Kubernetes ExternalName Service must explicitly list all ports you want to access in spec.ports. Only port, protocol, and name are used; other port fields have no effect.
Verify the egress service
Wait for the Kubernetes Service to become ready:
kubectl wait svc my-tailnet-device --for=condition=TailscaleEgressSvcReady=true --timeout=5m
Access the tailnet device from your workloads using the Kubernetes DNS name:
curl http://my-tailnet-device.default.svc.cluster.local
Traffic is round-robin load balanced across the ProxyGroup replicas. Any number of egress Kubernetes Services can reference a single ProxyGroup.
If your workloads need to connect to the tailnet device using its MagicDNS name (for example, for TLS certificate validation), refer to Enable MagicDNS resolution in your cluster.
Further exploration
- Enable MagicDNS resolution in your cluster to let workloads connect using MagicDNS names.
- Learn more about egress in the Tailscale Kubernetes Operator.
- Configure high availability for production deployments.
- Use Tailscale Services for stable VIPs on your tailnet.