add source code and readme

This commit is contained in:
2025-12-24 14:35:17 +01:00
parent 7c92e1e610
commit 74324d5a1b
331 changed files with 39272 additions and 1 deletions

View File

@@ -0,0 +1,59 @@
# Harbor Registry Firewall Rules for Direct Access
apiVersion: "cilium.io/v2"
kind: CiliumClusterwideNetworkPolicy
metadata:
name: "harbor-registry-host-firewall"
spec:
description: "Allow external access to ports 80/443 only for NGINX Ingress serving Harbor"
# Target NGINX Ingress Controller pods specifically (they use hostNetwork)
endpointSelector:
matchLabels:
app.kubernetes.io/name: "ingress-nginx"
app.kubernetes.io/component: "controller"
ingress:
# Allow external traffic to NGINX Ingress on HTTP/HTTPS ports
- fromEntities:
- world
- cluster
toPorts:
- ports:
- port: "80"
protocol: "TCP"
- port: "443"
protocol: "TCP"
# Allow cluster-internal traffic to NGINX Ingress
- fromEntities:
- cluster
toPorts:
- ports:
- port: "80"
protocol: "TCP"
- port: "443"
protocol: "TCP"
- port: "10254" # NGINX metrics port
protocol: "TCP"
---
# Allow NGINX Ingress to reach Harbor services
apiVersion: "cilium.io/v2"
kind: CiliumNetworkPolicy
metadata:
name: "harbor-services-access"
namespace: "harbor-registry"
spec:
description: "Allow NGINX Ingress Controller to reach Harbor services"
endpointSelector:
matchLabels:
app: "harbor"
ingress:
# Allow traffic from NGINX Ingress Controller
- fromEndpoints:
- matchLabels:
app.kubernetes.io/name: "ingress-nginx"
app.kubernetes.io/component: "controller"
# Allow traffic between Harbor components
- fromEndpoints:
- matchLabels:
app: "harbor"

View File

