Amazon EKS — API Server Endpoint
API Server Endpoint Access
The API server endpoint determines who can reach your Kubernetes API and how nodes communicate with the control plane. Getting this wrong is a common security misconfiguration.
Three Access Modes
API Server Endpoint Options
┌────────────────────────────────────────────────────────────┐
│ │
│ PUBLIC ONLY (default) PUBLIC + PRIVATE │
│ ┌──────────┐ ┌──────────┐ │
│ │ Internet │──▶ API Server │ Internet │──▶ API Server │
│ └──────────┘ └──────────┘ │
│ ┌──────────┐ ┌──────────┐ │
│ │ Nodes │──▶ Internet ──▶ │ Nodes │──▶ Private │
│ └──────────┘ API Server └──────────┘ ENIs │
│ │
│ PRIVATE ONLY │
│ ┌──────────┐ │
│ │ VPN/DC │──▶ Private ENIs ──▶ API Server │
│ └──────────┘ │
│ ┌──────────┐ │
│ │ Nodes │──▶ Private ENIs │
│ └──────────┘ │
└────────────────────────────────────────────────────────────┘
Comparison
| Feature | Public Only | Public + Private | Private Only |
|---|---|---|---|
| kubectl from internet | ✅ Yes | ✅ Yes | ❌ No (VPN/DC required) |
| Node-to-API path | Internet (NAT GW) | Private (ENIs in VPC) | Private (ENIs in VPC) |
| Security level | Low | Medium | High |
| NAT GW for API traffic | Required | Not needed | Not needed |
| Setup complexity | Low | Low | High (VPN/bastion needed) |
| Recommendation | Dev only | Most production | Strict compliance |
Configure Endpoint Access
With eksctl
# cluster.yaml
apiVersion: eksctl.io/v1alpha5
kind: ClusterConfig
metadata:
name: demo
region: us-east-1
vpc:
clusterEndpoints:
publicAccess: true
privateAccess: true # Recommended for production
With AWS CLI
$ aws eks update-cluster-config \
--name demo \
--resources-vpc-config \
endpointPublicAccess=true,endpointPrivateAccess=true
Restrict Public Access by CIDR
If you use public access, restrict it to your IP:
vpc:
clusterEndpoints:
publicAccess: true
privateAccess: true
publicAccessCIDRs:
- 203.0.113.0/24 # Your office IP range
- 198.51.100.10/32 # Your VPN exit IP
$ aws eks update-cluster-config \
--name demo \
--resources-vpc-config \
publicAccessCidrs=["203.0.113.0/24","198.51.100.10/32"]
Why Public + Private is Recommended
Public + Private — Best of Both Worlds
Developer laptop Worker Nodes
(anywhere) (in private subnets)
│ │
│ kubectl (public) │ kubelet (private)
▼ ▼
┌──────────┐ ┌──────────┐
│ Public │ │ Private │
│ Endpoint │ │ ENIs │
│ (NLB) │ │ (in VPC) │
└────┬─────┘ └────┬─────┘
│ │
└──────────┐ ┌────────────┘
▼ ▼
┌──────────────────┐
│ API Server │
│ (EKS managed) │
└──────────────────┘
Benefits:
- Developers can kubectl from their laptops
- Nodes talk to API server privately (no NAT GW costs for API traffic)
- Faster node-to-API communication (no internet hop)
- Can restrict public access to specific CIDRs
Common Mistakes
| Mistake | Impact |
|---|---|
| Public-only endpoint in production | Nodes route to API via internet (slow, costs NAT GW) |
| Private-only without VPN setup | Locked out of cluster |
| No CIDR restriction on public | Anyone can attempt API authentication |
| Changing endpoint without testing | Could lose kubectl access |
Quick Reference
# Check current endpoint access
$ aws eks describe-cluster --name demo \
--query 'cluster.resourcesVpcConfig.{Public:endpointPublicAccess, Private:endpointPrivateAccess}'
# Enable both
$ aws eks update-cluster-config --name demo \
--resources-vpc-config endpointPublicAccess=true,endpointPrivateAccess=true
# Restrict public
$ aws eks update-cluster-config --name demo \
--resources-vpc-config 'publicAccessCidrs=["YOUR_IP/32"]'
What’s Next?
Now let’s design the VPC properly: VPC Design.