Runners (EKS Kubernetes)¶
GitLab CI/CD runners for the CWIQ platform run as Kubernetes pods on AWS EKS. This page covers runner tiers, job tagging, networking constraints, and when to use each tier.
Architecture Overview¶
All active CWIQ runners are Kubernetes pods managed by the GitLab Runner Helm chart on the cluster cwiq-dev-eks-cluster (Kubernetes 1.31, Karpenter v1.1.1). When a pipeline job starts, the runner controller schedules a pod on EKS. Karpenter provisions EC2 nodes on demand based on the runner tier's resource profile.
flowchart TD
GL[GitLab CI Job Queue] --> RC[Runner Controller<br/>GitLab Runner Helm chart]
RC --> K8S[EKS Cluster<br/>cwiq-dev-eks-cluster]
K8S --> KARP[Karpenter v1.1.1<br/>on-demand node provisioning]
KARP --> SMALL[small node<br/>job pod]
KARP --> MEDIUM[medium node<br/>job pod]
KARP --> LARGE[large node<br/>job pod]
SMALL --> JOB1[lint / test / scan / deploy]
MEDIUM --> JOB2[Docker build / Kaniko]
LARGE --> JOB3[Nuitka compilation<br/>executor only]
Runner Tiers¶
Three runner tiers are available. The default tag is medium, which is set globally in .gitlab-ci-common.yml. Override it per job with an explicit tags: entry.
| Runner | ID | Tag | Primary Use | Default |
|---|---|---|---|---|
| k8s-small | 19 | small |
Lint, typecheck, test, security scan, deploy, verify | No |
| k8s-medium | 20 | medium |
Docker image builds (Kaniko), UI Kaniko builds | Yes |
| k8s-large | 21 | large |
Nuitka compilation and RPM builds (executor only) | No |
Choosing a Tag¶
Use small for lightweight jobs
Most jobs — lint, typecheck, pytest, Semgrep, Trivy FS scan, SSH deploy, health checks — are lightweight and run faster on small because they do not need to wait for a larger node to provision. Add tags: [small] to these jobs to reduce pipeline duration and cluster cost.
Reserve medium for Kaniko Docker builds, which require more memory. Reserve large exclusively for the executor's Nuitka compilation and RPM packaging steps.
# Example: lightweight jobs use small tag
lint:
extends: .python-lint
stage: validate
tags:
- small
# Docker builds use the default medium tag (no tags: entry needed)
build:
extends: .docker-build
stage: build
Networking Constraints¶
Tailscale is not available inside runner pods
Runner pods receive VPC IP addresses from the EKS VPC CNI plugin in subnets 10.1.34.0/24 and 10.1.35.0/24. Tailscale is not installed inside pods and Tailscale MagicDNS hostnames are not resolvable from pod network.
Any job that connects to another server (deploy, health check, migration) must use the server's VPC private IP. The DEV_SERVER_IP group-level CI/CD variable is set to the VPC private IP for this reason. Never use Tailscale IPs or .cwiq.io hostnames that resolve to Tailscale addresses in CI jobs.
The target DEV server must also allow inbound SSH (port 22) and HTTPS (port 443) from the EKS cluster security group.
Legacy Fleeting Runners (Paused)¶
Runners with IDs 16 (dev-small), 17 (dev-medium), and 18 (dev-large) were the previous generation of runners, based on the GitLab Fleeting plugin running on a dedicated EC2 Runner Manager instance. These runners were paused on 2026-02-27 when the EKS Kubernetes runners became fully operational. The Runner Manager EC2 instance has been stopped.
Do not use runner IDs 16–18. If you see a job waiting for these runners, check that your tags: entry matches one of the active tags: small, medium, or large.
Related Documentation¶
- Groups & Projects — Project IDs and group-level CI/CD variables
- Pipeline Overview — How stages and jobs are structured
- Kaniko Docker Builds — Why Kaniko is used instead of Docker-in-Docker
- Deploy Patterns — How deploy jobs SSH to the DEV server