@@ -0,0 +1,262 @@
# policies/host-fw-control-plane.yaml
apiVersion: "cilium.io/v2"
kind: CiliumClusterwideNetworkPolicy
metadata:
name: "host-fw-control-plane"
spec:
description: "control-plane specific access rules. Restricted to Tailscale network for security."
nodeSelector:
matchLabels:
node-role.kubernetes.io/control-plane: ""
ingress:
# Allow access to kube api from Tailscale network, VLAN, VIP, and external IPs
# VIP (<VIP_IP>) allows new nodes to bootstrap via VLAN without network changes
- fromCIDR:
- 100.64.0.0/10 # Tailscale CGNAT range
- 10.132.0.0/24 # VLAN subnet (includes VIP <VIP_IP> and node IPs)
- <VIP_IP>/32 # Explicit VIP for control plane (new node bootstrapping)
- <NODE_1_EXTERNAL_IP>/32 # n1 external IP
- <NODE_2_EXTERNAL_IP>/32 # n2 external IP
- <NODE_3_EXTERNAL_IP>/32 # n3 external IP
- fromEntities:
- cluster # Allow cluster-internal access
toPorts:
- ports:
- port: "6443"
protocol: "TCP"
# Allow access to talos from Tailscale network, VLAN, VIP, external IPs, and cluster
# Restricted access (not world) for security - authentication still required
# https://www.talos.dev/v1.4/learn-more/talos-network-connectivity/
- fromCIDR:
- 100.64.0.0/10 # Tailscale CGNAT range
- 10.132.0.0/24 # VLAN subnet for node bootstrapping
- <VIP_IP>/32 # VIP for control plane access
- <NODE_1_EXTERNAL_IP>/32 # n1 external IP
- <NODE_2_EXTERNAL_IP>/32 # n2 external IP
- <NODE_3_EXTERNAL_IP>/32 # n3 external IP
- fromEntities:
- cluster # Allow cluster-internal access
toPorts:
- ports:
- port: "50000"
protocol: "TCP"
- port: "50001"
protocol: "TCP"
# Allow worker nodes to access control plane Talos API
- fromEntities:
- remote-node
toPorts:
- ports:
- port: "50000"
protocol: "TCP"
- port: "50001"
protocol: "TCP"
# Allow kube-proxy-replacement from kube-apiserver
- fromEntities:
- kube-apiserver
toPorts:
- ports:
- port: "10250"
protocol: "TCP"
- port: "4244"
protocol: "TCP"
# Allow access from hubble-relay to hubble-peer (running on the node)
- fromEndpoints:
- matchLabels:
k8s-app: hubble-relay
toPorts:
- ports:
- port: "4244"
protocol: "TCP"
# Allow metrics-server to scrape
- fromEndpoints:
- matchLabels:
k8s-app: metrics-server
toPorts:
- ports:
- port: "10250"
protocol: "TCP"
# Allow ICMP Ping from/to anywhere.
- icmps:
- fields:
- type: 8
family: IPv4
- type: 128
family: IPv6
# Allow cilium tunnel/health checks from other nodes.
- fromEntities:
- remote-node
toPorts:
- ports:
- port: "8472"
protocol: "UDP"
- port: "4240"
protocol: "TCP"
# Allow etcd communication between control plane nodes
# Required for etcd cluster formation and peer communication
# Ports: 2379 (client API), 2380 (peer communication), 51871 (Talos etcd peer discovery)
- fromCIDR:
- 100.64.0.0/10 # Tailscale CGNAT range
- 10.132.0.0/24 # VLAN subnet (includes VIP <VIP_IP> and node IPs)
- <VIP_IP>/32 # Explicit VIP for control plane (new node bootstrapping)
- <NODE_1_EXTERNAL_IP>/32 # n1 external IP
- <NODE_2_EXTERNAL_IP>/32 # n2 external IP
- <NODE_3_EXTERNAL_IP>/32 # n3 external IP
- fromEntities:
- remote-node # Allow from other nodes (including bootstrapping control planes)
- cluster # Allow from cluster pods
toPorts:
- ports:
- port: "2379"
protocol: "TCP" # etcd client API
- port: "2380"
protocol: "TCP" # etcd peer communication
- port: "51871"
protocol: "UDP" # Talos etcd peer discovery
# HTTP and HTTPS access - allow external for Harbor direct access and Let's Encrypt challenges
# everything else is secured and I really hate this
- fromEntities:
- cluster
- world # Allow external access for Harbor and Let's Encrypt
- fromCIDR:
- 100.64.0.0/10 # Tailscale CGNAT range - allow Tailscale services (e.g., Kibana proxy)
toPorts:
- ports:
- port: "80"
protocol: "TCP"
- port: "443"
protocol: "TCP"
# Allow access from inside the cluster to the admission controller
- fromEntities:
- cluster
toPorts:
- ports:
- port: "8443"
protocol: "TCP"
# Allow PostgreSQL and Redis database connections from cluster
- fromEntities:
- cluster
toPorts:
- ports:
- port: "5432"
protocol: "TCP" # PostgreSQL
- port: "6379"
protocol: "TCP" # Redis
# Allow PostgreSQL monitoring/health checks and CloudNativePG coordination
- fromEntities:
- cluster
toPorts:
- ports:
- port: "9187"
protocol: "TCP" # PostgreSQL metrics port
- port: "8000"
protocol: "TCP" # CloudNativePG health endpoint
- port: "9443"
protocol: "TCP" # CloudNativePG operator webhook server
# Allow local kubelet health checks on control plane pods
# (kubelet on control plane needs to check health endpoints of local pods)
- fromEntities:
- host
toPorts:
- ports:
- port: "8000"
protocol: "TCP" # CloudNativePG health endpoint for kubelet probes
# OpenObserve and metrics collection ports
- fromEntities:
- cluster
toPorts:
- ports:
- port: "5080"
protocol: "TCP" # OpenObserve
- port: "10254"
protocol: "TCP" # NGINX Ingress metrics
egress:
# Allow all cluster communication (pods, services, nodes)
- toEntities:
- cluster
- remote-node
- host
# Allow etcd communication to other control plane nodes
# Required for etcd cluster formation and peer communication
- toCIDR:
- 10.132.0.0/24 # VLAN subnet (all control plane nodes)
- <VIP_IP>/32 # VIP
- toEntities:
- remote-node # Allow to other nodes
toPorts:
- ports:
- port: "2379"
protocol: "TCP" # etcd client API
- port: "2380"
protocol: "TCP" # etcd peer communication
- port: "51871"
protocol: "UDP" # Talos etcd peer discovery
# Allow control plane to reach CloudNativePG health endpoints on all nodes
- toEntities:
- cluster
- remote-node
- host
toPorts:
- ports:
- port: "8000"
protocol: "TCP" # CloudNativePG health endpoint
# Allow control plane to reach PostgreSQL databases on worker nodes
- toEntities:
- cluster
- remote-node
toPorts:
- ports:
- port: "5432"
protocol: "TCP" # PostgreSQL database
- port: "9187"
protocol: "TCP" # PostgreSQL metrics
- port: "8000"
protocol: "TCP" # CloudNativePG health endpoint (correct port)
- port: "8080"
protocol: "TCP" # Additional health/admin endpoints
- port: "9443"
protocol: "TCP" # CloudNativePG operator webhook server
# Allow DNS resolution
- toEntities:
- cluster
- remote-node
toPorts:
- ports:
- port: "53"
protocol: "TCP"
- port: "53"
protocol: "UDP"
# Allow outbound internet access for backup operations, image pulls, etc.
- toEntities:
- world
toPorts:
- ports:
- port: "443"
protocol: "TCP" # HTTPS
- port: "80"
protocol: "TCP" # HTTP
- port: "53"
protocol: "UDP" # DNS
- port: "123"
protocol: "UDP" # NTP time synchronization

