Place CI runners in their own network segment and allow only the specific destinations jobs need, such as the artifact registry, package mirror and a deploy target. Do not give runners a route to the whole internal network. A job runs code you did not fully review, so treat it as an untrusted host.
What the guidance says
GitLab's runner security page notes that the runner is designed to run user controlled scripts, and suggests running jobs in their own network segment, which provides separation from other infrastructure and reduces the attack surface if a job is malicious. The same page warns that with some executors, jobs can reach the runner host and its network, and that high security risks exist when running builds with the shell executor on a shared host.
Why migration changes the picture
A monolithic CI server often sat in a trusted internal zone with broad access, since it needed to deploy everywhere. Moving to many ephemeral pods or virtual machines can multiply that access if every pod inherits the same network position. One hijacked job then has the same reach as the whole server did.
Design in steps
- List destinations. For each pipeline type, write down what it must reach: source host, package mirror, registry, test services, deploy target.
- Create a runner segment. Use a separate subnet, namespace with network policy, or virtual network.
- Default deny. Block all traffic from the segment, then allow listed destinations by name and port.
- Route package traffic through a mirror. Jobs then need no direct internet access to package registries.
- Split by trust. Jobs from untrusted changes get a segment with no route to internal systems at all.
- Use short lived access for deploys. Where a job must reach an internal system, grant a credential and a route only for deploy jobs on protected branches.
- Log denied traffic. A blocked outbound call from a build is a signal worth reading.
Table of segments
| Segment | Who runs there | Allowed to reach |
|---|---|---|
| Untrusted builds | Pull requests from forks or new contributors | Package mirror and source host only |
| Standard builds | Trusted branches | Mirror, registry, test services |
| Deploy | Protected branches only | Registry and the specific deploy target |
| Privileged builds | Dedicated pool | Registry and mirrors only |
Egress matters as much as ingress
Most worry about CI network access focuses on what can reach in. For a hijacked job, the damage is usually what it can send out: tokens, source code or build outputs. Restrict outbound traffic and you shrink what a leak can reach. See what is egress filtering in CI.
Quick check
Do I need a VPN for runners to reach private systems?
Not necessarily. Many teams use private links or in-cluster routes. Whatever the method, allow only listed destinations and keep credentials short lived.
Is a separate cluster required?
Not always. Separate namespaces with network policy can work, but a separate cluster or account gives stronger isolation for sensitive deploys.
Sources
Last reviewed: 19 October 2026.