如何使用Cloudflare替代Route 53在AWS中部署KOPS集群(含YAML文件配置方法)
Great question! Deploying a KOPS cluster on AWS with Cloudflare instead of Route 53 is totally doable—let’s break this down into actionable steps, including the YAML config you need to make it work.
First, make sure you have these sorted:
- An AWS account with permissions to create EC2 instances, ELBs, VPC resources, and S3 buckets
- A Cloudflare account with your domain (e.g.,
example.com) fully managed by Cloudflare (NS records pointing to Cloudflare’s servers) - KOPS, AWS CLI, and kubectl installed on your local machine
- An S3 bucket created to store KOPS cluster state (this is required for KOPS to track cluster resources)
Before deploying the cluster, keep this in mind:
Cloudflare’s default proxy mode (orange cloud icon) will break cluster API communication. KOPS and kubectl need direct TCP access to the API server’s ELB, so all cluster-related DNS records must be set to DNS only (gray cloud).
You’ll need to create DNS records later, but note the domain names we’ll use:
- Cluster domain:
mycluster.example.com(replace with your subdomain) - API server domain:
api.mycluster.example.com
First, set up your environment variables:
export CLUSTER_NAME=mycluster.example.com export KOPS_STATE_STORE=s3://your-kops-state-bucket-name
Generate a base cluster YAML file (we’ll modify this to skip Route 53):
kops create cluster --name=${CLUSTER_NAME} --zones=us-east-1a,us-east-1b --dns=none --dry-run -o yaml > cluster.yaml
Now edit cluster.yaml to add critical Cloudflare-compatible settings. Here’s a complete, annotated example:
apiVersion: kops.k8s.io/v1alpha2 kind: Cluster metadata: name: mycluster.example.com spec: # Disable Route53 and internal DNS controller topology: dns: type: None # Specify your Cloudflare-managed domain dnsZone: example.com # Set the public API domain (matches what we'll create in Cloudflare) masterPublicName: api.mycluster.example.com # Basic AWS cluster settings cloudProvider: aws configBase: s3://your-kops-state-bucket-name/mycluster.example.com kubernetesVersion: 1.28.0 networkCIDR: 10.0.0.0/16 # Choose your CNI (Cilium used here, Calico works too) networking: cilium: {} # Master and node network topology (public for simplicity; use private in production) topology: masters: public nodes: public # Subnet config (match your AWS regions/zones) subnets: - cidr: 10.0.0.0/24 name: us-east-1a type: Public zone: us-east-1a - cidr: 10.0.1.0/24 name: us-east-1b type: Public zone: us-east-1b # API server access (restrict to your IP in production!) kubernetesApiAccess: - 0.0.0.0/0 # SSH access (restrict to your IP in production!) sshAccess: - 0.0.0.0/0 # Etcd cluster config (default setup) etcdClusters: - cpuRequest: 200m etcdMembers: - instanceGroup: master-us-east-1a name: a - instanceGroup: master-us-east-1b name: b memoryRequest: 100Mi name: main - cpuRequest: 100m etcdMembers: - instanceGroup: master-us-east-1a name: a - instanceGroup: master-us-east-1b name: b memoryRequest: 100Mi name: events
Next, create master and node instance groups. Generate their YAML files:
# Master instance group (us-east-1a) kops create ig --name=${CLUSTER_NAME} master-us-east-1a --role Master --subnet us-east-1a --dry-run -o yaml > master-ig.yaml # Node instance group (us-east-1a) kops create ig --name=${CLUSTER_NAME} nodes-us-east-1a --role Node --subnet us-east-1a --dry-run -o yaml > node-ig.yaml # Repeat for us-east-1b if needed
Apply the cluster configuration:
kops create -f cluster.yaml kops create -f master-ig.yaml kops create -f node-ig.yaml
Now deploy the cluster to AWS:
kops update cluster ${CLUSTER_NAME} --yes
Wait 5-10 minutes for AWS to provision all resources (ELB, EC2 instances, etc.).
Once the cluster is deployed, get the API server’s ELB DNS name:
aws elb describe-load-balancers --query 'LoadBalancerDescriptions[?contains(LoadBalancerName, `api`)]' --output json | jq -r '.[0].DNSName'
Go to your Cloudflare dashboard and create these records:
- CNAME Record:
api.mycluster.example.com→ [ELB DNS name from above], set to DNS only (gray cloud) - Optional A Record:
mycluster.example.com→ You can point this to the same ELB if needed, but the API record is critical for cluster access
Wait 2-3 minutes for DNS propagation to complete.
Configure kubectl to access your cluster:
kops export kubecfg ${CLUSTER_NAME}
Verify the cluster is healthy:
kubectl get nodes kops validate cluster --wait 10m
If everything works, you’ll see all nodes in Ready state and a message confirming the cluster is valid.
- DNS Proxy Mode: Double-check that your API DNS record is set to DNS only—this is the most common issue.
- DNS Propagation: Use
nslookup api.mycluster.example.comto confirm the record resolves to the ELB’s IP. - AWS Permissions: Ensure your IAM user has full permissions for EC2, ELB, S3, and VPC resources.
- KOPS State Store: Make sure your S3 bucket is accessible and has correct permissions for KOPS.
内容的提问来源于stack exchange,提问作者Aléxis Mosquera Caicedo