View File

@@ -0,0 +1,199 @@
# policies/host-fw-worker-nodes.yaml
apiVersion: "cilium.io/v2"
kind: CiliumClusterwideNetworkPolicy
metadata:
name: "host-fw-worker-nodes"
spec:
description: "Worker node firewall rules - more permissive for database workloads"
nodeSelector:
matchExpressions:
- key: node-role.kubernetes.io/control-plane
operator: DoesNotExist
ingress:
# Allow all cluster communication for database operations
- fromEntities:
- cluster
- remote-node
- host
# Allow PostgreSQL and Redis connections from anywhere in cluster
- fromEntities:
- cluster
toPorts:
- ports:
- port: "5432"
protocol: "TCP" # PostgreSQL
- port: "6379"
protocol: "TCP" # Redis
# Allow health check and monitoring ports
- fromEntities:
- cluster
toPorts:
- ports:
- port: "8000"
protocol: "TCP" # CloudNativePG health endpoint
- port: "8080"
protocol: "TCP"
- port: "9187"
protocol: "TCP" # PostgreSQL metrics
- port: "9443"
protocol: "TCP" # CloudNativePG operator webhook server
- port: "10250"
protocol: "TCP" # kubelet
# Allow kubelet access from VLAN for cluster operations
- fromCIDR:
- 10.132.0.0/24 # VLAN subnet
toPorts:
- ports:
- port: "10250"
protocol: "TCP" # kubelet API
# HTTP and HTTPS access - allow from cluster and Tailscale network
# Tailscale network needed for Tailscale operator proxy pods (e.g., Kibana via MagicDNS)
- fromEntities:
- cluster
- fromCIDR:
- 100.64.0.0/10 # Tailscale CGNAT range - allow Tailscale services
toPorts:
- ports:
- port: "80"
protocol: "TCP"
- port: "443"
protocol: "TCP"
# Allow access to Talos API from Tailscale network, VLAN, and external IPs
# Restricted access (not world) for security - authentication still required
- fromCIDR:
- 100.64.0.0/10 # Tailscale CGNAT range
- 10.132.0.0/24 # VLAN subnet for node bootstrapping
- <NODE_1_EXTERNAL_IP>/32 # n1 external IP
- <NODE_2_EXTERNAL_IP>/32 # n2 external IP
- <NODE_3_EXTERNAL_IP>/32 # n3 external IP
- fromEntities:
- cluster # Allow cluster-internal access
toPorts:
- ports:
- port: "50000"
protocol: "TCP"
- port: "50001"
protocol: "TCP"
# Allow ICMP Ping
- icmps:
- fields:
- type: 8
family: IPv4
- type: 128
family: IPv6
# Allow cilium tunnel/health checks
- fromEntities:
- remote-node
toPorts:
- ports:
- port: "8472"
protocol: "UDP"
- port: "4240"
protocol: "TCP"
# Allow hubble communication
- fromEndpoints:
- matchLabels:
k8s-app: hubble-relay
toPorts:
- ports:
- port: "4244"
protocol: "TCP"
# NGINX Ingress Controller metrics port
- fromEntities:
- cluster
toPorts:
- ports:
- port: "10254"
protocol: "TCP" # NGINX Ingress metrics
# OpenObserve metrics ingestion port
- fromEntities:
- cluster
toPorts:
- ports:
- port: "5080"
protocol: "TCP" # OpenObserve HTTP API
# Additional monitoring ports (removed unused Prometheus/Grafana ports)
# Note: OpenObserve is used instead of Prometheus/Grafana stack
egress:
# Allow all cluster communication (pods, services, nodes) - essential for CloudNativePG
- toEntities:
- cluster
- remote-node
- host
# Allow worker nodes to reach control plane services
- toEntities:
- cluster
- remote-node
toPorts:
- ports:
- port: "6443"
protocol: "TCP" # Kubernetes API server
- port: "8000"
protocol: "TCP" # CloudNativePG health endpoints
- port: "9443"
protocol: "TCP" # CloudNativePG operator webhook
- port: "5432"
protocol: "TCP" # PostgreSQL replication
- port: "9187"
protocol: "TCP" # PostgreSQL metrics
# Allow access to control plane via VLAN for node bootstrapping
# Explicit VIP access ensures new nodes can reach kubeapi without network changes
- toCIDR:
- 10.132.0.0/24 # VLAN subnet for cluster bootstrapping (includes VIP)
- <VIP_IP>/32 # Explicit VIP for control plane kubeapi
- <NODE_1_IP>/32 # n1 VLAN IP (fallback)
toPorts:
- ports:
- port: "6443"
protocol: "TCP" # Kubernetes API server
- port: "50000"
protocol: "TCP" # Talos API
- port: "50001"
protocol: "TCP" # Talos API trustd
# Allow DNS resolution
- toEndpoints:
- matchLabels:
k8s-app: kube-dns
toPorts:
- ports:
- port: "53"
protocol: "UDP"
- port: "53"
protocol: "TCP"
# Allow worker nodes to reach external services (OpenObserve, monitoring)
- toEntities:
- cluster
toPorts:
- ports:
- port: "5080"
protocol: "TCP" # OpenObserve
# Allow outbound internet access for NTP, image pulls, etc.
- toEntities:
- world
toPorts:
- ports:
- port: "443"
protocol: "TCP" # HTTPS
- port: "80"
protocol: "TCP" # HTTP
- port: "53"
protocol: "UDP" # DNS
- port: "123"
protocol: "UDP" # NTP time synchronization

