From 2dd9d44bf9ca9864c74d735b88705f7e2c6442b2 Mon Sep 17 00:00:00 2001 From: Graham McIntire Date: Sat, 10 Jan 2026 16:00:02 -0600 Subject: [PATCH] update and remove dns from tf --- ansible/group_vars/all/all.yml | 3 + .../group_vars/bind9_servers/mcintire.me.yml | 4 +- .../group_vars/bind9_servers/reverse_191.yml | 3 +- .../group_vars/bind9_servers/towerops.net.yml | 18 + ansible/host_vars/dokku.w5isp.com.yml | 6 + ansible/host_vars/monitor.vntx.net.yml | 6 + ansible/host_vars/netbox.vntx.net.yml | 6 +- ansible/host_vars/radius.vntx.net.yml | 6 + ansible/host_vars/skippy.w5isp.com.yml | 6 + ansible/host_vars/unimus.vntx.net.yml | 6 + ansible/host_vars/vpn.vntx.net.yml | 6 + ansible/hosts | 3 +- ansible/playbook.yml | 184 ++++---- ansible/roles/base/defaults/main.yml | 3 - .../roles/general/tasks/debian/icinga2.yml | 12 +- {home => old}/cluster/add-node3-to-etcd.sh | 0 {home => old}/cluster/aprs/README.md | 0 .../cluster/aprs/aprs-configmap.yaml | 0 .../cluster/aprs/aprs-ingressroute.yaml | 0 {home => old}/cluster/aprs/aprs-rbac.yaml | 0 .../cluster/aprs/aprs-secret-secure.yaml | 0 .../aprs-statefulset-with-pullsecret.yaml | 0 .../cluster/aprs/create-ghcr-secret.sh | 0 .../cluster/aprs/create-image-pull-secret.sh | 0 {home => old}/cluster/aprs/deploy.sh | 0 .../cluster/aprs/install-postgis-manual.sh | 0 {home => old}/cluster/aprs/namespace.yaml | 0 .../aprs/postgres-deployment-normal.yaml | 0 .../aprs/postgres-deployment-repair.yaml | 0 .../cluster/aprs/postgres-deployment.yaml | 0 .../cluster/aprs/postgres-normal-mode.sh | 0 .../cluster/aprs/postgres-repair-mode.sh | 0 .../cluster/aprs/postgres-secret-secure.yaml | 0 {home => old}/cluster/aprs/setup-database.sh | 0 .../cluster/aprs/setup-postgres-aprs.sql | 0 .../cert-manager/letsencrypt-prod.yaml | 0 {home => old}/cluster/controlplane.yaml | 0 {home => old}/cluster/deploy.md | 0 {home => old}/cluster/k3s-upgrade/plan.yaml | 0 .../cluster/longhorn-uservolume.yaml | 0 .../cluster/mariadb/mariadb-deployment.yaml | 0 {home => old}/cluster/metallb-config.yaml | 0 {home => old}/cluster/mikrotik-ha-setup.md | 0 {home => old}/cluster/n8n/deploy.sh | 0 {home => old}/cluster/n8n/ingress.yaml | 0 {home => old}/cluster/n8n/n8n-deployment.yaml | 0 {home => old}/cluster/n8n/n8n-pvc.yaml | 0 {home => old}/cluster/n8n/namespace.yaml | 0 .../cluster/n8n/postgres-deployment.yaml | 0 {home => old}/cluster/n8n/postgres-pvc.yaml | 0 {home => old}/cluster/n8n/secret.yaml | 0 {home => old}/cluster/node1.patch.yaml | 0 {home => old}/cluster/node2.patch.yaml | 0 {home => old}/cluster/node3.patch.yaml | 0 {home => old}/cluster/nodered/deploy.sh | 0 {home => old}/cluster/nodered/deployment.yaml | 0 {home => old}/cluster/nodered/ingress.yaml | 0 {home => old}/cluster/nodered/namespace.yaml | 0 {home => old}/cluster/nodered/pvc.yaml | 0 {home => old}/cluster/nodered/service.yaml | 0 .../cluster/nodered/settings-configmap.yaml | 0 {home => old}/cluster/schematic.yaml | 0 .../cluster/tailscale-operator-complete.yaml | 0 {home => old}/cluster/tailscale.patch.yaml | 0 {home => old}/cluster/talosconfig | 0 {home => old}/cluster/wavelog/README.md | 0 {home => old}/cluster/wavelog/deploy.sh | 0 .../cluster/wavelog/mariadb-deployment.yaml | 0 .../cluster/wavelog/mariadb-secret.yaml | 0 {home => old}/cluster/wavelog/namespace.yaml | 0 .../cluster/wavelog/wavelog-config-job.yaml | 0 .../cluster/wavelog/wavelog-deployment.yaml | 0 .../cluster/wavelog/wavelog-ingress.yaml | 0 .../cluster/wavelog/wavelog-ingressroute.yaml | 0 .../cluster/wavelog/wavelog-pvc.yaml | 0 .../cluster/wavelog/wavelog-secret.yaml | 0 {home => old}/cluster/worker.yaml | 0 talos/.gitignore | 7 + talos/CLUSTER_CONFIG.md | 114 +++++ talos/apply-configs.sh | 28 ++ talos/apply-worker-configs.sh | 53 +++ .../letsencrypt-clusterissuer.yaml | 35 ++ talos/cluster-config.yaml | 0 talos/controlplane.yaml | 403 ++++++++++++++++ talos/current-config.yaml | 1 + talos/deploy-cluster-services.sh | 194 ++++++++ talos/generate-node-configs.sh | 26 ++ talos/kubeconfig | 28 ++ talos/metallb/ipaddresspool-internal.yaml | 20 + talos/nodes/cp-1.yaml | 124 +++++ talos/nodes/cp-2.yaml | 124 +++++ talos/nodes/cp-3.yaml | 124 +++++ talos/nodes/worker-1.yaml | 118 +++++ talos/nodes/worker-2.yaml | 118 +++++ talos/nodes/worker-3.yaml | 118 +++++ talos/patches/cloud-provider.yaml | 4 + talos/patches/cp-1.yaml | 7 + talos/patches/cp-2.yaml | 7 + talos/patches/cp-3.yaml | 7 + .../patches/remove-controlplane-secrets.yaml | 2 + talos/patches/system-extensions.yaml | 28 ++ talos/patches/tailscale-config.yaml | 7 + talos/patches/tailscale-extension-config.yaml | 14 + talos/patches/worker-1.yaml | 5 + talos/patches/worker-2.yaml | 5 + talos/patches/worker-3.yaml | 5 + talos/patches/worker-type.yaml | 5 + talos/provision-workers.sh | 78 ++++ talos/proxmox-ccm/config.yaml | 6 + talos/proxmox-ccm/secret.yaml | 7 + talos/proxmox-csi/namespace.yaml | 8 + .../proxmox-csi/node-providerid-patches.yaml | 26 ++ talos/proxmox-csi/secret.yaml | 18 + talos/proxmox-csi/storageclass.yaml | 14 + talos/proxmox-csi/values.yaml | 15 + talos/reset-vms.sh | 76 +++ talos/schematic.yaml | 6 + talos/setup-proxmox-csi.sh | 43 ++ talos/update-proxmox-csi-permissions.sh | 24 + talos/worker-base.yaml | 114 +++++ talos/worker-base.yaml.backup | 121 +++++ talos/worker.yaml | 433 ++++++++++++++++++ terraform/.terraform.lock.hcl | 53 +-- terraform/dns_aprs.tf | 39 -- terraform/dns_manero.tf | 80 ---- terraform/dns_mcintire.tf | 100 ---- terraform/dns_ntxarms.tf | 80 ---- terraform/dns_powerdns_zones.tf | 91 ---- terraform/dns_reverse.tf | 103 ----- terraform/dns_towerops.tf | 62 --- terraform/dns_vntx_net.tf | 148 ------ terraform/dns_vntx_org.tf | 12 - terraform/dns_w5isp.tf | 262 ----------- terraform/main.tf | 9 - terraform/terraform.tfvars | 2 - terraform/tfplan | Bin 72862 -> 0 bytes terraform/variables.tf | 58 --- 137 files changed, 2908 insertions(+), 1183 deletions(-) create mode 100644 ansible/host_vars/dokku.w5isp.com.yml create mode 100644 ansible/host_vars/monitor.vntx.net.yml create mode 100644 ansible/host_vars/radius.vntx.net.yml create mode 100644 ansible/host_vars/skippy.w5isp.com.yml create mode 100644 ansible/host_vars/unimus.vntx.net.yml create mode 100644 ansible/host_vars/vpn.vntx.net.yml rename {home => old}/cluster/add-node3-to-etcd.sh (100%) rename {home => old}/cluster/aprs/README.md (100%) rename {home => old}/cluster/aprs/aprs-configmap.yaml (100%) rename {home => old}/cluster/aprs/aprs-ingressroute.yaml (100%) rename {home => old}/cluster/aprs/aprs-rbac.yaml (100%) rename {home => old}/cluster/aprs/aprs-secret-secure.yaml (100%) rename {home => old}/cluster/aprs/aprs-statefulset-with-pullsecret.yaml (100%) rename {home => old}/cluster/aprs/create-ghcr-secret.sh (100%) rename {home => old}/cluster/aprs/create-image-pull-secret.sh (100%) rename {home => old}/cluster/aprs/deploy.sh (100%) rename {home => old}/cluster/aprs/install-postgis-manual.sh (100%) rename {home => old}/cluster/aprs/namespace.yaml (100%) rename {home => old}/cluster/aprs/postgres-deployment-normal.yaml (100%) rename {home => old}/cluster/aprs/postgres-deployment-repair.yaml (100%) rename {home => old}/cluster/aprs/postgres-deployment.yaml (100%) rename {home => old}/cluster/aprs/postgres-normal-mode.sh (100%) rename {home => old}/cluster/aprs/postgres-repair-mode.sh (100%) rename {home => old}/cluster/aprs/postgres-secret-secure.yaml (100%) rename {home => old}/cluster/aprs/setup-database.sh (100%) rename {home => old}/cluster/aprs/setup-postgres-aprs.sql (100%) rename {home => old}/cluster/cert-manager/letsencrypt-prod.yaml (100%) rename {home => old}/cluster/controlplane.yaml (100%) rename {home => old}/cluster/deploy.md (100%) rename {home => old}/cluster/k3s-upgrade/plan.yaml (100%) rename {home => old}/cluster/longhorn-uservolume.yaml (100%) rename {home => old}/cluster/mariadb/mariadb-deployment.yaml (100%) rename {home => old}/cluster/metallb-config.yaml (100%) rename {home => old}/cluster/mikrotik-ha-setup.md (100%) rename {home => old}/cluster/n8n/deploy.sh (100%) rename {home => old}/cluster/n8n/ingress.yaml (100%) rename {home => old}/cluster/n8n/n8n-deployment.yaml (100%) rename {home => old}/cluster/n8n/n8n-pvc.yaml (100%) rename {home => old}/cluster/n8n/namespace.yaml (100%) rename {home => old}/cluster/n8n/postgres-deployment.yaml (100%) rename {home => old}/cluster/n8n/postgres-pvc.yaml (100%) rename {home => old}/cluster/n8n/secret.yaml (100%) rename {home => old}/cluster/node1.patch.yaml (100%) rename {home => old}/cluster/node2.patch.yaml (100%) rename {home => old}/cluster/node3.patch.yaml (100%) rename {home => old}/cluster/nodered/deploy.sh (100%) rename {home => old}/cluster/nodered/deployment.yaml (100%) rename {home => old}/cluster/nodered/ingress.yaml (100%) rename {home => old}/cluster/nodered/namespace.yaml (100%) rename {home => old}/cluster/nodered/pvc.yaml (100%) rename {home => old}/cluster/nodered/service.yaml (100%) rename {home => old}/cluster/nodered/settings-configmap.yaml (100%) rename {home => old}/cluster/schematic.yaml (100%) rename {home => old}/cluster/tailscale-operator-complete.yaml (100%) rename {home => old}/cluster/tailscale.patch.yaml (100%) rename {home => old}/cluster/talosconfig (100%) rename {home => old}/cluster/wavelog/README.md (100%) rename {home => old}/cluster/wavelog/deploy.sh (100%) rename {home => old}/cluster/wavelog/mariadb-deployment.yaml (100%) rename {home => old}/cluster/wavelog/mariadb-secret.yaml (100%) rename {home => old}/cluster/wavelog/namespace.yaml (100%) rename {home => old}/cluster/wavelog/wavelog-config-job.yaml (100%) rename {home => old}/cluster/wavelog/wavelog-deployment.yaml (100%) rename {home => old}/cluster/wavelog/wavelog-ingress.yaml (100%) rename {home => old}/cluster/wavelog/wavelog-ingressroute.yaml (100%) rename {home => old}/cluster/wavelog/wavelog-pvc.yaml (100%) rename {home => old}/cluster/wavelog/wavelog-secret.yaml (100%) rename {home => old}/cluster/worker.yaml (100%) create mode 100644 talos/.gitignore create mode 100644 talos/CLUSTER_CONFIG.md create mode 100755 talos/apply-configs.sh create mode 100755 talos/apply-worker-configs.sh create mode 100644 talos/cert-manager/letsencrypt-clusterissuer.yaml create mode 100644 talos/cluster-config.yaml create mode 100644 talos/controlplane.yaml create mode 100644 talos/current-config.yaml create mode 100755 talos/deploy-cluster-services.sh create mode 100755 talos/generate-node-configs.sh create mode 100644 talos/kubeconfig create mode 100644 talos/metallb/ipaddresspool-internal.yaml create mode 100644 talos/nodes/cp-1.yaml create mode 100644 talos/nodes/cp-2.yaml create mode 100644 talos/nodes/cp-3.yaml create mode 100644 talos/nodes/worker-1.yaml create mode 100644 talos/nodes/worker-2.yaml create mode 100644 talos/nodes/worker-3.yaml create mode 100644 talos/patches/cloud-provider.yaml create mode 100644 talos/patches/cp-1.yaml create mode 100644 talos/patches/cp-2.yaml create mode 100644 talos/patches/cp-3.yaml create mode 100644 talos/patches/remove-controlplane-secrets.yaml create mode 100644 talos/patches/system-extensions.yaml create mode 100644 talos/patches/tailscale-config.yaml create mode 100644 talos/patches/tailscale-extension-config.yaml create mode 100644 talos/patches/worker-1.yaml create mode 100644 talos/patches/worker-2.yaml create mode 100644 talos/patches/worker-3.yaml create mode 100644 talos/patches/worker-type.yaml create mode 100755 talos/provision-workers.sh create mode 100644 talos/proxmox-ccm/config.yaml create mode 100644 talos/proxmox-ccm/secret.yaml create mode 100644 talos/proxmox-csi/namespace.yaml create mode 100644 talos/proxmox-csi/node-providerid-patches.yaml create mode 100644 talos/proxmox-csi/secret.yaml create mode 100644 talos/proxmox-csi/storageclass.yaml create mode 100644 talos/proxmox-csi/values.yaml create mode 100755 talos/reset-vms.sh create mode 100644 talos/schematic.yaml create mode 100755 talos/setup-proxmox-csi.sh create mode 100644 talos/update-proxmox-csi-permissions.sh create mode 100644 talos/worker-base.yaml create mode 100644 talos/worker-base.yaml.backup create mode 100644 talos/worker.yaml delete mode 100644 terraform/dns_aprs.tf delete mode 100644 terraform/dns_manero.tf delete mode 100644 terraform/dns_mcintire.tf delete mode 100644 terraform/dns_ntxarms.tf delete mode 100644 terraform/dns_powerdns_zones.tf delete mode 100644 terraform/dns_reverse.tf delete mode 100644 terraform/dns_towerops.tf delete mode 100644 terraform/dns_vntx_net.tf delete mode 100644 terraform/dns_vntx_org.tf delete mode 100644 terraform/dns_w5isp.tf delete mode 100644 terraform/tfplan diff --git a/ansible/group_vars/all/all.yml b/ansible/group_vars/all/all.yml index d762a59..a73836f 100644 --- a/ansible/group_vars/all/all.yml +++ b/ansible/group_vars/all/all.yml @@ -38,6 +38,9 @@ managed_users: base: ntp: server: 0.us.pool.ntp.org + monitoring: + cert_dir: /var/lib/icinga2/certs + server: monitor.vntx.net # SSH service name (varies by distribution) ssh_service: "{{ 'ssh' if ansible_os_family == 'Debian' else 'sshd' }}" diff --git a/ansible/group_vars/bind9_servers/mcintire.me.yml b/ansible/group_vars/bind9_servers/mcintire.me.yml index 63d0c98..d34542d 100644 --- a/ansible/group_vars/bind9_servers/mcintire.me.yml +++ b/ansible/group_vars/bind9_servers/mcintire.me.yml @@ -14,7 +14,7 @@ mcintire_me_zone: preference: 20 hosts: - name: mail - ip: 204.110.191.5 + ip: 107.174.178.20 - name: photos ip: 204.110.191.8 other_name_servers: @@ -23,7 +23,7 @@ mcintire_me_zone: - _autodiscover._tcp.mcintire.me. IN SRV 0 0 443 mail.w5isp.com. text: - name: '@' - text: '"v=spf1 mx a ip4:204.110.191.5 ~all"' + text: '"v=spf1 mx a ip4:107.174.178.20 ~all"' - name: _dmarc text: '"v=DMARC1; p=quarantine; rua=mailto:postmaster@mcintire.me; ruf=mailto:postmaster@mcintire.me; fo=1"' - name: dkim._domainkey diff --git a/ansible/group_vars/bind9_servers/reverse_191.yml b/ansible/group_vars/bind9_servers/reverse_191.yml index 2c69efc..99864db 100644 --- a/ansible/group_vars/bind9_servers/reverse_191.yml +++ b/ansible/group_vars/bind9_servers/reverse_191.yml @@ -1,7 +1,6 @@ --- # 191.110.204.in-addr.arpa reverse DNS zone # Mapping 204.110.191.0-255 -> *.191.client.vntx.net -# Exception: 204.110.191.5 -> mail.mcintire.me reverse_191_zone: name: 191.110.204.in-addr.arpa type: master @@ -15,7 +14,7 @@ reverse_191_zone: - 2.191.110.204.in-addr.arpa. IN PTR 2.191.client.vntx.net. - 3.191.110.204.in-addr.arpa. IN PTR 3.191.client.vntx.net. - 4.191.110.204.in-addr.arpa. IN PTR 4.191.client.vntx.net. - - 5.191.110.204.in-addr.arpa. IN PTR mail.mcintire.me. + - 5.191.110.204.in-addr.arpa. IN PTR 5.191.client.vntx.net. - 6.191.110.204.in-addr.arpa. IN PTR 6.191.client.vntx.net. - 7.191.110.204.in-addr.arpa. IN PTR 7.191.client.vntx.net. - 8.191.110.204.in-addr.arpa. IN PTR 8.191.client.vntx.net. diff --git a/ansible/group_vars/bind9_servers/towerops.net.yml b/ansible/group_vars/bind9_servers/towerops.net.yml index 78a0055..649483a 100644 --- a/ansible/group_vars/bind9_servers/towerops.net.yml +++ b/ansible/group_vars/bind9_servers/towerops.net.yml @@ -7,13 +7,31 @@ towerops_net_zone: name_servers: - ns1.as393837.net. - ns-global.kjsl.com. + mail_servers: + - name: mail.mcintire.me. + preference: 10 + - name: mail.nsnw.ca. + preference: 20 hosts: - name: '@' ip: 204.110.191.195 other_name_servers: + - autodiscover.towerops.net. IN CNAME mail.mcintire.me. + - autoconfig.towerops.net. IN CNAME mail.mcintire.me. + - _autodiscover._tcp.towerops.net. IN SRV 0 0 443 mail.mcintire.me. + - 4uwsaywjpmk35j36pfiz4vr37dyy4v7z._domainkey.towerops.net. IN CNAME 4uwsaywjpmk35j36pfiz4vr37dyy4v7z.dkim.amazonses.com. + - l7lbifvot6nv3wwho5rs35xzqzzinz5f._domainkey.towerops.net. IN CNAME l7lbifvot6nv3wwho5rs35xzqzzinz5f.dkim.amazonses.com. + - 2skkb53ep3vfbkdstfmm2elfthurggid._domainkey.towerops.net. IN CNAME 2skkb53ep3vfbkdstfmm2elfthurggid.dkim.amazonses.com. + - mail.towerops.net. IN MX 10 feedback-smtp.us-east-1.amazonses.com. - em6505.towerops.net. IN CNAME u177982.wl233.sendgrid.net. - s1._domainkey.towerops.net. IN CNAME s1.domainkey.u177982.wl233.sendgrid.net. - s2._domainkey.towerops.net. IN CNAME s2.domainkey.u177982.wl233.sendgrid.net. text: + - name: '@' + text: '"v=spf1 mx a ip4:204.110.191.5 ~all"' + - name: mail + text: '"v=spf1 include:amazonses.com ~all"' - name: _dmarc text: '"v=DMARC1; p=none;"' + - name: dkim._domainkey + text: '"v=DKIM1;k=rsa;t=s;s=email;p=MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAuFm6nd0L7/nAO4m0MPxdjwRAup5C90DPSPa0TQBDT8S2WvASyQUPV8xSbICGMj6FjZYNd5ph/0VK47gDulxQgNQT96IVf2ooTfkvY/80bAyEdtJbpjEUzQnX5YBi/pJigQx2EeCdaojUZumeIdlFlzeb8QQIEtQhVnyc1Xc/Z8ljPMW1H9DXLSDINjV6UTaXX+PZ7jgpRKgU+RnJNcqTAkhhKQ4bMcRfOam/lF6wPOWte1A7ir08TdE8O67ioqygkr/ivAp7xvV4vGOkY6buLLE+c3exY+my2qTCZgJyUMAhkZzYqzGo1csfHH8x+O2XN/k8Z5jPhq8LSvl9XkllKwIDAQAB"' diff --git a/ansible/host_vars/dokku.w5isp.com.yml b/ansible/host_vars/dokku.w5isp.com.yml new file mode 100644 index 0000000..dedd960 --- /dev/null +++ b/ansible/host_vars/dokku.w5isp.com.yml @@ -0,0 +1,6 @@ +--- +ansible_user: ansible +ansible_host: 204.110.191.218 +ansible_python_interpreter: /usr/bin/python3 +ansible_ssh_private_key_file: /Users/graham/.ssh/ansible +ansible_ssh_common_args: '-o StrictHostKeyChecking=accept-new' diff --git a/ansible/host_vars/monitor.vntx.net.yml b/ansible/host_vars/monitor.vntx.net.yml new file mode 100644 index 0000000..6cc66eb --- /dev/null +++ b/ansible/host_vars/monitor.vntx.net.yml @@ -0,0 +1,6 @@ +--- +ansible_user: graham +ansible_host: 204.110.191.241 +ansible_python_interpreter: /usr/bin/python3 +ansible_ssh_private_key_file: /Users/graham/.ssh/id_ed25519 +ansible_ssh_common_args: '-o StrictHostKeyChecking=accept-new' diff --git a/ansible/host_vars/netbox.vntx.net.yml b/ansible/host_vars/netbox.vntx.net.yml index 6c7f3af..d91a10e 100644 --- a/ansible/host_vars/netbox.vntx.net.yml +++ b/ansible/host_vars/netbox.vntx.net.yml @@ -1,8 +1,12 @@ --- # Host-specific configuration for netbox.vntx.net -# Python interpreter +# Ansible connection settings +ansible_user: graham +ansible_host: 204.110.191.243 ansible_python_interpreter: /usr/bin/python3 +ansible_ssh_private_key_file: /Users/graham/.ssh/id_ed25519 +ansible_ssh_common_args: '-o StrictHostKeyChecking=accept-new' # Override defaults for NetBox installation netbox_port: 8001 diff --git a/ansible/host_vars/radius.vntx.net.yml b/ansible/host_vars/radius.vntx.net.yml new file mode 100644 index 0000000..fdf83b7 --- /dev/null +++ b/ansible/host_vars/radius.vntx.net.yml @@ -0,0 +1,6 @@ +--- +ansible_user: graham +ansible_host: 204.110.191.248 +ansible_python_interpreter: /usr/bin/python3 +ansible_ssh_private_key_file: /Users/graham/.ssh/id_ed25519 +ansible_ssh_common_args: '-o StrictHostKeyChecking=accept-new' diff --git a/ansible/host_vars/skippy.w5isp.com.yml b/ansible/host_vars/skippy.w5isp.com.yml new file mode 100644 index 0000000..080b481 --- /dev/null +++ b/ansible/host_vars/skippy.w5isp.com.yml @@ -0,0 +1,6 @@ +--- +ansible_user: ansible +ansible_host: 204.110.191.8 +ansible_python_interpreter: /usr/bin/python3 +ansible_ssh_private_key_file: /Users/graham/.ssh/ansible +ansible_ssh_common_args: '-o StrictHostKeyChecking=accept-new' diff --git a/ansible/host_vars/unimus.vntx.net.yml b/ansible/host_vars/unimus.vntx.net.yml new file mode 100644 index 0000000..960f7eb --- /dev/null +++ b/ansible/host_vars/unimus.vntx.net.yml @@ -0,0 +1,6 @@ +--- +ansible_user: ansible +ansible_host: 204.110.191.238 +ansible_python_interpreter: /usr/bin/python3 +ansible_ssh_private_key_file: /Users/graham/.ssh/ansible +ansible_ssh_common_args: '-o StrictHostKeyChecking=accept-new' diff --git a/ansible/host_vars/vpn.vntx.net.yml b/ansible/host_vars/vpn.vntx.net.yml new file mode 100644 index 0000000..3218bfb --- /dev/null +++ b/ansible/host_vars/vpn.vntx.net.yml @@ -0,0 +1,6 @@ +--- +ansible_user: ansible +ansible_host: 204.110.191.247 +ansible_python_interpreter: /usr/bin/python3 +ansible_ssh_private_key_file: /Users/graham/.ssh/ansible +ansible_ssh_common_args: '-o StrictHostKeyChecking=accept-new' diff --git a/ansible/hosts b/ansible/hosts index faeeb70..488d248 100755 --- a/ansible/hosts +++ b/ansible/hosts @@ -2,7 +2,6 @@ #logs.vntx.net radius.vntx.net vpn.vntx.net -librenms.vntx.net netbox.vntx.net #ntp.vntx.net unimus.vntx.net @@ -12,7 +11,7 @@ monitor.vntx.net [home_servers] skippy.w5isp.com -mail.mcintire.me ansible_host=204.110.191.5 +mail.mcintire.me ansible_host=107.174.178.20 dokku.w5isp.com camper diff --git a/ansible/playbook.yml b/ansible/playbook.yml index d97461a..6ac5209 100755 --- a/ansible/playbook.yml +++ b/ansible/playbook.yml @@ -15,91 +15,95 @@ community.general.timezone: name: "{{ timezone }}" -- name: Apply resolver config - hosts: resolvers - gather_facts: true - roles: - - { role: resolvers, become: true } +# Resolver play disabled - no hosts in resolvers group +#- name: Apply resolver config +# hosts: resolvers +# gather_facts: true +# roles: +# - { role: resolvers, become: true } -- name: Apply ns config - hosts: ns - gather_facts: true - become: true - roles: - - role: ns +# NS play disabled - replaced by BIND9 play below +#- name: Apply ns config +# hosts: ns +# gather_facts: true +# become: true +# roles: +# - role: ns -- name: Apply netbox config - hosts: netbox - gather_facts: true - become: true - roles: - - role: caddy_ansible.caddy_ansible - caddy_systemd_network_dependency: true - caddy_setcap: true - caddy_systemd_capabilities_enabled: true - caddy_systemd_capabilities: "CAP_NET_BIND_SERVICE" - caddy_config: | - {{ netbox.domain }} { - bind {{ netbox.bind_address }} - log { - level error - } - route /static* { - uri strip_prefix /static - root * /opt/netbox/netbox/static - file_server - } - @notStatic not path /static* - encode gzip zstd - reverse_proxy @notStatic http://localhost:{{ netbox.port }} { - header_up Host {http.request.host} - header_up X-Real-IP {http.request.remote.host} - header_up X-Forwarded-For {http.request.remote.host} - header_up X-Forwarded-Port {http.request.port} - header_up X-Forwarded-Proto {http.request.scheme} - } - } +# NetBox plays disabled - no hosts in netbox group +#- name: Apply netbox config +# hosts: netbox +# gather_facts: true +# become: true +# roles: +# - role: caddy_ansible.caddy_ansible +# caddy_systemd_network_dependency: true +# caddy_setcap: true +# caddy_systemd_capabilities_enabled: true +# caddy_systemd_capabilities: "CAP_NET_BIND_SERVICE" +# caddy_config: | +# {{ netbox.domain }} { +# bind {{ netbox.bind_address }} +# log { +# level error +# } +# route /static* { +# uri strip_prefix /static +# root * /opt/netbox/netbox/static +# file_server +# } +# @notStatic not path /static* +# encode gzip zstd +# reverse_proxy @notStatic http://localhost:{{ netbox.port }} { +# header_up Host {http.request.host} +# header_up X-Real-IP {http.request.remote.host} +# header_up X-Forwarded-For {http.request.remote.host} +# header_up X-Forwarded-Port {http.request.port} +# header_up X-Forwarded-Proto {http.request.scheme} +# } +# } +# +#- name: Apply firewall rules to netbox +# hosts: netbox +# become: true +# # remote_user: graham +# handlers: +# - import_tasks: playbook_handlers.yml +# +# tasks: +# - name: Permit traffic in default zone for http service +# ansible.posix.firewalld: +# zone: public +# service: http +# permanent: true +# state: enabled +# +# - name: Permit traffic in default zone for https service +# ansible.posix.firewalld: +# zone: public +# service: https +# permanent: true +# state: enabled +# notify: +# - Restart firewalld -- name: Apply firewall rules to netbox - hosts: netbox - become: true - # remote_user: graham - handlers: - - import_tasks: playbook_handlers.yml - - tasks: - - name: Permit traffic in default zone for http service - ansible.posix.firewalld: - zone: public - service: http - permanent: true - state: enabled - - - name: Permit traffic in default zone for https service - ansible.posix.firewalld: - zone: public - service: https - permanent: true - state: enabled - notify: - - Restart firewalld - -- name: Tailscale - hosts: tailscale_home - become: true - gather_facts: true - vars: - inject_facts_as_vars: false - roles: - - role: artis3n.tailscale - vars: - # Pull Tailscale auth key from environment variable - tailscale_authkey: "{{ lookup('ansible.builtin.env', 'TAILSCALE_KEY') }}" - tailscale_args: "--ssh --advertise-exit-node" - pre_tasks: - - name: Debug - Check Tailscale key (will be partially redacted) - debug: - msg: "Key exists and starts with: {{ lookup('ansible.builtin.env', 'TAILSCALE_KEY')[0:10] }}..." +# Tailscale play disabled - no hosts in tailscale_home group +#- name: Tailscale +# hosts: tailscale_home +# become: true +# gather_facts: true +# vars: +# inject_facts_as_vars: false +# roles: +# - role: artis3n.tailscale +# vars: +# # Pull Tailscale auth key from environment variable +# tailscale_authkey: "{{ lookup('ansible.builtin.env', 'TAILSCALE_KEY') }}" +# tailscale_args: "--ssh --advertise-exit-node" +# pre_tasks: +# - name: Debug - Check Tailscale key (will be partially redacted) +# debug: +# msg: "Key exists and starts with: {{ lookup('ansible.builtin.env', 'TAILSCALE_KEY')[0:10] }}..." - name: Install and configure Caddy hosts: caddy_servers @@ -152,6 +156,7 @@ - dns - bind9 - provision + - never vars: # Proxmox connection settings (matches terraform/variables.tf) proxmox_node: "{{ lookup('env', 'PROXMOX_NODE') | default('vm2-380', true) }}" @@ -274,10 +279,11 @@ tags: - general -- name: Syncthing servers - hosts: syncthing_servers - become: yes - become_method: sudo - tags: syncthing - roles: - - syncthing +# Syncthing play disabled - no hosts in syncthing_servers group +#- name: Syncthing servers +# hosts: syncthing_servers +# become: yes +# become_method: sudo +# tags: syncthing +# roles: +# - syncthing diff --git a/ansible/roles/base/defaults/main.yml b/ansible/roles/base/defaults/main.yml index b0b656d..875ce07 100644 --- a/ansible/roles/base/defaults/main.yml +++ b/ansible/roles/base/defaults/main.yml @@ -50,7 +50,6 @@ base_packages_by_distribution: - fzf - qemu-guest-agent - python3-apt - - btop Debian: - lsof - mosh @@ -63,11 +62,9 @@ base_packages_by_distribution: - pv - fzf - qemu-guest-agent - - btop AlmaLinux: - bind-utils - lsof - - btop - mosh - nano - net-tools diff --git a/ansible/roles/general/tasks/debian/icinga2.yml b/ansible/roles/general/tasks/debian/icinga2.yml index 320f16b..d4f0c23 100644 --- a/ansible/roles/general/tasks/debian/icinga2.yml +++ b/ansible/roles/general/tasks/debian/icinga2.yml @@ -35,13 +35,23 @@ tags: - icinga2_cert_dir +- name: Check if icinga2 CA certificate exists locally + stat: + path: "{{ playbook_dir }}/roles/general/files/var/lib/icinga2/certs/ca.crt" + delegate_to: localhost + become: false + register: icinga2_ca_cert_local + when: '"monitoring_servers" in group_names' + - name: install icinga2 CA certificate copy: src: var/lib/icinga2/certs/ca.crt dest: "{{ base.monitoring.cert_dir }}/ca.crt" owner: 'nagios' group: 'nagios' - when: '"monitoring_servers" in group_names' + when: + - '"monitoring_servers" in group_names' + - icinga2_ca_cert_local.stat.exists | default(false) - name: check for trusted master certificate stat: diff --git a/home/cluster/add-node3-to-etcd.sh b/old/cluster/add-node3-to-etcd.sh similarity index 100% rename from home/cluster/add-node3-to-etcd.sh rename to old/cluster/add-node3-to-etcd.sh diff --git a/home/cluster/aprs/README.md b/old/cluster/aprs/README.md similarity index 100% rename from home/cluster/aprs/README.md rename to old/cluster/aprs/README.md diff --git a/home/cluster/aprs/aprs-configmap.yaml b/old/cluster/aprs/aprs-configmap.yaml similarity index 100% rename from home/cluster/aprs/aprs-configmap.yaml rename to old/cluster/aprs/aprs-configmap.yaml diff --git a/home/cluster/aprs/aprs-ingressroute.yaml b/old/cluster/aprs/aprs-ingressroute.yaml similarity index 100% rename from home/cluster/aprs/aprs-ingressroute.yaml rename to old/cluster/aprs/aprs-ingressroute.yaml diff --git a/home/cluster/aprs/aprs-rbac.yaml b/old/cluster/aprs/aprs-rbac.yaml similarity index 100% rename from home/cluster/aprs/aprs-rbac.yaml rename to old/cluster/aprs/aprs-rbac.yaml diff --git a/home/cluster/aprs/aprs-secret-secure.yaml b/old/cluster/aprs/aprs-secret-secure.yaml similarity index 100% rename from home/cluster/aprs/aprs-secret-secure.yaml rename to old/cluster/aprs/aprs-secret-secure.yaml diff --git a/home/cluster/aprs/aprs-statefulset-with-pullsecret.yaml b/old/cluster/aprs/aprs-statefulset-with-pullsecret.yaml similarity index 100% rename from home/cluster/aprs/aprs-statefulset-with-pullsecret.yaml rename to old/cluster/aprs/aprs-statefulset-with-pullsecret.yaml diff --git a/home/cluster/aprs/create-ghcr-secret.sh b/old/cluster/aprs/create-ghcr-secret.sh similarity index 100% rename from home/cluster/aprs/create-ghcr-secret.sh rename to old/cluster/aprs/create-ghcr-secret.sh diff --git a/home/cluster/aprs/create-image-pull-secret.sh b/old/cluster/aprs/create-image-pull-secret.sh similarity index 100% rename from home/cluster/aprs/create-image-pull-secret.sh rename to old/cluster/aprs/create-image-pull-secret.sh diff --git a/home/cluster/aprs/deploy.sh b/old/cluster/aprs/deploy.sh similarity index 100% rename from home/cluster/aprs/deploy.sh rename to old/cluster/aprs/deploy.sh diff --git a/home/cluster/aprs/install-postgis-manual.sh b/old/cluster/aprs/install-postgis-manual.sh similarity index 100% rename from home/cluster/aprs/install-postgis-manual.sh rename to old/cluster/aprs/install-postgis-manual.sh diff --git a/home/cluster/aprs/namespace.yaml b/old/cluster/aprs/namespace.yaml similarity index 100% rename from home/cluster/aprs/namespace.yaml rename to old/cluster/aprs/namespace.yaml diff --git a/home/cluster/aprs/postgres-deployment-normal.yaml b/old/cluster/aprs/postgres-deployment-normal.yaml similarity index 100% rename from home/cluster/aprs/postgres-deployment-normal.yaml rename to old/cluster/aprs/postgres-deployment-normal.yaml diff --git a/home/cluster/aprs/postgres-deployment-repair.yaml b/old/cluster/aprs/postgres-deployment-repair.yaml similarity index 100% rename from home/cluster/aprs/postgres-deployment-repair.yaml rename to old/cluster/aprs/postgres-deployment-repair.yaml diff --git a/home/cluster/aprs/postgres-deployment.yaml b/old/cluster/aprs/postgres-deployment.yaml similarity index 100% rename from home/cluster/aprs/postgres-deployment.yaml rename to old/cluster/aprs/postgres-deployment.yaml diff --git a/home/cluster/aprs/postgres-normal-mode.sh b/old/cluster/aprs/postgres-normal-mode.sh similarity index 100% rename from home/cluster/aprs/postgres-normal-mode.sh rename to old/cluster/aprs/postgres-normal-mode.sh diff --git a/home/cluster/aprs/postgres-repair-mode.sh b/old/cluster/aprs/postgres-repair-mode.sh similarity index 100% rename from home/cluster/aprs/postgres-repair-mode.sh rename to old/cluster/aprs/postgres-repair-mode.sh diff --git a/home/cluster/aprs/postgres-secret-secure.yaml b/old/cluster/aprs/postgres-secret-secure.yaml similarity index 100% rename from home/cluster/aprs/postgres-secret-secure.yaml rename to old/cluster/aprs/postgres-secret-secure.yaml diff --git a/home/cluster/aprs/setup-database.sh b/old/cluster/aprs/setup-database.sh similarity index 100% rename from home/cluster/aprs/setup-database.sh rename to old/cluster/aprs/setup-database.sh diff --git a/home/cluster/aprs/setup-postgres-aprs.sql b/old/cluster/aprs/setup-postgres-aprs.sql similarity index 100% rename from home/cluster/aprs/setup-postgres-aprs.sql rename to old/cluster/aprs/setup-postgres-aprs.sql diff --git a/home/cluster/cert-manager/letsencrypt-prod.yaml b/old/cluster/cert-manager/letsencrypt-prod.yaml similarity index 100% rename from home/cluster/cert-manager/letsencrypt-prod.yaml rename to old/cluster/cert-manager/letsencrypt-prod.yaml diff --git a/home/cluster/controlplane.yaml b/old/cluster/controlplane.yaml similarity index 100% rename from home/cluster/controlplane.yaml rename to old/cluster/controlplane.yaml diff --git a/home/cluster/deploy.md b/old/cluster/deploy.md similarity index 100% rename from home/cluster/deploy.md rename to old/cluster/deploy.md diff --git a/home/cluster/k3s-upgrade/plan.yaml b/old/cluster/k3s-upgrade/plan.yaml similarity index 100% rename from home/cluster/k3s-upgrade/plan.yaml rename to old/cluster/k3s-upgrade/plan.yaml diff --git a/home/cluster/longhorn-uservolume.yaml b/old/cluster/longhorn-uservolume.yaml similarity index 100% rename from home/cluster/longhorn-uservolume.yaml rename to old/cluster/longhorn-uservolume.yaml diff --git a/home/cluster/mariadb/mariadb-deployment.yaml b/old/cluster/mariadb/mariadb-deployment.yaml similarity index 100% rename from home/cluster/mariadb/mariadb-deployment.yaml rename to old/cluster/mariadb/mariadb-deployment.yaml diff --git a/home/cluster/metallb-config.yaml b/old/cluster/metallb-config.yaml similarity index 100% rename from home/cluster/metallb-config.yaml rename to old/cluster/metallb-config.yaml diff --git a/home/cluster/mikrotik-ha-setup.md b/old/cluster/mikrotik-ha-setup.md similarity index 100% rename from home/cluster/mikrotik-ha-setup.md rename to old/cluster/mikrotik-ha-setup.md diff --git a/home/cluster/n8n/deploy.sh b/old/cluster/n8n/deploy.sh similarity index 100% rename from home/cluster/n8n/deploy.sh rename to old/cluster/n8n/deploy.sh diff --git a/home/cluster/n8n/ingress.yaml b/old/cluster/n8n/ingress.yaml similarity index 100% rename from home/cluster/n8n/ingress.yaml rename to old/cluster/n8n/ingress.yaml diff --git a/home/cluster/n8n/n8n-deployment.yaml b/old/cluster/n8n/n8n-deployment.yaml similarity index 100% rename from home/cluster/n8n/n8n-deployment.yaml rename to old/cluster/n8n/n8n-deployment.yaml diff --git a/home/cluster/n8n/n8n-pvc.yaml b/old/cluster/n8n/n8n-pvc.yaml similarity index 100% rename from home/cluster/n8n/n8n-pvc.yaml rename to old/cluster/n8n/n8n-pvc.yaml diff --git a/home/cluster/n8n/namespace.yaml b/old/cluster/n8n/namespace.yaml similarity index 100% rename from home/cluster/n8n/namespace.yaml rename to old/cluster/n8n/namespace.yaml diff --git a/home/cluster/n8n/postgres-deployment.yaml b/old/cluster/n8n/postgres-deployment.yaml similarity index 100% rename from home/cluster/n8n/postgres-deployment.yaml rename to old/cluster/n8n/postgres-deployment.yaml diff --git a/home/cluster/n8n/postgres-pvc.yaml b/old/cluster/n8n/postgres-pvc.yaml similarity index 100% rename from home/cluster/n8n/postgres-pvc.yaml rename to old/cluster/n8n/postgres-pvc.yaml diff --git a/home/cluster/n8n/secret.yaml b/old/cluster/n8n/secret.yaml similarity index 100% rename from home/cluster/n8n/secret.yaml rename to old/cluster/n8n/secret.yaml diff --git a/home/cluster/node1.patch.yaml b/old/cluster/node1.patch.yaml similarity index 100% rename from home/cluster/node1.patch.yaml rename to old/cluster/node1.patch.yaml diff --git a/home/cluster/node2.patch.yaml b/old/cluster/node2.patch.yaml similarity index 100% rename from home/cluster/node2.patch.yaml rename to old/cluster/node2.patch.yaml diff --git a/home/cluster/node3.patch.yaml b/old/cluster/node3.patch.yaml similarity index 100% rename from home/cluster/node3.patch.yaml rename to old/cluster/node3.patch.yaml diff --git a/home/cluster/nodered/deploy.sh b/old/cluster/nodered/deploy.sh similarity index 100% rename from home/cluster/nodered/deploy.sh rename to old/cluster/nodered/deploy.sh diff --git a/home/cluster/nodered/deployment.yaml b/old/cluster/nodered/deployment.yaml similarity index 100% rename from home/cluster/nodered/deployment.yaml rename to old/cluster/nodered/deployment.yaml diff --git a/home/cluster/nodered/ingress.yaml b/old/cluster/nodered/ingress.yaml similarity index 100% rename from home/cluster/nodered/ingress.yaml rename to old/cluster/nodered/ingress.yaml diff --git a/home/cluster/nodered/namespace.yaml b/old/cluster/nodered/namespace.yaml similarity index 100% rename from home/cluster/nodered/namespace.yaml rename to old/cluster/nodered/namespace.yaml diff --git a/home/cluster/nodered/pvc.yaml b/old/cluster/nodered/pvc.yaml similarity index 100% rename from home/cluster/nodered/pvc.yaml rename to old/cluster/nodered/pvc.yaml diff --git a/home/cluster/nodered/service.yaml b/old/cluster/nodered/service.yaml similarity index 100% rename from home/cluster/nodered/service.yaml rename to old/cluster/nodered/service.yaml diff --git a/home/cluster/nodered/settings-configmap.yaml b/old/cluster/nodered/settings-configmap.yaml similarity index 100% rename from home/cluster/nodered/settings-configmap.yaml rename to old/cluster/nodered/settings-configmap.yaml diff --git a/home/cluster/schematic.yaml b/old/cluster/schematic.yaml similarity index 100% rename from home/cluster/schematic.yaml rename to old/cluster/schematic.yaml diff --git a/home/cluster/tailscale-operator-complete.yaml b/old/cluster/tailscale-operator-complete.yaml similarity index 100% rename from home/cluster/tailscale-operator-complete.yaml rename to old/cluster/tailscale-operator-complete.yaml diff --git a/home/cluster/tailscale.patch.yaml b/old/cluster/tailscale.patch.yaml similarity index 100% rename from home/cluster/tailscale.patch.yaml rename to old/cluster/tailscale.patch.yaml diff --git a/home/cluster/talosconfig b/old/cluster/talosconfig similarity index 100% rename from home/cluster/talosconfig rename to old/cluster/talosconfig diff --git a/home/cluster/wavelog/README.md b/old/cluster/wavelog/README.md similarity index 100% rename from home/cluster/wavelog/README.md rename to old/cluster/wavelog/README.md diff --git a/home/cluster/wavelog/deploy.sh b/old/cluster/wavelog/deploy.sh similarity index 100% rename from home/cluster/wavelog/deploy.sh rename to old/cluster/wavelog/deploy.sh diff --git a/home/cluster/wavelog/mariadb-deployment.yaml b/old/cluster/wavelog/mariadb-deployment.yaml similarity index 100% rename from home/cluster/wavelog/mariadb-deployment.yaml rename to old/cluster/wavelog/mariadb-deployment.yaml diff --git a/home/cluster/wavelog/mariadb-secret.yaml b/old/cluster/wavelog/mariadb-secret.yaml similarity index 100% rename from home/cluster/wavelog/mariadb-secret.yaml rename to old/cluster/wavelog/mariadb-secret.yaml diff --git a/home/cluster/wavelog/namespace.yaml b/old/cluster/wavelog/namespace.yaml similarity index 100% rename from home/cluster/wavelog/namespace.yaml rename to old/cluster/wavelog/namespace.yaml diff --git a/home/cluster/wavelog/wavelog-config-job.yaml b/old/cluster/wavelog/wavelog-config-job.yaml similarity index 100% rename from home/cluster/wavelog/wavelog-config-job.yaml rename to old/cluster/wavelog/wavelog-config-job.yaml diff --git a/home/cluster/wavelog/wavelog-deployment.yaml b/old/cluster/wavelog/wavelog-deployment.yaml similarity index 100% rename from home/cluster/wavelog/wavelog-deployment.yaml rename to old/cluster/wavelog/wavelog-deployment.yaml diff --git a/home/cluster/wavelog/wavelog-ingress.yaml b/old/cluster/wavelog/wavelog-ingress.yaml similarity index 100% rename from home/cluster/wavelog/wavelog-ingress.yaml rename to old/cluster/wavelog/wavelog-ingress.yaml diff --git a/home/cluster/wavelog/wavelog-ingressroute.yaml b/old/cluster/wavelog/wavelog-ingressroute.yaml similarity index 100% rename from home/cluster/wavelog/wavelog-ingressroute.yaml rename to old/cluster/wavelog/wavelog-ingressroute.yaml diff --git a/home/cluster/wavelog/wavelog-pvc.yaml b/old/cluster/wavelog/wavelog-pvc.yaml similarity index 100% rename from home/cluster/wavelog/wavelog-pvc.yaml rename to old/cluster/wavelog/wavelog-pvc.yaml diff --git a/home/cluster/wavelog/wavelog-secret.yaml b/old/cluster/wavelog/wavelog-secret.yaml similarity index 100% rename from home/cluster/wavelog/wavelog-secret.yaml rename to old/cluster/wavelog/wavelog-secret.yaml diff --git a/home/cluster/worker.yaml b/old/cluster/worker.yaml similarity index 100% rename from home/cluster/worker.yaml rename to old/cluster/worker.yaml diff --git a/talos/.gitignore b/talos/.gitignore new file mode 100644 index 0000000..f6a6509 --- /dev/null +++ b/talos/.gitignore @@ -0,0 +1,7 @@ +# Talos secrets and sensitive files +secrets.yaml +talosconfig + +# Temporary files +*.tmp +*.bak diff --git a/talos/CLUSTER_CONFIG.md b/talos/CLUSTER_CONFIG.md new file mode 100644 index 0000000..756e482 --- /dev/null +++ b/talos/CLUSTER_CONFIG.md @@ -0,0 +1,114 @@ +# Talos Cluster Configuration Notes + +## Proxmox Environment + +- **Proxmox Cluster ID**: 380 +- **Proxmox Node Name**: vm2-380 +- **Proxmox API**: https://10.0.0.2:8006/api2/json + +## Network Configuration + +### Private Network (Cluster Internal) +- **Network**: 10.0.0.0/24 +- **Control Plane Nodes**: + - cp-1: 10.0.0.101 (DHCP) + - cp-2: 10.0.0.102 (DHCP) + - cp-3: 10.0.0.103 (DHCP) +- **Interface**: eth0 (net0 in Proxmox, no VLAN tag) +- **Usage**: Kubernetes API, etcd, internal pod communication + +### Public Network (External Services) +- **Network**: 204.110.191.192/26 +- **Gateway**: 204.110.191.254 +- **Node IPs**: + - cp-1: 204.110.191.193/26 (static) + - cp-2: 204.110.191.194/26 (static) + - cp-3: 204.110.191.195/26 (static) +- **Interface**: eth1 (net1 in Proxmox, VLAN tag 9) +- **Usage**: MetalLB LoadBalancer services, external access + +### MetalLB IP Pool +- **Range**: 204.110.191.193-215 +- **Interface**: eth1 +- **Mode**: L2 Advertisement +- **IMPORTANT**: LoadBalancer services must use `externalTrafficPolicy: Cluster` (not `Local`) to avoid routing issues with L2 mode + +## Required Node Labels + +All nodes must have the following labels for proper CSI and scheduling: + +```bash +# Topology labels for Proxmox CSI +topology.kubernetes.io/region=380 +topology.kubernetes.io/zone=vm2-380 + +# Platform label for CSI DaemonSet +node.cloudprovider.kubernetes.io/platform=nocloud +``` + +## Proxmox VM IDs + +Map Kubernetes nodes to Proxmox VM IDs for CSI provider IDs: + +- talos-if6-e42: VM 203 → `proxmox://380/203` +- talos-sbl-bvx: VM 202 → `proxmox://380/202` +- talos-xgb-7n7: VM 201 → `proxmox://380/201` + +**Note**: These mappings may change when VMs are recreated. Update `proxmox-csi/node-providerid-patches.yaml` accordingly. + +## Storage Configuration + +- **StorageClass**: proxmox-local-lvm +- **Backend**: Proxmox local-lvm storage +- **Filesystem**: ext4 +- **Binding Mode**: WaitForFirstConsumer +- **Allowed Topology**: region=380 + +## Service Deployment Order + +1. **MetalLB** - LoadBalancer capability for public IPs +2. **NFS Provisioner** - Persistent storage via NFS (10.0.0.253:/mnt/k8s/cluster) +3. **Tailscale Operator** - Private network access to services +4. **DNS Services** - PowerDNS with external PostgreSQL +5. **Other services** - As needed + +## External Dependencies + +### PostgreSQL Database +- **Host**: 10.0.0.252 +- **Database**: powerdns +- **User**: powerdns +- **Running on**: Proxmox (outside Kubernetes) +- **Credentials**: Stored in 1Password (item: t3nqhjmeci6msx4qouu64yfr3q) +- **PowerDNS Version**: 4.8 (uses `Primary`/`Secondary` instead of `Master`/`Slave`) +- **Zone Type**: All zones must be type `Primary` to support AXFR zone transfers +- **AXFR Settings**: + - `allow-axfr-ips=204.87.183.53` - Allow zone transfers from secondary + - `also-notify=204.87.183.53` - Send notifications on zone updates + +### NFS Storage +- **Server**: 10.0.0.253 +- **Export**: /mnt/k8s/cluster +- **Provider**: TrueNAS +- **Configuration**: Maproot user/group set to root + +### Tailscale +- **OAuth Credentials**: Stored in 1Password (item: almzem6nffphe3xv4pgxpkbaga) +- **Namespace**: tailscale +- **PodSecurity**: Must be set to 'privileged' for proxy pods to run + +## Bootstrap Checklist + +After recreating cluster: + +- [ ] Apply node configs via talosctl +- [ ] Bootstrap cluster: `talosctl -n 10.0.0.101 bootstrap` +- [ ] Get kubeconfig: `talosctl kubeconfig --force` +- [ ] Remove control-plane taint: `kubectl taint nodes --all node-role.kubernetes.io/control-plane:NoSchedule-` +- [ ] Deploy MetalLB for public LoadBalancer IPs +- [ ] Deploy NFS provisioner (10.0.0.253:/mnt/k8s/cluster) +- [ ] Deploy Tailscale operator: + - [ ] Set tailscale namespace to privileged PodSecurity + - [ ] Install operator with OAuth credentials from 1Password +- [ ] Verify external PostgreSQL is running (10.0.0.252) +- [ ] Deploy DNS services (PowerDNS) diff --git a/talos/apply-configs.sh b/talos/apply-configs.sh new file mode 100755 index 0000000..e0308d6 --- /dev/null +++ b/talos/apply-configs.sh @@ -0,0 +1,28 @@ +#!/bin/bash +set -e + +cd "$(dirname "$0")" + +echo "Applying configs to nodes..." + +echo " Applying config to talos-cp-1 (10.0.0.101)" +talosctl apply-config --insecure --nodes 10.0.0.101 --file nodes/cp-1.yaml --mode=auto + +echo " Applying config to talos-cp-2 (10.0.0.102)" +talosctl apply-config --insecure --nodes 10.0.0.102 --file nodes/cp-2.yaml --mode=auto + +echo " Applying config to talos-cp-3 (10.0.0.103)" +talosctl apply-config --insecure --nodes 10.0.0.103 --file nodes/cp-3.yaml --mode=auto + +echo "" +echo "Configs applied! Nodes will reboot and configure themselves." +echo "Wait about 2-3 minutes, then run:" +echo "" +echo " # Merge talosconfig" +echo " talosctl config merge talosconfig" +echo "" +echo " # Bootstrap the cluster (only run once!)" +echo " talosctl bootstrap --nodes 10.0.0.101" +echo "" +echo " # Check cluster health" +echo " talosctl health --nodes 10.0.0.101,10.0.0.102,10.0.0.103" diff --git a/talos/apply-worker-configs.sh b/talos/apply-worker-configs.sh new file mode 100755 index 0000000..abd97c9 --- /dev/null +++ b/talos/apply-worker-configs.sh @@ -0,0 +1,53 @@ +#!/bin/bash +set -e + +cd "$(dirname "$0")" + +WORKER_IPS=(10.0.0.104 10.0.0.105 10.0.0.106) +WORKER_NAMES=(worker-1 worker-2 worker-3) + +echo "=== Applying Talos Worker Node Configurations ===" +echo "" + +# Apply worker configs +for i in "${!WORKER_IPS[@]}"; do + IP=${WORKER_IPS[$i]} + NAME=${WORKER_NAMES[$i]} + + echo "Applying config to $NAME ($IP)..." + talosctl apply-config \ + --nodes $IP \ + --file nodes/$NAME.yaml \ + --insecure + + echo " ✓ Applied to $NAME" + echo "" +done + +echo "=== Worker nodes configured! ===" +echo "" +echo "The worker nodes will now join the cluster." +echo "Waiting for nodes to appear in cluster..." +sleep 15 + +# Get the worker node names (they're auto-generated) +WORKER_NODES=$(kubectl get nodes -o jsonpath='{range .items[*]}{.metadata.name}{"\n"}{end}' | grep -v -f <(kubectl get nodes -l node-role.kubernetes.io/control-plane -o jsonpath='{range .items[*]}{.metadata.name}{"\n"}{end}') 2>/dev/null || true) + +if [ -n "$WORKER_NODES" ]; then + echo "Found worker nodes, applying labels..." + for node in $WORKER_NODES; do + echo " Labeling $node..." + kubectl label node $node \ + topology.kubernetes.io/region=380 \ + topology.kubernetes.io/zone=vm2-380 \ + node.cloudprovider.kubernetes.io/platform=nocloud \ + node-role.kubernetes.io/worker= \ + --overwrite + done + echo "" + echo "Worker nodes labeled successfully!" + kubectl get nodes +else + echo "No worker nodes found yet. Label them manually with:" + echo " kubectl label node topology.kubernetes.io/region=380 topology.kubernetes.io/zone=vm2-380 node.cloudprovider.kubernetes.io/platform=nocloud node-role.kubernetes.io/worker=" +fi diff --git a/talos/cert-manager/letsencrypt-clusterissuer.yaml b/talos/cert-manager/letsencrypt-clusterissuer.yaml new file mode 100644 index 0000000..e119353 --- /dev/null +++ b/talos/cert-manager/letsencrypt-clusterissuer.yaml @@ -0,0 +1,35 @@ +apiVersion: cert-manager.io/v1 +kind: ClusterIssuer +metadata: + name: letsencrypt-prod +spec: + acme: + # Production Let's Encrypt server + server: https://acme-v02.api.letsencrypt.org/directory + email: graham@mcintire.me + privateKeySecretRef: + name: letsencrypt-prod + solvers: + # HTTP-01 solver with standalone pod + # cert-manager will create temporary pods to respond to challenges + - http01: + ingress: + ingressClassName: traefik +--- +apiVersion: cert-manager.io/v1 +kind: ClusterIssuer +metadata: + name: letsencrypt-staging +spec: + acme: + # Staging Let's Encrypt server (for testing, has higher rate limits) + server: https://acme-staging-v02.api.letsencrypt.org/directory + email: graham@mcintire.me + privateKeySecretRef: + name: letsencrypt-staging + solvers: + # HTTP-01 solver with standalone pod + # cert-manager will create temporary pods to respond to challenges + - http01: + ingress: + ingressClassName: traefik diff --git a/talos/cluster-config.yaml b/talos/cluster-config.yaml new file mode 100644 index 0000000..e69de29 diff --git a/talos/controlplane.yaml b/talos/controlplane.yaml new file mode 100644 index 0000000..6060c52 --- /dev/null +++ b/talos/controlplane.yaml @@ -0,0 +1,403 @@ +version: v1alpha1 # Indicates the schema used to decode the contents. +debug: false # Enable verbose logging to the console. +persist: true +# Provides machine specific configuration options. +machine: + type: controlplane # Defines the role of the machine within the cluster. + token: gwdkoe.5gbblli1cvxv1axx # The `token` is used by a machine to join the PKI of the cluster. + # The root certificate authority of the PKI. + ca: + crt: LS0tLS1CRUdJTiBDRVJUSUZJQ0FURS0tLS0tCk1JSUJQekNCOHFBREFnRUNBaEVBbk5ucllpRDF4bjZaaGVFY0hvTFZ5ekFGQmdNclpYQXdFREVPTUF3R0ExVUUKQ2hNRmRHRnNiM013SGhjTk1qVXhNakkzTWpNeU5UVTNXaGNOTXpVeE1qSTFNak15TlRVM1dqQVFNUTR3REFZRApWUVFLRXdWMFlXeHZjekFxTUFVR0F5dGxjQU1oQVBLMlRCTm5nWlhkRHRDQjBQRXprV0JxNW4zUk0zN0w3c1N1CkVrMGkveGRYbzJFd1h6QU9CZ05WSFE4QkFmOEVCQU1DQW9Rd0hRWURWUjBsQkJZd0ZBWUlLd1lCQlFVSEF3RUcKQ0NzR0FRVUZCd01DTUE4R0ExVWRFd0VCL3dRRk1BTUJBZjh3SFFZRFZSME9CQllFRkxFS0lGTWRTR09pZ09LaQozd3kzR0tWMGp2RDVNQVVHQXl0bGNBTkJBSmlXMEJqNGlaUHpwY2ZWWkhKWXk3dXphOWovOTBIZFJJcHpkdkwzCnc4U1RBcWs2emh0bFoyMVhEWlY1Y05vTWZpc0o0eC8zMzg1MXB6WTN6NHZBYVFvPQotLS0tLUVORCBDRVJUSUZJQ0FURS0tLS0tCg== + key: LS0tLS1CRUdJTiBFRDI1NTE5IFBSSVZBVEUgS0VZLS0tLS0KTUM0Q0FRQXdCUVlESzJWd0JDSUVJT0xneGYyN041VXhnUStER3NoZU04dThzdnlCbE8vUmRMYUpETEFHOEF3TAotLS0tLUVORCBFRDI1NTE5IFBSSVZBVEUgS0VZLS0tLS0K + # Extra certificate subject alternative names for the machine's certificate. + certSANs: [] + # # Uncomment this to enable SANs. + # - 10.0.0.10 + # - 172.16.0.10 + # - 192.168.0.10 + + # Used to provide additional options to the kubelet. + kubelet: + image: ghcr.io/siderolabs/kubelet:v1.35.0 # The `image` field is an optional reference to an alternative kubelet image. + # The `extraMounts` field is used to add additional mounts to the kubelet container. + extraMounts: + - destination: /var/lib/kubelet/plugins # Destination is the absolute path where the mount will be placed in the container. + type: bind # Type specifies the mount kind. + source: /var/lib/kubelet/plugins # Source specifies the source path of the mount. + # Options are fstab style mount options. + options: + - bind + - rshared + - rw + defaultRuntimeSeccompProfileEnabled: true # Enable container runtime default Seccomp profile. + disableManifestsDirectory: true # The `disableManifestsDirectory` field configures the kubelet to get static pod manifests from the /etc/kubernetes/manifests directory. + + # # The `ClusterDNS` field is an optional reference to an alternative kubelet clusterDNS ip list. + # clusterDNS: + # - 10.96.0.10 + # - 169.254.2.53 + + # # The `extraArgs` field is used to provide additional flags to the kubelet. + # extraArgs: + # key: value + + # # The `extraConfig` field is used to provide kubelet configuration overrides. + # extraConfig: + # serverTLSBootstrap: true + + # # The `KubeletCredentialProviderConfig` field is used to provide kubelet credential configuration. + # credentialProviderConfig: + # apiVersion: kubelet.config.k8s.io/v1 + # kind: CredentialProviderConfig + # providers: + # - apiVersion: credentialprovider.kubelet.k8s.io/v1 + # defaultCacheDuration: 12h + # matchImages: + # - '*.dkr.ecr.*.amazonaws.com' + # - '*.dkr.ecr.*.amazonaws.com.cn' + # - '*.dkr.ecr-fips.*.amazonaws.com' + # - '*.dkr.ecr.us-iso-east-1.c2s.ic.gov' + # - '*.dkr.ecr.us-isob-east-1.sc2s.sgov.gov' + # name: ecr-credential-provider + + # # The `nodeIP` field is used to configure `--node-ip` flag for the kubelet. + # nodeIP: + # # The `validSubnets` field configures the networks to pick kubelet node IP from. + # validSubnets: + # - 10.0.0.0/8 + # - '!10.0.0.3/32' + # - fdc7::/16 + # Provides machine specific network configuration options. + network: {} + # # Configures KubeSpan feature. + # kubespan: + # enabled: true # Enable the KubeSpan feature. + + # Used to provide instructions for installations. + install: + disk: /dev/sda # The disk used for installations. + image: factory.talos.dev/installer/959b38c028569ff2f710c3cfcb3f90d4015282b278f020bb58cf1bda1f9ef93a:v1.12.0 # Allows for supplying the image used to perform the installation. + wipe: false # Indicates if the installation disk should be wiped at installation time. + grubUseUKICmdline: true # Indicates if legacy GRUB bootloader should use kernel cmdline from the UKI instead of building it on the host. + + # # Look up disk using disk attributes like model, size, serial and others. + # diskSelector: + # size: 4GB # Disk size. + # model: WDC* # Disk model `/sys/block//device/model`. + # busPath: /pci0000:00/0000:00:17.0/ata1/host0/target0:0:0/0:0:0:0 # Disk bus path. + # Allows the addition of user specified files. + files: + - content: tskey-auth-k6cryUGtC521CNTRL-vnjxfuqSqs2Es4kX2SG1s2p3btRizMiG # The contents of the file. + permissions: 0o600 # The file's permissions in octal. + path: /var/etc/tailscale/auth.key # The path of the file. + op: create # The operation to use + - content: 10.0.0.0/24 # The contents of the file. + permissions: 0o600 # The file's permissions in octal. + path: /var/etc/tailscale/routes # The path of the file. + op: create # The operation to use + - content: --accept-routes --advertise-tags=tag:k8s-cp # The contents of the file. + permissions: 0o600 # The file's permissions in octal. + path: /var/etc/tailscale/args # The path of the file. + op: create # The operation to use + # Features describe individual Talos features that can be switched on or off. + features: + diskQuotaSupport: true # Enable XFS project quota support for EPHEMERAL partition and user disks. + # KubePrism - local proxy/load balancer on defined port that will distribute + kubePrism: + enabled: true # Enable KubePrism support - will start local load balancing proxy. + port: 7445 # KubePrism port. + # Configures host DNS caching resolver. + hostDNS: + enabled: true # Enable host DNS caching resolver. + forwardKubeDNSToHost: true # Use the host DNS resolver as upstream for Kubernetes CoreDNS pods. + + # # Configure Talos API access from Kubernetes pods. + # kubernetesTalosAPIAccess: + # enabled: true # Enable Talos API access from Kubernetes pods. + # # The list of Talos API roles which can be granted for access from Kubernetes pods. + # allowedRoles: + # - os:reader + # # The list of Kubernetes namespaces Talos API access is available from. + # allowedKubernetesNamespaces: + # - kube-system + # Configures the node labels for the machine. + nodeLabels: + node.kubernetes.io/exclude-from-external-load-balancers: "" + + # # Provides machine specific control plane configuration options. + + # # ControlPlane definition example. + # controlPlane: + # # Controller manager machine specific configuration options. + # controllerManager: + # disabled: false # Disable kube-controller-manager on the node. + # # Scheduler machine specific configuration options. + # scheduler: + # disabled: true # Disable kube-scheduler on the node. + + # # Used to provide static pod definitions to be run by the kubelet directly bypassing the kube-apiserver. + + # # nginx static pod. + # pods: + # - apiVersion: v1 + # kind: pod + # metadata: + # name: nginx + # spec: + # containers: + # - image: nginx + # name: nginx + + # # The `env` field allows for the addition of environment variables. + + # # Environment variables definition examples. + # env: + # GRPC_GO_LOG_SEVERITY_LEVEL: info + # GRPC_GO_LOG_VERBOSITY_LEVEL: "99" + # https_proxy: http://SERVER:PORT/ + # env: + # GRPC_GO_LOG_SEVERITY_LEVEL: error + # https_proxy: https://USERNAME:PASSWORD@SERVER:PORT/ + # env: + # https_proxy: http://DOMAIN\USERNAME:PASSWORD@SERVER:PORT/ + + # # Used to configure the machine's sysctls. + + # # MachineSysctls usage example. + # sysctls: + # kernel.domainname: talos.dev + # net.ipv4.ip_forward: "0" + # net/ipv6/conf/eth0.100/disable_ipv6: "1" + + # # Used to configure the machine's sysfs. + + # # MachineSysfs usage example. + # sysfs: + # devices.system.cpu.cpu0.cpufreq.scaling_governor: performance + + # # Configures the udev system. + # udev: + # # List of udev rules to apply to the udev system + # rules: + # - SUBSYSTEM=="drm", KERNEL=="renderD*", GROUP="44", MODE="0660" + + # # Configures the logging system. + # logging: + # # Logging destination. + # destinations: + # - endpoint: tcp://1.2.3.4:12345 # Where to send logs. Supported protocols are "tcp" and "udp". + # format: json_lines # Logs format. + + # # Configures the kernel. + # kernel: + # # Kernel modules to load. + # modules: + # - name: btrfs # Module name. + + # # Configures the seccomp profiles for the machine. + # seccompProfiles: + # - name: audit.json # The `name` field is used to provide the file name of the seccomp profile. + # # The `value` field is used to provide the seccomp profile. + # value: + # defaultAction: SCMP_ACT_LOG + + # # Override (patch) settings in the default OCI runtime spec for CRI containers. + + # # override default open file limit + # baseRuntimeSpecOverrides: + # process: + # rlimits: + # - hard: 1024 + # soft: 1024 + # type: RLIMIT_NOFILE + + # # Configures the node annotations for the machine. + + # # node annotations example. + # nodeAnnotations: + # customer.io/rack: r13a25 + + # # Configures the node taints for the machine. Effect is optional. + + # # node taints example. + # nodeTaints: + # exampleTaint: exampleTaintValue:NoSchedule +# Provides cluster specific configuration options. +cluster: + id: eKSkTfDUW0U4if1QcK9otzZnNktorUsvnndBrHM4WBE= # Globally unique identifier for this cluster (base64 encoded random 32 bytes). + secret: UumfthEFQUDRssdtWbbVezTJJZOtIIw3Db6f342SwW4= # Shared secret of cluster (base64 encoded random 32 bytes). + # Provides control plane specific configuration options. + controlPlane: + endpoint: https://10.0.0.101:6443 # Endpoint is the canonical controlplane endpoint, which can be an IP address or a DNS hostname. + clusterName: vntx # Configures the cluster's name. + # Provides cluster specific network configuration options. + network: + dnsDomain: cluster.local # The domain used by Kubernetes DNS. + # The pod subnet CIDR. + podSubnets: + - 10.244.0.0/16 + # The service subnet CIDR. + serviceSubnets: + - 10.96.0.0/12 + + # # The CNI used. + # cni: + # name: custom # Name of CNI to use. + # # URLs containing manifests to apply for the CNI. + # urls: + # - https://docs.projectcalico.org/archive/v3.20/manifests/canal.yaml + token: 71gr3x.96za7btksx23r8bk # The [bootstrap token](https://kubernetes.io/docs/reference/access-authn-authz/bootstrap-tokens/) used to join the cluster. + secretboxEncryptionSecret: 1+h+VmWKw3PPspmZ/+u27nhznTt8lRBd9RQQuepZ5/E= # A key used for the [encryption of secret data at rest](https://kubernetes.io/docs/tasks/administer-cluster/encrypt-data/). + # The base64 encoded root certificate authority used by Kubernetes. + ca: + crt: LS0tLS1CRUdJTiBDRVJUSUZJQ0FURS0tLS0tCk1JSUJpakNDQVMrZ0F3SUJBZ0lRVUxsZy9jbEovUkRzVFo1WHNvR0I3VEFLQmdncWhrak9QUVFEQWpBVk1STXcKRVFZRFZRUUtFd3ByZFdKbGNtNWxkR1Z6TUI0WERUSTFNVEl5TnpJek1qVTFOMW9YRFRNMU1USXlOVEl6TWpVMQpOMW93RlRFVE1CRUdBMVVFQ2hNS2EzVmlaWEp1WlhSbGN6QlpNQk1HQnlxR1NNNDlBZ0VHQ0NxR1NNNDlBd0VICkEwSUFCQ2xSVkxiQThpNTJjWUo2bnRRR2lpRnVTRnhVVnphMDA0UDhwM3VwK295SXFPWldJL3llSzY0VU9ueUkKeUF6YzhySXcxeTRjZGYyc1Y4OHhlczUvMzRhallUQmZNQTRHQTFVZER3RUIvd1FFQXdJQ2hEQWRCZ05WSFNVRQpGakFVQmdnckJnRUZCUWNEQVFZSUt3WUJCUVVIQXdJd0R3WURWUjBUQVFIL0JBVXdBd0VCL3pBZEJnTlZIUTRFCkZnUVVuVndjRnRKSHFRV0JuYk9ld3FlcCthUFByTnd3Q2dZSUtvWkl6ajBFQXdJRFNRQXdSZ0loQUlZTnFZaHUKNjNpQy9kMzUzQTFTeUhCN2lMWCtSQ1V2R2cza3BtQW1ybG5pQWlFQTdsSURuaElyUUJUMHNQa29aRHFIYWdJTgphZjRsTEhnbllaTUR3d0FVM3JFPQotLS0tLUVORCBDRVJUSUZJQ0FURS0tLS0tCg== + key: LS0tLS1CRUdJTiBFQyBQUklWQVRFIEtFWS0tLS0tCk1IY0NBUUVFSUpyNlRETEhtRk1aT1RJWXpIWmxNOS9tbTVYZ0l0cWowMEROMzk3Qk9uOEpvQW9HQ0NxR1NNNDkKQXdFSG9VUURRZ0FFS1ZGVXRzRHlMblp4Z25xZTFBYUtJVzVJWEZSWE5yVFRnL3luZTZuNmpJaW81bFlqL0o0cgpyaFE2ZklqSUROenlzakRYTGh4MS9heFh6ekY2em4vZmhnPT0KLS0tLS1FTkQgRUMgUFJJVkFURSBLRVktLS0tLQo= + # The base64 encoded aggregator certificate authority used by Kubernetes for front-proxy certificate generation. + aggregatorCA: + crt: LS0tLS1CRUdJTiBDRVJUSUZJQ0FURS0tLS0tCk1JSUJYekNDQVFhZ0F3SUJBZ0lSQUtGQ1hXS24vTnR4eVBuNmxYZjU4R2N3Q2dZSUtvWkl6ajBFQXdJd0FEQWUKRncweU5URXlNamN5TXpJMU5UZGFGdzB6TlRFeU1qVXlNekkxTlRkYU1BQXdXVEFUQmdjcWhrak9QUUlCQmdncQpoa2pPUFFNQkJ3TkNBQVMwMmptRnFCWU1hSURHeVRQWGNhTjQ2UTRBdCtTLzFob0lqd1QveHhZZUowVDJNeDh1ClRVSWQzNjVKT1dSK2FQS2dWdUkySVZpKzZDNXJOcnBSSnhES28yRXdYekFPQmdOVkhROEJBZjhFQkFNQ0FvUXcKSFFZRFZSMGxCQll3RkFZSUt3WUJCUVVIQXdFR0NDc0dBUVVGQndNQ01BOEdBMVVkRXdFQi93UUZNQU1CQWY4dwpIUVlEVlIwT0JCWUVGTXFxVnowdDVaaERQVTdzcS9hdUxKcWxjMVlkTUFvR0NDcUdTTTQ5QkFNQ0EwY0FNRVFDCklBdEI4L0hpSS9RakVEVjFiV29DZ1M1TkdtbDNzdUFTRGtUbkZjK2F3TmlEQWlBNzlPeHVJeVl1VFgyVUxvQlQKZWRXbDdEZ0Y0N3htTnM2OTNGcThLeXRGc0E9PQotLS0tLUVORCBDRVJUSUZJQ0FURS0tLS0tCg== + key: LS0tLS1CRUdJTiBFQyBQUklWQVRFIEtFWS0tLS0tCk1IY0NBUUVFSU9EVVVzMklrazhaeGowRDNRQVBLeTlpTCtTSVNaZGhOZjMrdVBqOHNudVRvQW9HQ0NxR1NNNDkKQXdFSG9VUURRZ0FFdE5vNWhhZ1dER2lBeHNrejEzR2plT2tPQUxma3Y5WWFDSThFLzhjV0hpZEU5ak1mTGsxQwpIZCt1U1Rsa2ZtanlvRmJpTmlGWXZ1Z3VhemE2VVNjUXlnPT0KLS0tLS1FTkQgRUMgUFJJVkFURSBLRVktLS0tLQo= + # The base64 encoded private key for service account token generation. + serviceAccount: + key: LS0tLS1CRUdJTiBSU0EgUFJJVkFURSBLRVktLS0tLQpNSUlKS1FJQkFBS0NBZ0VBM0gzV1hzZVU4clpGdzhkaUhIbzB3aWFQdnV3N3VpblJ3MS9xbnB6VldjVGRlWUcrCnJlQ0dMek1vNWlzaHBQT3N2WVd5UEVoZlVyZ01ldTY3cFlTMFNxSmtGcnJtY3lrQUNybHFtaE54ZzVBazZZcTIKOWhPeUphR0tKOVkrdEUzNmFjUjBIWTJ4UEV3K0lKbEdIVUpLNSs2RUsxUXVjYTF5TXpLc0pOM1VrSDVzNXpXeApEbCtSdHJLNklXdEsxYjZ5M213SmtaRTJIYktxUUdXdWxONDZ6M1gzTXJLNk9POVhHNTJ2S3dINFBzdHFHVDc5Ck92dlI3b21yaVF6OUJUclhSYXlqRGp4MEl3NGVTVVJ4QkFsRFlsZDlqd2E3aXd1NHU5bldlazYyRjM3S3VMTE4KYlpWWlQ4WjJqQlJ5WGp5ZXdkTkFpL0Z4bElNSWtSdjE0VVV4M3NEdDhycGh2b2xERDBXVGlRcTNyQkNSUUNrVQpldWpZUmloaDNnQUI4QTN5dGJrZGJSNlgrQ2IrR21NMFVycmgwb2RnWDg0dkdrY1lhR1NrSnRKSEttSlNDUGN3CkJYa29taHd2dDJ4UzVEQTM4aUhPWDc5OTgrQzdJQWpyWnpka3ZLSXZIc1grSklvYTF4d0ZiclJTOUIrNUNDMXQKdnVFd1pvVXlTWEdDOWh0bkd5M1ZjcUdsbFBUQ3NEaForZkpXNGRNazE2cldaVW5uSmM3ek1Fa2pleVJzUERnZAptM215Z0w1RDd2S2w1SnBGNWphM2wzOEt4OC9xKzU3OFY2RllSblhvUElGS25TbGFLNmorKzdmeFZyMFdPNlk4CjRKVnFyUG5LYVVvQ0I0WTFrZGlqSkI1TndVRjVWazdqNVUyWThYRk1vWjRtNGdWQ29jS3laUDlIYXlNQ0F3RUEKQVFLQ0FnQUl3bGovUitkell1bFBsejZmQ2YzSmpyV2NMSTlNM0hkd1R3R25qbXh0VmdSRVhQS2h2cThsOWQ3VQprZmNTc2ZsMVIvZm1MQ3ZaUWVXQkJyWGVvL0J6bkpMa1VrVndZcnNWTWZ0NXBuY1dkbVg0L3lFNGtseTc0UGgzCmo2dkxCdVFCU3FRZ1BtNUJpbmZYWEs5cjN5UFJwZWlMUGh0Z09iYzFNSGlsT0VqRytyYkIwcUMzaFBWcGNCMHoKMGFyVjVlNytKZ1dWU2xML2lBYjZhdSt1QzB3RHpOaG1vN0lCTEFUbVhIUEdmaHdLQnBPdThCRW9SRE81U2EvTwpVSDFHdFdreTQrSlFZUGR1SXhQeDdpMmRMdThGMjVycDBTY25KVzZQeTk0WTJzS2lHVS9kV1lFT3J1V3U1Ui8xCmZhUnplTzRIbmloTXh1a3ZzS3JvOU5ibVBaVDNCUXR2SGl4ZlVNU2pmTXZFcUorNDhpdlA1RTNiYUJHRk5Mc3oKbUZXZW91MFEzVzNTMU50RkQvWnIybFJpT3VrVzhLLytBSm1PL210RWd2NG1UK3pHa05BUGhPT3lQcUlTakgxTAp1WTY3c08wRGlJWmJ1REdmZDQ2YXN3bHBZQis1Z0ZMZGxONDNJcGRxZG5GMFdtbjkybXk3cVluVVhkSkJENnZNCm5TWGJJOTZZOSt6K3V6citTZWMzeWhEckd6a1c1NWJ4VHJqb1FMZ2d6RDRVSWEyMm1ueUFOb3UrZzkyU09RSnEKb0hmWGZoeDdJeEZyM2h2V3ZaVVlYNit6bndUZTBKeVI0cy9NaXZxM2NIVERzV1A2NXBMd3VNQXRMMW1qWHNOcgp4aGhzZDQrNkJYb0R1OGl1V1NFRDlndlFIbVFlN3p3azVEVlNPbXJOTHlZTnZ3Y0U1UUtDQVFFQTYxaWR3VUp0CmJEMUlzQ1RBaVJnaFEvT0oxY3cwcmNqSDhGcGRNaFg1MHc2NUJqcmk5OEU5eDNkK2JpZVA3eXk5cVNMcnN5dzIKSDNteTJXOEZOSHdUUnJCT2NnQVg0cWhSa205Y0tBSlhGS0xVbGY4TlJocWJrR3RyVnMybEdDdXBEZHJxN2RpTApHRGdxY2gxbHpXR1d1UlQyOWZDRXRzZWVyd2NFemtXYTE0MDRYWEIyTi9EK0FHbVB2Mmp2dEFOSml0ekFuL0pWCnQ4NnZLVyttbWlxNVFQNlZHZjFtVmZTMGlSQy9TVzJMditGR3J2ZmRsNHN4WXJONnoweVdZSUZqK2J3aVNYblIKZXhTKzYyUUtleGJCalZwa2gzRnJTNWNsZWJ1ajg0aWVEaVQ1ZDFsTTNhaHlpSjRJYk1IaVJyeG1wSFNDVmkrUQorOHpSbHRwcGI2eko5UUtDQVFFQTc5ZDkwWDhqeFJKV015MUFWTDlrMnN5YjZacG9XN2FHL3AwNTlHVi80dXBNCi9DdTRXVVdOajdWdW1sRmppUFdtT0hhMkxIVnZmVW5DY3M1WTYxRTJVWm9mNXcxLzZ5R2ZwdEtzZ0V5eElUZGMKMFRFV0pPTy9QeVZabEhXR2xJVVNsMlBsTlFuclh6OCsvY29RZklSS29OZmd6K1p5NHdLdFpMWDdpUDBlaGt4YgphWmhNWWF0azNhN0FyQURPRFZiZ1Z3dkdjaER6Vm5oNjc4TzF3a0p0WjJ6TUlrOGF4cy9WR1VMQ0NRdURTV2pICkdsb2IvQlA3TERBdWxKVlN3ajNOY2NLK01ZMnpSSXEwcHNYWkxsVlJicTRZSlhFbUxoRFEzUXhvUklLQVZQM08KWkZWR2lDT3lXU1dJclprZkZHaEkrNlFram1YazJmYmNPTE9QNGUyNXR3S0NBUUVBd3ZKcDR0OXlvcGwxTDZ1Ugo3VDRXdUNIeFNDOWFaNllNc0xVNXc3WmVkZzBaQ09jWWdXQUtHOE9JOEJoSGF6aWxkb2hkczlKb2x0UUphWUZFClQ0Q0R1eWRxSTVhZU1udDQ3cExlUktvRGxpMTNhVFNYdXoxcEpVMUY0ZWFBM2krMFhxeTdzLytPNEtZTnl1ODkKRjg3QnVsaDZaYWt4VmZLdktJN28xVERsSGE1MlJUaFdST3FVaktUa2xRcUluSldvZ3FWdnprNC80UDBOTFlhMQorN2h1TWo5d0pOSTV4ZlBvNUMwQ053SE9KRWlvYzJFUXBtcC9veUhIRmhaNzdqN2dJTXRObjQyUUQ2TlVyc24wCndKZE9CeGdjYy9Gb2pub0thZmNielN5YXVGNjZZcm1QS1lGU05vYXB0ZVU0MloxUWJPT3gzMUNSaVhMVkhsK1gKdlJEbFRRS0NBUUJBNkVpY2taUFVtWW5LZjh5Ukl0cmdlODhXQVR1TTFuRGlKeHF3RVdmeXVRWHNtTWhqSUhlWApGTHJCK0pTL1UvdVAvRkNBNTZjc2VQR3VzRGxRTmNKRmd6aHZCekEvS2ZKUzYyRFR0KzJYMTZ1KzBWSDAyYzNBCkFST2xJY2t5R0hGWGx5bEltVTZoa0RRejZxTmJqMUhEQmFsSm1rd3RNMlJKaFJaMWxFcldmWU9mcUIvRHJ1YTEKTjczY3pycjAwVFlWV0pKei9ESmVqR3g0eHJaQnhFaG5YUUpCcHJiUVp4NThuNXh6WmpJNWc2bWVjQlJ5dTlXVgp0OVJqVWFYNyswM0dJN1hsSXp3SXFLRUxJVEFOWWZtUHduMjJaRkM0MXNRdmpsUUpkbWZVbUh0cW04bGl2b1pkCnFkSzdhRjBJNE5BZmllUjZ4UWlTRkVTMDg2TlV1VWt4QW9JQkFRRG9WL0pJRlNEejl3Z3dneUhhdmdwSnR0UGkKNWZBeEpZaktZbUtsLzdpZUdkZ0pzN1dwR3dxNXlQZFVVRE1yMnNKUDBGWDhEZFJTSktWLzExRzMvaklTL1JyQQpwcDVsS2hGbEFncVBvZ1EvL0IzTVBiNXZiNTBSMExrNGJtVWVYcUVhMkJBSTlmc0R3WEFZbFhsMnJOT0drdEdSCnJZd1BEdHlhbnI1d0grVEtoYjdqODdWN2Z1TWpRcU5SK21TQVJqZXpvRHNQdnJvUHB0d1o0RnBSOTNCUXJqUGoKRWF6Z1UvbHlSRkVCNklISFhvbWFaR1ExYlY1TG85ZTlUZGp6VFpiT2tJMUFsL3B6cWx5WlpzdnU5RnFURUdUbwpRckt6Nm9xeFJyR1lhUVNJbGpydWhPajdiWUVPeGp2VnFEdmNIaGNxV1paN0h5VWNjS2gzNFZReWhCdTQKLS0tLS1FTkQgUlNBIFBSSVZBVEUgS0VZLS0tLS0K + # API server specific configuration options. + apiServer: + image: registry.k8s.io/kube-apiserver:v1.35.0 # The container image used in the API server manifest. + # Configure the API server admission plugins. + admissionControl: + - name: PodSecurity # Name is the name of the admission controller. + # Configuration is an embedded configuration object to be used as the plugin's + configuration: + apiVersion: pod-security.admission.config.k8s.io/v1alpha1 + defaults: + audit: restricted + audit-version: latest + enforce: baseline + enforce-version: latest + warn: restricted + warn-version: latest + exemptions: + namespaces: + - kube-system + runtimeClasses: [] + usernames: [] + kind: PodSecurityConfiguration + # Configure the API server audit policy. + auditPolicy: + apiVersion: audit.k8s.io/v1 + kind: Policy + rules: + - level: Metadata + + # # Configure the API server authorization config. Node and RBAC authorizers are always added irrespective of the configuration. + # authorizationConfig: + # - type: Webhook # Type is the name of the authorizer. Allowed values are `Node`, `RBAC`, and `Webhook`. + # name: webhook # Name is used to describe the authorizer. + # # webhook is the configuration for the webhook authorizer. + # webhook: + # connectionInfo: + # type: InClusterConfig + # failurePolicy: Deny + # matchConditionSubjectAccessReviewVersion: v1 + # matchConditions: + # - expression: has(request.resourceAttributes) + # - expression: '!(\''system:serviceaccounts:kube-system\'' in request.groups)' + # subjectAccessReviewVersion: v1 + # timeout: 3s + # - type: Webhook # Type is the name of the authorizer. Allowed values are `Node`, `RBAC`, and `Webhook`. + # name: in-cluster-authorizer # Name is used to describe the authorizer. + # # webhook is the configuration for the webhook authorizer. + # webhook: + # connectionInfo: + # type: InClusterConfig + # failurePolicy: NoOpinion + # matchConditionSubjectAccessReviewVersion: v1 + # subjectAccessReviewVersion: v1 + # timeout: 3s + # Controller manager server specific configuration options. + controllerManager: + image: registry.k8s.io/kube-controller-manager:v1.35.0 # The container image used in the controller manager manifest. + # Kube-proxy server-specific configuration options + proxy: + image: registry.k8s.io/kube-proxy:v1.35.0 # The container image used in the kube-proxy manifest. + + # # Disable kube-proxy deployment on cluster bootstrap. + # disabled: false + # Scheduler server specific configuration options. + scheduler: + image: registry.k8s.io/kube-scheduler:v1.35.0 # The container image used in the scheduler manifest. + # Configures cluster member discovery. + discovery: + enabled: true # Enable the cluster membership discovery feature. + # Configure registries used for cluster member discovery. + registries: + # Kubernetes registry uses Kubernetes API server to discover cluster members and stores additional information + kubernetes: + disabled: true # Disable Kubernetes discovery registry. + # Service registry is using an external service to push and pull information about cluster members. + service: {} + # # External service endpoint. + # endpoint: https://discovery.talos.dev/ + # Etcd specific configuration options. + etcd: + # The `ca` is the root certificate authority of the PKI. + ca: + crt: LS0tLS1CRUdJTiBDRVJUSUZJQ0FURS0tLS0tCk1JSUJmVENDQVNPZ0F3SUJBZ0lRY1hQekZ3N2lYdnlnY2FVMGlUQ3lGekFLQmdncWhrak9QUVFEQWpBUE1RMHcKQ3dZRFZRUUtFd1JsZEdOa01CNFhEVEkxTVRJeU56SXpNalUxTjFvWERUTTFNVEl5TlRJek1qVTFOMW93RHpFTgpNQXNHQTFVRUNoTUVaWFJqWkRCWk1CTUdCeXFHU000OUFnRUdDQ3FHU000OUF3RUhBMElBQlBpREhoWTkzT1FFClpaS2x1L1M3NVBnRmlvNks5SjV1RUZwNk12c3N4NnYzWld6RXJ2clBoNW53QkFqVFFOOUdodTRmQ1dXbXdsQmgKVVhIU09RcHh5OStqWVRCZk1BNEdBMVVkRHdFQi93UUVBd0lDaERBZEJnTlZIU1VFRmpBVUJnZ3JCZ0VGQlFjRApBUVlJS3dZQkJRVUhBd0l3RHdZRFZSMFRBUUgvQkFVd0F3RUIvekFkQmdOVkhRNEVGZ1FVYnc1N01IV1JvWnYyClZ6UndZNGIyY3c1VGw3c3dDZ1lJS29aSXpqMEVBd0lEU0FBd1JRSWdHR1BOZmNzT2M0ajlFblNIbkhRV2dydEQKbEdZWitpZ3JKQnZSWGFSa1FRd0NJUUNOeUlRVU9reWx5U0Vpc1ZyNzFhR3hTRHJ5UFgwZlRuMEdZM25qalpkQQpaUT09Ci0tLS0tRU5EIENFUlRJRklDQVRFLS0tLS0K + key: LS0tLS1CRUdJTiBFQyBQUklWQVRFIEtFWS0tLS0tCk1IY0NBUUVFSUtpazBDeFdObEx6ZWJaY2kwSVYyUHNqOGRoRis5L0Nsb3JXbzAySUdRb1BvQW9HQ0NxR1NNNDkKQXdFSG9VUURRZ0FFK0lNZUZqM2M1QVJsa3FXNzlMdmsrQVdLam9yMG5tNFFXbm95K3l6SHEvZGxiTVN1K3MrSAptZkFFQ05OQTMwYUc3aDhKWmFiQ1VHRlJjZEk1Q25ITDN3PT0KLS0tLS1FTkQgRUMgUFJJVkFURSBLRVktLS0tLQo= + + # # The container image used to create the etcd service. + # image: registry.k8s.io/etcd:v3.6.7 + + # # The `advertisedSubnets` field configures the networks to pick etcd advertised IP from. + # advertisedSubnets: + # - 10.0.0.0/8 + # A list of urls that point to additional manifests. + extraManifests: [] + # - https://www.example.com/manifest1.yaml + # - https://www.example.com/manifest2.yaml + + # A list of inline Kubernetes manifests. + inlineManifests: [] + # - name: namespace-ci # Name of the manifest. + # contents: |- # Manifest contents as a string. + # apiVersion: v1 + # kind: Namespace + # metadata: + # name: ci + + + # # A key used for the [encryption of secret data at rest](https://kubernetes.io/docs/tasks/administer-cluster/encrypt-data/). + + # # Decryption secret example (do not use in production!). + # aescbcEncryptionSecret: z01mye6j16bspJYtTB/5SFX8j7Ph4JXxM2Xuu4vsBPM= + + # # Core DNS specific configuration options. + # coreDNS: + # image: registry.k8s.io/coredns/coredns:v1.13.2 # The `image` field is an override to the default coredns image. + + # # External cloud provider configuration. + # externalCloudProvider: + # enabled: true # Enable external cloud provider. + # # A list of urls that point to additional manifests for an external cloud provider. + # manifests: + # - https://raw.githubusercontent.com/kubernetes/cloud-provider-aws/v1.20.0-alpha.0/manifests/rbac.yaml + # - https://raw.githubusercontent.com/kubernetes/cloud-provider-aws/v1.20.0-alpha.0/manifests/aws-cloud-controller-manager-daemonset.yaml + + # # A map of key value pairs that will be added while fetching the extraManifests. + # extraManifestHeaders: + # Token: "1234567" + # X-ExtraInfo: info + + # # Settings for admin kubeconfig generation. + # adminKubeconfig: + # certLifetime: 1h0m0s # Admin kubeconfig certificate lifetime (default is 1 year). + + # # Allows running workload on control-plane nodes. + # allowSchedulingOnControlPlanes: true +--- +apiVersion: v1alpha1 +kind: HostnameConfig +auto: stable # A method to automatically generate a hostname for the machine. + +# # A static hostname to set for the machine. +# hostname: controlplane1 +# hostname: controlplane1.example.org diff --git a/talos/current-config.yaml b/talos/current-config.yaml new file mode 100644 index 0000000..6c20382 --- /dev/null +++ b/talos/current-config.yaml @@ -0,0 +1 @@ +rpc error: code = NotFound desc = resource "config" is not registered diff --git a/talos/deploy-cluster-services.sh b/talos/deploy-cluster-services.sh new file mode 100755 index 0000000..d0b5bbe --- /dev/null +++ b/talos/deploy-cluster-services.sh @@ -0,0 +1,194 @@ +#!/usr/bin/env bash +set -euo pipefail + +# Talos Cluster Services Deployment Script +# This script deploys core infrastructure services in the correct order + +SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)" +VNTX_INFRA_DIR="$(dirname "$SCRIPT_DIR")" + +echo "=== Talos Cluster Services Deployment ===" +echo "" + +# Color output +GREEN='\033[0;32m' +YELLOW='\033[1;33m' +NC='\033[0m' # No Color + +step() { + echo -e "${GREEN}==>${NC} $1" +} + +wait_for_pods() { + local namespace=$1 + local label=$2 + local timeout=${3:-120} + + echo "Waiting for pods in namespace $namespace with label $label..." + kubectl wait --for=condition=ready pod \ + -l "$label" \ + -n "$namespace" \ + --timeout="${timeout}s" 2>/dev/null || true +} + +# Step 0: Remove control-plane taint +step "0. Removing control-plane taint..." +kubectl taint nodes --all node-role.kubernetes.io/control-plane:NoSchedule- 2>/dev/null || echo "Taint already removed or not present" + +echo "" + +# Step 1: Deploy MetalLB +step "1. Deploying MetalLB..." +kubectl apply -f https://raw.githubusercontent.com/metallb/metallb/v0.14.9/config/manifests/metallb-native.yaml + +echo "Waiting for MetalLB controller..." +wait_for_pods metallb-system component=controller 120 + +# Create memberlist secret if needed +kubectl get secret -n metallb-system memberlist &>/dev/null || \ + kubectl create secret generic -n metallb-system memberlist \ + --from-literal=secretkey="$(openssl rand -base64 128)" + +echo "Waiting for MetalLB speakers..." +wait_for_pods metallb-system component=speaker 120 + +step "Applying MetalLB IP pool configuration..." +kubectl apply -f "$VNTX_INFRA_DIR/contexts/metallb/ipaddresspool.yaml" + +echo "" + +# Step 2: Deploy NFS Provisioner +step "2. Deploying NFS Provisioner..." +helm repo add nfs-subdir-external-provisioner https://kubernetes-sigs.github.io/nfs-subdir-external-provisioner/ 2>/dev/null || true +helm repo update + +helm upgrade --install nfs-subdir-external-provisioner nfs-subdir-external-provisioner/nfs-subdir-external-provisioner \ + --namespace nfs-provisioner \ + --create-namespace \ + --set nfs.server=10.0.0.253 \ + --set nfs.path=/mnt/k8s/cluster \ + --set storageClass.name=nfs \ + --set storageClass.defaultClass=true \ + --set storageClass.reclaimPolicy=Delete \ + --wait + +echo "" + +# Step 3: Deploy Tailscale Operator +step "3. Deploying Tailscale Operator..." + +# Set namespace to privileged for Tailscale proxies +kubectl create namespace tailscale 2>/dev/null || true +kubectl label namespace tailscale \ + pod-security.kubernetes.io/enforce=privileged \ + pod-security.kubernetes.io/audit=privileged \ + pod-security.kubernetes.io/warn=privileged \ + --overwrite + +# Get Tailscale OAuth credentials from 1Password +TAILSCALE_CLIENT_ID=$(op item get almzem6nffphe3xv4pgxpkbaga --account=YOOATCZZSVGH7AD6VABUVPORLI --fields client_id --reveal) +TAILSCALE_CLIENT_SECRET=$(op item get almzem6nffphe3xv4pgxpkbaga --account=YOOATCZZSVGH7AD6VABUVPORLI --fields client_secret --reveal) + +helm repo add tailscale https://pkgs.tailscale.com/helmcharts 2>/dev/null || true +helm repo update + +helm upgrade --install tailscale-operator tailscale/tailscale-operator \ + --namespace=tailscale \ + --set-string oauth.clientId="$TAILSCALE_CLIENT_ID" \ + --set-string oauth.clientSecret="$TAILSCALE_CLIENT_SECRET" \ + --wait + +echo "" + +# Step 4: Deploy DNS Services (PowerDNS) +step "4. Deploying DNS Services (PowerDNS)..." + +# Create PostgreSQL credentials secret from 1Password +kubectl create secret generic postgresql-credentials -n dns \ + --from-literal="POSTGRES_USER=$(op item get t3nqhjmeci6msx4qouu64yfr3q --account=YOOATCZZSVGH7AD6VABUVPORLI --fields POSTGRES_USER --reveal)" \ + --from-literal="POSTGRES_PASSWORD=$(op item get t3nqhjmeci6msx4qouu64yfr3q --account=YOOATCZZSVGH7AD6VABUVPORLI --fields POSTGRES_PASSWORD --reveal)" \ + --from-literal="POSTGRES_DB=$(op item get t3nqhjmeci6msx4qouu64yfr3q --account=YOOATCZZSVGH7AD6VABUVPORLI --fields POSTGRES_DB --reveal)" \ + --dry-run=client -o yaml | kubectl apply -f - + +# Create PowerDNS API secret from 1Password +kubectl create secret generic powerdns-secrets -n dns \ + --from-literal="API_KEY=$(op item get t3nqhjmeci6msx4qouu64yfr3q --account=YOOATCZZSVGH7AD6VABUVPORLI --fields POWERDNS_API_KEY --reveal)" \ + --dry-run=client -o yaml | kubectl apply -f - + +# Create PowerDNS config +kubectl create configmap powerdns-config -n dns --from-literal="pdns.conf=launch=gpgsql +gpgsql-host=10.0.0.252 +gpgsql-port=5432 +gpgsql-dbname=powerdns +gpgsql-user=powerdns +gpgsql-password=$(op item get t3nqhjmeci6msx4qouu64yfr3q --account=YOOATCZZSVGH7AD6VABUVPORLI --fields POSTGRES_PASSWORD --reveal) +gpgsql-dnssec=yes + +receiver-threads=4 +distributor-threads=4 +reuseport=yes +max-tcp-connections=100 + +api=yes +api-key=$(op item get t3nqhjmeci6msx4qouu64yfr3q --account=YOOATCZZSVGH7AD6VABUVPORLI --fields POWERDNS_API_KEY --reveal) +webserver=yes +webserver-address=0.0.0.0 +webserver-port=8081 +webserver-allow-from=0.0.0.0/0 +webserver-max-bodysize=10485760 + +local-address=0.0.0.0 +local-port=53 + +log-dns-queries=yes +loglevel=6" \ + --dry-run=client -o yaml | kubectl apply -f - + +# Deploy PowerDNS services and deployment +kubectl apply -f "$VNTX_INFRA_DIR/contexts/dns/powerdns-service.yaml" +kubectl apply -f "$VNTX_INFRA_DIR/contexts/dns/powerdns-deployment.yaml" + +echo "Waiting for PowerDNS..." +wait_for_pods dns app=powerdns 120 + +echo "" + +# Step 5: Verify deployment +step "5. Verifying deployment..." + +echo "" +echo "MetalLB Status:" +kubectl get pods -n metallb-system +echo "" +kubectl get ipaddresspool,l2advertisement -n metallb-system + +echo "" +echo "NFS Provisioner Status:" +kubectl get pods -n nfs-provisioner +echo "" +kubectl get storageclass + +echo "" +echo "Tailscale Operator Status:" +kubectl get pods -n tailscale +echo "" + +echo "" +echo "DNS Services Status:" +kubectl get pods,svc -n dns + +echo "" +echo -e "${GREEN}=== Deployment Complete ===${NC}" +echo "" +echo "Services deployed:" +echo " - MetalLB (Public LoadBalancer)" +echo " - NFS Provisioner (Storage from 10.0.0.253)" +echo " - Tailscale Operator (Private network access)" +echo " - PowerDNS (Authoritative DNS)" +echo "" +echo "External Dependencies:" +echo " - PostgreSQL: 10.0.0.252" +echo " - NFS: 10.0.0.253:/mnt/k8s/cluster" +echo "" +echo "LoadBalancer Services:" +kubectl get svc --all-namespaces -o wide | grep LoadBalancer || echo " No LoadBalancer services yet" diff --git a/talos/generate-node-configs.sh b/talos/generate-node-configs.sh new file mode 100755 index 0000000..07bbad6 --- /dev/null +++ b/talos/generate-node-configs.sh @@ -0,0 +1,26 @@ +#!/bin/bash +set -e + +cd "$(dirname "$0")" + +echo "Generating individual node configs..." + +# Generate control plane configs +for node in cp-1 cp-2 cp-3; do + echo " Creating nodes/${node}.yaml (control plane)" + talosctl machineconfig patch controlplane.yaml \ + --patch @patches/cloud-provider.yaml \ + --patch @patches/${node}.yaml \ + -o nodes/${node}.yaml +done + +# Generate worker configs +for node in worker-1 worker-2 worker-3; do + echo " Creating nodes/${node}.yaml (worker)" + talosctl machineconfig patch worker-base.yaml \ + --patch @patches/cloud-provider.yaml \ + --patch @patches/${node}.yaml \ + -o nodes/${node}.yaml +done + +echo "Done! Node configs created in nodes/" diff --git a/talos/kubeconfig b/talos/kubeconfig new file mode 100644 index 0000000..4584e21 --- /dev/null +++ b/talos/kubeconfig @@ -0,0 +1,28 @@ +apiVersion: v1 +clusters: +- cluster: + certificate-authority-data: LS0tLS1CRUdJTiBDRVJUSUZJQ0FURS0tLS0tCk1JSUJpakNDQVMrZ0F3SUJBZ0lRVUxsZy9jbEovUkRzVFo1WHNvR0I3VEFLQmdncWhrak9QUVFEQWpBVk1STXcKRVFZRFZRUUtFd3ByZFdKbGNtNWxkR1Z6TUI0WERUSTFNVEl5TnpJek1qVTFOMW9YRFRNMU1USXlOVEl6TWpVMQpOMW93RlRFVE1CRUdBMVVFQ2hNS2EzVmlaWEp1WlhSbGN6QlpNQk1HQnlxR1NNNDlBZ0VHQ0NxR1NNNDlBd0VICkEwSUFCQ2xSVkxiQThpNTJjWUo2bnRRR2lpRnVTRnhVVnphMDA0UDhwM3VwK295SXFPWldJL3llSzY0VU9ueUkKeUF6YzhySXcxeTRjZGYyc1Y4OHhlczUvMzRhallUQmZNQTRHQTFVZER3RUIvd1FFQXdJQ2hEQWRCZ05WSFNVRQpGakFVQmdnckJnRUZCUWNEQVFZSUt3WUJCUVVIQXdJd0R3WURWUjBUQVFIL0JBVXdBd0VCL3pBZEJnTlZIUTRFCkZnUVVuVndjRnRKSHFRV0JuYk9ld3FlcCthUFByTnd3Q2dZSUtvWkl6ajBFQXdJRFNRQXdSZ0loQUlZTnFZaHUKNjNpQy9kMzUzQTFTeUhCN2lMWCtSQ1V2R2cza3BtQW1ybG5pQWlFQTdsSURuaElyUUJUMHNQa29aRHFIYWdJTgphZjRsTEhnbllaTUR3d0FVM3JFPQotLS0tLUVORCBDRVJUSUZJQ0FURS0tLS0tCg== + server: https://10.0.0.101:6443 + name: vntx +contexts: +- context: + cluster: vntx + namespace: default + user: admin@vntx + name: admin@vntx +- context: + cluster: vntx + namespace: default + user: admin@vntx-1 + name: vntx +current-context: admin@vntx +kind: Config +users: +- name: admin@vntx + user: + client-certificate-data: LS0tLS1CRUdJTiBDRVJUSUZJQ0FURS0tLS0tCk1JSUJoakNDQVN1Z0F3SUJBZ0lSQUxPR2NEbnd5alVRc1pBZTBXdUlQZUl3Q2dZSUtvWkl6ajBFQXdJd0ZURVQKTUJFR0ExVUVDaE1LYTNWaVpYSnVaWFJsY3pBZUZ3MHlOakF4TURFeU1UVTRNVGxhRncweU56QXhNREV5TVRVNApNamxhTUNreEZ6QVZCZ05WQkFvVERuTjVjM1JsYlRwdFlYTjBaWEp6TVE0d0RBWURWUVFERXdWaFpHMXBiakJaCk1CTUdCeXFHU000OUFnRUdDQ3FHU000OUF3RUhBMElBQkEvQ1VyajRzbTI3TG9sOVQ1cjhzMFZsQ0lKZmNEcUUKaTljcnp1M0lUdDYzbG9CVVByMXZyTVFwSzBvSEFsWmd5SjArSHVERjIrUElUU1JMQ1ZVcFFzcWpTREJHTUE0RwpBMVVkRHdFQi93UUVBd0lGb0RBVEJnTlZIU1VFRERBS0JnZ3JCZ0VGQlFjREFqQWZCZ05WSFNNRUdEQVdnQlNkClhCd1cwa2VwQllHZHM1N0NwNm41bzgrczNEQUtCZ2dxaGtqT1BRUURBZ05KQURCR0FpRUExTmRjcUxPRmpUc1cKT3RRalhNeU1ucGZPMDJMQTFma1U0NHYzaERscTZ1TUNJUURBOEQyT29vdXk2K2JkNkoxeUs3UGIzeU9ud0JlcgpyY0lGM1luMlg1ZTFvZz09Ci0tLS0tRU5EIENFUlRJRklDQVRFLS0tLS0K + client-key-data: LS0tLS1CRUdJTiBFQyBQUklWQVRFIEtFWS0tLS0tCk1IY0NBUUVFSUh2U2dSVVhyK1NYVTRZUTJCdTVUWWVoL2tZRFBsczd6Mm9mSU9ad3ZHR05vQW9HQ0NxR1NNNDkKQXdFSG9VUURRZ0FFRDhKU3VQaXliYnN1aVgxUG12eXpSV1VJZ2w5d09vU0wxeXZPN2NoTzNyZVdnRlErdlcrcwp4Q2tyU2djQ1ZtREluVDRlNE1YYjQ4aE5KRXNKVlNsQ3lnPT0KLS0tLS1FTkQgRUMgUFJJVkFURSBLRVktLS0tLQo= +- name: admin@vntx-1 + user: + client-certificate-data: LS0tLS1CRUdJTiBDRVJUSUZJQ0FURS0tLS0tCk1JSUJoVENDQVN1Z0F3SUJBZ0lSQUtHcFVGbUpJaTh4cGwzUzN0bmRRZ3N3Q2dZSUtvWkl6ajBFQXdJd0ZURVQKTUJFR0ExVUVDaE1LYTNWaVpYSnVaWFJsY3pBZUZ3MHlOVEV5TWpnd01EQTFOVGRhRncweU5qRXlNamd3TURBMgpNRGRhTUNreEZ6QVZCZ05WQkFvVERuTjVjM1JsYlRwdFlYTjBaWEp6TVE0d0RBWURWUVFERXdWaFpHMXBiakJaCk1CTUdCeXFHU000OUFnRUdDQ3FHU000OUF3RUhBMElBQkRtZldUV2RnWXh1V3RIREE0NkdpS2VSTkRmc010ZGcKNnlYSUtRbzRsNVNabFFwaWs4ZXp1em9rQlIvUXdjYVJ1bGlEUktkOWlobGpIeGtWbDFPKzZnbWpTREJHTUE0RwpBMVVkRHdFQi93UUVBd0lGb0RBVEJnTlZIU1VFRERBS0JnZ3JCZ0VGQlFjREFqQWZCZ05WSFNNRUdEQVdnQlNkClhCd1cwa2VwQllHZHM1N0NwNm41bzgrczNEQUtCZ2dxaGtqT1BRUURBZ05JQURCRkFpQTFrVWlsUmQ5MGdQc0MKRk5JZ2c5QkZzbUJzV1RBaDhJN05mRVFvMWxaeG1BSWhBSnZ6L2IzSnZ1T2V3UWUyNm54WloycWZuYStpemlRawo2VTlIVlZzNU5jZEoKLS0tLS1FTkQgQ0VSVElGSUNBVEUtLS0tLQo= + client-key-data: LS0tLS1CRUdJTiBFQyBQUklWQVRFIEtFWS0tLS0tCk1IY0NBUUVFSUNjK3UvaFFWVHB3V2RDSEt1U2ZneTlCMStYWml6ME1mcnVQS1N1eS9TV1NvQW9HQ0NxR1NNNDkKQXdFSG9VUURRZ0FFT1o5Wk5aMkJqRzVhMGNNRGpvYUlwNUUwTit3eTEyRHJKY2dwQ2ppWGxKbVZDbUtUeDdPNwpPaVFGSDlEQnhwRzZXSU5FcDMyS0dXTWZHUldYVTc3cUNRPT0KLS0tLS1FTkQgRUMgUFJJVkFURSBLRVktLS0tLQo= diff --git a/talos/metallb/ipaddresspool-internal.yaml b/talos/metallb/ipaddresspool-internal.yaml new file mode 100644 index 0000000..03e9cfd --- /dev/null +++ b/talos/metallb/ipaddresspool-internal.yaml @@ -0,0 +1,20 @@ +apiVersion: metallb.io/v1beta1 +kind: IPAddressPool +metadata: + name: internal-pool + namespace: metallb-system +spec: + addresses: + - 10.0.0.10-10.0.0.99 + autoAssign: true +--- +apiVersion: metallb.io/v1beta1 +kind: L2Advertisement +metadata: + name: internal-l2 + namespace: metallb-system +spec: + ipAddressPools: + - internal-pool + interfaces: + - eth0 diff --git a/talos/nodes/cp-1.yaml b/talos/nodes/cp-1.yaml new file mode 100644 index 0000000..09f91e5 --- /dev/null +++ b/talos/nodes/cp-1.yaml @@ -0,0 +1,124 @@ +version: v1alpha1 +debug: false +persist: true +machine: + type: controlplane + token: gwdkoe.5gbblli1cvxv1axx + ca: + crt: LS0tLS1CRUdJTiBDRVJUSUZJQ0FURS0tLS0tCk1JSUJQekNCOHFBREFnRUNBaEVBbk5ucllpRDF4bjZaaGVFY0hvTFZ5ekFGQmdNclpYQXdFREVPTUF3R0ExVUUKQ2hNRmRHRnNiM013SGhjTk1qVXhNakkzTWpNeU5UVTNXaGNOTXpVeE1qSTFNak15TlRVM1dqQVFNUTR3REFZRApWUVFLRXdWMFlXeHZjekFxTUFVR0F5dGxjQU1oQVBLMlRCTm5nWlhkRHRDQjBQRXprV0JxNW4zUk0zN0w3c1N1CkVrMGkveGRYbzJFd1h6QU9CZ05WSFE4QkFmOEVCQU1DQW9Rd0hRWURWUjBsQkJZd0ZBWUlLd1lCQlFVSEF3RUcKQ0NzR0FRVUZCd01DTUE4R0ExVWRFd0VCL3dRRk1BTUJBZjh3SFFZRFZSME9CQllFRkxFS0lGTWRTR09pZ09LaQozd3kzR0tWMGp2RDVNQVVHQXl0bGNBTkJBSmlXMEJqNGlaUHpwY2ZWWkhKWXk3dXphOWovOTBIZFJJcHpkdkwzCnc4U1RBcWs2emh0bFoyMVhEWlY1Y05vTWZpc0o0eC8zMzg1MXB6WTN6NHZBYVFvPQotLS0tLUVORCBDRVJUSUZJQ0FURS0tLS0tCg== + key: LS0tLS1CRUdJTiBFRDI1NTE5IFBSSVZBVEUgS0VZLS0tLS0KTUM0Q0FRQXdCUVlESzJWd0JDSUVJT0xneGYyN041VXhnUStER3NoZU04dThzdnlCbE8vUmRMYUpETEFHOEF3TAotLS0tLUVORCBFRDI1NTE5IFBSSVZBVEUgS0VZLS0tLS0K + certSANs: [] + kubelet: + image: ghcr.io/siderolabs/kubelet:v1.35.0 + extraArgs: + cloud-provider: external + extraMounts: + - destination: /var/lib/kubelet/plugins + type: bind + source: /var/lib/kubelet/plugins + options: + - bind + - rshared + - rw + defaultRuntimeSeccompProfileEnabled: true + disableManifestsDirectory: true + network: + interfaces: + - interface: eth0 + dhcp: true + - interface: eth1 + dhcp: false + install: + disk: /dev/sda + image: factory.talos.dev/installer/959b38c028569ff2f710c3cfcb3f90d4015282b278f020bb58cf1bda1f9ef93a:v1.12.0 + wipe: false + grubUseUKICmdline: true + files: + - content: tskey-auth-k6cryUGtC521CNTRL-vnjxfuqSqs2Es4kX2SG1s2p3btRizMiG + permissions: 0o600 + path: /var/etc/tailscale/auth.key + op: create + - content: 10.0.0.0/24 + permissions: 0o600 + path: /var/etc/tailscale/routes + op: create + - content: --accept-routes --advertise-tags=tag:k8s-cp + permissions: 0o600 + path: /var/etc/tailscale/args + op: create + features: + diskQuotaSupport: true + kubePrism: + enabled: true + port: 7445 + hostDNS: + enabled: true + forwardKubeDNSToHost: true + nodeLabels: + node.kubernetes.io/exclude-from-external-load-balancers: "" +cluster: + id: eKSkTfDUW0U4if1QcK9otzZnNktorUsvnndBrHM4WBE= + secret: UumfthEFQUDRssdtWbbVezTJJZOtIIw3Db6f342SwW4= + controlPlane: + endpoint: https://10.0.0.101:6443 + clusterName: vntx + network: + dnsDomain: cluster.local + podSubnets: + - 10.244.0.0/16 + serviceSubnets: + - 10.96.0.0/12 + token: 71gr3x.96za7btksx23r8bk + secretboxEncryptionSecret: 1+h+VmWKw3PPspmZ/+u27nhznTt8lRBd9RQQuepZ5/E= + ca: + crt: LS0tLS1CRUdJTiBDRVJUSUZJQ0FURS0tLS0tCk1JSUJpakNDQVMrZ0F3SUJBZ0lRVUxsZy9jbEovUkRzVFo1WHNvR0I3VEFLQmdncWhrak9QUVFEQWpBVk1STXcKRVFZRFZRUUtFd3ByZFdKbGNtNWxkR1Z6TUI0WERUSTFNVEl5TnpJek1qVTFOMW9YRFRNMU1USXlOVEl6TWpVMQpOMW93RlRFVE1CRUdBMVVFQ2hNS2EzVmlaWEp1WlhSbGN6QlpNQk1HQnlxR1NNNDlBZ0VHQ0NxR1NNNDlBd0VICkEwSUFCQ2xSVkxiQThpNTJjWUo2bnRRR2lpRnVTRnhVVnphMDA0UDhwM3VwK295SXFPWldJL3llSzY0VU9ueUkKeUF6YzhySXcxeTRjZGYyc1Y4OHhlczUvMzRhallUQmZNQTRHQTFVZER3RUIvd1FFQXdJQ2hEQWRCZ05WSFNVRQpGakFVQmdnckJnRUZCUWNEQVFZSUt3WUJCUVVIQXdJd0R3WURWUjBUQVFIL0JBVXdBd0VCL3pBZEJnTlZIUTRFCkZnUVVuVndjRnRKSHFRV0JuYk9ld3FlcCthUFByTnd3Q2dZSUtvWkl6ajBFQXdJRFNRQXdSZ0loQUlZTnFZaHUKNjNpQy9kMzUzQTFTeUhCN2lMWCtSQ1V2R2cza3BtQW1ybG5pQWlFQTdsSURuaElyUUJUMHNQa29aRHFIYWdJTgphZjRsTEhnbllaTUR3d0FVM3JFPQotLS0tLUVORCBDRVJUSUZJQ0FURS0tLS0tCg== + key: LS0tLS1CRUdJTiBFQyBQUklWQVRFIEtFWS0tLS0tCk1IY0NBUUVFSUpyNlRETEhtRk1aT1RJWXpIWmxNOS9tbTVYZ0l0cWowMEROMzk3Qk9uOEpvQW9HQ0NxR1NNNDkKQXdFSG9VUURRZ0FFS1ZGVXRzRHlMblp4Z25xZTFBYUtJVzVJWEZSWE5yVFRnL3luZTZuNmpJaW81bFlqL0o0cgpyaFE2ZklqSUROenlzakRYTGh4MS9heFh6ekY2em4vZmhnPT0KLS0tLS1FTkQgRUMgUFJJVkFURSBLRVktLS0tLQo= + aggregatorCA: + crt: LS0tLS1CRUdJTiBDRVJUSUZJQ0FURS0tLS0tCk1JSUJYekNDQVFhZ0F3SUJBZ0lSQUtGQ1hXS24vTnR4eVBuNmxYZjU4R2N3Q2dZSUtvWkl6ajBFQXdJd0FEQWUKRncweU5URXlNamN5TXpJMU5UZGFGdzB6TlRFeU1qVXlNekkxTlRkYU1BQXdXVEFUQmdjcWhrak9QUUlCQmdncQpoa2pPUFFNQkJ3TkNBQVMwMmptRnFCWU1hSURHeVRQWGNhTjQ2UTRBdCtTLzFob0lqd1QveHhZZUowVDJNeDh1ClRVSWQzNjVKT1dSK2FQS2dWdUkySVZpKzZDNXJOcnBSSnhES28yRXdYekFPQmdOVkhROEJBZjhFQkFNQ0FvUXcKSFFZRFZSMGxCQll3RkFZSUt3WUJCUVVIQXdFR0NDc0dBUVVGQndNQ01BOEdBMVVkRXdFQi93UUZNQU1CQWY4dwpIUVlEVlIwT0JCWUVGTXFxVnowdDVaaERQVTdzcS9hdUxKcWxjMVlkTUFvR0NDcUdTTTQ5QkFNQ0EwY0FNRVFDCklBdEI4L0hpSS9RakVEVjFiV29DZ1M1TkdtbDNzdUFTRGtUbkZjK2F3TmlEQWlBNzlPeHVJeVl1VFgyVUxvQlQKZWRXbDdEZ0Y0N3htTnM2OTNGcThLeXRGc0E9PQotLS0tLUVORCBDRVJUSUZJQ0FURS0tLS0tCg== + key: LS0tLS1CRUdJTiBFQyBQUklWQVRFIEtFWS0tLS0tCk1IY0NBUUVFSU9EVVVzMklrazhaeGowRDNRQVBLeTlpTCtTSVNaZGhOZjMrdVBqOHNudVRvQW9HQ0NxR1NNNDkKQXdFSG9VUURRZ0FFdE5vNWhhZ1dER2lBeHNrejEzR2plT2tPQUxma3Y5WWFDSThFLzhjV0hpZEU5ak1mTGsxQwpIZCt1U1Rsa2ZtanlvRmJpTmlGWXZ1Z3VhemE2VVNjUXlnPT0KLS0tLS1FTkQgRUMgUFJJVkFURSBLRVktLS0tLQo= + serviceAccount: + key: LS0tLS1CRUdJTiBSU0EgUFJJVkFURSBLRVktLS0tLQpNSUlKS1FJQkFBS0NBZ0VBM0gzV1hzZVU4clpGdzhkaUhIbzB3aWFQdnV3N3VpblJ3MS9xbnB6VldjVGRlWUcrCnJlQ0dMek1vNWlzaHBQT3N2WVd5UEVoZlVyZ01ldTY3cFlTMFNxSmtGcnJtY3lrQUNybHFtaE54ZzVBazZZcTIKOWhPeUphR0tKOVkrdEUzNmFjUjBIWTJ4UEV3K0lKbEdIVUpLNSs2RUsxUXVjYTF5TXpLc0pOM1VrSDVzNXpXeApEbCtSdHJLNklXdEsxYjZ5M213SmtaRTJIYktxUUdXdWxONDZ6M1gzTXJLNk9POVhHNTJ2S3dINFBzdHFHVDc5Ck92dlI3b21yaVF6OUJUclhSYXlqRGp4MEl3NGVTVVJ4QkFsRFlsZDlqd2E3aXd1NHU5bldlazYyRjM3S3VMTE4KYlpWWlQ4WjJqQlJ5WGp5ZXdkTkFpL0Z4bElNSWtSdjE0VVV4M3NEdDhycGh2b2xERDBXVGlRcTNyQkNSUUNrVQpldWpZUmloaDNnQUI4QTN5dGJrZGJSNlgrQ2IrR21NMFVycmgwb2RnWDg0dkdrY1lhR1NrSnRKSEttSlNDUGN3CkJYa29taHd2dDJ4UzVEQTM4aUhPWDc5OTgrQzdJQWpyWnpka3ZLSXZIc1grSklvYTF4d0ZiclJTOUIrNUNDMXQKdnVFd1pvVXlTWEdDOWh0bkd5M1ZjcUdsbFBUQ3NEaForZkpXNGRNazE2cldaVW5uSmM3ek1Fa2pleVJzUERnZAptM215Z0w1RDd2S2w1SnBGNWphM2wzOEt4OC9xKzU3OFY2RllSblhvUElGS25TbGFLNmorKzdmeFZyMFdPNlk4CjRKVnFyUG5LYVVvQ0I0WTFrZGlqSkI1TndVRjVWazdqNVUyWThYRk1vWjRtNGdWQ29jS3laUDlIYXlNQ0F3RUEKQVFLQ0FnQUl3bGovUitkell1bFBsejZmQ2YzSmpyV2NMSTlNM0hkd1R3R25qbXh0VmdSRVhQS2h2cThsOWQ3VQprZmNTc2ZsMVIvZm1MQ3ZaUWVXQkJyWGVvL0J6bkpMa1VrVndZcnNWTWZ0NXBuY1dkbVg0L3lFNGtseTc0UGgzCmo2dkxCdVFCU3FRZ1BtNUJpbmZYWEs5cjN5UFJwZWlMUGh0Z09iYzFNSGlsT0VqRytyYkIwcUMzaFBWcGNCMHoKMGFyVjVlNytKZ1dWU2xML2lBYjZhdSt1QzB3RHpOaG1vN0lCTEFUbVhIUEdmaHdLQnBPdThCRW9SRE81U2EvTwpVSDFHdFdreTQrSlFZUGR1SXhQeDdpMmRMdThGMjVycDBTY25KVzZQeTk0WTJzS2lHVS9kV1lFT3J1V3U1Ui8xCmZhUnplTzRIbmloTXh1a3ZzS3JvOU5ibVBaVDNCUXR2SGl4ZlVNU2pmTXZFcUorNDhpdlA1RTNiYUJHRk5Mc3oKbUZXZW91MFEzVzNTMU50RkQvWnIybFJpT3VrVzhLLytBSm1PL210RWd2NG1UK3pHa05BUGhPT3lQcUlTakgxTAp1WTY3c08wRGlJWmJ1REdmZDQ2YXN3bHBZQis1Z0ZMZGxONDNJcGRxZG5GMFdtbjkybXk3cVluVVhkSkJENnZNCm5TWGJJOTZZOSt6K3V6citTZWMzeWhEckd6a1c1NWJ4VHJqb1FMZ2d6RDRVSWEyMm1ueUFOb3UrZzkyU09RSnEKb0hmWGZoeDdJeEZyM2h2V3ZaVVlYNit6bndUZTBKeVI0cy9NaXZxM2NIVERzV1A2NXBMd3VNQXRMMW1qWHNOcgp4aGhzZDQrNkJYb0R1OGl1V1NFRDlndlFIbVFlN3p3azVEVlNPbXJOTHlZTnZ3Y0U1UUtDQVFFQTYxaWR3VUp0CmJEMUlzQ1RBaVJnaFEvT0oxY3cwcmNqSDhGcGRNaFg1MHc2NUJqcmk5OEU5eDNkK2JpZVA3eXk5cVNMcnN5dzIKSDNteTJXOEZOSHdUUnJCT2NnQVg0cWhSa205Y0tBSlhGS0xVbGY4TlJocWJrR3RyVnMybEdDdXBEZHJxN2RpTApHRGdxY2gxbHpXR1d1UlQyOWZDRXRzZWVyd2NFemtXYTE0MDRYWEIyTi9EK0FHbVB2Mmp2dEFOSml0ekFuL0pWCnQ4NnZLVyttbWlxNVFQNlZHZjFtVmZTMGlSQy9TVzJMditGR3J2ZmRsNHN4WXJONnoweVdZSUZqK2J3aVNYblIKZXhTKzYyUUtleGJCalZwa2gzRnJTNWNsZWJ1ajg0aWVEaVQ1ZDFsTTNhaHlpSjRJYk1IaVJyeG1wSFNDVmkrUQorOHpSbHRwcGI2eko5UUtDQVFFQTc5ZDkwWDhqeFJKV015MUFWTDlrMnN5YjZacG9XN2FHL3AwNTlHVi80dXBNCi9DdTRXVVdOajdWdW1sRmppUFdtT0hhMkxIVnZmVW5DY3M1WTYxRTJVWm9mNXcxLzZ5R2ZwdEtzZ0V5eElUZGMKMFRFV0pPTy9QeVZabEhXR2xJVVNsMlBsTlFuclh6OCsvY29RZklSS29OZmd6K1p5NHdLdFpMWDdpUDBlaGt4YgphWmhNWWF0azNhN0FyQURPRFZiZ1Z3dkdjaER6Vm5oNjc4TzF3a0p0WjJ6TUlrOGF4cy9WR1VMQ0NRdURTV2pICkdsb2IvQlA3TERBdWxKVlN3ajNOY2NLK01ZMnpSSXEwcHNYWkxsVlJicTRZSlhFbUxoRFEzUXhvUklLQVZQM08KWkZWR2lDT3lXU1dJclprZkZHaEkrNlFram1YazJmYmNPTE9QNGUyNXR3S0NBUUVBd3ZKcDR0OXlvcGwxTDZ1Ugo3VDRXdUNIeFNDOWFaNllNc0xVNXc3WmVkZzBaQ09jWWdXQUtHOE9JOEJoSGF6aWxkb2hkczlKb2x0UUphWUZFClQ0Q0R1eWRxSTVhZU1udDQ3cExlUktvRGxpMTNhVFNYdXoxcEpVMUY0ZWFBM2krMFhxeTdzLytPNEtZTnl1ODkKRjg3QnVsaDZaYWt4VmZLdktJN28xVERsSGE1MlJUaFdST3FVaktUa2xRcUluSldvZ3FWdnprNC80UDBOTFlhMQorN2h1TWo5d0pOSTV4ZlBvNUMwQ053SE9KRWlvYzJFUXBtcC9veUhIRmhaNzdqN2dJTXRObjQyUUQ2TlVyc24wCndKZE9CeGdjYy9Gb2pub0thZmNielN5YXVGNjZZcm1QS1lGU05vYXB0ZVU0MloxUWJPT3gzMUNSaVhMVkhsK1gKdlJEbFRRS0NBUUJBNkVpY2taUFVtWW5LZjh5Ukl0cmdlODhXQVR1TTFuRGlKeHF3RVdmeXVRWHNtTWhqSUhlWApGTHJCK0pTL1UvdVAvRkNBNTZjc2VQR3VzRGxRTmNKRmd6aHZCekEvS2ZKUzYyRFR0KzJYMTZ1KzBWSDAyYzNBCkFST2xJY2t5R0hGWGx5bEltVTZoa0RRejZxTmJqMUhEQmFsSm1rd3RNMlJKaFJaMWxFcldmWU9mcUIvRHJ1YTEKTjczY3pycjAwVFlWV0pKei9ESmVqR3g0eHJaQnhFaG5YUUpCcHJiUVp4NThuNXh6WmpJNWc2bWVjQlJ5dTlXVgp0OVJqVWFYNyswM0dJN1hsSXp3SXFLRUxJVEFOWWZtUHduMjJaRkM0MXNRdmpsUUpkbWZVbUh0cW04bGl2b1pkCnFkSzdhRjBJNE5BZmllUjZ4UWlTRkVTMDg2TlV1VWt4QW9JQkFRRG9WL0pJRlNEejl3Z3dneUhhdmdwSnR0UGkKNWZBeEpZaktZbUtsLzdpZUdkZ0pzN1dwR3dxNXlQZFVVRE1yMnNKUDBGWDhEZFJTSktWLzExRzMvaklTL1JyQQpwcDVsS2hGbEFncVBvZ1EvL0IzTVBiNXZiNTBSMExrNGJtVWVYcUVhMkJBSTlmc0R3WEFZbFhsMnJOT0drdEdSCnJZd1BEdHlhbnI1d0grVEtoYjdqODdWN2Z1TWpRcU5SK21TQVJqZXpvRHNQdnJvUHB0d1o0RnBSOTNCUXJqUGoKRWF6Z1UvbHlSRkVCNklISFhvbWFaR1ExYlY1TG85ZTlUZGp6VFpiT2tJMUFsL3B6cWx5WlpzdnU5RnFURUdUbwpRckt6Nm9xeFJyR1lhUVNJbGpydWhPajdiWUVPeGp2VnFEdmNIaGNxV1paN0h5VWNjS2gzNFZReWhCdTQKLS0tLS1FTkQgUlNBIFBSSVZBVEUgS0VZLS0tLS0K + apiServer: + image: registry.k8s.io/kube-apiserver:v1.35.0 + admissionControl: + - name: PodSecurity + configuration: + apiVersion: pod-security.admission.config.k8s.io/v1alpha1 + defaults: + audit: restricted + audit-version: latest + enforce: baseline + enforce-version: latest + warn: restricted + warn-version: latest + exemptions: + namespaces: + - kube-system + runtimeClasses: [] + usernames: [] + kind: PodSecurityConfiguration + auditPolicy: + apiVersion: audit.k8s.io/v1 + kind: Policy + rules: + - level: Metadata + controllerManager: + image: registry.k8s.io/kube-controller-manager:v1.35.0 + proxy: + image: registry.k8s.io/kube-proxy:v1.35.0 + scheduler: + image: registry.k8s.io/kube-scheduler:v1.35.0 + discovery: + enabled: true + registries: + kubernetes: + disabled: true + service: {} + etcd: + ca: + crt: LS0tLS1CRUdJTiBDRVJUSUZJQ0FURS0tLS0tCk1JSUJmVENDQVNPZ0F3SUJBZ0lRY1hQekZ3N2lYdnlnY2FVMGlUQ3lGekFLQmdncWhrak9QUVFEQWpBUE1RMHcKQ3dZRFZRUUtFd1JsZEdOa01CNFhEVEkxTVRJeU56SXpNalUxTjFvWERUTTFNVEl5TlRJek1qVTFOMW93RHpFTgpNQXNHQTFVRUNoTUVaWFJqWkRCWk1CTUdCeXFHU000OUFnRUdDQ3FHU000OUF3RUhBMElBQlBpREhoWTkzT1FFClpaS2x1L1M3NVBnRmlvNks5SjV1RUZwNk12c3N4NnYzWld6RXJ2clBoNW53QkFqVFFOOUdodTRmQ1dXbXdsQmgKVVhIU09RcHh5OStqWVRCZk1BNEdBMVVkRHdFQi93UUVBd0lDaERBZEJnTlZIU1VFRmpBVUJnZ3JCZ0VGQlFjRApBUVlJS3dZQkJRVUhBd0l3RHdZRFZSMFRBUUgvQkFVd0F3RUIvekFkQmdOVkhRNEVGZ1FVYnc1N01IV1JvWnYyClZ6UndZNGIyY3c1VGw3c3dDZ1lJS29aSXpqMEVBd0lEU0FBd1JRSWdHR1BOZmNzT2M0ajlFblNIbkhRV2dydEQKbEdZWitpZ3JKQnZSWGFSa1FRd0NJUUNOeUlRVU9reWx5U0Vpc1ZyNzFhR3hTRHJ5UFgwZlRuMEdZM25qalpkQQpaUT09Ci0tLS0tRU5EIENFUlRJRklDQVRFLS0tLS0K + key: LS0tLS1CRUdJTiBFQyBQUklWQVRFIEtFWS0tLS0tCk1IY0NBUUVFSUtpazBDeFdObEx6ZWJaY2kwSVYyUHNqOGRoRis5L0Nsb3JXbzAySUdRb1BvQW9HQ0NxR1NNNDkKQXdFSG9VUURRZ0FFK0lNZUZqM2M1QVJsa3FXNzlMdmsrQVdLam9yMG5tNFFXbm95K3l6SHEvZGxiTVN1K3MrSAptZkFFQ05OQTMwYUc3aDhKWmFiQ1VHRlJjZEk1Q25ITDN3PT0KLS0tLS1FTkQgRUMgUFJJVkFURSBLRVktLS0tLQo= +--- +apiVersion: v1alpha1 +kind: HostnameConfig +auto: stable diff --git a/talos/nodes/cp-2.yaml b/talos/nodes/cp-2.yaml new file mode 100644 index 0000000..09f91e5 --- /dev/null +++ b/talos/nodes/cp-2.yaml @@ -0,0 +1,124 @@ +version: v1alpha1 +debug: false +persist: true +machine: + type: controlplane + token: gwdkoe.5gbblli1cvxv1axx + ca: + crt: LS0tLS1CRUdJTiBDRVJUSUZJQ0FURS0tLS0tCk1JSUJQekNCOHFBREFnRUNBaEVBbk5ucllpRDF4bjZaaGVFY0hvTFZ5ekFGQmdNclpYQXdFREVPTUF3R0ExVUUKQ2hNRmRHRnNiM013SGhjTk1qVXhNakkzTWpNeU5UVTNXaGNOTXpVeE1qSTFNak15TlRVM1dqQVFNUTR3REFZRApWUVFLRXdWMFlXeHZjekFxTUFVR0F5dGxjQU1oQVBLMlRCTm5nWlhkRHRDQjBQRXprV0JxNW4zUk0zN0w3c1N1CkVrMGkveGRYbzJFd1h6QU9CZ05WSFE4QkFmOEVCQU1DQW9Rd0hRWURWUjBsQkJZd0ZBWUlLd1lCQlFVSEF3RUcKQ0NzR0FRVUZCd01DTUE4R0ExVWRFd0VCL3dRRk1BTUJBZjh3SFFZRFZSME9CQllFRkxFS0lGTWRTR09pZ09LaQozd3kzR0tWMGp2RDVNQVVHQXl0bGNBTkJBSmlXMEJqNGlaUHpwY2ZWWkhKWXk3dXphOWovOTBIZFJJcHpkdkwzCnc4U1RBcWs2emh0bFoyMVhEWlY1Y05vTWZpc0o0eC8zMzg1MXB6WTN6NHZBYVFvPQotLS0tLUVORCBDRVJUSUZJQ0FURS0tLS0tCg== + key: LS0tLS1CRUdJTiBFRDI1NTE5IFBSSVZBVEUgS0VZLS0tLS0KTUM0Q0FRQXdCUVlESzJWd0JDSUVJT0xneGYyN041VXhnUStER3NoZU04dThzdnlCbE8vUmRMYUpETEFHOEF3TAotLS0tLUVORCBFRDI1NTE5IFBSSVZBVEUgS0VZLS0tLS0K + certSANs: [] + kubelet: + image: ghcr.io/siderolabs/kubelet:v1.35.0 + extraArgs: + cloud-provider: external + extraMounts: + - destination: /var/lib/kubelet/plugins + type: bind + source: /var/lib/kubelet/plugins + options: + - bind + - rshared + - rw + defaultRuntimeSeccompProfileEnabled: true + disableManifestsDirectory: true + network: + interfaces: + - interface: eth0 + dhcp: true + - interface: eth1 + dhcp: false + install: + disk: /dev/sda + image: factory.talos.dev/installer/959b38c028569ff2f710c3cfcb3f90d4015282b278f020bb58cf1bda1f9ef93a:v1.12.0 + wipe: false + grubUseUKICmdline: true + files: + - content: tskey-auth-k6cryUGtC521CNTRL-vnjxfuqSqs2Es4kX2SG1s2p3btRizMiG + permissions: 0o600 + path: /var/etc/tailscale/auth.key + op: create + - content: 10.0.0.0/24 + permissions: 0o600 + path: /var/etc/tailscale/routes + op: create + - content: --accept-routes --advertise-tags=tag:k8s-cp + permissions: 0o600 + path: /var/etc/tailscale/args + op: create + features: + diskQuotaSupport: true + kubePrism: + enabled: true + port: 7445 + hostDNS: + enabled: true + forwardKubeDNSToHost: true + nodeLabels: + node.kubernetes.io/exclude-from-external-load-balancers: "" +cluster: + id: eKSkTfDUW0U4if1QcK9otzZnNktorUsvnndBrHM4WBE= + secret: UumfthEFQUDRssdtWbbVezTJJZOtIIw3Db6f342SwW4= + controlPlane: + endpoint: https://10.0.0.101:6443 + clusterName: vntx + network: + dnsDomain: cluster.local + podSubnets: + - 10.244.0.0/16 + serviceSubnets: + - 10.96.0.0/12 + token: 71gr3x.96za7btksx23r8bk + secretboxEncryptionSecret: 1+h+VmWKw3PPspmZ/+u27nhznTt8lRBd9RQQuepZ5/E= + ca: + crt: LS0tLS1CRUdJTiBDRVJUSUZJQ0FURS0tLS0tCk1JSUJpakNDQVMrZ0F3SUJBZ0lRVUxsZy9jbEovUkRzVFo1WHNvR0I3VEFLQmdncWhrak9QUVFEQWpBVk1STXcKRVFZRFZRUUtFd3ByZFdKbGNtNWxkR1Z6TUI0WERUSTFNVEl5TnpJek1qVTFOMW9YRFRNMU1USXlOVEl6TWpVMQpOMW93RlRFVE1CRUdBMVVFQ2hNS2EzVmlaWEp1WlhSbGN6QlpNQk1HQnlxR1NNNDlBZ0VHQ0NxR1NNNDlBd0VICkEwSUFCQ2xSVkxiQThpNTJjWUo2bnRRR2lpRnVTRnhVVnphMDA0UDhwM3VwK295SXFPWldJL3llSzY0VU9ueUkKeUF6YzhySXcxeTRjZGYyc1Y4OHhlczUvMzRhallUQmZNQTRHQTFVZER3RUIvd1FFQXdJQ2hEQWRCZ05WSFNVRQpGakFVQmdnckJnRUZCUWNEQVFZSUt3WUJCUVVIQXdJd0R3WURWUjBUQVFIL0JBVXdBd0VCL3pBZEJnTlZIUTRFCkZnUVVuVndjRnRKSHFRV0JuYk9ld3FlcCthUFByTnd3Q2dZSUtvWkl6ajBFQXdJRFNRQXdSZ0loQUlZTnFZaHUKNjNpQy9kMzUzQTFTeUhCN2lMWCtSQ1V2R2cza3BtQW1ybG5pQWlFQTdsSURuaElyUUJUMHNQa29aRHFIYWdJTgphZjRsTEhnbllaTUR3d0FVM3JFPQotLS0tLUVORCBDRVJUSUZJQ0FURS0tLS0tCg== + key: LS0tLS1CRUdJTiBFQyBQUklWQVRFIEtFWS0tLS0tCk1IY0NBUUVFSUpyNlRETEhtRk1aT1RJWXpIWmxNOS9tbTVYZ0l0cWowMEROMzk3Qk9uOEpvQW9HQ0NxR1NNNDkKQXdFSG9VUURRZ0FFS1ZGVXRzRHlMblp4Z25xZTFBYUtJVzVJWEZSWE5yVFRnL3luZTZuNmpJaW81bFlqL0o0cgpyaFE2ZklqSUROenlzakRYTGh4MS9heFh6ekY2em4vZmhnPT0KLS0tLS1FTkQgRUMgUFJJVkFURSBLRVktLS0tLQo= + aggregatorCA: + crt: LS0tLS1CRUdJTiBDRVJUSUZJQ0FURS0tLS0tCk1JSUJYekNDQVFhZ0F3SUJBZ0lSQUtGQ1hXS24vTnR4eVBuNmxYZjU4R2N3Q2dZSUtvWkl6ajBFQXdJd0FEQWUKRncweU5URXlNamN5TXpJMU5UZGFGdzB6TlRFeU1qVXlNekkxTlRkYU1BQXdXVEFUQmdjcWhrak9QUUlCQmdncQpoa2pPUFFNQkJ3TkNBQVMwMmptRnFCWU1hSURHeVRQWGNhTjQ2UTRBdCtTLzFob0lqd1QveHhZZUowVDJNeDh1ClRVSWQzNjVKT1dSK2FQS2dWdUkySVZpKzZDNXJOcnBSSnhES28yRXdYekFPQmdOVkhROEJBZjhFQkFNQ0FvUXcKSFFZRFZSMGxCQll3RkFZSUt3WUJCUVVIQXdFR0NDc0dBUVVGQndNQ01BOEdBMVVkRXdFQi93UUZNQU1CQWY4dwpIUVlEVlIwT0JCWUVGTXFxVnowdDVaaERQVTdzcS9hdUxKcWxjMVlkTUFvR0NDcUdTTTQ5QkFNQ0EwY0FNRVFDCklBdEI4L0hpSS9RakVEVjFiV29DZ1M1TkdtbDNzdUFTRGtUbkZjK2F3TmlEQWlBNzlPeHVJeVl1VFgyVUxvQlQKZWRXbDdEZ0Y0N3htTnM2OTNGcThLeXRGc0E9PQotLS0tLUVORCBDRVJUSUZJQ0FURS0tLS0tCg== + key: LS0tLS1CRUdJTiBFQyBQUklWQVRFIEtFWS0tLS0tCk1IY0NBUUVFSU9EVVVzMklrazhaeGowRDNRQVBLeTlpTCtTSVNaZGhOZjMrdVBqOHNudVRvQW9HQ0NxR1NNNDkKQXdFSG9VUURRZ0FFdE5vNWhhZ1dER2lBeHNrejEzR2plT2tPQUxma3Y5WWFDSThFLzhjV0hpZEU5ak1mTGsxQwpIZCt1U1Rsa2ZtanlvRmJpTmlGWXZ1Z3VhemE2VVNjUXlnPT0KLS0tLS1FTkQgRUMgUFJJVkFURSBLRVktLS0tLQo= + serviceAccount: + key: LS0tLS1CRUdJTiBSU0EgUFJJVkFURSBLRVktLS0tLQpNSUlKS1FJQkFBS0NBZ0VBM0gzV1hzZVU4clpGdzhkaUhIbzB3aWFQdnV3N3VpblJ3MS9xbnB6VldjVGRlWUcrCnJlQ0dMek1vNWlzaHBQT3N2WVd5UEVoZlVyZ01ldTY3cFlTMFNxSmtGcnJtY3lrQUNybHFtaE54ZzVBazZZcTIKOWhPeUphR0tKOVkrdEUzNmFjUjBIWTJ4UEV3K0lKbEdIVUpLNSs2RUsxUXVjYTF5TXpLc0pOM1VrSDVzNXpXeApEbCtSdHJLNklXdEsxYjZ5M213SmtaRTJIYktxUUdXdWxONDZ6M1gzTXJLNk9POVhHNTJ2S3dINFBzdHFHVDc5Ck92dlI3b21yaVF6OUJUclhSYXlqRGp4MEl3NGVTVVJ4QkFsRFlsZDlqd2E3aXd1NHU5bldlazYyRjM3S3VMTE4KYlpWWlQ4WjJqQlJ5WGp5ZXdkTkFpL0Z4bElNSWtSdjE0VVV4M3NEdDhycGh2b2xERDBXVGlRcTNyQkNSUUNrVQpldWpZUmloaDNnQUI4QTN5dGJrZGJSNlgrQ2IrR21NMFVycmgwb2RnWDg0dkdrY1lhR1NrSnRKSEttSlNDUGN3CkJYa29taHd2dDJ4UzVEQTM4aUhPWDc5OTgrQzdJQWpyWnpka3ZLSXZIc1grSklvYTF4d0ZiclJTOUIrNUNDMXQKdnVFd1pvVXlTWEdDOWh0bkd5M1ZjcUdsbFBUQ3NEaForZkpXNGRNazE2cldaVW5uSmM3ek1Fa2pleVJzUERnZAptM215Z0w1RDd2S2w1SnBGNWphM2wzOEt4OC9xKzU3OFY2RllSblhvUElGS25TbGFLNmorKzdmeFZyMFdPNlk4CjRKVnFyUG5LYVVvQ0I0WTFrZGlqSkI1TndVRjVWazdqNVUyWThYRk1vWjRtNGdWQ29jS3laUDlIYXlNQ0F3RUEKQVFLQ0FnQUl3bGovUitkell1bFBsejZmQ2YzSmpyV2NMSTlNM0hkd1R3R25qbXh0VmdSRVhQS2h2cThsOWQ3VQprZmNTc2ZsMVIvZm1MQ3ZaUWVXQkJyWGVvL0J6bkpMa1VrVndZcnNWTWZ0NXBuY1dkbVg0L3lFNGtseTc0UGgzCmo2dkxCdVFCU3FRZ1BtNUJpbmZYWEs5cjN5UFJwZWlMUGh0Z09iYzFNSGlsT0VqRytyYkIwcUMzaFBWcGNCMHoKMGFyVjVlNytKZ1dWU2xML2lBYjZhdSt1QzB3RHpOaG1vN0lCTEFUbVhIUEdmaHdLQnBPdThCRW9SRE81U2EvTwpVSDFHdFdreTQrSlFZUGR1SXhQeDdpMmRMdThGMjVycDBTY25KVzZQeTk0WTJzS2lHVS9kV1lFT3J1V3U1Ui8xCmZhUnplTzRIbmloTXh1a3ZzS3JvOU5ibVBaVDNCUXR2SGl4ZlVNU2pmTXZFcUorNDhpdlA1RTNiYUJHRk5Mc3oKbUZXZW91MFEzVzNTMU50RkQvWnIybFJpT3VrVzhLLytBSm1PL210RWd2NG1UK3pHa05BUGhPT3lQcUlTakgxTAp1WTY3c08wRGlJWmJ1REdmZDQ2YXN3bHBZQis1Z0ZMZGxONDNJcGRxZG5GMFdtbjkybXk3cVluVVhkSkJENnZNCm5TWGJJOTZZOSt6K3V6citTZWMzeWhEckd6a1c1NWJ4VHJqb1FMZ2d6RDRVSWEyMm1ueUFOb3UrZzkyU09RSnEKb0hmWGZoeDdJeEZyM2h2V3ZaVVlYNit6bndUZTBKeVI0cy9NaXZxM2NIVERzV1A2NXBMd3VNQXRMMW1qWHNOcgp4aGhzZDQrNkJYb0R1OGl1V1NFRDlndlFIbVFlN3p3azVEVlNPbXJOTHlZTnZ3Y0U1UUtDQVFFQTYxaWR3VUp0CmJEMUlzQ1RBaVJnaFEvT0oxY3cwcmNqSDhGcGRNaFg1MHc2NUJqcmk5OEU5eDNkK2JpZVA3eXk5cVNMcnN5dzIKSDNteTJXOEZOSHdUUnJCT2NnQVg0cWhSa205Y0tBSlhGS0xVbGY4TlJocWJrR3RyVnMybEdDdXBEZHJxN2RpTApHRGdxY2gxbHpXR1d1UlQyOWZDRXRzZWVyd2NFemtXYTE0MDRYWEIyTi9EK0FHbVB2Mmp2dEFOSml0ekFuL0pWCnQ4NnZLVyttbWlxNVFQNlZHZjFtVmZTMGlSQy9TVzJMditGR3J2ZmRsNHN4WXJONnoweVdZSUZqK2J3aVNYblIKZXhTKzYyUUtleGJCalZwa2gzRnJTNWNsZWJ1ajg0aWVEaVQ1ZDFsTTNhaHlpSjRJYk1IaVJyeG1wSFNDVmkrUQorOHpSbHRwcGI2eko5UUtDQVFFQTc5ZDkwWDhqeFJKV015MUFWTDlrMnN5YjZacG9XN2FHL3AwNTlHVi80dXBNCi9DdTRXVVdOajdWdW1sRmppUFdtT0hhMkxIVnZmVW5DY3M1WTYxRTJVWm9mNXcxLzZ5R2ZwdEtzZ0V5eElUZGMKMFRFV0pPTy9QeVZabEhXR2xJVVNsMlBsTlFuclh6OCsvY29RZklSS29OZmd6K1p5NHdLdFpMWDdpUDBlaGt4YgphWmhNWWF0azNhN0FyQURPRFZiZ1Z3dkdjaER6Vm5oNjc4TzF3a0p0WjJ6TUlrOGF4cy9WR1VMQ0NRdURTV2pICkdsb2IvQlA3TERBdWxKVlN3ajNOY2NLK01ZMnpSSXEwcHNYWkxsVlJicTRZSlhFbUxoRFEzUXhvUklLQVZQM08KWkZWR2lDT3lXU1dJclprZkZHaEkrNlFram1YazJmYmNPTE9QNGUyNXR3S0NBUUVBd3ZKcDR0OXlvcGwxTDZ1Ugo3VDRXdUNIeFNDOWFaNllNc0xVNXc3WmVkZzBaQ09jWWdXQUtHOE9JOEJoSGF6aWxkb2hkczlKb2x0UUphWUZFClQ0Q0R1eWRxSTVhZU1udDQ3cExlUktvRGxpMTNhVFNYdXoxcEpVMUY0ZWFBM2krMFhxeTdzLytPNEtZTnl1ODkKRjg3QnVsaDZaYWt4VmZLdktJN28xVERsSGE1MlJUaFdST3FVaktUa2xRcUluSldvZ3FWdnprNC80UDBOTFlhMQorN2h1TWo5d0pOSTV4ZlBvNUMwQ053SE9KRWlvYzJFUXBtcC9veUhIRmhaNzdqN2dJTXRObjQyUUQ2TlVyc24wCndKZE9CeGdjYy9Gb2pub0thZmNielN5YXVGNjZZcm1QS1lGU05vYXB0ZVU0MloxUWJPT3gzMUNSaVhMVkhsK1gKdlJEbFRRS0NBUUJBNkVpY2taUFVtWW5LZjh5Ukl0cmdlODhXQVR1TTFuRGlKeHF3RVdmeXVRWHNtTWhqSUhlWApGTHJCK0pTL1UvdVAvRkNBNTZjc2VQR3VzRGxRTmNKRmd6aHZCekEvS2ZKUzYyRFR0KzJYMTZ1KzBWSDAyYzNBCkFST2xJY2t5R0hGWGx5bEltVTZoa0RRejZxTmJqMUhEQmFsSm1rd3RNMlJKaFJaMWxFcldmWU9mcUIvRHJ1YTEKTjczY3pycjAwVFlWV0pKei9ESmVqR3g0eHJaQnhFaG5YUUpCcHJiUVp4NThuNXh6WmpJNWc2bWVjQlJ5dTlXVgp0OVJqVWFYNyswM0dJN1hsSXp3SXFLRUxJVEFOWWZtUHduMjJaRkM0MXNRdmpsUUpkbWZVbUh0cW04bGl2b1pkCnFkSzdhRjBJNE5BZmllUjZ4UWlTRkVTMDg2TlV1VWt4QW9JQkFRRG9WL0pJRlNEejl3Z3dneUhhdmdwSnR0UGkKNWZBeEpZaktZbUtsLzdpZUdkZ0pzN1dwR3dxNXlQZFVVRE1yMnNKUDBGWDhEZFJTSktWLzExRzMvaklTL1JyQQpwcDVsS2hGbEFncVBvZ1EvL0IzTVBiNXZiNTBSMExrNGJtVWVYcUVhMkJBSTlmc0R3WEFZbFhsMnJOT0drdEdSCnJZd1BEdHlhbnI1d0grVEtoYjdqODdWN2Z1TWpRcU5SK21TQVJqZXpvRHNQdnJvUHB0d1o0RnBSOTNCUXJqUGoKRWF6Z1UvbHlSRkVCNklISFhvbWFaR1ExYlY1TG85ZTlUZGp6VFpiT2tJMUFsL3B6cWx5WlpzdnU5RnFURUdUbwpRckt6Nm9xeFJyR1lhUVNJbGpydWhPajdiWUVPeGp2VnFEdmNIaGNxV1paN0h5VWNjS2gzNFZReWhCdTQKLS0tLS1FTkQgUlNBIFBSSVZBVEUgS0VZLS0tLS0K + apiServer: + image: registry.k8s.io/kube-apiserver:v1.35.0 + admissionControl: + - name: PodSecurity + configuration: + apiVersion: pod-security.admission.config.k8s.io/v1alpha1 + defaults: + audit: restricted + audit-version: latest + enforce: baseline + enforce-version: latest + warn: restricted + warn-version: latest + exemptions: + namespaces: + - kube-system + runtimeClasses: [] + usernames: [] + kind: PodSecurityConfiguration + auditPolicy: + apiVersion: audit.k8s.io/v1 + kind: Policy + rules: + - level: Metadata + controllerManager: + image: registry.k8s.io/kube-controller-manager:v1.35.0 + proxy: + image: registry.k8s.io/kube-proxy:v1.35.0 + scheduler: + image: registry.k8s.io/kube-scheduler:v1.35.0 + discovery: + enabled: true + registries: + kubernetes: + disabled: true + service: {} + etcd: + ca: + crt: LS0tLS1CRUdJTiBDRVJUSUZJQ0FURS0tLS0tCk1JSUJmVENDQVNPZ0F3SUJBZ0lRY1hQekZ3N2lYdnlnY2FVMGlUQ3lGekFLQmdncWhrak9QUVFEQWpBUE1RMHcKQ3dZRFZRUUtFd1JsZEdOa01CNFhEVEkxTVRJeU56SXpNalUxTjFvWERUTTFNVEl5TlRJek1qVTFOMW93RHpFTgpNQXNHQTFVRUNoTUVaWFJqWkRCWk1CTUdCeXFHU000OUFnRUdDQ3FHU000OUF3RUhBMElBQlBpREhoWTkzT1FFClpaS2x1L1M3NVBnRmlvNks5SjV1RUZwNk12c3N4NnYzWld6RXJ2clBoNW53QkFqVFFOOUdodTRmQ1dXbXdsQmgKVVhIU09RcHh5OStqWVRCZk1BNEdBMVVkRHdFQi93UUVBd0lDaERBZEJnTlZIU1VFRmpBVUJnZ3JCZ0VGQlFjRApBUVlJS3dZQkJRVUhBd0l3RHdZRFZSMFRBUUgvQkFVd0F3RUIvekFkQmdOVkhRNEVGZ1FVYnc1N01IV1JvWnYyClZ6UndZNGIyY3c1VGw3c3dDZ1lJS29aSXpqMEVBd0lEU0FBd1JRSWdHR1BOZmNzT2M0ajlFblNIbkhRV2dydEQKbEdZWitpZ3JKQnZSWGFSa1FRd0NJUUNOeUlRVU9reWx5U0Vpc1ZyNzFhR3hTRHJ5UFgwZlRuMEdZM25qalpkQQpaUT09Ci0tLS0tRU5EIENFUlRJRklDQVRFLS0tLS0K + key: LS0tLS1CRUdJTiBFQyBQUklWQVRFIEtFWS0tLS0tCk1IY0NBUUVFSUtpazBDeFdObEx6ZWJaY2kwSVYyUHNqOGRoRis5L0Nsb3JXbzAySUdRb1BvQW9HQ0NxR1NNNDkKQXdFSG9VUURRZ0FFK0lNZUZqM2M1QVJsa3FXNzlMdmsrQVdLam9yMG5tNFFXbm95K3l6SHEvZGxiTVN1K3MrSAptZkFFQ05OQTMwYUc3aDhKWmFiQ1VHRlJjZEk1Q25ITDN3PT0KLS0tLS1FTkQgRUMgUFJJVkFURSBLRVktLS0tLQo= +--- +apiVersion: v1alpha1 +kind: HostnameConfig +auto: stable diff --git a/talos/nodes/cp-3.yaml b/talos/nodes/cp-3.yaml new file mode 100644 index 0000000..09f91e5 --- /dev/null +++ b/talos/nodes/cp-3.yaml @@ -0,0 +1,124 @@ +version: v1alpha1 +debug: false +persist: true +machine: + type: controlplane + token: gwdkoe.5gbblli1cvxv1axx + ca: + crt: LS0tLS1CRUdJTiBDRVJUSUZJQ0FURS0tLS0tCk1JSUJQekNCOHFBREFnRUNBaEVBbk5ucllpRDF4bjZaaGVFY0hvTFZ5ekFGQmdNclpYQXdFREVPTUF3R0ExVUUKQ2hNRmRHRnNiM013SGhjTk1qVXhNakkzTWpNeU5UVTNXaGNOTXpVeE1qSTFNak15TlRVM1dqQVFNUTR3REFZRApWUVFLRXdWMFlXeHZjekFxTUFVR0F5dGxjQU1oQVBLMlRCTm5nWlhkRHRDQjBQRXprV0JxNW4zUk0zN0w3c1N1CkVrMGkveGRYbzJFd1h6QU9CZ05WSFE4QkFmOEVCQU1DQW9Rd0hRWURWUjBsQkJZd0ZBWUlLd1lCQlFVSEF3RUcKQ0NzR0FRVUZCd01DTUE4R0ExVWRFd0VCL3dRRk1BTUJBZjh3SFFZRFZSME9CQllFRkxFS0lGTWRTR09pZ09LaQozd3kzR0tWMGp2RDVNQVVHQXl0bGNBTkJBSmlXMEJqNGlaUHpwY2ZWWkhKWXk3dXphOWovOTBIZFJJcHpkdkwzCnc4U1RBcWs2emh0bFoyMVhEWlY1Y05vTWZpc0o0eC8zMzg1MXB6WTN6NHZBYVFvPQotLS0tLUVORCBDRVJUSUZJQ0FURS0tLS0tCg== + key: LS0tLS1CRUdJTiBFRDI1NTE5IFBSSVZBVEUgS0VZLS0tLS0KTUM0Q0FRQXdCUVlESzJWd0JDSUVJT0xneGYyN041VXhnUStER3NoZU04dThzdnlCbE8vUmRMYUpETEFHOEF3TAotLS0tLUVORCBFRDI1NTE5IFBSSVZBVEUgS0VZLS0tLS0K + certSANs: [] + kubelet: + image: ghcr.io/siderolabs/kubelet:v1.35.0 + extraArgs: + cloud-provider: external + extraMounts: + - destination: /var/lib/kubelet/plugins + type: bind + source: /var/lib/kubelet/plugins + options: + - bind + - rshared + - rw + defaultRuntimeSeccompProfileEnabled: true + disableManifestsDirectory: true + network: + interfaces: + - interface: eth0 + dhcp: true + - interface: eth1 + dhcp: false + install: + disk: /dev/sda + image: factory.talos.dev/installer/959b38c028569ff2f710c3cfcb3f90d4015282b278f020bb58cf1bda1f9ef93a:v1.12.0 + wipe: false + grubUseUKICmdline: true + files: + - content: tskey-auth-k6cryUGtC521CNTRL-vnjxfuqSqs2Es4kX2SG1s2p3btRizMiG + permissions: 0o600 + path: /var/etc/tailscale/auth.key + op: create + - content: 10.0.0.0/24 + permissions: 0o600 + path: /var/etc/tailscale/routes + op: create + - content: --accept-routes --advertise-tags=tag:k8s-cp + permissions: 0o600 + path: /var/etc/tailscale/args + op: create + features: + diskQuotaSupport: true + kubePrism: + enabled: true + port: 7445 + hostDNS: + enabled: true + forwardKubeDNSToHost: true + nodeLabels: + node.kubernetes.io/exclude-from-external-load-balancers: "" +cluster: + id: eKSkTfDUW0U4if1QcK9otzZnNktorUsvnndBrHM4WBE= + secret: UumfthEFQUDRssdtWbbVezTJJZOtIIw3Db6f342SwW4= + controlPlane: + endpoint: https://10.0.0.101:6443 + clusterName: vntx + network: + dnsDomain: cluster.local + podSubnets: + - 10.244.0.0/16 + serviceSubnets: + - 10.96.0.0/12 + token: 71gr3x.96za7btksx23r8bk + secretboxEncryptionSecret: 1+h+VmWKw3PPspmZ/+u27nhznTt8lRBd9RQQuepZ5/E= + ca: + crt: LS0tLS1CRUdJTiBDRVJUSUZJQ0FURS0tLS0tCk1JSUJpakNDQVMrZ0F3SUJBZ0lRVUxsZy9jbEovUkRzVFo1WHNvR0I3VEFLQmdncWhrak9QUVFEQWpBVk1STXcKRVFZRFZRUUtFd3ByZFdKbGNtNWxkR1Z6TUI0WERUSTFNVEl5TnpJek1qVTFOMW9YRFRNMU1USXlOVEl6TWpVMQpOMW93RlRFVE1CRUdBMVVFQ2hNS2EzVmlaWEp1WlhSbGN6QlpNQk1HQnlxR1NNNDlBZ0VHQ0NxR1NNNDlBd0VICkEwSUFCQ2xSVkxiQThpNTJjWUo2bnRRR2lpRnVTRnhVVnphMDA0UDhwM3VwK295SXFPWldJL3llSzY0VU9ueUkKeUF6YzhySXcxeTRjZGYyc1Y4OHhlczUvMzRhallUQmZNQTRHQTFVZER3RUIvd1FFQXdJQ2hEQWRCZ05WSFNVRQpGakFVQmdnckJnRUZCUWNEQVFZSUt3WUJCUVVIQXdJd0R3WURWUjBUQVFIL0JBVXdBd0VCL3pBZEJnTlZIUTRFCkZnUVVuVndjRnRKSHFRV0JuYk9ld3FlcCthUFByTnd3Q2dZSUtvWkl6ajBFQXdJRFNRQXdSZ0loQUlZTnFZaHUKNjNpQy9kMzUzQTFTeUhCN2lMWCtSQ1V2R2cza3BtQW1ybG5pQWlFQTdsSURuaElyUUJUMHNQa29aRHFIYWdJTgphZjRsTEhnbllaTUR3d0FVM3JFPQotLS0tLUVORCBDRVJUSUZJQ0FURS0tLS0tCg== + key: LS0tLS1CRUdJTiBFQyBQUklWQVRFIEtFWS0tLS0tCk1IY0NBUUVFSUpyNlRETEhtRk1aT1RJWXpIWmxNOS9tbTVYZ0l0cWowMEROMzk3Qk9uOEpvQW9HQ0NxR1NNNDkKQXdFSG9VUURRZ0FFS1ZGVXRzRHlMblp4Z25xZTFBYUtJVzVJWEZSWE5yVFRnL3luZTZuNmpJaW81bFlqL0o0cgpyaFE2ZklqSUROenlzakRYTGh4MS9heFh6ekY2em4vZmhnPT0KLS0tLS1FTkQgRUMgUFJJVkFURSBLRVktLS0tLQo= + aggregatorCA: + crt: LS0tLS1CRUdJTiBDRVJUSUZJQ0FURS0tLS0tCk1JSUJYekNDQVFhZ0F3SUJBZ0lSQUtGQ1hXS24vTnR4eVBuNmxYZjU4R2N3Q2dZSUtvWkl6ajBFQXdJd0FEQWUKRncweU5URXlNamN5TXpJMU5UZGFGdzB6TlRFeU1qVXlNekkxTlRkYU1BQXdXVEFUQmdjcWhrak9QUUlCQmdncQpoa2pPUFFNQkJ3TkNBQVMwMmptRnFCWU1hSURHeVRQWGNhTjQ2UTRBdCtTLzFob0lqd1QveHhZZUowVDJNeDh1ClRVSWQzNjVKT1dSK2FQS2dWdUkySVZpKzZDNXJOcnBSSnhES28yRXdYekFPQmdOVkhROEJBZjhFQkFNQ0FvUXcKSFFZRFZSMGxCQll3RkFZSUt3WUJCUVVIQXdFR0NDc0dBUVVGQndNQ01BOEdBMVVkRXdFQi93UUZNQU1CQWY4dwpIUVlEVlIwT0JCWUVGTXFxVnowdDVaaERQVTdzcS9hdUxKcWxjMVlkTUFvR0NDcUdTTTQ5QkFNQ0EwY0FNRVFDCklBdEI4L0hpSS9RakVEVjFiV29DZ1M1TkdtbDNzdUFTRGtUbkZjK2F3TmlEQWlBNzlPeHVJeVl1VFgyVUxvQlQKZWRXbDdEZ0Y0N3htTnM2OTNGcThLeXRGc0E9PQotLS0tLUVORCBDRVJUSUZJQ0FURS0tLS0tCg== + key: LS0tLS1CRUdJTiBFQyBQUklWQVRFIEtFWS0tLS0tCk1IY0NBUUVFSU9EVVVzMklrazhaeGowRDNRQVBLeTlpTCtTSVNaZGhOZjMrdVBqOHNudVRvQW9HQ0NxR1NNNDkKQXdFSG9VUURRZ0FFdE5vNWhhZ1dER2lBeHNrejEzR2plT2tPQUxma3Y5WWFDSThFLzhjV0hpZEU5ak1mTGsxQwpIZCt1U1Rsa2ZtanlvRmJpTmlGWXZ1Z3VhemE2VVNjUXlnPT0KLS0tLS1FTkQgRUMgUFJJVkFURSBLRVktLS0tLQo= + serviceAccount: + key: LS0tLS1CRUdJTiBSU0EgUFJJVkFURSBLRVktLS0tLQpNSUlKS1FJQkFBS0NBZ0VBM0gzV1hzZVU4clpGdzhkaUhIbzB3aWFQdnV3N3VpblJ3MS9xbnB6VldjVGRlWUcrCnJlQ0dMek1vNWlzaHBQT3N2WVd5UEVoZlVyZ01ldTY3cFlTMFNxSmtGcnJtY3lrQUNybHFtaE54ZzVBazZZcTIKOWhPeUphR0tKOVkrdEUzNmFjUjBIWTJ4UEV3K0lKbEdIVUpLNSs2RUsxUXVjYTF5TXpLc0pOM1VrSDVzNXpXeApEbCtSdHJLNklXdEsxYjZ5M213SmtaRTJIYktxUUdXdWxONDZ6M1gzTXJLNk9POVhHNTJ2S3dINFBzdHFHVDc5Ck92dlI3b21yaVF6OUJUclhSYXlqRGp4MEl3NGVTVVJ4QkFsRFlsZDlqd2E3aXd1NHU5bldlazYyRjM3S3VMTE4KYlpWWlQ4WjJqQlJ5WGp5ZXdkTkFpL0Z4bElNSWtSdjE0VVV4M3NEdDhycGh2b2xERDBXVGlRcTNyQkNSUUNrVQpldWpZUmloaDNnQUI4QTN5dGJrZGJSNlgrQ2IrR21NMFVycmgwb2RnWDg0dkdrY1lhR1NrSnRKSEttSlNDUGN3CkJYa29taHd2dDJ4UzVEQTM4aUhPWDc5OTgrQzdJQWpyWnpka3ZLSXZIc1grSklvYTF4d0ZiclJTOUIrNUNDMXQKdnVFd1pvVXlTWEdDOWh0bkd5M1ZjcUdsbFBUQ3NEaForZkpXNGRNazE2cldaVW5uSmM3ek1Fa2pleVJzUERnZAptM215Z0w1RDd2S2w1SnBGNWphM2wzOEt4OC9xKzU3OFY2RllSblhvUElGS25TbGFLNmorKzdmeFZyMFdPNlk4CjRKVnFyUG5LYVVvQ0I0WTFrZGlqSkI1TndVRjVWazdqNVUyWThYRk1vWjRtNGdWQ29jS3laUDlIYXlNQ0F3RUEKQVFLQ0FnQUl3bGovUitkell1bFBsejZmQ2YzSmpyV2NMSTlNM0hkd1R3R25qbXh0VmdSRVhQS2h2cThsOWQ3VQprZmNTc2ZsMVIvZm1MQ3ZaUWVXQkJyWGVvL0J6bkpMa1VrVndZcnNWTWZ0NXBuY1dkbVg0L3lFNGtseTc0UGgzCmo2dkxCdVFCU3FRZ1BtNUJpbmZYWEs5cjN5UFJwZWlMUGh0Z09iYzFNSGlsT0VqRytyYkIwcUMzaFBWcGNCMHoKMGFyVjVlNytKZ1dWU2xML2lBYjZhdSt1QzB3RHpOaG1vN0lCTEFUbVhIUEdmaHdLQnBPdThCRW9SRE81U2EvTwpVSDFHdFdreTQrSlFZUGR1SXhQeDdpMmRMdThGMjVycDBTY25KVzZQeTk0WTJzS2lHVS9kV1lFT3J1V3U1Ui8xCmZhUnplTzRIbmloTXh1a3ZzS3JvOU5ibVBaVDNCUXR2SGl4ZlVNU2pmTXZFcUorNDhpdlA1RTNiYUJHRk5Mc3oKbUZXZW91MFEzVzNTMU50RkQvWnIybFJpT3VrVzhLLytBSm1PL210RWd2NG1UK3pHa05BUGhPT3lQcUlTakgxTAp1WTY3c08wRGlJWmJ1REdmZDQ2YXN3bHBZQis1Z0ZMZGxONDNJcGRxZG5GMFdtbjkybXk3cVluVVhkSkJENnZNCm5TWGJJOTZZOSt6K3V6citTZWMzeWhEckd6a1c1NWJ4VHJqb1FMZ2d6RDRVSWEyMm1ueUFOb3UrZzkyU09RSnEKb0hmWGZoeDdJeEZyM2h2V3ZaVVlYNit6bndUZTBKeVI0cy9NaXZxM2NIVERzV1A2NXBMd3VNQXRMMW1qWHNOcgp4aGhzZDQrNkJYb0R1OGl1V1NFRDlndlFIbVFlN3p3azVEVlNPbXJOTHlZTnZ3Y0U1UUtDQVFFQTYxaWR3VUp0CmJEMUlzQ1RBaVJnaFEvT0oxY3cwcmNqSDhGcGRNaFg1MHc2NUJqcmk5OEU5eDNkK2JpZVA3eXk5cVNMcnN5dzIKSDNteTJXOEZOSHdUUnJCT2NnQVg0cWhSa205Y0tBSlhGS0xVbGY4TlJocWJrR3RyVnMybEdDdXBEZHJxN2RpTApHRGdxY2gxbHpXR1d1UlQyOWZDRXRzZWVyd2NFemtXYTE0MDRYWEIyTi9EK0FHbVB2Mmp2dEFOSml0ekFuL0pWCnQ4NnZLVyttbWlxNVFQNlZHZjFtVmZTMGlSQy9TVzJMditGR3J2ZmRsNHN4WXJONnoweVdZSUZqK2J3aVNYblIKZXhTKzYyUUtleGJCalZwa2gzRnJTNWNsZWJ1ajg0aWVEaVQ1ZDFsTTNhaHlpSjRJYk1IaVJyeG1wSFNDVmkrUQorOHpSbHRwcGI2eko5UUtDQVFFQTc5ZDkwWDhqeFJKV015MUFWTDlrMnN5YjZacG9XN2FHL3AwNTlHVi80dXBNCi9DdTRXVVdOajdWdW1sRmppUFdtT0hhMkxIVnZmVW5DY3M1WTYxRTJVWm9mNXcxLzZ5R2ZwdEtzZ0V5eElUZGMKMFRFV0pPTy9QeVZabEhXR2xJVVNsMlBsTlFuclh6OCsvY29RZklSS29OZmd6K1p5NHdLdFpMWDdpUDBlaGt4YgphWmhNWWF0azNhN0FyQURPRFZiZ1Z3dkdjaER6Vm5oNjc4TzF3a0p0WjJ6TUlrOGF4cy9WR1VMQ0NRdURTV2pICkdsb2IvQlA3TERBdWxKVlN3ajNOY2NLK01ZMnpSSXEwcHNYWkxsVlJicTRZSlhFbUxoRFEzUXhvUklLQVZQM08KWkZWR2lDT3lXU1dJclprZkZHaEkrNlFram1YazJmYmNPTE9QNGUyNXR3S0NBUUVBd3ZKcDR0OXlvcGwxTDZ1Ugo3VDRXdUNIeFNDOWFaNllNc0xVNXc3WmVkZzBaQ09jWWdXQUtHOE9JOEJoSGF6aWxkb2hkczlKb2x0UUphWUZFClQ0Q0R1eWRxSTVhZU1udDQ3cExlUktvRGxpMTNhVFNYdXoxcEpVMUY0ZWFBM2krMFhxeTdzLytPNEtZTnl1ODkKRjg3QnVsaDZaYWt4VmZLdktJN28xVERsSGE1MlJUaFdST3FVaktUa2xRcUluSldvZ3FWdnprNC80UDBOTFlhMQorN2h1TWo5d0pOSTV4ZlBvNUMwQ053SE9KRWlvYzJFUXBtcC9veUhIRmhaNzdqN2dJTXRObjQyUUQ2TlVyc24wCndKZE9CeGdjYy9Gb2pub0thZmNielN5YXVGNjZZcm1QS1lGU05vYXB0ZVU0MloxUWJPT3gzMUNSaVhMVkhsK1gKdlJEbFRRS0NBUUJBNkVpY2taUFVtWW5LZjh5Ukl0cmdlODhXQVR1TTFuRGlKeHF3RVdmeXVRWHNtTWhqSUhlWApGTHJCK0pTL1UvdVAvRkNBNTZjc2VQR3VzRGxRTmNKRmd6aHZCekEvS2ZKUzYyRFR0KzJYMTZ1KzBWSDAyYzNBCkFST2xJY2t5R0hGWGx5bEltVTZoa0RRejZxTmJqMUhEQmFsSm1rd3RNMlJKaFJaMWxFcldmWU9mcUIvRHJ1YTEKTjczY3pycjAwVFlWV0pKei9ESmVqR3g0eHJaQnhFaG5YUUpCcHJiUVp4NThuNXh6WmpJNWc2bWVjQlJ5dTlXVgp0OVJqVWFYNyswM0dJN1hsSXp3SXFLRUxJVEFOWWZtUHduMjJaRkM0MXNRdmpsUUpkbWZVbUh0cW04bGl2b1pkCnFkSzdhRjBJNE5BZmllUjZ4UWlTRkVTMDg2TlV1VWt4QW9JQkFRRG9WL0pJRlNEejl3Z3dneUhhdmdwSnR0UGkKNWZBeEpZaktZbUtsLzdpZUdkZ0pzN1dwR3dxNXlQZFVVRE1yMnNKUDBGWDhEZFJTSktWLzExRzMvaklTL1JyQQpwcDVsS2hGbEFncVBvZ1EvL0IzTVBiNXZiNTBSMExrNGJtVWVYcUVhMkJBSTlmc0R3WEFZbFhsMnJOT0drdEdSCnJZd1BEdHlhbnI1d0grVEtoYjdqODdWN2Z1TWpRcU5SK21TQVJqZXpvRHNQdnJvUHB0d1o0RnBSOTNCUXJqUGoKRWF6Z1UvbHlSRkVCNklISFhvbWFaR1ExYlY1TG85ZTlUZGp6VFpiT2tJMUFsL3B6cWx5WlpzdnU5RnFURUdUbwpRckt6Nm9xeFJyR1lhUVNJbGpydWhPajdiWUVPeGp2VnFEdmNIaGNxV1paN0h5VWNjS2gzNFZReWhCdTQKLS0tLS1FTkQgUlNBIFBSSVZBVEUgS0VZLS0tLS0K + apiServer: + image: registry.k8s.io/kube-apiserver:v1.35.0 + admissionControl: + - name: PodSecurity + configuration: + apiVersion: pod-security.admission.config.k8s.io/v1alpha1 + defaults: + audit: restricted + audit-version: latest + enforce: baseline + enforce-version: latest + warn: restricted + warn-version: latest + exemptions: + namespaces: + - kube-system + runtimeClasses: [] + usernames: [] + kind: PodSecurityConfiguration + auditPolicy: + apiVersion: audit.k8s.io/v1 + kind: Policy + rules: + - level: Metadata + controllerManager: + image: registry.k8s.io/kube-controller-manager:v1.35.0 + proxy: + image: registry.k8s.io/kube-proxy:v1.35.0 + scheduler: + image: registry.k8s.io/kube-scheduler:v1.35.0 + discovery: + enabled: true + registries: + kubernetes: + disabled: true + service: {} + etcd: + ca: + crt: LS0tLS1CRUdJTiBDRVJUSUZJQ0FURS0tLS0tCk1JSUJmVENDQVNPZ0F3SUJBZ0lRY1hQekZ3N2lYdnlnY2FVMGlUQ3lGekFLQmdncWhrak9QUVFEQWpBUE1RMHcKQ3dZRFZRUUtFd1JsZEdOa01CNFhEVEkxTVRJeU56SXpNalUxTjFvWERUTTFNVEl5TlRJek1qVTFOMW93RHpFTgpNQXNHQTFVRUNoTUVaWFJqWkRCWk1CTUdCeXFHU000OUFnRUdDQ3FHU000OUF3RUhBMElBQlBpREhoWTkzT1FFClpaS2x1L1M3NVBnRmlvNks5SjV1RUZwNk12c3N4NnYzWld6RXJ2clBoNW53QkFqVFFOOUdodTRmQ1dXbXdsQmgKVVhIU09RcHh5OStqWVRCZk1BNEdBMVVkRHdFQi93UUVBd0lDaERBZEJnTlZIU1VFRmpBVUJnZ3JCZ0VGQlFjRApBUVlJS3dZQkJRVUhBd0l3RHdZRFZSMFRBUUgvQkFVd0F3RUIvekFkQmdOVkhRNEVGZ1FVYnc1N01IV1JvWnYyClZ6UndZNGIyY3c1VGw3c3dDZ1lJS29aSXpqMEVBd0lEU0FBd1JRSWdHR1BOZmNzT2M0ajlFblNIbkhRV2dydEQKbEdZWitpZ3JKQnZSWGFSa1FRd0NJUUNOeUlRVU9reWx5U0Vpc1ZyNzFhR3hTRHJ5UFgwZlRuMEdZM25qalpkQQpaUT09Ci0tLS0tRU5EIENFUlRJRklDQVRFLS0tLS0K + key: LS0tLS1CRUdJTiBFQyBQUklWQVRFIEtFWS0tLS0tCk1IY0NBUUVFSUtpazBDeFdObEx6ZWJaY2kwSVYyUHNqOGRoRis5L0Nsb3JXbzAySUdRb1BvQW9HQ0NxR1NNNDkKQXdFSG9VUURRZ0FFK0lNZUZqM2M1QVJsa3FXNzlMdmsrQVdLam9yMG5tNFFXbm95K3l6SHEvZGxiTVN1K3MrSAptZkFFQ05OQTMwYUc3aDhKWmFiQ1VHRlJjZEk1Q25ITDN3PT0KLS0tLS1FTkQgRUMgUFJJVkFURSBLRVktLS0tLQo= +--- +apiVersion: v1alpha1 +kind: HostnameConfig +auto: stable diff --git a/talos/nodes/worker-1.yaml b/talos/nodes/worker-1.yaml new file mode 100644 index 0000000..00b4283 --- /dev/null +++ b/talos/nodes/worker-1.yaml @@ -0,0 +1,118 @@ +version: v1alpha1 +debug: false +persist: true +machine: + type: worker + token: gwdkoe.5gbblli1cvxv1axx + ca: + crt: LS0tLS1CRUdJTiBDRVJUSUZJQ0FURS0tLS0tCk1JSUJQekNCOHFBREFnRUNBaEVBbk5ucllpRDF4bjZaaGVFY0hvTFZ5ekFGQmdNclpYQXdFREVPTUF3R0ExVUUKQ2hNRmRHRnNiM013SGhjTk1qVXhNakkzTWpNeU5UVTNXaGNOTXpVeE1qSTFNak15TlRVM1dqQVFNUTR3REFZRApWUVFLRXdWMFlXeHZjekFxTUFVR0F5dGxjQU1oQVBLMlRCTm5nWlhkRHRDQjBQRXprV0JxNW4zUk0zN0w3c1N1CkVrMGkveGRYbzJFd1h6QU9CZ05WSFE4QkFmOEVCQU1DQW9Rd0hRWURWUjBsQkJZd0ZBWUlLd1lCQlFVSEF3RUcKQ0NzR0FRVUZCd01DTUE4R0ExVWRFd0VCL3dRRk1BTUJBZjh3SFFZRFZSME9CQllFRkxFS0lGTWRTR09pZ09LaQozd3kzR0tWMGp2RDVNQVVHQXl0bGNBTkJBSmlXMEJqNGlaUHpwY2ZWWkhKWXk3dXphOWovOTBIZFJJcHpkdkwzCnc4U1RBcWs2emh0bFoyMVhEWlY1Y05vTWZpc0o0eC8zMzg1MXB6WTN6NHZBYVFvPQotLS0tLUVORCBDRVJUSUZJQ0FURS0tLS0tCg== + key: "" + certSANs: [] + kubelet: + image: ghcr.io/siderolabs/kubelet:v1.35.0 + extraArgs: + cloud-provider: external + extraMounts: + - destination: /var/lib/kubelet/plugins + type: bind + source: /var/lib/kubelet/plugins + options: + - bind + - rshared + - rw + defaultRuntimeSeccompProfileEnabled: true + disableManifestsDirectory: true + network: + interfaces: + - interface: eth0 + dhcp: true + install: + disk: /dev/sda + image: factory.talos.dev/installer/959b38c028569ff2f710c3cfcb3f90d4015282b278f020bb58cf1bda1f9ef93a:v1.12.0 + wipe: false + grubUseUKICmdline: true + files: + - content: tskey-auth-k6cryUGtC521CNTRL-vnjxfuqSqs2Es4kX2SG1s2p3btRizMiG + permissions: 0o600 + path: /var/etc/tailscale/auth.key + op: create + - content: 10.0.0.0/24 + permissions: 0o600 + path: /var/etc/tailscale/routes + op: create + - content: --accept-routes --advertise-tags=tag:k8s-cp + permissions: 0o600 + path: /var/etc/tailscale/args + op: create + features: + diskQuotaSupport: true + kubePrism: + enabled: true + port: 7445 + hostDNS: + enabled: true + forwardKubeDNSToHost: true + nodeLabels: + node.kubernetes.io/exclude-from-external-load-balancers: "" +cluster: + id: eKSkTfDUW0U4if1QcK9otzZnNktorUsvnndBrHM4WBE= + secret: UumfthEFQUDRssdtWbbVezTJJZOtIIw3Db6f342SwW4= + controlPlane: + endpoint: https://10.0.0.101:6443 + clusterName: vntx + network: + dnsDomain: cluster.local + podSubnets: + - 10.244.0.0/16 + serviceSubnets: + - 10.96.0.0/12 + token: 71gr3x.96za7btksx23r8bk + secretboxEncryptionSecret: 1+h+VmWKw3PPspmZ/+u27nhznTt8lRBd9RQQuepZ5/E= + ca: + crt: LS0tLS1CRUdJTiBDRVJUSUZJQ0FURS0tLS0tCk1JSUJpakNDQVMrZ0F3SUJBZ0lRVUxsZy9jbEovUkRzVFo1WHNvR0I3VEFLQmdncWhrak9QUVFEQWpBVk1STXcKRVFZRFZRUUtFd3ByZFdKbGNtNWxkR1Z6TUI0WERUSTFNVEl5TnpJek1qVTFOMW9YRFRNMU1USXlOVEl6TWpVMQpOMW93RlRFVE1CRUdBMVVFQ2hNS2EzVmlaWEp1WlhSbGN6QlpNQk1HQnlxR1NNNDlBZ0VHQ0NxR1NNNDlBd0VICkEwSUFCQ2xSVkxiQThpNTJjWUo2bnRRR2lpRnVTRnhVVnphMDA0UDhwM3VwK295SXFPWldJL3llSzY0VU9ueUkKeUF6YzhySXcxeTRjZGYyc1Y4OHhlczUvMzRhallUQmZNQTRHQTFVZER3RUIvd1FFQXdJQ2hEQWRCZ05WSFNVRQpGakFVQmdnckJnRUZCUWNEQVFZSUt3WUJCUVVIQXdJd0R3WURWUjBUQVFIL0JBVXdBd0VCL3pBZEJnTlZIUTRFCkZnUVVuVndjRnRKSHFRV0JuYk9ld3FlcCthUFByTnd3Q2dZSUtvWkl6ajBFQXdJRFNRQXdSZ0loQUlZTnFZaHUKNjNpQy9kMzUzQTFTeUhCN2lMWCtSQ1V2R2cza3BtQW1ybG5pQWlFQTdsSURuaElyUUJUMHNQa29aRHFIYWdJTgphZjRsTEhnbllaTUR3d0FVM3JFPQotLS0tLUVORCBDRVJUSUZJQ0FURS0tLS0tCg== + key: "" + aggregatorCA: + crt: LS0tLS1CRUdJTiBDRVJUSUZJQ0FURS0tLS0tCk1JSUJYekNDQVFhZ0F3SUJBZ0lSQUtGQ1hXS24vTnR4eVBuNmxYZjU4R2N3Q2dZSUtvWkl6ajBFQXdJd0FEQWUKRncweU5URXlNamN5TXpJMU5UZGFGdzB6TlRFeU1qVXlNekkxTlRkYU1BQXdXVEFUQmdjcWhrak9QUUlCQmdncQpoa2pPUFFNQkJ3TkNBQVMwMmptRnFCWU1hSURHeVRQWGNhTjQ2UTRBdCtTLzFob0lqd1QveHhZZUowVDJNeDh1ClRVSWQzNjVKT1dSK2FQS2dWdUkySVZpKzZDNXJOcnBSSnhES28yRXdYekFPQmdOVkhROEJBZjhFQkFNQ0FvUXcKSFFZRFZSMGxCQll3RkFZSUt3WUJCUVVIQXdFR0NDc0dBUVVGQndNQ01BOEdBMVVkRXdFQi93UUZNQU1CQWY4dwpIUVlEVlIwT0JCWUVGTXFxVnowdDVaaERQVTdzcS9hdUxKcWxjMVlkTUFvR0NDcUdTTTQ5QkFNQ0EwY0FNRVFDCklBdEI4L0hpSS9RakVEVjFiV29DZ1M1TkdtbDNzdUFTRGtUbkZjK2F3TmlEQWlBNzlPeHVJeVl1VFgyVUxvQlQKZWRXbDdEZ0Y0N3htTnM2OTNGcThLeXRGc0E9PQotLS0tLUVORCBDRVJUSUZJQ0FURS0tLS0tCg== + key: "" + serviceAccount: + key: "" + apiServer: + image: registry.k8s.io/kube-apiserver:v1.35.0 + admissionControl: + - name: PodSecurity + configuration: + apiVersion: pod-security.admission.config.k8s.io/v1alpha1 + defaults: + audit: restricted + audit-version: latest + enforce: baseline + enforce-version: latest + warn: restricted + warn-version: latest + exemptions: + namespaces: + - kube-system + runtimeClasses: [] + usernames: [] + kind: PodSecurityConfiguration + auditPolicy: + apiVersion: audit.k8s.io/v1 + kind: Policy + rules: + - level: Metadata + controllerManager: + image: registry.k8s.io/kube-controller-manager:v1.35.0 + proxy: + image: registry.k8s.io/kube-proxy:v1.35.0 + scheduler: + image: registry.k8s.io/kube-scheduler:v1.35.0 + discovery: + enabled: true + registries: + kubernetes: + disabled: true + service: {} +--- +apiVersion: v1alpha1 +kind: HostnameConfig +auto: stable diff --git a/talos/nodes/worker-2.yaml b/talos/nodes/worker-2.yaml new file mode 100644 index 0000000..00b4283 --- /dev/null +++ b/talos/nodes/worker-2.yaml @@ -0,0 +1,118 @@ +version: v1alpha1 +debug: false +persist: true +machine: + type: worker + token: gwdkoe.5gbblli1cvxv1axx + ca: + crt: LS0tLS1CRUdJTiBDRVJUSUZJQ0FURS0tLS0tCk1JSUJQekNCOHFBREFnRUNBaEVBbk5ucllpRDF4bjZaaGVFY0hvTFZ5ekFGQmdNclpYQXdFREVPTUF3R0ExVUUKQ2hNRmRHRnNiM013SGhjTk1qVXhNakkzTWpNeU5UVTNXaGNOTXpVeE1qSTFNak15TlRVM1dqQVFNUTR3REFZRApWUVFLRXdWMFlXeHZjekFxTUFVR0F5dGxjQU1oQVBLMlRCTm5nWlhkRHRDQjBQRXprV0JxNW4zUk0zN0w3c1N1CkVrMGkveGRYbzJFd1h6QU9CZ05WSFE4QkFmOEVCQU1DQW9Rd0hRWURWUjBsQkJZd0ZBWUlLd1lCQlFVSEF3RUcKQ0NzR0FRVUZCd01DTUE4R0ExVWRFd0VCL3dRRk1BTUJBZjh3SFFZRFZSME9CQllFRkxFS0lGTWRTR09pZ09LaQozd3kzR0tWMGp2RDVNQVVHQXl0bGNBTkJBSmlXMEJqNGlaUHpwY2ZWWkhKWXk3dXphOWovOTBIZFJJcHpkdkwzCnc4U1RBcWs2emh0bFoyMVhEWlY1Y05vTWZpc0o0eC8zMzg1MXB6WTN6NHZBYVFvPQotLS0tLUVORCBDRVJUSUZJQ0FURS0tLS0tCg== + key: "" + certSANs: [] + kubelet: + image: ghcr.io/siderolabs/kubelet:v1.35.0 + extraArgs: + cloud-provider: external + extraMounts: + - destination: /var/lib/kubelet/plugins + type: bind + source: /var/lib/kubelet/plugins + options: + - bind + - rshared + - rw + defaultRuntimeSeccompProfileEnabled: true + disableManifestsDirectory: true + network: + interfaces: + - interface: eth0 + dhcp: true + install: + disk: /dev/sda + image: factory.talos.dev/installer/959b38c028569ff2f710c3cfcb3f90d4015282b278f020bb58cf1bda1f9ef93a:v1.12.0 + wipe: false + grubUseUKICmdline: true + files: + - content: tskey-auth-k6cryUGtC521CNTRL-vnjxfuqSqs2Es4kX2SG1s2p3btRizMiG + permissions: 0o600 + path: /var/etc/tailscale/auth.key + op: create + - content: 10.0.0.0/24 + permissions: 0o600 + path: /var/etc/tailscale/routes + op: create + - content: --accept-routes --advertise-tags=tag:k8s-cp + permissions: 0o600 + path: /var/etc/tailscale/args + op: create + features: + diskQuotaSupport: true + kubePrism: + enabled: true + port: 7445 + hostDNS: + enabled: true + forwardKubeDNSToHost: true + nodeLabels: + node.kubernetes.io/exclude-from-external-load-balancers: "" +cluster: + id: eKSkTfDUW0U4if1QcK9otzZnNktorUsvnndBrHM4WBE= + secret: UumfthEFQUDRssdtWbbVezTJJZOtIIw3Db6f342SwW4= + controlPlane: + endpoint: https://10.0.0.101:6443 + clusterName: vntx + network: + dnsDomain: cluster.local + podSubnets: + - 10.244.0.0/16 + serviceSubnets: + - 10.96.0.0/12 + token: 71gr3x.96za7btksx23r8bk + secretboxEncryptionSecret: 1+h+VmWKw3PPspmZ/+u27nhznTt8lRBd9RQQuepZ5/E= + ca: + crt: LS0tLS1CRUdJTiBDRVJUSUZJQ0FURS0tLS0tCk1JSUJpakNDQVMrZ0F3SUJBZ0lRVUxsZy9jbEovUkRzVFo1WHNvR0I3VEFLQmdncWhrak9QUVFEQWpBVk1STXcKRVFZRFZRUUtFd3ByZFdKbGNtNWxkR1Z6TUI0WERUSTFNVEl5TnpJek1qVTFOMW9YRFRNMU1USXlOVEl6TWpVMQpOMW93RlRFVE1CRUdBMVVFQ2hNS2EzVmlaWEp1WlhSbGN6QlpNQk1HQnlxR1NNNDlBZ0VHQ0NxR1NNNDlBd0VICkEwSUFCQ2xSVkxiQThpNTJjWUo2bnRRR2lpRnVTRnhVVnphMDA0UDhwM3VwK295SXFPWldJL3llSzY0VU9ueUkKeUF6YzhySXcxeTRjZGYyc1Y4OHhlczUvMzRhallUQmZNQTRHQTFVZER3RUIvd1FFQXdJQ2hEQWRCZ05WSFNVRQpGakFVQmdnckJnRUZCUWNEQVFZSUt3WUJCUVVIQXdJd0R3WURWUjBUQVFIL0JBVXdBd0VCL3pBZEJnTlZIUTRFCkZnUVVuVndjRnRKSHFRV0JuYk9ld3FlcCthUFByTnd3Q2dZSUtvWkl6ajBFQXdJRFNRQXdSZ0loQUlZTnFZaHUKNjNpQy9kMzUzQTFTeUhCN2lMWCtSQ1V2R2cza3BtQW1ybG5pQWlFQTdsSURuaElyUUJUMHNQa29aRHFIYWdJTgphZjRsTEhnbllaTUR3d0FVM3JFPQotLS0tLUVORCBDRVJUSUZJQ0FURS0tLS0tCg== + key: "" + aggregatorCA: + crt: LS0tLS1CRUdJTiBDRVJUSUZJQ0FURS0tLS0tCk1JSUJYekNDQVFhZ0F3SUJBZ0lSQUtGQ1hXS24vTnR4eVBuNmxYZjU4R2N3Q2dZSUtvWkl6ajBFQXdJd0FEQWUKRncweU5URXlNamN5TXpJMU5UZGFGdzB6TlRFeU1qVXlNekkxTlRkYU1BQXdXVEFUQmdjcWhrak9QUUlCQmdncQpoa2pPUFFNQkJ3TkNBQVMwMmptRnFCWU1hSURHeVRQWGNhTjQ2UTRBdCtTLzFob0lqd1QveHhZZUowVDJNeDh1ClRVSWQzNjVKT1dSK2FQS2dWdUkySVZpKzZDNXJOcnBSSnhES28yRXdYekFPQmdOVkhROEJBZjhFQkFNQ0FvUXcKSFFZRFZSMGxCQll3RkFZSUt3WUJCUVVIQXdFR0NDc0dBUVVGQndNQ01BOEdBMVVkRXdFQi93UUZNQU1CQWY4dwpIUVlEVlIwT0JCWUVGTXFxVnowdDVaaERQVTdzcS9hdUxKcWxjMVlkTUFvR0NDcUdTTTQ5QkFNQ0EwY0FNRVFDCklBdEI4L0hpSS9RakVEVjFiV29DZ1M1TkdtbDNzdUFTRGtUbkZjK2F3TmlEQWlBNzlPeHVJeVl1VFgyVUxvQlQKZWRXbDdEZ0Y0N3htTnM2OTNGcThLeXRGc0E9PQotLS0tLUVORCBDRVJUSUZJQ0FURS0tLS0tCg== + key: "" + serviceAccount: + key: "" + apiServer: + image: registry.k8s.io/kube-apiserver:v1.35.0 + admissionControl: + - name: PodSecurity + configuration: + apiVersion: pod-security.admission.config.k8s.io/v1alpha1 + defaults: + audit: restricted + audit-version: latest + enforce: baseline + enforce-version: latest + warn: restricted + warn-version: latest + exemptions: + namespaces: + - kube-system + runtimeClasses: [] + usernames: [] + kind: PodSecurityConfiguration + auditPolicy: + apiVersion: audit.k8s.io/v1 + kind: Policy + rules: + - level: Metadata + controllerManager: + image: registry.k8s.io/kube-controller-manager:v1.35.0 + proxy: + image: registry.k8s.io/kube-proxy:v1.35.0 + scheduler: + image: registry.k8s.io/kube-scheduler:v1.35.0 + discovery: + enabled: true + registries: + kubernetes: + disabled: true + service: {} +--- +apiVersion: v1alpha1 +kind: HostnameConfig +auto: stable diff --git a/talos/nodes/worker-3.yaml b/talos/nodes/worker-3.yaml new file mode 100644 index 0000000..00b4283 --- /dev/null +++ b/talos/nodes/worker-3.yaml @@ -0,0 +1,118 @@ +version: v1alpha1 +debug: false +persist: true +machine: + type: worker + token: gwdkoe.5gbblli1cvxv1axx + ca: + crt: LS0tLS1CRUdJTiBDRVJUSUZJQ0FURS0tLS0tCk1JSUJQekNCOHFBREFnRUNBaEVBbk5ucllpRDF4bjZaaGVFY0hvTFZ5ekFGQmdNclpYQXdFREVPTUF3R0ExVUUKQ2hNRmRHRnNiM013SGhjTk1qVXhNakkzTWpNeU5UVTNXaGNOTXpVeE1qSTFNak15TlRVM1dqQVFNUTR3REFZRApWUVFLRXdWMFlXeHZjekFxTUFVR0F5dGxjQU1oQVBLMlRCTm5nWlhkRHRDQjBQRXprV0JxNW4zUk0zN0w3c1N1CkVrMGkveGRYbzJFd1h6QU9CZ05WSFE4QkFmOEVCQU1DQW9Rd0hRWURWUjBsQkJZd0ZBWUlLd1lCQlFVSEF3RUcKQ0NzR0FRVUZCd01DTUE4R0ExVWRFd0VCL3dRRk1BTUJBZjh3SFFZRFZSME9CQllFRkxFS0lGTWRTR09pZ09LaQozd3kzR0tWMGp2RDVNQVVHQXl0bGNBTkJBSmlXMEJqNGlaUHpwY2ZWWkhKWXk3dXphOWovOTBIZFJJcHpkdkwzCnc4U1RBcWs2emh0bFoyMVhEWlY1Y05vTWZpc0o0eC8zMzg1MXB6WTN6NHZBYVFvPQotLS0tLUVORCBDRVJUSUZJQ0FURS0tLS0tCg== + key: "" + certSANs: [] + kubelet: + image: ghcr.io/siderolabs/kubelet:v1.35.0 + extraArgs: + cloud-provider: external + extraMounts: + - destination: /var/lib/kubelet/plugins + type: bind + source: /var/lib/kubelet/plugins + options: + - bind + - rshared + - rw + defaultRuntimeSeccompProfileEnabled: true + disableManifestsDirectory: true + network: + interfaces: + - interface: eth0 + dhcp: true + install: + disk: /dev/sda + image: factory.talos.dev/installer/959b38c028569ff2f710c3cfcb3f90d4015282b278f020bb58cf1bda1f9ef93a:v1.12.0 + wipe: false + grubUseUKICmdline: true + files: + - content: tskey-auth-k6cryUGtC521CNTRL-vnjxfuqSqs2Es4kX2SG1s2p3btRizMiG + permissions: 0o600 + path: /var/etc/tailscale/auth.key + op: create + - content: 10.0.0.0/24 + permissions: 0o600 + path: /var/etc/tailscale/routes + op: create + - content: --accept-routes --advertise-tags=tag:k8s-cp + permissions: 0o600 + path: /var/etc/tailscale/args + op: create + features: + diskQuotaSupport: true + kubePrism: + enabled: true + port: 7445 + hostDNS: + enabled: true + forwardKubeDNSToHost: true + nodeLabels: + node.kubernetes.io/exclude-from-external-load-balancers: "" +cluster: + id: eKSkTfDUW0U4if1QcK9otzZnNktorUsvnndBrHM4WBE= + secret: UumfthEFQUDRssdtWbbVezTJJZOtIIw3Db6f342SwW4= + controlPlane: + endpoint: https://10.0.0.101:6443 + clusterName: vntx + network: + dnsDomain: cluster.local + podSubnets: + - 10.244.0.0/16 + serviceSubnets: + - 10.96.0.0/12 + token: 71gr3x.96za7btksx23r8bk + secretboxEncryptionSecret: 1+h+VmWKw3PPspmZ/+u27nhznTt8lRBd9RQQuepZ5/E= + ca: + crt: LS0tLS1CRUdJTiBDRVJUSUZJQ0FURS0tLS0tCk1JSUJpakNDQVMrZ0F3SUJBZ0lRVUxsZy9jbEovUkRzVFo1WHNvR0I3VEFLQmdncWhrak9QUVFEQWpBVk1STXcKRVFZRFZRUUtFd3ByZFdKbGNtNWxkR1Z6TUI0WERUSTFNVEl5TnpJek1qVTFOMW9YRFRNMU1USXlOVEl6TWpVMQpOMW93RlRFVE1CRUdBMVVFQ2hNS2EzVmlaWEp1WlhSbGN6QlpNQk1HQnlxR1NNNDlBZ0VHQ0NxR1NNNDlBd0VICkEwSUFCQ2xSVkxiQThpNTJjWUo2bnRRR2lpRnVTRnhVVnphMDA0UDhwM3VwK295SXFPWldJL3llSzY0VU9ueUkKeUF6YzhySXcxeTRjZGYyc1Y4OHhlczUvMzRhallUQmZNQTRHQTFVZER3RUIvd1FFQXdJQ2hEQWRCZ05WSFNVRQpGakFVQmdnckJnRUZCUWNEQVFZSUt3WUJCUVVIQXdJd0R3WURWUjBUQVFIL0JBVXdBd0VCL3pBZEJnTlZIUTRFCkZnUVVuVndjRnRKSHFRV0JuYk9ld3FlcCthUFByTnd3Q2dZSUtvWkl6ajBFQXdJRFNRQXdSZ0loQUlZTnFZaHUKNjNpQy9kMzUzQTFTeUhCN2lMWCtSQ1V2R2cza3BtQW1ybG5pQWlFQTdsSURuaElyUUJUMHNQa29aRHFIYWdJTgphZjRsTEhnbllaTUR3d0FVM3JFPQotLS0tLUVORCBDRVJUSUZJQ0FURS0tLS0tCg== + key: "" + aggregatorCA: + crt: LS0tLS1CRUdJTiBDRVJUSUZJQ0FURS0tLS0tCk1JSUJYekNDQVFhZ0F3SUJBZ0lSQUtGQ1hXS24vTnR4eVBuNmxYZjU4R2N3Q2dZSUtvWkl6ajBFQXdJd0FEQWUKRncweU5URXlNamN5TXpJMU5UZGFGdzB6TlRFeU1qVXlNekkxTlRkYU1BQXdXVEFUQmdjcWhrak9QUUlCQmdncQpoa2pPUFFNQkJ3TkNBQVMwMmptRnFCWU1hSURHeVRQWGNhTjQ2UTRBdCtTLzFob0lqd1QveHhZZUowVDJNeDh1ClRVSWQzNjVKT1dSK2FQS2dWdUkySVZpKzZDNXJOcnBSSnhES28yRXdYekFPQmdOVkhROEJBZjhFQkFNQ0FvUXcKSFFZRFZSMGxCQll3RkFZSUt3WUJCUVVIQXdFR0NDc0dBUVVGQndNQ01BOEdBMVVkRXdFQi93UUZNQU1CQWY4dwpIUVlEVlIwT0JCWUVGTXFxVnowdDVaaERQVTdzcS9hdUxKcWxjMVlkTUFvR0NDcUdTTTQ5QkFNQ0EwY0FNRVFDCklBdEI4L0hpSS9RakVEVjFiV29DZ1M1TkdtbDNzdUFTRGtUbkZjK2F3TmlEQWlBNzlPeHVJeVl1VFgyVUxvQlQKZWRXbDdEZ0Y0N3htTnM2OTNGcThLeXRGc0E9PQotLS0tLUVORCBDRVJUSUZJQ0FURS0tLS0tCg== + key: "" + serviceAccount: + key: "" + apiServer: + image: registry.k8s.io/kube-apiserver:v1.35.0 + admissionControl: + - name: PodSecurity + configuration: + apiVersion: pod-security.admission.config.k8s.io/v1alpha1 + defaults: + audit: restricted + audit-version: latest + enforce: baseline + enforce-version: latest + warn: restricted + warn-version: latest + exemptions: + namespaces: + - kube-system + runtimeClasses: [] + usernames: [] + kind: PodSecurityConfiguration + auditPolicy: + apiVersion: audit.k8s.io/v1 + kind: Policy + rules: + - level: Metadata + controllerManager: + image: registry.k8s.io/kube-controller-manager:v1.35.0 + proxy: + image: registry.k8s.io/kube-proxy:v1.35.0 + scheduler: + image: registry.k8s.io/kube-scheduler:v1.35.0 + discovery: + enabled: true + registries: + kubernetes: + disabled: true + service: {} +--- +apiVersion: v1alpha1 +kind: HostnameConfig +auto: stable diff --git a/talos/patches/cloud-provider.yaml b/talos/patches/cloud-provider.yaml new file mode 100644 index 0000000..c9e7efa --- /dev/null +++ b/talos/patches/cloud-provider.yaml @@ -0,0 +1,4 @@ +machine: + kubelet: + extraArgs: + cloud-provider: external diff --git a/talos/patches/cp-1.yaml b/talos/patches/cp-1.yaml new file mode 100644 index 0000000..94bc867 --- /dev/null +++ b/talos/patches/cp-1.yaml @@ -0,0 +1,7 @@ +machine: + network: + interfaces: + - interface: eth0 + dhcp: true + - interface: eth1 + dhcp: false diff --git a/talos/patches/cp-2.yaml b/talos/patches/cp-2.yaml new file mode 100644 index 0000000..94bc867 --- /dev/null +++ b/talos/patches/cp-2.yaml @@ -0,0 +1,7 @@ +machine: + network: + interfaces: + - interface: eth0 + dhcp: true + - interface: eth1 + dhcp: false diff --git a/talos/patches/cp-3.yaml b/talos/patches/cp-3.yaml new file mode 100644 index 0000000..94bc867 --- /dev/null +++ b/talos/patches/cp-3.yaml @@ -0,0 +1,7 @@ +machine: + network: + interfaces: + - interface: eth0 + dhcp: true + - interface: eth1 + dhcp: false diff --git a/talos/patches/remove-controlplane-secrets.yaml b/talos/patches/remove-controlplane-secrets.yaml new file mode 100644 index 0000000..c3401af --- /dev/null +++ b/talos/patches/remove-controlplane-secrets.yaml @@ -0,0 +1,2 @@ +# This patch is no longer needed since we manually fixed worker-base.yaml +# Keeping file for reference but it won't be used diff --git a/talos/patches/system-extensions.yaml b/talos/patches/system-extensions.yaml new file mode 100644 index 0000000..23b7a3d --- /dev/null +++ b/talos/patches/system-extensions.yaml @@ -0,0 +1,28 @@ +machine: + install: + extensions: + - image: ghcr.io/siderolabs/qemu-guest-agent:8.2.2 + - image: ghcr.io/siderolabs/iscsi-tools:v0.1.6 + - image: ghcr.io/siderolabs/tailscale:1.78.3 + files: + - content: tskey-auth-k6cryUGtC521CNTRL-vnjxfuqSqs2Es4kX2SG1s2p3btRizMiG + path: /var/etc/tailscale/auth.key + op: create + permissions: 0o600 + - content: "10.0.0.0/24" + path: /var/etc/tailscale/routes + op: create + permissions: 0o600 + - content: "--accept-routes --advertise-tags=tag:k8s-cp" + path: /var/etc/tailscale/args + op: create + permissions: 0o600 + kubelet: + extraMounts: + - destination: /var/lib/kubelet/plugins + type: bind + source: /var/lib/kubelet/plugins + options: + - bind + - rshared + - rw diff --git a/talos/patches/tailscale-config.yaml b/talos/patches/tailscale-config.yaml new file mode 100644 index 0000000..d81b8a9 --- /dev/null +++ b/talos/patches/tailscale-config.yaml @@ -0,0 +1,7 @@ +apiVersion: v1alpha1 +kind: ExtensionServiceConfig +name: tailscale +environment: + - TS_AUTHKEY=tskey-auth-k6cryUGtC521CNTRL-vnjxfuqSqs2Es4kX2SG1s2p3btRizMiG + - TS_ROUTES=10.0.0.0/24 + - TS_EXTRA_ARGS=--accept-routes --advertise-tags=tag:k8s-cp diff --git a/talos/patches/tailscale-extension-config.yaml b/talos/patches/tailscale-extension-config.yaml new file mode 100644 index 0000000..ae06ab0 --- /dev/null +++ b/talos/patches/tailscale-extension-config.yaml @@ -0,0 +1,14 @@ +machine: + files: + - content: tskey-auth-k6cryUGtC521CNTRL-vnjxfuqSqs2Es4kX2SG1s2p3btRizMiG + path: /var/etc/tailscale/auth.key + op: create + permissions: 0o600 + - content: "10.0.0.0/24" + path: /var/etc/tailscale/routes + op: create + permissions: 0o600 + - content: "--accept-routes --advertise-tags=tag:k8s-cp" + path: /var/etc/tailscale/args + op: create + permissions: 0o600 diff --git a/talos/patches/worker-1.yaml b/talos/patches/worker-1.yaml new file mode 100644 index 0000000..0ade6d9 --- /dev/null +++ b/talos/patches/worker-1.yaml @@ -0,0 +1,5 @@ +machine: + network: + interfaces: + - interface: eth0 + dhcp: true diff --git a/talos/patches/worker-2.yaml b/talos/patches/worker-2.yaml new file mode 100644 index 0000000..0ade6d9 --- /dev/null +++ b/talos/patches/worker-2.yaml @@ -0,0 +1,5 @@ +machine: + network: + interfaces: + - interface: eth0 + dhcp: true diff --git a/talos/patches/worker-3.yaml b/talos/patches/worker-3.yaml new file mode 100644 index 0000000..0ade6d9 --- /dev/null +++ b/talos/patches/worker-3.yaml @@ -0,0 +1,5 @@ +machine: + network: + interfaces: + - interface: eth0 + dhcp: true diff --git a/talos/patches/worker-type.yaml b/talos/patches/worker-type.yaml new file mode 100644 index 0000000..bf2fe64 --- /dev/null +++ b/talos/patches/worker-type.yaml @@ -0,0 +1,5 @@ +machine: + type: worker + # Remove control plane specific config + controlPlane: + null diff --git a/talos/provision-workers.sh b/talos/provision-workers.sh new file mode 100755 index 0000000..24b0395 --- /dev/null +++ b/talos/provision-workers.sh @@ -0,0 +1,78 @@ +#!/bin/bash +set -e + +TEMPLATE_ID=9001 +VM_IDS=(204 205 206) +VM_NAMES=(talos-worker-1 talos-worker-2 talos-worker-3) +VM_MACS=(BC:24:11:2D:7F:C4 BC:24:11:28:B5:ED BC:24:11:17:90:1B) + +echo "=== Proxmox Worker Node Provisioning Script ===" +echo "" +echo "This will:" +echo " 1. Stop and destroy VMs ${VM_IDS[@]}" +echo " 2. Clone fresh VMs from template $TEMPLATE_ID" +echo " 3. Set specific MAC addresses for consistent IPs" +echo " 4. Start the VMs" +echo "" +read -p "Continue? (y/n) " -n 1 -r +echo +if [[ ! $REPLY =~ ^[Yy]$ ]]; then + echo "Aborted." + exit 1 +fi + +# Stop and destroy VMs +echo "" +echo "Stopping and destroying VMs..." +for VM_ID in "${VM_IDS[@]}"; do + if qm status $VM_ID &>/dev/null; then + echo " Stopping VM $VM_ID..." + qm stop $VM_ID 2>/dev/null || true + sleep 2 + echo " Destroying VM $VM_ID..." + qm destroy $VM_ID + fi +done + +# Clone fresh VMs +echo "" +echo "Cloning fresh VMs from template $TEMPLATE_ID..." +for i in "${!VM_IDS[@]}"; do + VM_ID=${VM_IDS[$i]} + VM_NAME=${VM_NAMES[$i]} + echo " Cloning $VM_ID ($VM_NAME)..." + qm clone $TEMPLATE_ID $VM_ID --name $VM_NAME --full + + # Resize disk to 64G + qm resize $VM_ID scsi0 64G +done + +# Set MAC addresses and configure network +echo "" +echo "Setting MAC addresses..." +for i in "${!VM_IDS[@]}"; do + VM_ID=${VM_IDS[$i]} + MAC=${VM_MACS[$i]} + echo " VM $VM_ID: setting MAC to $MAC" + qm set $VM_ID --net0 virtio=$MAC,bridge=vmbr0 + + # Remove net1 if it exists (workers don't need public network) + qm set $VM_ID --delete net1 2>/dev/null || true +done + +# Start VMs +echo "" +echo "Starting VMs..." +for VM_ID in "${VM_IDS[@]}"; do + echo " Starting VM $VM_ID..." + qm start $VM_ID +done + +echo "" +echo "=== Done! ===" +echo "VMs are booting. Wait ~30 seconds for them to reach maintenance mode." +echo "They should have the same IPs: 10.0.0.104, 10.0.0.105, 10.0.0.106" +echo "" +echo "Next steps:" +echo " 1. ./generate-node-configs.sh" +echo " 2. ./apply-worker-configs.sh" diff --git a/talos/proxmox-ccm/config.yaml b/talos/proxmox-ccm/config.yaml new file mode 100644 index 0000000..a688b8d --- /dev/null +++ b/talos/proxmox-ccm/config.yaml @@ -0,0 +1,6 @@ +clusters: +- url: https://10.0.0.2:8006/api2/json + insecure: true + token_id: "kubernetes-csi@pve!csi" + token_secret: "e1085086-68ee-4a60-bc9e-9e0e36e46f73" + region: "380" diff --git a/talos/proxmox-ccm/secret.yaml b/talos/proxmox-ccm/secret.yaml new file mode 100644 index 0000000..bdcdbcd --- /dev/null +++ b/talos/proxmox-ccm/secret.yaml @@ -0,0 +1,7 @@ +apiVersion: v1 +data: + config.yaml: Y2x1c3RlcnM6Ci0gdXJsOiBodHRwczovLzEwLjAuMC4yOjgwMDYvYXBpMi9qc29uCiAgaW5zZWN1cmU6IHRydWUKICB0b2tlbl9pZDogImt1YmVybmV0ZXMtY3NpQHB2ZSFjc2kiCiAgdG9rZW5fc2VjcmV0OiAiZTEwODUwODYtNjhlZS00YTYwLWJjOWUtOWUwZTM2ZTQ2ZjczIgogIHJlZ2lvbjogIjM4MCIK +kind: Secret +metadata: + name: proxmox-cloud-controller-manager + namespace: kube-system diff --git a/talos/proxmox-csi/namespace.yaml b/talos/proxmox-csi/namespace.yaml new file mode 100644 index 0000000..bbc67cd --- /dev/null +++ b/talos/proxmox-csi/namespace.yaml @@ -0,0 +1,8 @@ +apiVersion: v1 +kind: Namespace +metadata: + name: csi-proxmox + labels: + pod-security.kubernetes.io/enforce: privileged + pod-security.kubernetes.io/audit: baseline + pod-security.kubernetes.io/warn: baseline diff --git a/talos/proxmox-csi/node-providerid-patches.yaml b/talos/proxmox-csi/node-providerid-patches.yaml new file mode 100644 index 0000000..c690ba1 --- /dev/null +++ b/talos/proxmox-csi/node-providerid-patches.yaml @@ -0,0 +1,26 @@ +--- +# Patch for talos-if6-e42 (VM 203) +apiVersion: v1 +kind: Node +metadata: + name: talos-if6-e42 +spec: + providerID: proxmox://380/203 + +--- +# Patch for talos-sbl-bvx (VM 202) +apiVersion: v1 +kind: Node +metadata: + name: talos-sbl-bvx +spec: + providerID: proxmox://380/202 + +--- +# Patch for talos-xgb-7n7 (VM 201) +apiVersion: v1 +kind: Node +metadata: + name: talos-xgb-7n7 +spec: + providerID: proxmox://380/201 diff --git a/talos/proxmox-csi/secret.yaml b/talos/proxmox-csi/secret.yaml new file mode 100644 index 0000000..328c2ab --- /dev/null +++ b/talos/proxmox-csi/secret.yaml @@ -0,0 +1,18 @@ +apiVersion: v1 +kind: Secret +metadata: + name: proxmox-csi-plugin + namespace: csi-proxmox +stringData: + config.yaml: | + clusters: + - url: https://10.0.0.2:8006/api2/json + insecure: true + token_id: "kubernetes-csi@pve!csi" + token_secret: "e1085086-68ee-4a60-bc9e-9e0e36e46f73" + region: "380" + - url: https://10.0.0.1:8006/api2/json + insecure: true + token_id: "kubernetes-csi@pve!csi" + token_secret: "e1085086-68ee-4a60-bc9e-9e0e36e46f73" + region: "380" diff --git a/talos/proxmox-csi/storageclass.yaml b/talos/proxmox-csi/storageclass.yaml new file mode 100644 index 0000000..3e28c79 --- /dev/null +++ b/talos/proxmox-csi/storageclass.yaml @@ -0,0 +1,14 @@ +apiVersion: storage.k8s.io/v1 +kind: StorageClass +metadata: + name: proxmox-local-lvm + annotations: + storageclass.kubernetes.io/is-default-class: "true" +provisioner: csi.proxmox.sinextra.dev +parameters: + storage: local-lvm + csi.storage.k8s.io/fstype: ext4 + cache: writethrough +allowVolumeExpansion: true +reclaimPolicy: Delete +volumeBindingMode: Immediate diff --git a/talos/proxmox-csi/values.yaml b/talos/proxmox-csi/values.yaml new file mode 100644 index 0000000..ee49e54 --- /dev/null +++ b/talos/proxmox-csi/values.yaml @@ -0,0 +1,15 @@ +# Proxmox CSI Plugin Helm Values +config: + clusters: + - url: https://10.0.0.2:8006/api2/json + insecure: false + token_id: "kubernetes-csi@pve!csi" + token_secret: "e1085086-68ee-4a60-bc9e-9e0e36e46f73" + region: 380 + +storageClass: + - name: proxmox-local-lvm + storage: local-lvm + reclaimPolicy: Delete + fstype: ext4 + cache: writethrough diff --git a/talos/reset-vms.sh b/talos/reset-vms.sh new file mode 100755 index 0000000..29d3ba2 --- /dev/null +++ b/talos/reset-vms.sh @@ -0,0 +1,76 @@ +#!/bin/bash +set -e + +TEMPLATE_ID=9001 +VM_IDS=(201 202 203) +VM_NAMES=(talos-cp-1 talos-cp-2 talos-cp-3) + +echo "=== Proxmox VM Reset Script ===" +echo "" +echo "This will:" +echo " 1. Save MAC addresses from VMs ${VM_IDS[@]}" +echo " 2. Stop and destroy those VMs" +echo " 3. Clone fresh VMs from template $TEMPLATE_ID" +echo " 4. Restore the original MAC addresses" +echo " 5. Start the VMs" +echo "" +read -p "Continue? (y/n) " -n 1 -r +echo +if [[ ! $REPLY =~ ^[Yy]$ ]]; then + echo "Aborted." + exit 1 +fi + +# Save MAC addresses +echo "" +echo "Saving MAC addresses..." +declare -A MACS +for i in "${!VM_IDS[@]}"; do + VM_ID=${VM_IDS[$i]} + MAC=$(qm config $VM_ID | grep "^net0:" | sed -n 's/.*virtio=\([^,]*\).*/\1/p') + MACS[$VM_ID]=$MAC + echo " VM $VM_ID: $MAC" +done + +# Stop and destroy VMs +echo "" +echo "Stopping and destroying VMs..." +for VM_ID in "${VM_IDS[@]}"; do + echo " Stopping VM $VM_ID..." + qm stop $VM_ID 2>/dev/null || true + sleep 2 + echo " Destroying VM $VM_ID..." + qm destroy $VM_ID +done + +# Clone fresh VMs +echo "" +echo "Cloning fresh VMs from template $TEMPLATE_ID..." +for i in "${!VM_IDS[@]}"; do + VM_ID=${VM_IDS[$i]} + VM_NAME=${VM_NAMES[$i]} + echo " Cloning $VM_ID ($VM_NAME)..." + qm clone $TEMPLATE_ID $VM_ID --name $VM_NAME --full +done + +# Restore MAC addresses +echo "" +echo "Restoring MAC addresses..." +for VM_ID in "${VM_IDS[@]}"; do + MAC=${MACS[$VM_ID]} + echo " VM $VM_ID: setting MAC to $MAC" + qm set $VM_ID --net0 virtio=$MAC,bridge=vmbr0 +done + +# Start VMs +echo "" +echo "Starting VMs..." +for VM_ID in "${VM_IDS[@]}"; do + echo " Starting VM $VM_ID..." + qm start $VM_ID +done + +echo "" +echo "=== Done! ===" +echo "VMs are booting. Wait ~30 seconds for them to reach maintenance mode." +echo "They should have the same IPs: 10.0.0.101, 10.0.0.102, 10.0.0.103" diff --git a/talos/schematic.yaml b/talos/schematic.yaml new file mode 100644 index 0000000..a4a289f --- /dev/null +++ b/talos/schematic.yaml @@ -0,0 +1,6 @@ +customization: + systemExtensions: + officialExtensions: + - siderolabs/qemu-guest-agent + - siderolabs/iscsi-tools + - siderolabs/tailscale diff --git a/talos/setup-proxmox-csi.sh b/talos/setup-proxmox-csi.sh new file mode 100755 index 0000000..814a102 --- /dev/null +++ b/talos/setup-proxmox-csi.sh @@ -0,0 +1,43 @@ +#!/bin/bash +# Run this script on your Proxmox host (10.0.0.2) + +set -e + +echo "=== Proxmox CSI Setup ===" +echo "" + +# Create CSI role with required permissions +echo "Creating CSI role..." +pveum role add CSI -privs "VM.Audit VM.Config.Disk Datastore.Allocate Datastore.AllocateSpace Datastore.Audit" || echo "Role may already exist" + +# Create kubernetes-csi user +echo "Creating kubernetes-csi user..." +pveum user add kubernetes-csi@pve --comment "User for Kubernetes Proxmox CSI Plugin" || echo "User may already exist" + +# Add ACL for the user +echo "Setting ACL permissions..." +pveum aclmod / -user kubernetes-csi@pve -role CSI + +# Remove existing token if it exists +echo "Removing old token if exists..." +pveum user token remove kubernetes-csi@pve csi 2>/dev/null || true + +# Create API token +echo "Creating API token..." +pveum user token add kubernetes-csi@pve csi --privsep 0 --output-format json > /tmp/csi-token.json + +# Extract token details +TOKEN_ID=$(jq -r '.["full-tokenid"]' /tmp/csi-token.json) +TOKEN_SECRET=$(jq -r '.value' /tmp/csi-token.json) + +echo "" +echo "=== Setup Complete ===" +echo "" +echo "Token ID: $TOKEN_ID" +echo "Token Secret: $TOKEN_SECRET" +echo "" +echo "Save these values! You'll need them for Kubernetes configuration." +echo "" + +# Clean up +rm /tmp/csi-token.json diff --git a/talos/update-proxmox-csi-permissions.sh b/talos/update-proxmox-csi-permissions.sh new file mode 100644 index 0000000..f1ee74f --- /dev/null +++ b/talos/update-proxmox-csi-permissions.sh @@ -0,0 +1,24 @@ +#!/bin/bash +# Run this script on your Proxmox host (10.0.0.2) to update CSI permissions + +set -e + +echo "=== Updating Proxmox CSI Permissions ===" +echo "" + +# Update CSI role with all required permissions +echo "Updating CSI role with comprehensive permissions..." +pveum role modify CSI -privs "VM.Audit VM.Config.Disk VM.Config.CDROM VM.Monitor VM.Allocate Datastore.Allocate Datastore.AllocateSpace Datastore.Audit" + +# Verify the role permissions +echo "" +echo "Current CSI role permissions:" +pveum role list | grep -A 1 CSI + +# Verify ACL is set +echo "" +echo "Current ACL for kubernetes-csi@pve:" +pveum acl list | grep kubernetes-csi + +echo "" +echo "=== Update Complete ===" diff --git a/talos/worker-base.yaml b/talos/worker-base.yaml new file mode 100644 index 0000000..e89d2c0 --- /dev/null +++ b/talos/worker-base.yaml @@ -0,0 +1,114 @@ +--- +version: v1alpha1 +debug: false +persist: true +machine: + type: worker + token: gwdkoe.5gbblli1cvxv1axx + ca: + crt: LS0tLS1CRUdJTiBDRVJUSUZJQ0FURS0tLS0tCk1JSUJQekNCOHFBREFnRUNBaEVBbk5ucllpRDF4bjZaaGVFY0hvTFZ5ekFGQmdNclpYQXdFREVPTUF3R0ExVUUKQ2hNRmRHRnNiM013SGhjTk1qVXhNakkzTWpNeU5UVTNXaGNOTXpVeE1qSTFNak15TlRVM1dqQVFNUTR3REFZRApWUVFLRXdWMFlXeHZjekFxTUFVR0F5dGxjQU1oQVBLMlRCTm5nWlhkRHRDQjBQRXprV0JxNW4zUk0zN0w3c1N1CkVrMGkveGRYbzJFd1h6QU9CZ05WSFE4QkFmOEVCQU1DQW9Rd0hRWURWUjBsQkJZd0ZBWUlLd1lCQlFVSEF3RUcKQ0NzR0FRVUZCd01DTUE4R0ExVWRFd0VCL3dRRk1BTUJBZjh3SFFZRFZSME9CQllFRkxFS0lGTWRTR09pZ09LaQozd3kzR0tWMGp2RDVNQVVHQXl0bGNBTkJBSmlXMEJqNGlaUHpwY2ZWWkhKWXk3dXphOWovOTBIZFJJcHpkdkwzCnc4U1RBcWs2emh0bFoyMVhEWlY1Y05vTWZpc0o0eC8zMzg1MXB6WTN6NHZBYVFvPQotLS0tLUVORCBDRVJUSUZJQ0FURS0tLS0tCg== + key: null + certSANs: [] + kubelet: + image: ghcr.io/siderolabs/kubelet:v1.35.0 + extraMounts: + - destination: /var/lib/kubelet/plugins + type: bind + source: /var/lib/kubelet/plugins + options: + - bind + - rshared + - rw + defaultRuntimeSeccompProfileEnabled: true + disableManifestsDirectory: true + network: {} + install: + disk: /dev/sda + image: factory.talos.dev/installer/959b38c028569ff2f710c3cfcb3f90d4015282b278f020bb58cf1bda1f9ef93a:v1.12.0 + wipe: false + grubUseUKICmdline: true + files: + - content: tskey-auth-k6cryUGtC521CNTRL-vnjxfuqSqs2Es4kX2SG1s2p3btRizMiG + permissions: 0o600 + path: /var/etc/tailscale/auth.key + op: create + - content: 10.0.0.0/24 + permissions: 0o600 + path: /var/etc/tailscale/routes + op: create + - content: --accept-routes --advertise-tags=tag:k8s-cp + permissions: 0o600 + path: /var/etc/tailscale/args + op: create + features: + diskQuotaSupport: true + kubePrism: + enabled: true + port: 7445 + hostDNS: + enabled: true + forwardKubeDNSToHost: true + nodeLabels: + node.kubernetes.io/exclude-from-external-load-balancers: '' +cluster: + id: eKSkTfDUW0U4if1QcK9otzZnNktorUsvnndBrHM4WBE= + secret: UumfthEFQUDRssdtWbbVezTJJZOtIIw3Db6f342SwW4= + controlPlane: + endpoint: https://10.0.0.101:6443 + clusterName: vntx + network: + dnsDomain: cluster.local + podSubnets: + - 10.244.0.0/16 + serviceSubnets: + - 10.96.0.0/12 + token: 71gr3x.96za7btksx23r8bk + secretboxEncryptionSecret: 1+h+VmWKw3PPspmZ/+u27nhznTt8lRBd9RQQuepZ5/E= + ca: + crt: LS0tLS1CRUdJTiBDRVJUSUZJQ0FURS0tLS0tCk1JSUJpakNDQVMrZ0F3SUJBZ0lRVUxsZy9jbEovUkRzVFo1WHNvR0I3VEFLQmdncWhrak9QUVFEQWpBVk1STXcKRVFZRFZRUUtFd3ByZFdKbGNtNWxkR1Z6TUI0WERUSTFNVEl5TnpJek1qVTFOMW9YRFRNMU1USXlOVEl6TWpVMQpOMW93RlRFVE1CRUdBMVVFQ2hNS2EzVmlaWEp1WlhSbGN6QlpNQk1HQnlxR1NNNDlBZ0VHQ0NxR1NNNDlBd0VICkEwSUFCQ2xSVkxiQThpNTJjWUo2bnRRR2lpRnVTRnhVVnphMDA0UDhwM3VwK295SXFPWldJL3llSzY0VU9ueUkKeUF6YzhySXcxeTRjZGYyc1Y4OHhlczUvMzRhallUQmZNQTRHQTFVZER3RUIvd1FFQXdJQ2hEQWRCZ05WSFNVRQpGakFVQmdnckJnRUZCUWNEQVFZSUt3WUJCUVVIQXdJd0R3WURWUjBUQVFIL0JBVXdBd0VCL3pBZEJnTlZIUTRFCkZnUVVuVndjRnRKSHFRV0JuYk9ld3FlcCthUFByTnd3Q2dZSUtvWkl6ajBFQXdJRFNRQXdSZ0loQUlZTnFZaHUKNjNpQy9kMzUzQTFTeUhCN2lMWCtSQ1V2R2cza3BtQW1ybG5pQWlFQTdsSURuaElyUUJUMHNQa29aRHFIYWdJTgphZjRsTEhnbllaTUR3d0FVM3JFPQotLS0tLUVORCBDRVJUSUZJQ0FURS0tLS0tCg== + key: null + aggregatorCA: + crt: LS0tLS1CRUdJTiBDRVJUSUZJQ0FURS0tLS0tCk1JSUJYekNDQVFhZ0F3SUJBZ0lSQUtGQ1hXS24vTnR4eVBuNmxYZjU4R2N3Q2dZSUtvWkl6ajBFQXdJd0FEQWUKRncweU5URXlNamN5TXpJMU5UZGFGdzB6TlRFeU1qVXlNekkxTlRkYU1BQXdXVEFUQmdjcWhrak9QUUlCQmdncQpoa2pPUFFNQkJ3TkNBQVMwMmptRnFCWU1hSURHeVRQWGNhTjQ2UTRBdCtTLzFob0lqd1QveHhZZUowVDJNeDh1ClRVSWQzNjVKT1dSK2FQS2dWdUkySVZpKzZDNXJOcnBSSnhES28yRXdYekFPQmdOVkhROEJBZjhFQkFNQ0FvUXcKSFFZRFZSMGxCQll3RkFZSUt3WUJCUVVIQXdFR0NDc0dBUVVGQndNQ01BOEdBMVVkRXdFQi93UUZNQU1CQWY4dwpIUVlEVlIwT0JCWUVGTXFxVnowdDVaaERQVTdzcS9hdUxKcWxjMVlkTUFvR0NDcUdTTTQ5QkFNQ0EwY0FNRVFDCklBdEI4L0hpSS9RakVEVjFiV29DZ1M1TkdtbDNzdUFTRGtUbkZjK2F3TmlEQWlBNzlPeHVJeVl1VFgyVUxvQlQKZWRXbDdEZ0Y0N3htTnM2OTNGcThLeXRGc0E9PQotLS0tLUVORCBDRVJUSUZJQ0FURS0tLS0tCg== + key: null + serviceAccount: + key: null + apiServer: + image: registry.k8s.io/kube-apiserver:v1.35.0 + admissionControl: + - name: PodSecurity + configuration: + apiVersion: pod-security.admission.config.k8s.io/v1alpha1 + defaults: + audit: restricted + audit-version: latest + enforce: baseline + enforce-version: latest + warn: restricted + warn-version: latest + exemptions: + namespaces: + - kube-system + runtimeClasses: [] + usernames: [] + kind: PodSecurityConfiguration + auditPolicy: + apiVersion: audit.k8s.io/v1 + kind: Policy + rules: + - level: Metadata + controllerManager: + image: registry.k8s.io/kube-controller-manager:v1.35.0 + proxy: + image: registry.k8s.io/kube-proxy:v1.35.0 + scheduler: + image: registry.k8s.io/kube-scheduler:v1.35.0 + discovery: + enabled: true + registries: + kubernetes: + disabled: true + service: {} +--- +apiVersion: v1alpha1 +kind: HostnameConfig +auto: stable diff --git a/talos/worker-base.yaml.backup b/talos/worker-base.yaml.backup new file mode 100644 index 0000000..42c29cb --- /dev/null +++ b/talos/worker-base.yaml.backup @@ -0,0 +1,121 @@ +version: v1alpha1 +debug: false +persist: true +machine: + type: worker + token: gwdkoe.5gbblli1cvxv1axx + ca: + crt: LS0tLS1CRUdJTiBDRVJUSUZJQ0FURS0tLS0tCk1JSUJQekNCOHFBREFnRUNBaEVBbk5ucllpRDF4bjZaaGVFY0hvTFZ5ekFGQmdNclpYQXdFREVPTUF3R0ExVUUKQ2hNRmRHRnNiM013SGhjTk1qVXhNakkzTWpNeU5UVTNXaGNOTXpVeE1qSTFNak15TlRVM1dqQVFNUTR3REFZRApWUVFLRXdWMFlXeHZjekFxTUFVR0F5dGxjQU1oQVBLMlRCTm5nWlhkRHRDQjBQRXprV0JxNW4zUk0zN0w3c1N1CkVrMGkveGRYbzJFd1h6QU9CZ05WSFE4QkFmOEVCQU1DQW9Rd0hRWURWUjBsQkJZd0ZBWUlLd1lCQlFVSEF3RUcKQ0NzR0FRVUZCd01DTUE4R0ExVWRFd0VCL3dRRk1BTUJBZjh3SFFZRFZSME9CQllFRkxFS0lGTWRTR09pZ09LaQozd3kzR0tWMGp2RDVNQVVHQXl0bGNBTkJBSmlXMEJqNGlaUHpwY2ZWWkhKWXk3dXphOWovOTBIZFJJcHpkdkwzCnc4U1RBcWs2emh0bFoyMVhEWlY1Y05vTWZpc0o0eC8zMzg1MXB6WTN6NHZBYVFvPQotLS0tLUVORCBDRVJUSUZJQ0FURS0tLS0tCg== + key: LS0tLS1CRUdJTiBFRDI1NTE5IFBSSVZBVEUgS0VZLS0tLS0KTUM0Q0FRQXdCUVlESzJWd0JDSUVJT0xneGYyN041VXhnUStER3NoZU04dThzdnlCbE8vUmRMYUpETEFHOEF3TAotLS0tLUVORCBFRDI1NTE5IFBSSVZBVEUgS0VZLS0tLS0K + certSANs: [] + kubelet: + image: ghcr.io/siderolabs/kubelet:v1.35.0 + extraMounts: + - destination: /var/lib/kubelet/plugins + type: bind + source: /var/lib/kubelet/plugins + options: + - bind + - rshared + - rw + defaultRuntimeSeccompProfileEnabled: true + disableManifestsDirectory: true + network: {} + install: + disk: /dev/sda + image: ghcr.io/siderolabs/installer:v1.12.0 + extensions: + - image: ghcr.io/siderolabs/qemu-guest-agent:8.2.2 + - image: ghcr.io/siderolabs/iscsi-tools:v0.1.6 + - image: ghcr.io/siderolabs/tailscale:1.78.3 + wipe: false + grubUseUKICmdline: true + files: + - content: tskey-auth-k6cryUGtC521CNTRL-vnjxfuqSqs2Es4kX2SG1s2p3btRizMiG + permissions: 0o600 + path: /var/etc/tailscale/auth.key + op: create + - content: 10.0.0.0/24 + permissions: 0o600 + path: /var/etc/tailscale/routes + op: create + - content: --accept-routes --advertise-tags=tag:k8s-cp + permissions: 0o600 + path: /var/etc/tailscale/args + op: create + features: + diskQuotaSupport: true + kubePrism: + enabled: true + port: 7445 + hostDNS: + enabled: true + forwardKubeDNSToHost: true + nodeLabels: + node.kubernetes.io/exclude-from-external-load-balancers: "" +cluster: + id: eKSkTfDUW0U4if1QcK9otzZnNktorUsvnndBrHM4WBE= + secret: UumfthEFQUDRssdtWbbVezTJJZOtIIw3Db6f342SwW4= + controlPlane: + endpoint: https://10.0.0.101:6443 + clusterName: vntx + network: + dnsDomain: cluster.local + podSubnets: + - 10.244.0.0/16 + serviceSubnets: + - 10.96.0.0/12 + token: 71gr3x.96za7btksx23r8bk + secretboxEncryptionSecret: 1+h+VmWKw3PPspmZ/+u27nhznTt8lRBd9RQQuepZ5/E= + ca: + crt: LS0tLS1CRUdJTiBDRVJUSUZJQ0FURS0tLS0tCk1JSUJpakNDQVMrZ0F3SUJBZ0lRVUxsZy9jbEovUkRzVFo1WHNvR0I3VEFLQmdncWhrak9QUVFEQWpBVk1STXcKRVFZRFZRUUtFd3ByZFdKbGNtNWxkR1Z6TUI0WERUSTFNVEl5TnpJek1qVTFOMW9YRFRNMU1USXlOVEl6TWpVMQpOMW93RlRFVE1CRUdBMVVFQ2hNS2EzVmlaWEp1WlhSbGN6QlpNQk1HQnlxR1NNNDlBZ0VHQ0NxR1NNNDlBd0VICkEwSUFCQ2xSVkxiQThpNTJjWUo2bnRRR2lpRnVTRnhVVnphMDA0UDhwM3VwK295SXFPWldJL3llSzY0VU9ueUkKeUF6YzhySXcxeTRjZGYyc1Y4OHhlczUvMzRhallUQmZNQTRHQTFVZER3RUIvd1FFQXdJQ2hEQWRCZ05WSFNVRQpGakFVQmdnckJnRUZCUWNEQVFZSUt3WUJCUVVIQXdJd0R3WURWUjBUQVFIL0JBVXdBd0VCL3pBZEJnTlZIUTRFCkZnUVVuVndjRnRKSHFRV0JuYk9ld3FlcCthUFByTnd3Q2dZSUtvWkl6ajBFQXdJRFNRQXdSZ0loQUlZTnFZaHUKNjNpQy9kMzUzQTFTeUhCN2lMWCtSQ1V2R2cza3BtQW1ybG5pQWlFQTdsSURuaElyUUJUMHNQa29aRHFIYWdJTgphZjRsTEhnbllaTUR3d0FVM3JFPQotLS0tLUVORCBDRVJUSUZJQ0FURS0tLS0tCg== + key: LS0tLS1CRUdJTiBFQyBQUklWQVRFIEtFWS0tLS0tCk1IY0NBUUVFSUpyNlRETEhtRk1aT1RJWXpIWmxNOS9tbTVYZ0l0cWowMEROMzk3Qk9uOEpvQW9HQ0NxR1NNNDkKQXdFSG9VUURRZ0FFS1ZGVXRzRHlMblp4Z25xZTFBYUtJVzVJWEZSWE5yVFRnL3luZTZuNmpJaW81bFlqL0o0cgpyaFE2ZklqSUROenlzakRYTGh4MS9heFh6ekY2em4vZmhnPT0KLS0tLS1FTkQgRUMgUFJJVkFURSBLRVktLS0tLQo= + aggregatorCA: + crt: LS0tLS1CRUdJTiBDRVJUSUZJQ0FURS0tLS0tCk1JSUJYekNDQVFhZ0F3SUJBZ0lSQUtGQ1hXS24vTnR4eVBuNmxYZjU4R2N3Q2dZSUtvWkl6ajBFQXdJd0FEQWUKRncweU5URXlNamN5TXpJMU5UZGFGdzB6TlRFeU1qVXlNekkxTlRkYU1BQXdXVEFUQmdjcWhrak9QUUlCQmdncQpoa2pPUFFNQkJ3TkNBQVMwMmptRnFCWU1hSURHeVRQWGNhTjQ2UTRBdCtTLzFob0lqd1QveHhZZUowVDJNeDh1ClRVSWQzNjVKT1dSK2FQS2dWdUkySVZpKzZDNXJOcnBSSnhES28yRXdYekFPQmdOVkhROEJBZjhFQkFNQ0FvUXcKSFFZRFZSMGxCQll3RkFZSUt3WUJCUVVIQXdFR0NDc0dBUVVGQndNQ01BOEdBMVVkRXdFQi93UUZNQU1CQWY4dwpIUVlEVlIwT0JCWUVGTXFxVnowdDVaaERQVTdzcS9hdUxKcWxjMVlkTUFvR0NDcUdTTTQ5QkFNQ0EwY0FNRVFDCklBdEI4L0hpSS9RakVEVjFiV29DZ1M1TkdtbDNzdUFTRGtUbkZjK2F3TmlEQWlBNzlPeHVJeVl1VFgyVUxvQlQKZWRXbDdEZ0Y0N3htTnM2OTNGcThLeXRGc0E9PQotLS0tLUVORCBDRVJUSUZJQ0FURS0tLS0tCg== + key: LS0tLS1CRUdJTiBFQyBQUklWQVRFIEtFWS0tLS0tCk1IY0NBUUVFSU9EVVVzMklrazhaeGowRDNRQVBLeTlpTCtTSVNaZGhOZjMrdVBqOHNudVRvQW9HQ0NxR1NNNDkKQXdFSG9VUURRZ0FFdE5vNWhhZ1dER2lBeHNrejEzR2plT2tPQUxma3Y5WWFDSThFLzhjV0hpZEU5ak1mTGsxQwpIZCt1U1Rsa2ZtanlvRmJpTmlGWXZ1Z3VhemE2VVNjUXlnPT0KLS0tLS1FTkQgRUMgUFJJVkFURSBLRVktLS0tLQo= + serviceAccount: + key: LS0tLS1CRUdJTiBSU0EgUFJJVkFURSBLRVktLS0tLQpNSUlKS1FJQkFBS0NBZ0VBM0gzV1hzZVU4clpGdzhkaUhIbzB3aWFQdnV3N3VpblJ3MS9xbnB6VldjVGRlWUcrCnJlQ0dMek1vNWlzaHBQT3N2WVd5UEVoZlVyZ01ldTY3cFlTMFNxSmtGcnJtY3lrQUNybHFtaE54ZzVBazZZcTIKOWhPeUphR0tKOVkrdEUzNmFjUjBIWTJ4UEV3K0lKbEdIVUpLNSs2RUsxUXVjYTF5TXpLc0pOM1VrSDVzNXpXeApEbCtSdHJLNklXdEsxYjZ5M213SmtaRTJIYktxUUdXdWxONDZ6M1gzTXJLNk9POVhHNTJ2S3dINFBzdHFHVDc5Ck92dlI3b21yaVF6OUJUclhSYXlqRGp4MEl3NGVTVVJ4QkFsRFlsZDlqd2E3aXd1NHU5bldlazYyRjM3S3VMTE4KYlpWWlQ4WjJqQlJ5WGp5ZXdkTkFpL0Z4bElNSWtSdjE0VVV4M3NEdDhycGh2b2xERDBXVGlRcTNyQkNSUUNrVQpldWpZUmloaDNnQUI4QTN5dGJrZGJSNlgrQ2IrR21NMFVycmgwb2RnWDg0dkdrY1lhR1NrSnRKSEttSlNDUGN3CkJYa29taHd2dDJ4UzVEQTM4aUhPWDc5OTgrQzdJQWpyWnpka3ZLSXZIc1grSklvYTF4d0ZiclJTOUIrNUNDMXQKdnVFd1pvVXlTWEdDOWh0bkd5M1ZjcUdsbFBUQ3NEaForZkpXNGRNazE2cldaVW5uSmM3ek1Fa2pleVJzUERnZAptM215Z0w1RDd2S2w1SnBGNWphM2wzOEt4OC9xKzU3OFY2RllSblhvUElGS25TbGFLNmorKzdmeFZyMFdPNlk4CjRKVnFyUG5LYVVvQ0I0WTFrZGlqSkI1TndVRjVWazdqNVUyWThYRk1vWjRtNGdWQ29jS3laUDlIYXlNQ0F3RUEKQVFLQ0FnQUl3bGovUitkell1bFBsejZmQ2YzSmpyV2NMSTlNM0hkd1R3R25qbXh0VmdSRVhQS2h2cThsOWQ3VQprZmNTc2ZsMVIvZm1MQ3ZaUWVXQkJyWGVvL0J6bkpMa1VrVndZcnNWTWZ0NXBuY1dkbVg0L3lFNGtseTc0UGgzCmo2dkxCdVFCU3FRZ1BtNUJpbmZYWEs5cjN5UFJwZWlMUGh0Z09iYzFNSGlsT0VqRytyYkIwcUMzaFBWcGNCMHoKMGFyVjVlNytKZ1dWU2xML2lBYjZhdSt1QzB3RHpOaG1vN0lCTEFUbVhIUEdmaHdLQnBPdThCRW9SRE81U2EvTwpVSDFHdFdreTQrSlFZUGR1SXhQeDdpMmRMdThGMjVycDBTY25KVzZQeTk0WTJzS2lHVS9kV1lFT3J1V3U1Ui8xCmZhUnplTzRIbmloTXh1a3ZzS3JvOU5ibVBaVDNCUXR2SGl4ZlVNU2pmTXZFcUorNDhpdlA1RTNiYUJHRk5Mc3oKbUZXZW91MFEzVzNTMU50RkQvWnIybFJpT3VrVzhLLytBSm1PL210RWd2NG1UK3pHa05BUGhPT3lQcUlTakgxTAp1WTY3c08wRGlJWmJ1REdmZDQ2YXN3bHBZQis1Z0ZMZGxONDNJcGRxZG5GMFdtbjkybXk3cVluVVhkSkJENnZNCm5TWGJJOTZZOSt6K3V6citTZWMzeWhEckd6a1c1NWJ4VHJqb1FMZ2d6RDRVSWEyMm1ueUFOb3UrZzkyU09RSnEKb0hmWGZoeDdJeEZyM2h2V3ZaVVlYNit6bndUZTBKeVI0cy9NaXZxM2NIVERzV1A2NXBMd3VNQXRMMW1qWHNOcgp4aGhzZDQrNkJYb0R1OGl1V1NFRDlndlFIbVFlN3p3azVEVlNPbXJOTHlZTnZ3Y0U1UUtDQVFFQTYxaWR3VUp0CmJEMUlzQ1RBaVJnaFEvT0oxY3cwcmNqSDhGcGRNaFg1MHc2NUJqcmk5OEU5eDNkK2JpZVA3eXk5cVNMcnN5dzIKSDNteTJXOEZOSHdUUnJCT2NnQVg0cWhSa205Y0tBSlhGS0xVbGY4TlJocWJrR3RyVnMybEdDdXBEZHJxN2RpTApHRGdxY2gxbHpXR1d1UlQyOWZDRXRzZWVyd2NFemtXYTE0MDRYWEIyTi9EK0FHbVB2Mmp2dEFOSml0ekFuL0pWCnQ4NnZLVyttbWlxNVFQNlZHZjFtVmZTMGlSQy9TVzJMditGR3J2ZmRsNHN4WXJONnoweVdZSUZqK2J3aVNYblIKZXhTKzYyUUtleGJCalZwa2gzRnJTNWNsZWJ1ajg0aWVEaVQ1ZDFsTTNhaHlpSjRJYk1IaVJyeG1wSFNDVmkrUQorOHpSbHRwcGI2eko5UUtDQVFFQTc5ZDkwWDhqeFJKV015MUFWTDlrMnN5YjZacG9XN2FHL3AwNTlHVi80dXBNCi9DdTRXVVdOajdWdW1sRmppUFdtT0hhMkxIVnZmVW5DY3M1WTYxRTJVWm9mNXcxLzZ5R2ZwdEtzZ0V5eElUZGMKMFRFV0pPTy9QeVZabEhXR2xJVVNsMlBsTlFuclh6OCsvY29RZklSS29OZmd6K1p5NHdLdFpMWDdpUDBlaGt4YgphWmhNWWF0azNhN0FyQURPRFZiZ1Z3dkdjaER6Vm5oNjc4TzF3a0p0WjJ6TUlrOGF4cy9WR1VMQ0NRdURTV2pICkdsb2IvQlA3TERBdWxKVlN3ajNOY2NLK01ZMnpSSXEwcHNYWkxsVlJicTRZSlhFbUxoRFEzUXhvUklLQVZQM08KWkZWR2lDT3lXU1dJclprZkZHaEkrNlFram1YazJmYmNPTE9QNGUyNXR3S0NBUUVBd3ZKcDR0OXlvcGwxTDZ1Ugo3VDRXdUNIeFNDOWFaNllNc0xVNXc3WmVkZzBaQ09jWWdXQUtHOE9JOEJoSGF6aWxkb2hkczlKb2x0UUphWUZFClQ0Q0R1eWRxSTVhZU1udDQ3cExlUktvRGxpMTNhVFNYdXoxcEpVMUY0ZWFBM2krMFhxeTdzLytPNEtZTnl1ODkKRjg3QnVsaDZaYWt4VmZLdktJN28xVERsSGE1MlJUaFdST3FVaktUa2xRcUluSldvZ3FWdnprNC80UDBOTFlhMQorN2h1TWo5d0pOSTV4ZlBvNUMwQ053SE9KRWlvYzJFUXBtcC9veUhIRmhaNzdqN2dJTXRObjQyUUQ2TlVyc24wCndKZE9CeGdjYy9Gb2pub0thZmNielN5YXVGNjZZcm1QS1lGU05vYXB0ZVU0MloxUWJPT3gzMUNSaVhMVkhsK1gKdlJEbFRRS0NBUUJBNkVpY2taUFVtWW5LZjh5Ukl0cmdlODhXQVR1TTFuRGlKeHF3RVdmeXVRWHNtTWhqSUhlWApGTHJCK0pTL1UvdVAvRkNBNTZjc2VQR3VzRGxRTmNKRmd6aHZCekEvS2ZKUzYyRFR0KzJYMTZ1KzBWSDAyYzNBCkFST2xJY2t5R0hGWGx5bEltVTZoa0RRejZxTmJqMUhEQmFsSm1rd3RNMlJKaFJaMWxFcldmWU9mcUIvRHJ1YTEKTjczY3pycjAwVFlWV0pKei9ESmVqR3g0eHJaQnhFaG5YUUpCcHJiUVp4NThuNXh6WmpJNWc2bWVjQlJ5dTlXVgp0OVJqVWFYNyswM0dJN1hsSXp3SXFLRUxJVEFOWWZtUHduMjJaRkM0MXNRdmpsUUpkbWZVbUh0cW04bGl2b1pkCnFkSzdhRjBJNE5BZmllUjZ4UWlTRkVTMDg2TlV1VWt4QW9JQkFRRG9WL0pJRlNEejl3Z3dneUhhdmdwSnR0UGkKNWZBeEpZaktZbUtsLzdpZUdkZ0pzN1dwR3dxNXlQZFVVRE1yMnNKUDBGWDhEZFJTSktWLzExRzMvaklTL1JyQQpwcDVsS2hGbEFncVBvZ1EvL0IzTVBiNXZiNTBSMExrNGJtVWVYcUVhMkJBSTlmc0R3WEFZbFhsMnJOT0drdEdSCnJZd1BEdHlhbnI1d0grVEtoYjdqODdWN2Z1TWpRcU5SK21TQVJqZXpvRHNQdnJvUHB0d1o0RnBSOTNCUXJqUGoKRWF6Z1UvbHlSRkVCNklISFhvbWFaR1ExYlY1TG85ZTlUZGp6VFpiT2tJMUFsL3B6cWx5WlpzdnU5RnFURUdUbwpRckt6Nm9xeFJyR1lhUVNJbGpydWhPajdiWUVPeGp2VnFEdmNIaGNxV1paN0h5VWNjS2gzNFZReWhCdTQKLS0tLS1FTkQgUlNBIFBSSVZBVEUgS0VZLS0tLS0K + apiServer: + image: registry.k8s.io/kube-apiserver:v1.35.0 + admissionControl: + - name: PodSecurity + configuration: + apiVersion: pod-security.admission.config.k8s.io/v1alpha1 + defaults: + audit: restricted + audit-version: latest + enforce: baseline + enforce-version: latest + warn: restricted + warn-version: latest + exemptions: + namespaces: + - kube-system + runtimeClasses: [] + usernames: [] + kind: PodSecurityConfiguration + auditPolicy: + apiVersion: audit.k8s.io/v1 + kind: Policy + rules: + - level: Metadata + controllerManager: + image: registry.k8s.io/kube-controller-manager:v1.35.0 + proxy: + image: registry.k8s.io/kube-proxy:v1.35.0 + scheduler: + image: registry.k8s.io/kube-scheduler:v1.35.0 + discovery: + enabled: true + registries: + kubernetes: + disabled: true + service: {} + etcd: + ca: + crt: LS0tLS1CRUdJTiBDRVJUSUZJQ0FURS0tLS0tCk1JSUJmVENDQVNPZ0F3SUJBZ0lRY1hQekZ3N2lYdnlnY2FVMGlUQ3lGekFLQmdncWhrak9QUVFEQWpBUE1RMHcKQ3dZRFZRUUtFd1JsZEdOa01CNFhEVEkxTVRJeU56SXpNalUxTjFvWERUTTFNVEl5TlRJek1qVTFOMW93RHpFTgpNQXNHQTFVRUNoTUVaWFJqWkRCWk1CTUdCeXFHU000OUFnRUdDQ3FHU000OUF3RUhBMElBQlBpREhoWTkzT1FFClpaS2x1L1M3NVBnRmlvNks5SjV1RUZwNk12c3N4NnYzWld6RXJ2clBoNW53QkFqVFFOOUdodTRmQ1dXbXdsQmgKVVhIU09RcHh5OStqWVRCZk1BNEdBMVVkRHdFQi93UUVBd0lDaERBZEJnTlZIU1VFRmpBVUJnZ3JCZ0VGQlFjRApBUVlJS3dZQkJRVUhBd0l3RHdZRFZSMFRBUUgvQkFVd0F3RUIvekFkQmdOVkhRNEVGZ1FVYnc1N01IV1JvWnYyClZ6UndZNGIyY3c1VGw3c3dDZ1lJS29aSXpqMEVBd0lEU0FBd1JRSWdHR1BOZmNzT2M0ajlFblNIbkhRV2dydEQKbEdZWitpZ3JKQnZSWGFSa1FRd0NJUUNOeUlRVU9reWx5U0Vpc1ZyNzFhR3hTRHJ5UFgwZlRuMEdZM25qalpkQQpaUT09Ci0tLS0tRU5EIENFUlRJRklDQVRFLS0tLS0K + key: LS0tLS1CRUdJTiBFQyBQUklWQVRFIEtFWS0tLS0tCk1IY0NBUUVFSUtpazBDeFdObEx6ZWJaY2kwSVYyUHNqOGRoRis5L0Nsb3JXbzAySUdRb1BvQW9HQ0NxR1NNNDkKQXdFSG9VUURRZ0FFK0lNZUZqM2M1QVJsa3FXNzlMdmsrQVdLam9yMG5tNFFXbm95K3l6SHEvZGxiTVN1K3MrSAptZkFFQ05OQTMwYUc3aDhKWmFiQ1VHRlJjZEk1Q25ITDN3PT0KLS0tLS1FTkQgRUMgUFJJVkFURSBLRVktLS0tLQo= +--- +apiVersion: v1alpha1 +kind: HostnameConfig +auto: stable diff --git a/talos/worker.yaml b/talos/worker.yaml new file mode 100644 index 0000000..59c8a35 --- /dev/null +++ b/talos/worker.yaml @@ -0,0 +1,433 @@ +version: v1alpha1 # Indicates the schema used to decode the contents. +debug: false # Enable verbose logging to the console. +persist: true +# Provides machine specific configuration options. +machine: + type: worker # Defines the role of the machine within the cluster. + token: crmyjb.dxygte3bpfb9bhbx # The `token` is used by a machine to join the PKI of the cluster. + # The root certificate authority of the PKI. + ca: + crt: LS0tLS1CRUdJTiBDRVJUSUZJQ0FURS0tLS0tCk1JSUJQakNCOGFBREFnRUNBaEJCTXQvK0c0T3h2dVJvZVhIZWVvaitNQVVHQXl0bGNEQVFNUTR3REFZRFZRUUsKRXdWMFlXeHZjekFlRncweU5qQXhNREV5TWpBeE16bGFGdzB6TlRFeU16QXlNakF4TXpsYU1CQXhEakFNQmdOVgpCQW9UQlhSaGJHOXpNQ293QlFZREsyVndBeUVBZUZGeHM1ZjhlcEg5RFJ3WlZPVTBlM3NLbEdYQ3ZlbDZqU2pqCjRzOEp0WWVqWVRCZk1BNEdBMVVkRHdFQi93UUVBd0lDaERBZEJnTlZIU1VFRmpBVUJnZ3JCZ0VGQlFjREFRWUkKS3dZQkJRVUhBd0l3RHdZRFZSMFRBUUgvQkFVd0F3RUIvekFkQmdOVkhRNEVGZ1FVNHluSml6aUYwbFFJUUVISwpnUzB3YmtyNmNKd3dCUVlESzJWd0EwRUFtdjZMNVRpem9YaTk0NXY2aU4rT2w4SDdHM0dCOFFyVXhMYnF5Nk1SCkdnNUtsZkVNYUhQTGlNMXVPaTNsd2FnWndhd2wvTDFVckNGdDhOdmNHQjZkQ2c9PQotLS0tLUVORCBDRVJUSUZJQ0FURS0tLS0tCg== + key: "" + # Extra certificate subject alternative names for the machine's certificate. + certSANs: [] + # # Uncomment this to enable SANs. + # - 10.0.0.10 + # - 172.16.0.10 + # - 192.168.0.10 + + # Used to provide additional options to the kubelet. + kubelet: + image: ghcr.io/siderolabs/kubelet:v1.35.0 # The `image` field is an optional reference to an alternative kubelet image. + defaultRuntimeSeccompProfileEnabled: true # Enable container runtime default Seccomp profile. + disableManifestsDirectory: true # The `disableManifestsDirectory` field configures the kubelet to get static pod manifests from the /etc/kubernetes/manifests directory. + + # # The `ClusterDNS` field is an optional reference to an alternative kubelet clusterDNS ip list. + # clusterDNS: + # - 10.96.0.10 + # - 169.254.2.53 + + # # The `extraArgs` field is used to provide additional flags to the kubelet. + # extraArgs: + # key: value + + # # The `extraMounts` field is used to add additional mounts to the kubelet container. + # extraMounts: + # - destination: /var/lib/example # Destination is the absolute path where the mount will be placed in the container. + # type: bind # Type specifies the mount kind. + # source: /var/lib/example # Source specifies the source path of the mount. + # # Options are fstab style mount options. + # options: + # - bind + # - rshared + # - rw + + # # The `extraConfig` field is used to provide kubelet configuration overrides. + # extraConfig: + # serverTLSBootstrap: true + + # # The `KubeletCredentialProviderConfig` field is used to provide kubelet credential configuration. + # credentialProviderConfig: + # apiVersion: kubelet.config.k8s.io/v1 + # kind: CredentialProviderConfig + # providers: + # - apiVersion: credentialprovider.kubelet.k8s.io/v1 + # defaultCacheDuration: 12h + # matchImages: + # - '*.dkr.ecr.*.amazonaws.com' + # - '*.dkr.ecr.*.amazonaws.com.cn' + # - '*.dkr.ecr-fips.*.amazonaws.com' + # - '*.dkr.ecr.us-iso-east-1.c2s.ic.gov' + # - '*.dkr.ecr.us-isob-east-1.sc2s.sgov.gov' + # name: ecr-credential-provider + + # # The `nodeIP` field is used to configure `--node-ip` flag for the kubelet. + # nodeIP: + # # The `validSubnets` field configures the networks to pick kubelet node IP from. + # validSubnets: + # - 10.0.0.0/8 + # - '!10.0.0.3/32' + # - fdc7::/16 + # Provides machine specific network configuration options. + network: {} + # # Configures KubeSpan feature. + # kubespan: + # enabled: true # Enable the KubeSpan feature. + + # Used to provide instructions for installations. + install: + disk: /dev/sda # The disk used for installations. + image: ghcr.io/siderolabs/installer:v1.12.0 # Allows for supplying the image used to perform the installation. + wipe: false # Indicates if the installation disk should be wiped at installation time. + grubUseUKICmdline: true # Indicates if legacy GRUB bootloader should use kernel cmdline from the UKI instead of building it on the host. + + # # Look up disk using disk attributes like model, size, serial and others. + # diskSelector: + # size: 4GB # Disk size. + # model: WDC* # Disk model `/sys/block//device/model`. + # busPath: /pci0000:00/0000:00:17.0/ata1/host0/target0:0:0/0:0:0:0 # Disk bus path. + registries: {} + # Features describe individual Talos features that can be switched on or off. + features: + diskQuotaSupport: true # Enable XFS project quota support for EPHEMERAL partition and user disks. + # KubePrism - local proxy/load balancer on defined port that will distribute + kubePrism: + enabled: true # Enable KubePrism support - will start local load balancing proxy. + port: 7445 # KubePrism port. + # Configures host DNS caching resolver. + hostDNS: + enabled: true # Enable host DNS caching resolver. + forwardKubeDNSToHost: true # Use the host DNS resolver as upstream for Kubernetes CoreDNS pods. + + # # Configure Talos API access from Kubernetes pods. + # kubernetesTalosAPIAccess: + # enabled: true # Enable Talos API access from Kubernetes pods. + # # The list of Talos API roles which can be granted for access from Kubernetes pods. + # allowedRoles: + # - os:reader + # # The list of Kubernetes namespaces Talos API access is available from. + # allowedKubernetesNamespaces: + # - kube-system + + # # Provides machine specific control plane configuration options. + + # # ControlPlane definition example. + # controlPlane: + # # Controller manager machine specific configuration options. + # controllerManager: + # disabled: false # Disable kube-controller-manager on the node. + # # Scheduler machine specific configuration options. + # scheduler: + # disabled: true # Disable kube-scheduler on the node. + + # # Used to provide static pod definitions to be run by the kubelet directly bypassing the kube-apiserver. + + # # nginx static pod. + # pods: + # - apiVersion: v1 + # kind: pod + # metadata: + # name: nginx + # spec: + # containers: + # - image: nginx + # name: nginx + + # # Allows the addition of user specified files. + + # # MachineFiles usage example. + # files: + # - content: '...' # The contents of the file. + # permissions: 0o666 # The file's permissions in octal. + # path: /tmp/file.txt # The path of the file. + # op: append # The operation to use + + # # The `env` field allows for the addition of environment variables. + + # # Environment variables definition examples. + # env: + # GRPC_GO_LOG_SEVERITY_LEVEL: info + # GRPC_GO_LOG_VERBOSITY_LEVEL: "99" + # https_proxy: http://SERVER:PORT/ + # env: + # GRPC_GO_LOG_SEVERITY_LEVEL: error + # https_proxy: https://USERNAME:PASSWORD@SERVER:PORT/ + # env: + # https_proxy: http://DOMAIN\USERNAME:PASSWORD@SERVER:PORT/ + + # # Used to configure the machine's sysctls. + + # # MachineSysctls usage example. + # sysctls: + # kernel.domainname: talos.dev + # net.ipv4.ip_forward: "0" + # net/ipv6/conf/eth0.100/disable_ipv6: "1" + + # # Used to configure the machine's sysfs. + + # # MachineSysfs usage example. + # sysfs: + # devices.system.cpu.cpu0.cpufreq.scaling_governor: performance + + # # Configures the udev system. + # udev: + # # List of udev rules to apply to the udev system + # rules: + # - SUBSYSTEM=="drm", KERNEL=="renderD*", GROUP="44", MODE="0660" + + # # Configures the logging system. + # logging: + # # Logging destination. + # destinations: + # - endpoint: tcp://1.2.3.4:12345 # Where to send logs. Supported protocols are "tcp" and "udp". + # format: json_lines # Logs format. + + # # Configures the kernel. + # kernel: + # # Kernel modules to load. + # modules: + # - name: btrfs # Module name. + + # # Configures the seccomp profiles for the machine. + # seccompProfiles: + # - name: audit.json # The `name` field is used to provide the file name of the seccomp profile. + # # The `value` field is used to provide the seccomp profile. + # value: + # defaultAction: SCMP_ACT_LOG + + # # Override (patch) settings in the default OCI runtime spec for CRI containers. + + # # override default open file limit + # baseRuntimeSpecOverrides: + # process: + # rlimits: + # - hard: 1024 + # soft: 1024 + # type: RLIMIT_NOFILE + + # # Configures the node labels for the machine. + + # # node labels example. + # nodeLabels: + # exampleLabel: exampleLabelValue + + # # Configures the node annotations for the machine. + + # # node annotations example. + # nodeAnnotations: + # customer.io/rack: r13a25 + + # # Configures the node taints for the machine. Effect is optional. + + # # node taints example. + # nodeTaints: + # exampleTaint: exampleTaintValue:NoSchedule +# Provides cluster specific configuration options. +cluster: + id: mTc4onTNw_N-wtS8vazkBogBrVccq9ESY6XEUgLP3NQ= # Globally unique identifier for this cluster (base64 encoded random 32 bytes). + secret: c9Yv3y6djM9jG3Y7gN1lhmo35Fh0ap/eA4asTicPZEQ= # Shared secret of cluster (base64 encoded random 32 bytes). + # Provides control plane specific configuration options. + controlPlane: + endpoint: https://10.0.0.101:6443 # Endpoint is the canonical controlplane endpoint, which can be an IP address or a DNS hostname. + clusterName: vntx # Configures the cluster's name. + # Provides cluster specific network configuration options. + network: + dnsDomain: cluster.local # The domain used by Kubernetes DNS. + # The pod subnet CIDR. + podSubnets: + - 10.244.0.0/16 + # The service subnet CIDR. + serviceSubnets: + - 10.96.0.0/12 + + # # The CNI used. + # cni: + # name: custom # Name of CNI to use. + # # URLs containing manifests to apply for the CNI. + # urls: + # - https://docs.projectcalico.org/archive/v3.20/manifests/canal.yaml + token: kcout8.f7gf8hxd6jqvkiyb # The [bootstrap token](https://kubernetes.io/docs/reference/access-authn-authz/bootstrap-tokens/) used to join the cluster. + # The base64 encoded root certificate authority used by Kubernetes. + ca: + crt: LS0tLS1CRUdJTiBDRVJUSUZJQ0FURS0tLS0tCk1JSUJpakNDQVRDZ0F3SUJBZ0lSQU9LdVVqbjZ6UFR6WUdLLysrb0VtelF3Q2dZSUtvWkl6ajBFQXdJd0ZURVQKTUJFR0ExVUVDaE1LYTNWaVpYSnVaWFJsY3pBZUZ3MHlOakF4TURFeU1qQXhNemxhRncwek5URXlNekF5TWpBeApNemxhTUJVeEV6QVJCZ05WQkFvVENtdDFZbVZ5Ym1WMFpYTXdXVEFUQmdjcWhrak9QUUlCQmdncWhrak9QUU1CCkJ3TkNBQVFSa0swVkNNSjIzeEJ3dTNlMWkySlhwUGVEcVdFOEJqZHR4dDMyNHBZY1B3Y2ljM0k0ZGFkejVRMHYKYU9aZ2FDb1NNanRYNWJ1ZCtQd0lLN1VGK0JNNW8yRXdYekFPQmdOVkhROEJBZjhFQkFNQ0FvUXdIUVlEVlIwbApCQll3RkFZSUt3WUJCUVVIQXdFR0NDc0dBUVVGQndNQ01BOEdBMVVkRXdFQi93UUZNQU1CQWY4d0hRWURWUjBPCkJCWUVGTmg0MGZFV2lpa08vWXpqL3poNmJJQ1M3ODc5TUFvR0NDcUdTTTQ5QkFNQ0EwZ0FNRVVDSUdNcVRGNjAKZlhqcU1zYUREMFEvU1VVWjhjdkZHazJ2aXRPOFlSdFk4QnZGQWlFQXpqTTY4cmRPSHMxb0wrK01HRmJvN1BzdgpVWTdya2xmbkJ6bjBDYmRsYTBFPQotLS0tLUVORCBDRVJUSUZJQ0FURS0tLS0tCg== + key: "" + # Configures cluster member discovery. + discovery: + enabled: true # Enable the cluster membership discovery feature. + # Configure registries used for cluster member discovery. + registries: + # Kubernetes registry uses Kubernetes API server to discover cluster members and stores additional information + kubernetes: + disabled: true # Disable Kubernetes discovery registry. + # Service registry is using an external service to push and pull information about cluster members. + service: {} + # # External service endpoint. + # endpoint: https://discovery.talos.dev/ + + # # A key used for the [encryption of secret data at rest](https://kubernetes.io/docs/tasks/administer-cluster/encrypt-data/). + + # # Decryption secret example (do not use in production!). + # aescbcEncryptionSecret: z01mye6j16bspJYtTB/5SFX8j7Ph4JXxM2Xuu4vsBPM= + + # # A key used for the [encryption of secret data at rest](https://kubernetes.io/docs/tasks/administer-cluster/encrypt-data/). + + # # Decryption secret example (do not use in production!). + # secretboxEncryptionSecret: z01mye6j16bspJYtTB/5SFX8j7Ph4JXxM2Xuu4vsBPM= + + # # The base64 encoded aggregator certificate authority used by Kubernetes for front-proxy certificate generation. + + # # AggregatorCA example. + # aggregatorCA: + # crt: LS0tIEVYQU1QTEUgQ0VSVElGSUNBVEUgLS0t + # key: LS0tIEVYQU1QTEUgS0VZIC0tLQ== + + # # The base64 encoded private key for service account token generation. + + # # AggregatorCA example. + # serviceAccount: + # key: LS0tIEVYQU1QTEUgS0VZIC0tLQ== + + # # API server specific configuration options. + # apiServer: + # image: registry.k8s.io/kube-apiserver:v1.35.0 # The container image used in the API server manifest. + # # Extra arguments to supply to the API server. + # extraArgs: + # feature-gates: ServerSideApply=true + # http2-max-streams-per-connection: "32" + # # Extra certificate subject alternative names for the API server's certificate. + # certSANs: + # - 1.2.3.4 + # - 4.5.6.7 + # # Configure the API server admission plugins. + # admissionControl: + # - name: PodSecurity # Name is the name of the admission controller. + # # Configuration is an embedded configuration object to be used as the plugin's + # configuration: + # apiVersion: pod-security.admission.config.k8s.io/v1alpha1 + # defaults: + # audit: restricted + # audit-version: latest + # enforce: baseline + # enforce-version: latest + # warn: restricted + # warn-version: latest + # exemptions: + # namespaces: + # - kube-system + # runtimeClasses: [] + # usernames: [] + # kind: PodSecurityConfiguration + # # Configure the API server audit policy. + # auditPolicy: + # apiVersion: audit.k8s.io/v1 + # kind: Policy + # rules: + # - level: Metadata + # # Configure the API server authorization config. Node and RBAC authorizers are always added irrespective of the configuration. + # authorizationConfig: + # - type: Webhook # Type is the name of the authorizer. Allowed values are `Node`, `RBAC`, and `Webhook`. + # name: webhook # Name is used to describe the authorizer. + # # webhook is the configuration for the webhook authorizer. + # webhook: + # connectionInfo: + # type: InClusterConfig + # failurePolicy: Deny + # matchConditionSubjectAccessReviewVersion: v1 + # matchConditions: + # - expression: has(request.resourceAttributes) + # - expression: '!(\''system:serviceaccounts:kube-system\'' in request.groups)' + # subjectAccessReviewVersion: v1 + # timeout: 3s + # - type: Webhook # Type is the name of the authorizer. Allowed values are `Node`, `RBAC`, and `Webhook`. + # name: in-cluster-authorizer # Name is used to describe the authorizer. + # # webhook is the configuration for the webhook authorizer. + # webhook: + # connectionInfo: + # type: InClusterConfig + # failurePolicy: NoOpinion + # matchConditionSubjectAccessReviewVersion: v1 + # subjectAccessReviewVersion: v1 + # timeout: 3s + + # # Controller manager server specific configuration options. + # controllerManager: + # image: registry.k8s.io/kube-controller-manager:v1.35.0 # The container image used in the controller manager manifest. + # # Extra arguments to supply to the controller manager. + # extraArgs: + # feature-gates: ServerSideApply=true + + # # Kube-proxy server-specific configuration options + # proxy: + # disabled: false # Disable kube-proxy deployment on cluster bootstrap. + # image: registry.k8s.io/kube-proxy:v1.35.0 # The container image used in the kube-proxy manifest. + # mode: ipvs # proxy mode of kube-proxy. + # # Extra arguments to supply to kube-proxy. + # extraArgs: + # proxy-mode: iptables + + # # Scheduler server specific configuration options. + # scheduler: + # image: registry.k8s.io/kube-scheduler:v1.35.0 # The container image used in the scheduler manifest. + # # Extra arguments to supply to the scheduler. + # extraArgs: + # feature-gates: AllBeta=true + + # # Etcd specific configuration options. + # etcd: + # image: registry.k8s.io/etcd:v3.6.7 # The container image used to create the etcd service. + # # The `ca` is the root certificate authority of the PKI. + # ca: + # crt: LS0tIEVYQU1QTEUgQ0VSVElGSUNBVEUgLS0t + # key: LS0tIEVYQU1QTEUgS0VZIC0tLQ== + # # Extra arguments to supply to etcd. + # extraArgs: + # election-timeout: "5000" + # # The `advertisedSubnets` field configures the networks to pick etcd advertised IP from. + # advertisedSubnets: + # - 10.0.0.0/8 + + # # Core DNS specific configuration options. + # coreDNS: + # image: registry.k8s.io/coredns/coredns:v1.13.2 # The `image` field is an override to the default coredns image. + + # # External cloud provider configuration. + # externalCloudProvider: + # enabled: true # Enable external cloud provider. + # # A list of urls that point to additional manifests for an external cloud provider. + # manifests: + # - https://raw.githubusercontent.com/kubernetes/cloud-provider-aws/v1.20.0-alpha.0/manifests/rbac.yaml + # - https://raw.githubusercontent.com/kubernetes/cloud-provider-aws/v1.20.0-alpha.0/manifests/aws-cloud-controller-manager-daemonset.yaml + + # # A list of urls that point to additional manifests. + # extraManifests: + # - https://www.example.com/manifest1.yaml + # - https://www.example.com/manifest2.yaml + + # # A map of key value pairs that will be added while fetching the extraManifests. + # extraManifestHeaders: + # Token: "1234567" + # X-ExtraInfo: info + + # # A list of inline Kubernetes manifests. + # inlineManifests: + # - name: namespace-ci # Name of the manifest. + # contents: |- # Manifest contents as a string. + # apiVersion: v1 + # kind: Namespace + # metadata: + # name: ci + + # # Settings for admin kubeconfig generation. + # adminKubeconfig: + # certLifetime: 1h0m0s # Admin kubeconfig certificate lifetime (default is 1 year). + + # # Allows running workload on control-plane nodes. + # allowSchedulingOnControlPlanes: true +--- +apiVersion: v1alpha1 +kind: HostnameConfig +auto: stable # A method to automatically generate a hostname for the machine. + +# # A static hostname to set for the machine. +# hostname: controlplane1 +# hostname: controlplane1.example.org diff --git a/terraform/.terraform.lock.hcl b/terraform/.terraform.lock.hcl index 361726b..1e0570c 100644 --- a/terraform/.terraform.lock.hcl +++ b/terraform/.terraform.lock.hcl @@ -19,24 +19,24 @@ provider "registry.opentofu.org/cloudflare/cloudflare" { } provider "registry.opentofu.org/dnsimple/dnsimple" { - version = "2.0.0" + version = "2.0.1" constraints = "~> 2.0" hashes = [ - "h1:wWsupXlmlShs8m4C2dTaNcYTxFJtDipftKWlXk+jX1U=", - "zh:0fb015799f6d37323cdc2776eed67657721df24311bf5b458f7fcce65ec66dea", - "zh:533cd0f6edd4ed6610b324b39aa3abb5e84293a3aaa176042826f17f10a20557", - "zh:77d13ff083eeeb408822e885934925b9010462ca7601d35f2a1c2b0d5faf2f52", - "zh:9be63f37c98050a30e43066805ac70db3e3ddfcf03607c9c8d8d13ebd3503648", - "zh:a66a61ab90840b5ae9513f302f76e2348acb8bca50cb702e1f6fbcd24b1111fb", - "zh:b65d2f77f20a9587f169aaeccd8e12f07a713294fd687043ff041538c5da5cf9", - "zh:c24faaefb7f87050f1dfbf6c7a9a522df07ab97e9ce73d7fd20bce761d092076", - "zh:d0072167c5f52cd63e245d6b136a8e62979c0b0979fbea5a07015d5bfb6e7191", - "zh:d07dee2322cf12ffc439059f7f3a58a5d740fe7ad934f96b84b0be3257ee31cb", - "zh:d0c898dcc7d51427348d641474a74521c029d2cd9713f262e404f5fb36f4c3a5", - "zh:d9322e1a3dba21316713ada4b8de6c4090ca6b76b418ef55b85dbe7c0a578391", - "zh:e0e0b5f07293ff2c0ddb1c561dcb430924897022995006c4bb71719cf3995d9d", - "zh:e4eb3deac11f7798ea991fd044aec6a23592cbd887a7f3d1d415e8f553ba7b39", - "zh:f1d307fe43f3a8be6a97111dbe025ccd0bb4a5c8dadd54abc48adec8701336b1", + "h1:LEE/1x9UzZxlMBpdnkpLymZgW4jWN5DYCWT1l0w3NlE=", + "zh:29902e0ad5242f26c96f966c4a90436b886e23e6be6ad7cb9ec24a35166a74e3", + "zh:2c0e2166acb1245687b5db8b8d3c632537d2e44d58bed17e8014ccc8212d9d90", + "zh:444d2f5306653348f1f65276bff75eebeee2406ddeaec77d701d094b09b53d84", + "zh:5734a4f034543fb80dcfdeacdeaf58f60ee7b69ff9124a738eb0c048529b21f8", + "zh:5c367802be7642ec80269af4bf8a1273d74f41393684a66a9cff03cc96a6f808", + "zh:82487106a9eca25b0e3374684e74a0add4c0bcb1704208850f8b94ca5a6dbff2", + "zh:8ac5ea42e90a37c990f6c05b10e29016de63f6b2ad76e66f8bdf597d15f0cc8d", + "zh:9afdf5a24ac9128d5b23e6d9d3817b8cbe48ae221cdcf399ec5a11f8167d6071", + "zh:9b9e76e5a3a7ad2dafe83dc0ef2b303051167ac73ad12d5feca419ac9f84649f", + "zh:add817dd33b42c1a8d88ff3cc31b8aea46b25c08f0e4a2fa8e2847a237e57fdd", + "zh:d58a889473174614094efe9b854470dc8f353222198614fba9de49f27232ae0a", + "zh:d991a0659a18909d8a9862d4405b2039d5ca004511ad28badc7a1c6e50d5e8b5", + "zh:dbc5e352e4183a0ab978fec7eb712e154516911d86506279ac3e2de37ca5a713", + "zh:eb4c1a4dc9a5c833e282ff54ec25d4aa37bcd1a3ab49880e85868d68908e3785", "zh:f809ab383cca0a5f83072981c64208cbd7fa67e986a86ee02dd2c82333221e32", ] } @@ -82,27 +82,6 @@ provider "registry.opentofu.org/kyswtn/porkbun" { ] } -provider "registry.opentofu.org/pan-net/powerdns" { - version = "1.5.0" - constraints = "~> 1.5" - hashes = [ - "h1:oMzrqQGFY88Cwx06YkFHP6io3jow/22FRZkeK0UZtGY=", - "zh:02d1a87c28635779f66d1dcf165b5f16530f809deb6c71c35c3e58d715a88bf4", - "zh:1285a419c7fd2947f891771bd77d2f6e7dd0cb00621c547b6993947085616009", - "zh:340faecd0a0036e721480564acbad2ba0da6a9c0c0cd633957dcde76a4ba3798", - "zh:5646f78d9980038c4ae70e09828da01c7cc6ba2b3b1e9ea8a1988efafaba1b75", - "zh:66fef65aede775d9972be163a2bd25d8fda5a8ad2235ceef30d515bf35e2e5d4", - "zh:7130faa5dd892b1d41b9b3ebd1b2d7854bf780193073de58806e088311bb554c", - "zh:9f47b66ce7f4b23d25c4a726ffc5e504f797f247912cfa5dff23b3da0ba18982", - "zh:ada63a886bc5d7980eeb22b59b166713617847626627007d2e8429eeb4346327", - "zh:c853237b7831942d3d0f0f7a7a334e8f9df8a12f217c5680a76db256e368230d", - "zh:d2e8827d9d8662a892dbd1df6155823c8167db6f6762f38885037c7da87612b1", - "zh:d6e1069bb9d9f368e5d55a8bdf55de23636a586d698515f0075733499d6b9ccc", - "zh:dd224d521af2f72bfdc3498c5ccd54b09844cfaa347b3008f61faad465cc9769", - "zh:e02960d79ccfeeaea64c07aa1ad88cdd3688f49b670c9b607ea188283cd519d6", - ] -} - provider "registry.opentofu.org/vultr/vultr" { version = "2.28.0" constraints = "~> 2.28" diff --git a/terraform/dns_aprs.tf b/terraform/dns_aprs.tf deleted file mode 100644 index 5557cd1..0000000 --- a/terraform/dns_aprs.tf +++ /dev/null @@ -1,39 +0,0 @@ -# DNS configuration for aprs.me domain -# Points to Traefik ingress on k3s cluster for APRS application - -resource "powerdns_record" "aprs_me_soa" { - depends_on = [powerdns_zone.aprs_me] - zone = "aprs.me." - name = "aprs.me." - type = "SOA" - ttl = 3600 - records = ["ns1.as393837.net. graham.mcintire.me. 0 10800 3600 604800 3600"] -} - -resource "powerdns_record" "aprs_me_root" { - depends_on = [powerdns_zone.aprs_me] - zone = "aprs.me." - name = "aprs.me." - type = "A" - ttl = 3600 - records = ["204.110.191.195"] # Traefik ingress on k3s cluster -} - -resource "powerdns_record" "aprs_me_www" { - depends_on = [powerdns_zone.aprs_me] - zone = "aprs.me." - name = "www.aprs.me." - type = "A" - ttl = 3600 - records = ["204.110.191.195"] # Traefik ingress on k3s cluster -} - -# CAA record for Let's Encrypt SSL certificates -resource "powerdns_record" "aprs_me_caa" { - depends_on = [powerdns_zone.aprs_me] - zone = "aprs.me." - name = "aprs.me." - type = "CAA" - ttl = 3600 - records = ["0 issue \"letsencrypt.org\""] -} diff --git a/terraform/dns_manero.tf b/terraform/dns_manero.tf deleted file mode 100644 index d02f8b3..0000000 --- a/terraform/dns_manero.tf +++ /dev/null @@ -1,80 +0,0 @@ -# PowerDNS records for manero.org -# Zone defined in dns_powerdns_zones.tf - -resource "powerdns_record" "manero_soa" { - depends_on = [powerdns_zone.manero_org] - zone = "manero.org." - name = "manero.org." - type = "SOA" - ttl = 3600 - records = ["ns1.as393837.net. graham.mcintire.me. 0 10800 3600 604800 3600"] -} - -# Root A records (GitHub Pages) -resource "powerdns_record" "manero_root_a" { - depends_on = [powerdns_zone.manero_org] - zone = "manero.org." - name = "manero.org." - type = "A" - ttl = 3600 - records = [ - "185.199.108.153", - "185.199.109.153", - "185.199.110.153", - "185.199.111.153" - ] -} - -resource "powerdns_record" "manero_irc_a" { - depends_on = [powerdns_zone.manero_org] - zone = "manero.org." - name = "irc.manero.org." - type = "A" - ttl = 3600 - records = ["149.28.242.178"] -} - -resource "powerdns_record" "manero_us_a" { - depends_on = [powerdns_zone.manero_org] - zone = "manero.org." - name = "us.manero.org." - type = "A" - ttl = 3600 - records = ["149.28.242.178"] -} - -resource "powerdns_record" "manero_us_aaaa" { - depends_on = [powerdns_zone.manero_org] - zone = "manero.org." - name = "us.manero.org." - type = "AAAA" - ttl = 3600 - records = ["2001:19f0:6401:19e6:5400:5ff:fe45:5701"] -} - -resource "powerdns_record" "manero_ca_a" { - depends_on = [powerdns_zone.manero_org] - zone = "manero.org." - name = "ca.manero.org." - type = "A" - ttl = 3600 - records = ["167.114.209.151"] -} - -resource "powerdns_record" "manero_tankfox_a" { - depends_on = [powerdns_zone.manero_org] - zone = "manero.org." - name = "tankfox.manero.org." - type = "A" - ttl = 3600 - records = ["137.184.202.89"] -} - -resource "powerdns_record" "manero_404_cname" { - depends_on = [powerdns_zone.manero_org] - zone = "manero.org." - name = "404.manero.org." - type = "CNAME" - ttl = 3600 - records = ["404.al."] -} diff --git a/terraform/dns_mcintire.tf b/terraform/dns_mcintire.tf deleted file mode 100644 index b21315a..0000000 --- a/terraform/dns_mcintire.tf +++ /dev/null @@ -1,100 +0,0 @@ -resource "powerdns_record" "mcintire_soa" { - depends_on = [powerdns_zone.mcintire_me] - zone = "mcintire.me." - name = "mcintire.me." - type = "SOA" - ttl = 3600 - records = ["ns1.as393837.net. graham.mcintire.me. 0 10800 3600 604800 3600"] -} - -# Mailcow MX records (primary and backup) -resource "powerdns_record" "mcintire_mx" { - depends_on = [powerdns_zone.mcintire_me] - zone = "mcintire.me." - name = "mcintire.me." - type = "MX" - ttl = 3600 - records = [ - "10 mail.mcintire.me.", - "20 mail.nsnw.ca." - ] -} - -# Mail server -resource "powerdns_record" "mcintire_mail" { - depends_on = [powerdns_zone.mcintire_me] - zone = "mcintire.me." - name = "mail.mcintire.me." - type = "A" - ttl = 3600 - records = ["204.110.191.5"] -} - -# Autodiscover for mail clients -resource "powerdns_record" "mcintire_autodiscover" { - depends_on = [powerdns_zone.mcintire_me] - zone = "mcintire.me." - name = "autodiscover.mcintire.me." - type = "CNAME" - ttl = 3600 - records = ["mail.w5isp.com."] -} - -# Autodiscover SRV record -resource "powerdns_record" "mcintire_autodiscover_srv" { - depends_on = [powerdns_zone.mcintire_me] - zone = "mcintire.me." - name = "_autodiscover._tcp.mcintire.me." - type = "SRV" - ttl = 3600 - records = ["0 0 443 mail.w5isp.com."] -} - -# Autoconfig for mail clients -resource "powerdns_record" "mcintire_autoconfig" { - depends_on = [powerdns_zone.mcintire_me] - zone = "mcintire.me." - name = "autoconfig.mcintire.me." - type = "CNAME" - ttl = 3600 - records = ["mail.w5isp.com."] -} - -# SPF record for Mailcow -resource "powerdns_record" "mcintire_spf_mailcow" { - depends_on = [powerdns_zone.mcintire_me] - zone = "mcintire.me." - name = "mcintire.me." - type = "TXT" - ttl = 3600 - records = ["\"v=spf1 mx a ip4:204.110.191.5 ~all\""] -} - -# DMARC record for Mailcow -resource "powerdns_record" "mcintire_dmarc_mailcow" { - depends_on = [powerdns_zone.mcintire_me] - zone = "mcintire.me." - name = "_dmarc.mcintire.me." - type = "TXT" - ttl = 3600 - records = ["\"v=DMARC1; p=quarantine; rua=mailto:postmaster@mcintire.me; ruf=mailto:postmaster@mcintire.me; fo=1\""] -} - -# DKIM record from Mailcow -resource "powerdns_record" "mcintire_dkim_mailcow" { - depends_on = [powerdns_zone.mcintire_me] - zone = "mcintire.me." - name = "dkim._domainkey.mcintire.me." - type = "TXT" - ttl = 3600 - records = ["\"v=DKIM1;k=rsa;t=s;s=email;p=MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEA0rQie7Hz5AmDbVUX+rKNgp6Hf7crtWyfy6qKbqnrxmmernz1rQ6HyOrHhFAlc8nVLNKr8XP2DOROb1jAnrjndZo9I/ymbrrrCBsi9w6zAht2BheijO/R9k5CDRjeSafm6bg0oMKihtNMIdXvEj9ND8hDpZZKxtOrKFH7zLm4CPmm7jf0gqZH2yK+AA3OYUGSYa1OT0LtdMXadk0IVOI2VYf37Hzb3RUvGOYMVkT0xi+23DiyFk7AyCiyv3LQVBMT+/bwyd4k3yVVn2cr9+Nor+HXVjqASLtqcFLMf1SuX0ezSAjBG7BbqQr5G6Jz+n5YglqEIUKVYzJFE7JdDmqQYQIDAQAB\""] -} - -resource "powerdns_record" "mcintire_photos" { - depends_on = [powerdns_zone.mcintire_me] - zone = "mcintire.me." - name = "photos.mcintire.me." - type = "A" - ttl = 3600 - records = ["204.110.191.8"] -} diff --git a/terraform/dns_ntxarms.tf b/terraform/dns_ntxarms.tf deleted file mode 100644 index c792894..0000000 --- a/terraform/dns_ntxarms.tf +++ /dev/null @@ -1,80 +0,0 @@ -# SOA record for ntxarms.com -resource "powerdns_record" "ntxarms_soa" { - depends_on = [powerdns_zone.ntxarms_com] - zone = "ntxarms.com." - name = "ntxarms.com." - type = "SOA" - ttl = 3600 - records = ["ns1.as393837.net. graham.mcintire.me. 0 10800 3600 604800 3600"] -} - -# Root A record -resource "powerdns_record" "ntxarms_root" { - depends_on = [powerdns_zone.ntxarms_com] - zone = "ntxarms.com." - name = "ntxarms.com." - type = "A" - ttl = 3600 - records = ["75.2.60.5"] -} - -# www CNAME to Netlify -resource "powerdns_record" "ntxarms_www" { - depends_on = [powerdns_zone.ntxarms_com] - zone = "ntxarms.com." - name = "www.ntxarms.com." - type = "CNAME" - ttl = 3600 - records = ["ntxarms.netlify.app."] -} - -# Fastmail MX records -resource "powerdns_record" "ntxarms_mx" { - depends_on = [powerdns_zone.ntxarms_com] - zone = "ntxarms.com." - name = "ntxarms.com." - type = "MX" - ttl = 3600 - records = [ - "10 in1-smtp.messagingengine.com.", - "20 in2-smtp.messagingengine.com." - ] -} - -# Fastmail DKIM records -resource "powerdns_record" "ntxarms_dkim_fm1" { - depends_on = [powerdns_zone.ntxarms_com] - zone = "ntxarms.com." - name = "fm1._domainkey.ntxarms.com." - type = "CNAME" - ttl = 3600 - records = ["fm1.ntxarms.com.dkim.fmhosted.com."] -} - -resource "powerdns_record" "ntxarms_dkim_fm2" { - depends_on = [powerdns_zone.ntxarms_com] - zone = "ntxarms.com." - name = "fm2._domainkey.ntxarms.com." - type = "CNAME" - ttl = 3600 - records = ["fm2.ntxarms.com.dkim.fmhosted.com."] -} - -resource "powerdns_record" "ntxarms_dkim_fm3" { - depends_on = [powerdns_zone.ntxarms_com] - zone = "ntxarms.com." - name = "fm3._domainkey.ntxarms.com." - type = "CNAME" - ttl = 3600 - records = ["fm3.ntxarms.com.dkim.fmhosted.com."] -} - -# Fastmail SPF record -resource "powerdns_record" "ntxarms_spf" { - depends_on = [powerdns_zone.ntxarms_com] - zone = "ntxarms.com." - name = "ntxarms.com." - type = "TXT" - ttl = 3600 - records = ["\"v=spf1 include:spf.messagingengine.com ?all\""] -} diff --git a/terraform/dns_powerdns_zones.tf b/terraform/dns_powerdns_zones.tf deleted file mode 100644 index 87ec72b..0000000 --- a/terraform/dns_powerdns_zones.tf +++ /dev/null @@ -1,91 +0,0 @@ -# Vultr PowerDNS Zones -# All zones managed on the Vultr PowerDNS instance -# -# AXFR Configuration: -# AXFR (zone transfers) and notifications are configured globally in the PowerDNS -# ConfigMap (allow-axfr-ips and also-notify settings). These apply to all zones. - -resource "powerdns_zone" "w5isp_com" { - name = "w5isp.com." - kind = "Primary" - soa_edit_api = "DEFAULT" - nameservers = ["ns1.as393837.net.", "ns-global.kjsl.com."] -} - -resource "powerdns_zone" "aprs_me" { - name = "aprs.me." - kind = "Primary" - soa_edit_api = "DEFAULT" - nameservers = ["ns1.as393837.net.", "ns-global.kjsl.com."] -} - -resource "powerdns_zone" "mcintire_me" { - name = "mcintire.me." - kind = "Primary" - soa_edit_api = "DEFAULT" - nameservers = ["ns1.as393837.net.", "ns-global.kjsl.com."] -} - -resource "powerdns_zone" "manero_org" { - name = "manero.org." - kind = "Primary" - soa_edit_api = "DEFAULT" - nameservers = ["ns1.as393837.net.", "ns-global.kjsl.com."] -} - -resource "powerdns_zone" "ntxarms_com" { - name = "ntxarms.com." - kind = "Primary" - soa_edit_api = "DEFAULT" - nameservers = ["ns1.as393837.net.", "ns-global.kjsl.com."] -} - -resource "powerdns_zone" "towerops_net" { - name = "towerops.net." - kind = "Primary" - soa_edit_api = "DEFAULT" - nameservers = ["ns1.as393837.net.", "ns-global.kjsl.com."] -} - -resource "powerdns_zone" "vntx_net" { - name = "vntx.net." - kind = "Primary" - soa_edit_api = "DEFAULT" - nameservers = ["ns1.as393837.net.", "ns-global.kjsl.com."] -} - -resource "powerdns_zone" "vntx_org" { - name = "vntx.org." - kind = "Primary" - soa_edit_api = "DEFAULT" - nameservers = ["ns1.as393837.net.", "ns-global.kjsl.com."] -} - -# Reverse DNS zones -resource "powerdns_zone" "reverse_188" { - name = "188.110.204.in-addr.arpa." - kind = "Primary" - soa_edit_api = "DEFAULT" - nameservers = ["ns1.as393837.net.", "ns-global.kjsl.com."] -} - -resource "powerdns_zone" "reverse_189" { - name = "189.110.204.in-addr.arpa." - kind = "Primary" - soa_edit_api = "DEFAULT" - nameservers = ["ns1.as393837.net.", "ns-global.kjsl.com."] -} - -resource "powerdns_zone" "reverse_190" { - name = "190.110.204.in-addr.arpa." - kind = "Primary" - soa_edit_api = "DEFAULT" - nameservers = ["ns1.as393837.net.", "ns-global.kjsl.com."] -} - -resource "powerdns_zone" "reverse_191" { - name = "191.110.204.in-addr.arpa." - kind = "Primary" - soa_edit_api = "DEFAULT" - nameservers = ["ns1.as393837.net.", "ns-global.kjsl.com."] -} diff --git a/terraform/dns_reverse.tf b/terraform/dns_reverse.tf deleted file mode 100644 index d5fc89d..0000000 --- a/terraform/dns_reverse.tf +++ /dev/null @@ -1,103 +0,0 @@ -# Reverse DNS zones are defined in dns_powerdns_zones.tf - -# SOA records for reverse zones -resource "powerdns_record" "vntx1_soa" { - depends_on = [powerdns_zone.reverse_188] - zone = "188.110.204.in-addr.arpa." - name = "188.110.204.in-addr.arpa." - type = "SOA" - ttl = 3600 - records = ["ns1.as393837.net. graham.mcintire.me. 0 10800 3600 604800 3600"] -} - -resource "powerdns_record" "vntx2_soa" { - depends_on = [powerdns_zone.reverse_189] - zone = "189.110.204.in-addr.arpa." - name = "189.110.204.in-addr.arpa." - type = "SOA" - ttl = 3600 - records = ["ns1.as393837.net. graham.mcintire.me. 0 10800 3600 604800 3600"] -} - -resource "powerdns_record" "vntx3_soa" { - depends_on = [powerdns_zone.reverse_190] - zone = "190.110.204.in-addr.arpa." - name = "190.110.204.in-addr.arpa." - type = "SOA" - ttl = 3600 - records = ["ns1.as393837.net. graham.mcintire.me. 0 10800 3600 604800 3600"] -} - -resource "powerdns_record" "vntx4_soa" { - depends_on = [powerdns_zone.reverse_191] - zone = "191.110.204.in-addr.arpa." - name = "191.110.204.in-addr.arpa." - type = "SOA" - ttl = 3600 - records = ["ns1.as393837.net. graham.mcintire.me. 0 10800 3600 604800 3600"] -} - -resource "powerdns_record" "ptr_records1" { - depends_on = [powerdns_zone.reverse_188] - for_each = { - for i in range(256) : tostring(i) => { - name = "${i}.188.110.204.in-addr.arpa." - record = "${i}.188.client.vntx.net." - } - } - - zone = "188.110.204.in-addr.arpa." - name = each.value.name - type = "PTR" - ttl = 3600 - records = [each.value.record] -} - -resource "powerdns_record" "ptr_records2" { - depends_on = [powerdns_zone.reverse_189] - for_each = { - for i in range(256) : tostring(i) => { - name = "${i}.189.110.204.in-addr.arpa." - record = "${i}.189.client.vntx.net." - } - } - - zone = "189.110.204.in-addr.arpa." - name = each.value.name - type = "PTR" - ttl = 3600 - records = [each.value.record] -} - -resource "powerdns_record" "ptr_records3" { - depends_on = [powerdns_zone.reverse_190] - for_each = { - for i in range(256) : tostring(i) => { - name = "${i}.190.110.204.in-addr.arpa." - record = "${i}.190.client.vntx.net." - } - if !contains([119, 168], i) - } - - zone = "190.110.204.in-addr.arpa." - name = each.value.name - type = "PTR" - ttl = 3600 - records = [each.value.record] -} - -resource "powerdns_record" "ptr_records4" { - depends_on = [powerdns_zone.reverse_191] - for_each = { - for i in range(256) : tostring(i) => { - name = "${i}.191.110.204.in-addr.arpa." - record = tostring(i) == "5" ? "mail.mcintire.me." : "${i}.191.client.vntx.net." - } - } - - zone = "191.110.204.in-addr.arpa." - name = each.value.name - type = "PTR" - ttl = 3600 - records = [each.value.record] -} diff --git a/terraform/dns_towerops.tf b/terraform/dns_towerops.tf deleted file mode 100644 index 94d5303..0000000 --- a/terraform/dns_towerops.tf +++ /dev/null @@ -1,62 +0,0 @@ -# PowerDNS records for towerops.net -# SendGrid email authentication records - -# SOA record for towerops.net -resource "powerdns_record" "towerops_soa" { - depends_on = [powerdns_zone.towerops_net] - zone = "towerops.net." - name = "towerops.net." - type = "SOA" - ttl = 3600 - records = ["ns1.as393837.net. graham.mcintire.me. 0 10800 3600 604800 3600"] -} - -# Root A record -resource "powerdns_record" "towerops_root_a" { - depends_on = [powerdns_zone.towerops_net] - zone = "towerops.net." - name = "towerops.net." - type = "A" - ttl = 3600 - records = ["204.110.191.195"] -} - -# SendGrid domain CNAME -resource "powerdns_record" "towerops_sendgrid_domain" { - depends_on = [powerdns_zone.towerops_net] - zone = "towerops.net." - name = "em6505.towerops.net." - type = "CNAME" - ttl = 600 - records = ["u177982.wl233.sendgrid.net."] -} - -# SendGrid DKIM key 1 -resource "powerdns_record" "towerops_sendgrid_dkim1" { - depends_on = [powerdns_zone.towerops_net] - zone = "towerops.net." - name = "s1._domainkey.towerops.net." - type = "CNAME" - ttl = 600 - records = ["s1.domainkey.u177982.wl233.sendgrid.net."] -} - -# SendGrid DKIM key 2 -resource "powerdns_record" "towerops_sendgrid_dkim2" { - depends_on = [powerdns_zone.towerops_net] - zone = "towerops.net." - name = "s2._domainkey.towerops.net." - type = "CNAME" - ttl = 600 - records = ["s2.domainkey.u177982.wl233.sendgrid.net."] -} - -# DMARC policy -resource "powerdns_record" "towerops_dmarc" { - depends_on = [powerdns_zone.towerops_net] - zone = "towerops.net." - name = "_dmarc.towerops.net." - type = "TXT" - ttl = 600 - records = ["\"v=DMARC1; p=none;\""] -} diff --git a/terraform/dns_vntx_net.tf b/terraform/dns_vntx_net.tf deleted file mode 100644 index e178045..0000000 --- a/terraform/dns_vntx_net.tf +++ /dev/null @@ -1,148 +0,0 @@ -# SOA record for vntx.net -resource "powerdns_record" "vntx_net_soa" { - depends_on = [powerdns_zone.vntx_net] - zone = "vntx.net." - name = "vntx.net." - type = "SOA" - ttl = 3600 - records = ["ns1.as393837.net. graham.mcintire.me. 0 10800 3600 604800 3600"] -} - -# Generate client IP records dynamically -locals { - # Subnets to create client records for - vntx_subnets = [188, 189, 190, 191] - - # Generate all client IPs dynamically - client_ips = merge([ - for subnet in local.vntx_subnets : { - for i in range(1, 255) : "${i}.${subnet}.client" => "204.110.${subnet}.${i}" - } - ]...) - - # Named hosts with specific IPs - named_hosts = { - "climax" = "204.110.188.62" - "core" = "10.254.254.253" - "culleoka" = "204.110.188.158" - "edge" = "204.110.191.190" - "librenms" = "204.110.191.227" - "logs" = "204.110.191.229" - "monitor" = "204.110.191.241" - "netbox" = "204.110.191.243" - "newhope" = "204.110.188.190" - "ns1" = "204.110.191.249" - "ns2" = "204.110.191.239" - "preseem" = "204.110.191.225" - "resolver-01" = "204.110.191.240" - "resolver-02" = "204.110.191.250" - "resolver1" = "204.110.191.240" - "resolver2" = "204.110.191.250" - "unimus" = "204.110.191.238" - "verona" = "204.110.188.254" - "@" = "198.185.159.144" - "routers" = "155.138.241.157" - "vpn" = "204.110.191.247" - "radius" = "204.110.191.248" - "speedtest" = "204.110.191.228" - "aprs" = "204.110.191.232" - "g2" = "204.110.191.221" - "net" = "104.238.146.79" - "uisp" = "204.110.191.224" - "dns" = "204.110.191.193" - } - - # Merge client IPs and named hosts - all_a_records = merge(local.client_ips, local.named_hosts) -} - -resource "powerdns_record" "vntx_a_records" { - for_each = local.all_a_records - - depends_on = [powerdns_zone.vntx_net] - zone = "vntx.net." - name = each.key == "@" ? "vntx.net." : "${each.key}.vntx.net." - type = "A" - ttl = 3600 - records = [each.value] -} - -# Microsoft 365 MX record -resource "powerdns_record" "vntx_mx" { - depends_on = [powerdns_zone.vntx_net] - zone = "vntx.net." - name = "vntx.net." - type = "MX" - ttl = 3600 - records = ["0 vntx-net.mail.protection.outlook.com."] -} - -resource "powerdns_record" "vntx_txt_records" { - for_each = { - "_twilio" = "twilio-domain-verification=12bf63d61b86412618bdb4ab6c2b287a" - "_dmarc" = "v=DMARC1; p=none" - "_updown" = "updown-page=p/34yuc" - "_github-challenge-vntx" = "34ea2705e4" - "_github-pages-challenge-gmcintire" = "d125f4244edd0120ee0fa073d3acf1" - "krs._domainkey.mg" = "k=rsa; p=MIGfMA0GCSqGSIb3DQEBAQUAA4GNADCBiQKBgQDHbWtJ5uPGEOPmJrT36WBXKxVL0b4fqjIM4n6oXK4zaUucqYp7jeoKG+FTO5XEjyja7hsP9WahntUrVb8WI5V6Cj0CznesMrM7oQRntcyuy8mSD1zilmZe4q2Kc65gj2MRrkg3tkJfogXHNz2rxmquNu/DxsFLeQP8a2E5tYXVFwIDAQAB" - "pic._domainkey.mg" = "k=rsa; p=MIGfMA0GCSqGSIb3DQEBAQUAA4GNADCBiQKBgQDdv4ZUjhb9l0Nt1aEJMnH/TVNdVn9CEKkb8+RX3qBPMFGmJWrJ3BIFwOSTUBiPeCgd2vc4zOOv7iQhEgNTlIVNT/V1sY70Myo5t+tJCuJQT/G4h5D1u7LZB6YEOKTgd5wF5AoW/nLvKVEPyKl5mThB9KmIGqF5FMm9C9FWP8m6SQIDAQAB" - "s1._domainkey.mg" = "k=rsa; p=MIGfMA0GCSqGSIb3DQEBAQUAA4GNADCBiQKBgQDI3w7b9bBNcWzSH8DspZbRNp+9G9pHbCfmHmr3r2JqXh+F8bFlCK6gJqEQW7SIJgYMmSJ5GlYyy4A3VxJJFcWLZb3dxMoWkGjrJ3gEUNQGmG6rnJ7eXJxKb5J2mGgEfQgCgkWXPFRmJhKXPWoZP3RqU2vJZ3t7vJxWHmv0bQPHKQIDAQAB" - "s2._domainkey.mg" = "k=rsa; p=MIGfMA0GCSqGSIb3DQEBAQUAA4GNADCBiQKBgQDc3JXQvGMBl3cW+3N2OPLJwlP4cMvPp9yOQM9X1TLxJWX7Hd7m6rJ1Xf2T3PGP9ZDPfJGXh+PfGPYVJYP2JXGPfP9HPfP3GPfPHGPYVP9fPH+PfP+PfPHGPYVP9fPH+PfP+PfPHGPYVP9fPH+PfP+PfPHGPYVP9fPH+PfP+PfPHQIDAQAB" - "@" = "v=spf1 include:spf.protection.outlook.com include:mailgun.org -all" - } - - depends_on = [powerdns_zone.vntx_net] - zone = "vntx.net." - name = each.key == "@" ? "vntx.net." : "${each.key}.vntx.net." - type = "TXT" - ttl = 3600 - records = ["\"${each.value}\""] -} - -resource "powerdns_record" "vntx_cname_records" { - for_each = { - # Current records - "mg" = "mailgun.org." - "email.mg" = "mailgun.org." - "*.w5isp" = "dokku.w5isp.com." - "mail.speedtest" = "mail.speedtest.vntx.net.s2.mailersendapp.com." - "status" = "stats.uptimerobot.com." - "ntp" = "0.us.pool.ntp.org." - "iptrack" = "dokku.w5isp.com." - - "_4080c249b6e72dd04f2a9508aa1a1b7f.kivrak" = "_de3e5d511f3869bbd271b935a3b4f973.tljzshvwok.acm-validations.aws." - "_83337805c305955c6823504cc5e6ca29" = "_baf97cdcc7b6458fa5719e4261e9932f.sdgjtdhdhz.acm-validations.aws." - "_bc1077259b1fbbb11c1e16756e1883f9.irc" = "793f217a963b25f361ec1975e0fd7d54.dc2ec86a36550aed25a0011c0b2b044b.62f7abe714ec1.comodoca.com." - "177982" = "sendgrid.net." - "4809fce066c3da4d14197c7276ba083f.irc" = "b58bf151af520d34d8fad99d05274cb536893031.comodoca.com." - "9p83fpanfdgs8xdgcnzd" = "verify.squarespace.com." - "activate" = "verona-networks-checkout.gaiia-consumer.com." - "autodiscover.o365" = "autodiscover.outlook.com." - "autodiscover" = "autodiscover.outlook.com." - "em924886" = "return.smtp2go.net." - "em9279" = "u177982.wl233.sendgrid.net." - "email" = "mandrillapp.com." - "enterpriseenrollment.o365" = "enterpriseenrollment.manage.microsoft.com." - "enterpriseregistration.o365" = "enterpriseregistration.windows.net." - "link" = "track.smtp2go.net." - "lyncdiscover.o365" = "webdir.online.lync.com." - "mte1._domainkey" = "dkim1.mandrillapp.com." - "mte2._domainkey" = "dkim2.mandrillapp.com." - "portal" = "verona-networks-clientportal.gaiia-consumer.com." - "s1._domainkey" = "s1.domainkey.u177982.wl233.sendgrid.net." - "s2._domainkey" = "s2.domainkey.u177982.wl233.sendgrid.net." - "s924886._domainkey" = "dkim.smtp2go.net." - "sip.o365" = "sipdir.online.lync.com." - "uptime" = "page.updown.io." - "url62" = "sendgrid.net." - "url9812" = "sendgrid.net." - "www" = "ext-cust.squarespace.com." - } - - depends_on = [powerdns_zone.vntx_net] - zone = "vntx.net." - name = "${each.key}.vntx.net." - type = "CNAME" - ttl = 3600 - records = [each.value] -} diff --git a/terraform/dns_vntx_org.tf b/terraform/dns_vntx_org.tf deleted file mode 100644 index b5ff35a..0000000 --- a/terraform/dns_vntx_org.tf +++ /dev/null @@ -1,12 +0,0 @@ -# DNS records for vntx.org domain -# Zone defined in dns_powerdns_zones.tf - -# SOA record for vntx.org -resource "powerdns_record" "vntx_org_soa" { - depends_on = [powerdns_zone.vntx_org] - zone = "vntx.org." - name = "vntx.org." - type = "SOA" - ttl = 3600 - records = ["ns1.as393837.net. graham.mcintire.me. 0 10800 3600 604800 3600"] -} diff --git a/terraform/dns_w5isp.tf b/terraform/dns_w5isp.tf deleted file mode 100644 index af9b12e..0000000 --- a/terraform/dns_w5isp.tf +++ /dev/null @@ -1,262 +0,0 @@ -resource "powerdns_record" "w5isp_soa" { - depends_on = [powerdns_zone.w5isp_com] - zone = "w5isp.com." - name = "w5isp.com." - type = "SOA" - ttl = 3600 - records = ["ns1.as393837.net. graham.mcintire.me. 0 10800 3600 604800 3600"] -} - -resource "powerdns_record" "w5isp_root" { - depends_on = [powerdns_zone.w5isp_com] - zone = "w5isp.com." - name = "w5isp.com." - type = "A" - ttl = 3600 - records = ["204.110.191.5"] -} - -resource "powerdns_record" "w5isp_git" { - depends_on = [powerdns_zone.w5isp_com] - zone = "w5isp.com." - name = "git.w5isp.com." - type = "A" - ttl = 3600 - records = ["66.206.18.163"] -} - -resource "powerdns_record" "w5isp_home" { - depends_on = [powerdns_zone.w5isp_com] - zone = "w5isp.com." - name = "home.w5isp.com." - type = "A" - ttl = 3600 - records = ["204.110.191.1"] -} - -resource "powerdns_record" "w5isp_photos" { - depends_on = [powerdns_zone.w5isp_com] - zone = "w5isp.com." - name = "photos.w5isp.com." - type = "A" - ttl = 3600 - records = ["204.110.191.8"] -} - -resource "powerdns_record" "w5isp_skippy" { - depends_on = [powerdns_zone.w5isp_com] - zone = "w5isp.com." - name = "skippy.w5isp.com." - type = "A" - ttl = 3600 - records = ["204.110.191.8"] -} - -resource "powerdns_record" "w5isp_ha" { - depends_on = [powerdns_zone.w5isp_com] - zone = "w5isp.com." - name = "ha.w5isp.com." - type = "CNAME" - ttl = 3600 - records = ["q1l09qiycnaagngmjsg1qas0rhqcfoou.ui.nabu.casa."] -} - -resource "powerdns_record" "w5isp_mx1" { - depends_on = [powerdns_zone.w5isp_com] - zone = "w5isp.com." - name = "w5isp.com." - type = "MX" - ttl = 3600 - records = ["10 mail.w5isp.com."] -} - -resource "powerdns_record" "w5isp_txt" { - depends_on = [powerdns_zone.w5isp_com] - zone = "w5isp.com." - name = "w5isp.com." - type = "TXT" - ttl = 3600 - records = ["\"v=spf1 mx a ip4:204.110.191.5 ~all\""] -} - -# DKIM record -resource "powerdns_record" "w5isp_dkim" { - depends_on = [powerdns_zone.w5isp_com] - zone = "w5isp.com." - name = "dkim._domainkey.w5isp.com." - type = "TXT" - ttl = 3600 - records = ["\"v=DKIM1;k=rsa;t=s;s=email;p=MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAxti2t8TvzIqKF9BpKn3rQExKg3sS1SyQuwtQgL0r/ELEJ0D9cKU/iM+eB1ROJctKHoMqKDJoRCMP6eibFcgq2kLKqf+aceEOIBx2OK2WCXML+CNqQZA6yO+A8/Jq7iFZPq8D5FmOoxbwRZkso7CkSennSz/+F7nBPI/OfyEiiI4xJzWH3t8SaAkkcy46O+1K0iCkTpsthon7E2PHa3SPkrjbep/5NImTJLK5LuffiLJtLsiK+73mvsAYCDmrNxPTaDjXkj0TWdKl/d/TnlVJl+YloqWIDt/7LtZQM0C7GZ9flIr7z9hHpSWERXAA5Gj5NQ0/hcY3nF4dPoqWs3VeeQIDAQAB\""] -} - -resource "powerdns_record" "w5isp_g" { - depends_on = [powerdns_zone.w5isp_com] - zone = "w5isp.com." - name = "g.w5isp.com." - type = "CNAME" - ttl = 3600 - records = ["mail.mcintire.me."] -} - -resource "powerdns_record" "w5isp_truck" { - depends_on = [powerdns_zone.w5isp_com] - zone = "w5isp.com." - name = "truck.w5isp.com." - type = "CNAME" - ttl = 3600 - records = ["mail.mcintire.me."] -} - -resource "powerdns_record" "w5isp_sendgrid1" { - depends_on = [powerdns_zone.w5isp_com] - zone = "w5isp.com." - name = "em40.w5isp.com." - type = "CNAME" - ttl = 3600 - records = ["u177982.wl233.sendgrid.net."] -} - -resource "powerdns_record" "w5isp_sendgrid2" { - depends_on = [powerdns_zone.w5isp_com] - zone = "w5isp.com." - name = "s1._domainkey.w5isp.com." - type = "CNAME" - ttl = 3600 - records = ["s1.domainkey.u177982.wl233.sendgrid.net."] -} - -resource "powerdns_record" "w5isp_sendgrid3" { - depends_on = [powerdns_zone.w5isp_com] - zone = "w5isp.com." - name = "s2._domainkey.w5isp.com." - type = "CNAME" - ttl = 3600 - records = ["s2.domainkey.u177982.wl233.sendgrid.net."] -} - -resource "powerdns_record" "w5isp_dmarc" { - depends_on = [powerdns_zone.w5isp_com] - zone = "w5isp.com." - name = "_dmarc.w5isp.com." - type = "TXT" - ttl = 3600 - records = ["\"v=DMARC1; p=quarantine; rua=mailto:postmaster@w5isp.com; ruf=mailto:postmaster@w5isp.com; fo=1\""] -} - -# Mail server -resource "powerdns_record" "w5isp_mail" { - depends_on = [powerdns_zone.w5isp_com] - zone = "w5isp.com." - name = "mail.w5isp.com." - type = "A" - ttl = 3600 - records = ["204.110.191.5"] -} - -resource "powerdns_record" "w5isp_sync" { - depends_on = [powerdns_zone.w5isp_com] - zone = "w5isp.com." - name = "sync.w5isp.com." - type = "A" - ttl = 3600 - records = ["204.110.191.216"] -} - -resource "powerdns_record" "w5isp_log" { - depends_on = [powerdns_zone.w5isp_com] - zone = "w5isp.com." - name = "log.w5isp.com." - type = "CNAME" - ttl = 3600 - records = ["mail.mcintire.me."] -} - -resource "powerdns_record" "w5isp_autodiscover" { - depends_on = [powerdns_zone.w5isp_com] - zone = "w5isp.com." - name = "autodiscover.w5isp.com." - type = "CNAME" - ttl = 3600 - records = ["mail.w5isp.com."] -} - -resource "powerdns_record" "w5isp_autodiscover_srv" { - depends_on = [powerdns_zone.w5isp_com] - zone = "w5isp.com." - name = "_autodiscover._tcp.w5isp.com." - type = "SRV" - ttl = 3600 - records = ["0 0 443 mail.w5isp.com."] -} - -resource "powerdns_record" "w5isp_autoconfig" { - depends_on = [powerdns_zone.w5isp_com] - zone = "w5isp.com." - name = "autoconfig.w5isp.com." - type = "CNAME" - ttl = 3600 - records = ["mail.w5isp.com."] -} - -resource "powerdns_record" "w5isp_n8n" { - depends_on = [powerdns_zone.w5isp_com] - zone = "w5isp.com." - name = "n8n.w5isp.com." - type = "A" - ttl = 3600 - records = ["204.110.191.2"] # Traefik ingress on k3s cluster -} - -resource "powerdns_record" "w5isp_nodered" { - depends_on = [powerdns_zone.w5isp_com] - zone = "w5isp.com." - name = "nodered.w5isp.com." - type = "A" - ttl = 3600 - records = ["204.110.191.2"] # Node-RED via Traefik on k3s cluster -} - -resource "powerdns_record" "w5isp_headscale" { - depends_on = [powerdns_zone.w5isp_com] - zone = "w5isp.com." - name = "headscale.w5isp.com." - type = "A" - ttl = 3600 - records = ["66.206.18.166"] -} - -resource "powerdns_record" "w5isp_hs" { - depends_on = [powerdns_zone.w5isp_com] - zone = "w5isp.com." - name = "hs.w5isp.com." - type = "A" - ttl = 3600 - records = ["66.206.18.166"] -} - -resource "powerdns_record" "w5isp_dokku" { - depends_on = [powerdns_zone.w5isp_com] - zone = "w5isp.com." - name = "dokku.w5isp.com." - type = "A" - ttl = 3600 - records = ["204.110.191.218"] -} - -resource "powerdns_record" "w5isp_camper" { - depends_on = [powerdns_zone.w5isp_com] - zone = "w5isp.com." - name = "camper.w5isp.com." - type = "CNAME" - ttl = 3600 - records = ["skippy.w5isp.com."] -} - -resource "powerdns_record" "w5isp_wildcard" { - depends_on = [powerdns_zone.w5isp_com] - zone = "w5isp.com." - name = "*.w5isp.com." - type = "A" - ttl = 3600 - records = ["172.245.56.83"] -} diff --git a/terraform/main.tf b/terraform/main.tf index e5e7db9..d5e36fa 100644 --- a/terraform/main.tf +++ b/terraform/main.tf @@ -8,10 +8,6 @@ terraform { source = "kyswtn/porkbun" version = "~> 0.1" } - powerdns = { - source = "pan-net/powerdns" - version = "~> 1.5" - } vultr = { source = "vultr/vultr" version = "~> 2.28" @@ -45,11 +41,6 @@ provider "porkbun" { secret_api_key = var.porkbun_secret_api_key } -provider "powerdns" { - api_key = var.pdns_api_key - server_url = var.pdns_server_url -} - provider "cloudflare" { # API token is read from CLOUDFLARE_API_TOKEN environment variable # No explicit api_token parameter needed - provider automatically reads the env var diff --git a/terraform/terraform.tfvars b/terraform/terraform.tfvars index fa3f9c2..3155aa2 100644 --- a/terraform/terraform.tfvars +++ b/terraform/terraform.tfvars @@ -6,5 +6,3 @@ token_id = "terraform@pve!terraform-token" dnsimple_token = "dnsimple_a_sRmKiuHrxR2UiMHf0NREqAtgfELyRVAI" porkbun_api_key = "pk1_5f321ff82ce0c085e67f9569db48976d838f302bc15b88292373e4b6b9891f17" porkbun_secret_api_key = "sk1_854fd74c8221bceaec27cf17edf3402b074e67447befe1363cf0247b620c82c5" -pdns_api_key = "f6N7v8ldcqINh4hnAfczEKpA/2g5D+ftzJkQKQz1/G0=" -pdns_server_url = "http://100.119.7.112:8081" diff --git a/terraform/tfplan b/terraform/tfplan deleted file mode 100644 index 3a84f6be547f4ad4c49517d9a621433d8a14eef0..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 72862 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 diff --git a/terraform/variables.tf b/terraform/variables.tf index c22c5d4..f27201b 100644 --- a/terraform/variables.tf +++ b/terraform/variables.tf @@ -38,41 +38,12 @@ variable "proxmox_nodes" { default = ["vm2-380"] } -variable "cluster_name" { - description = "Name prefix for the K3s cluster nodes" - type = string - default = "home-k3s" -} - -variable "vm_template" { - description = "Name of the VM template to clone" - type = string - default = "debian-13-cloudinit" -} - -variable "storage_pool" { - description = "Storage pool for VM disks" - type = string - default = "ceph" -} - variable "network_bridge" { description = "Network bridge to use for VMs" type = string default = "vmbr0" } -variable "network_cidr" { - description = "Network CIDR for the cluster" - type = string - default = "10.0.16.0/22" -} - -variable "network_gateway" { - description = "Network gateway" - type = string - default = "10.0.19.254" -} variable "control_plane_count" { description = "Number of control plane nodes" @@ -98,12 +69,6 @@ variable "control_plane_disk_size" { default = 32 } -variable "control_plane_ip_start" { - description = "Starting IP offset for control plane nodes" - type = number - default = 868 # 10.0.19.100 = offset 868 from 10.0.16.0 (3*256 + 100) -} - variable "worker_count" { description = "Number of worker nodes" type = number @@ -128,12 +93,6 @@ variable "worker_disk_size" { default = 64 } -variable "worker_ip_start" { - description = "Starting IP offset for worker nodes" - type = number - default = 878 # 10.0.19.110 = offset 878 from 10.0.16.0 (3*256 + 110) -} - variable "ssh_user" { description = "SSH user for the VMs" type = string @@ -177,12 +136,6 @@ variable "proxmox_host" { default = "vm2-380" } -variable "template_name" { - description = "VM template name" - type = string - default = "ubuntu" -} - variable "nic_name" { description = "Network interface name" type = string @@ -205,14 +158,3 @@ variable "token_id" { description = "Proxmox token ID" type = string } - -variable "pdns_api_key" { - description = "PowerDNS API key" - type = string - sensitive = true -} - -variable "pdns_server_url" { - description = "PowerDNS server URL" - type = string -}