Kubernetes Hardening
The Helm chart includes several optional hardening resources. All are disabled by default — enable them explicitly in your values file.
HorizontalPodAutoscaler
Scales the deployment based on CPU and memory utilization.
autoscaling:
enabled: true
minReplicas: 2
maxReplicas: 5
targetCPUUtilizationPercentage: 70
targetMemoryUtilizationPercentage: 80
When autoscaling.enabled is true, the replicaCount field in the Deployment is suppressed — HPA owns replica count.
Requires the metrics-server to be running in the cluster. On minikube:
minikube addons enable metrics-server
PodDisruptionBudget
Ensures a minimum number of pods remain available during voluntary disruptions (node drains, rolling updates):
podDisruptionBudget:
enabled: true
minAvailable: 1
Requires at least 2 running replicas to be meaningful. Best used alongside HPA.
NetworkPolicy
Restricts traffic to only what the service needs:
- Ingress: port 8888 from any source
- Egress: DNS (port 53) only
networkPolicy:
enabled: true
Requires a CNI plugin that enforces NetworkPolicy (e.g. Calico, Cilium). On minikube:
minikube start --network-plugin=cni --cni=calico
ResourceQuota
Caps total resource consumption in the namespace:
resourceQuota:
enabled: true
hard:
pods: "10"
requests.cpu: "2"
requests.memory: 2Gi
limits.cpu: "4"
limits.memory: 4Gi
Protects the cluster from runaway resource usage. The quota applies to the namespace the chart is installed in.
ConfigMap
Application config (PORT, NODE_ENV) is stored in a ConfigMap and mounted as environment variables. This separates config from the container image.
config:
PORT: "8888"
NODE_ENV: "production"
Security context
The container runs as a non-root user. The Deployment sets:
securityContext:
runAsNonRoot: true
runAsUser: 1000
Secrets
See the Secrets page for the Kubernetes Secrets pattern used in this project.