View File

@@ -0,0 +1,68 @@
---
# Fix for apiserver-kubelet-client RBAC permissions
# Required when adding new control plane nodes to Talos clusters
# This ensures the kubelet can access node/pods subresource for static pod management
#
# The system:kubelet-api-admin ClusterRole should already exist in Kubernetes,
# but we ensure the ClusterRoleBinding exists and has the correct permissions.
apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRoleBinding
metadata:
name: system:apiserver-kubelet-client
annotations:
description: "Grants apiserver-kubelet-client permission to access nodes and pods for kubelet operations"
roleRef:
apiGroup: rbac.authorization.k8s.io
kind: ClusterRole
name: system:kubelet-api-admin
subjects:
- apiGroup: rbac.authorization.k8s.io
kind: User
name: system:apiserver-kubelet-client
---
# Ensure the ClusterRole has nodes/pods subresource permission
# This may need to be created if it doesn't exist or updated if missing nodes/pods
apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRole
metadata:
name: system:kubelet-api-admin
labels:
kubernetes.io/bootstrapping: rbac-defaults
rules:
- apiGroups:
- ""
resources:
- nodes
- nodes/proxy
- nodes/stats
- nodes/log
- nodes/spec
- nodes/metrics
- nodes/pods # CRITICAL: Required for kubelet to get pod status on nodes
verbs:
- get
- list
- watch
- create
- patch
- update
- delete
- apiGroups:
- ""
resources:
- pods
- pods/status
- pods/log
- pods/exec
- pods/portforward
- pods/proxy
verbs:
- get
- list
- watch
- create
- patch
- update
- delete

View File

@@ -0,0 +1,7 @@
apiVersion: kustomize.config.k8s.io/v1beta1
kind: Kustomization
resources:
- host-fw-control-plane.yaml
- host-fw-worker-nodes.yaml
- harbor-registry-firewall.yaml