GitLab on Kubernetes with the Helm chart or Operator

Deploying GitLab on Kubernetes with the official Helm chart or GitLab Operator, using the Cloud Native Hybrid layout with stateful services outside the cluster, plus the decisions, build sequence and checks that come with it.

On this page

GitLab on Kubernetes starts with a question about where state lives

A platform team that already runs Kubernetes and wants GitLab there should first decide where the stateful services will live. GitLab can run on Kubernetes through the official Helm chart or the GitLab Operator, but the reference architectures do not support running stateful components such as PostgreSQL and Redis inside Kubernetes. The usual shape is therefore the Cloud Native Hybrid layout, in which stateless GitLab components run as pods while the stateful services run on virtual machines or managed services outside the cluster.

The install command suggests a small decision, but it hides a larger one. The chart can deploy PostgreSQL and Redis for evaluation, and a team that is not careful can let those defaults reach production. Once they do, the team owns database backups, failover, storage classes, version upgrades and restore tests for components that the reference architectures do not cover inside the cluster. Before the first install, write down where PostgreSQL, Redis and Gitaly will run, who patches them, how their backups are taken and who is paged when one fails. Confirm with GitLab's reference architecture documentation which Cloud Native Hybrid variant matches your user count, since the sizing and external service requirements differ by scale.

Gitaly needs particular attention because it stores repository data on disk. Gitaly on Kubernetes depends on persistent volumes with storage behavior your team can verify, including performance under concurrent Git operations, volume expansion and snapshot support. Ask the storage team whether the volumes sit on the same failure domain as the rest of the cluster, and whether a node or zone loss would leave repositories unavailable. Those answers change the recovery plan more than the Helm values do.

The Linux package is a legitimate alternative, not a fallback for teams that have not finished their Kubernetes work. It bundles PostgreSQL, Redis and Sidekiq and is the method GitLab describes as the most mature and scalable. If the team lacks depth in running stateful workloads on Kubernetes, or if the platform group would be the only people who understand the instance during an incident, a package install on virtual machines may carry less operational risk. Choose by asking who will restore the database at 2 a.m., not by which method looks more modern.

Make the decision in writing before any cluster work starts. Record the chosen method, the external PostgreSQL, Redis and Gitaly locations, the owner of each service, the backup target and the upgrade path, including the required upgrade stops. Test a restore into a separate namespace or environment before go-live, because a Kubernetes deployment that has never been restored is an untested backup.

Helm chart, Operator or Linux package: choosing the GitLab on Kubernetes path

This table compares the three GitLab installation methods that matter for this decision: the Linux package, the Helm chart and the GitLab Operator. Read each row as a question to answer for your own team, since the Kubernetes options shift who owns the upgrade path and where stateful services run. The main takeaway is that the Linux package is GitLab's most mature and scalable method and bundles its own PostgreSQL, Redis and Sidekiq, so the Kubernetes paths only make sense when your platform team will run that layer.

Decision pointLinux packageHelm chartGitLab Operator
When it fitsDedicated VMs with a single supported installation path and the most mature scaling optionsTeams with an existing Kubernetes platform, GitOps practice and capacity to own chart valuesTeams that want Kubernetes-native lifecycle management through a custom resource and operator
Maturity for scaleGitLab lists it as the most mature and scalable installation methodSupported for Cloud Native Hybrid layouts with stateful services placed outside the clusterSupported for Kubernetes deployments; confirm current feature parity with the chart for your release
Bundled stateful servicesBundles PostgreSQL, Redis and Sidekiq on the same server groupExpects PostgreSQL, Redis and Gitaly to run outside the cluster in the Hybrid layoutFollows the same external service model as the chart; confirm the supported layout with GitLab
Who maintains the Kubernetes layerNot applicable; your team maintains the operating system and GitLab packagesYour platform team owns the cluster, ingress, storage classes, secrets and chart valuesYour platform team owns the cluster and the operator version alongside GitLab releases
Upgrade handlingPackage upgrades with GitLab's documented steps and required upgrade stopsChart version must match the target GitLab release and upgrade stops applyOperator and GitLab version must be moved together; upgrade stops still apply
Stateful service placementCo-located by default, with a split into separate servers for larger scalePostgreSQL, Redis and Gitaly placed on VMs or managed services outside KubernetesStateful services kept outside the cluster in the supported layout; confirm before design
Operational cost to watchServer patching, package upgrades and capacity planning on VMsChart value drift, cluster upgrades and separate database and storage operationsOperator upgrades, custom resource review and coordinated cluster and GitLab changes
Ask the vendor or your team to confirmRequired reference architecture for your user countChart and GitLab release compatibility for your target versionSupported topology, operator lifecycle and whether your cloud or data center is covered

Which GitLab components move into Kubernetes and which stay outside

GitLab's reference architectures separate stateless services, which can run as Kubernetes workloads, from stateful services that need stable storage. The Cloud Native Hybrid layout follows that split: the chart schedules the stateless parts, while Gitaly, PostgreSQL, Redis and object storage stay on VMs or managed services. Each card below shows where a component runs and which chart values or external connections you need to confirm.

Stateless web and API services

The webservice and API pods handle browser sessions, Git over HTTPS and REST or GraphQL requests. The Cloud Native Hybrid layout places them on Kubernetes, where the chart scales them by replica count. Check ingress, TLS termination, session handling and the replica counts that match the reference architecture size you chose for your user count. Confirm the chart values for replicas and resource requests before you change them from the defaults.

Sidekiq background workers

Sidekiq processes background jobs such as notifications, repository housekeeping and CI pipeline work. It is stateless, so the Cloud Native Hybrid layout runs it on Kubernetes and scales it through replicas. Its job queues depend on Redis and PostgreSQL outside the cluster, so verify network paths, credentials and network policies before you scale workers up. Confirm the chart values for worker replicas and queue settings for your target GitLab version.

Gitaly repository storage

Gitaly serves Git repository data from local disk, which makes it a stateful service. The reference architecture guidance keeps stateful components out of Kubernetes, so the Cloud Native Hybrid layout runs Gitaly on VMs. Plan disk sizing, backup method and, for 3,000 users or more, whether Gitaly Cluster with Praefect is needed for high availability. Confirm the chart values that point the platform at external Gitaly nodes before you deploy.

PostgreSQL and Redis data services

PostgreSQL stores metadata for projects, users and merge requests, while Redis holds cache and queue state. The reference architecture documentation says running either inside Kubernetes is not supported, so both run on VMs or managed services in the Cloud Native Hybrid layout. Confirm the chart values for external database and Redis connections, TLS and credentials. Plan high availability for these services separately, because the chart does not manage them.

Object storage for artifacts and registry

Object storage holds data such as CI artifacts, LFS objects, uploads and container registry data, depending on how you configure each type. It runs outside the cluster as a cloud bucket or an S3-compatible service you operate. Confirm which object types your chart version can store in external buckets, plus the lifecycle rules, encryption and access policies for each bucket. Test a restore that includes this data, since backups depend on it.

GitLab Runner placement

GitLab Runner executes CI/CD jobs and is a separate application from the platform components. You can run it on Kubernetes with the Kubernetes executor or on VMs with Docker, shell or autoscaling executors. The reference architecture guidance covers the platform services, so decide Runner placement on job isolation, capacity and cost, and check the reference architecture page for any Runner guidance. Keep Runner major and minor versions aligned with GitLab.

How to build GitLab on Kubernetes in the Cloud Native Hybrid layout

This sequence takes a self-managed GitLab instance from sizing to a production cutover, with stateless components on Kubernetes and stateful services on infrastructure you operate. Each step closes with a check, so the platform owner can confirm readiness before moving on.

  1. Confirm the reference architecture for your user count

    Match your user count and expected API load to a GitLab reference architecture, which the documentation lists from 1,000 users up to 50,000 users. The documentation generally recommends a high availability strategy at 3,000 or more users, which changes how the stateful services are designed, so confirm early whether this layout fits your scale. The output is a sizing sheet with node counts, CPU, memory and storage for each component. The step is done when the platform owner and infrastructure lead both approve that sheet against the reference architecture table.

  2. Provision PostgreSQL, Redis and Gitaly outside the cluster

    Build the stateful services on virtual machines or managed services outside Kubernetes, because the reference architectures do not support running PostgreSQL or Redis inside the cluster. Your infrastructure team or implementation partner sizes each service from the approved sheet and confirms the Gitaly placement against the current documentation. Set up access controls, backups and monitoring for each service at this point. The check is that each service is reachable on its intended port from a test host in the same network segment that the cluster nodes will use.

  3. Set up object storage and secrets

    Create object storage buckets for artifacts, LFS objects, uploads, packages and registry data, then give the GitLab service account only the permissions it needs. Store the secrets that GitLab generates and depends on, including the initial root credentials, database and Redis passwords, and the object storage keys, in your cluster secret store or external vault. Record which secrets must be saved separately from database backups, because restoring an instance requires them. The step is done when a test write and read to each bucket succeed with the service credentials and the secret store returns every required value.

  4. Point the chart or Operator at external services

    Set the Helm chart values or the GitLab Operator custom resource so the stateless components use your external PostgreSQL, Redis, Gitaly and object storage endpoints, and disable the bundled stateful services. Confirm the exact keys in the chart version or Operator release you plan to install, since these settings change between releases. Keep the configuration in version control so the same values can be reviewed and reapplied. The check is a rendered manifest review in which no bundled database or Redis deployment appears and every endpoint matches the values recorded in your sizing sheet.

  5. Install the release in a non-production namespace

    Deploy the release into a separate, non-production namespace that mirrors the production network policies, storage classes and ingress configuration. Your team or partner watches the rollout until every pod reports ready and the migration jobs complete without errors. Confirm the license is applied and the web interface loads through the intended hostname. The step is done when the pods are healthy, the database migrations finish cleanly and an administrator can sign in through the ingress with the secrets stored earlier.

  6. Verify the install with a test pipeline and a restore

    Run a test project through the full path: push a commit, execute a CI pipeline that uses a runner, store an artifact and confirm the object storage bucket holds it. Then restore a backup taken from the test instance into a second clean environment, following your backup procedure. Use the backup and restore guidance for the detailed steps rather than repeating them here. The step is done when the pipeline passes, the artifact downloads and the restored instance shows the same test project and users.

  7. Cut over production traffic after sign-off

    Complete the security review of identity, hardening and runner settings before the production namespace receives users, and schedule the change window with the business owners. Migrate or import the production data using the migration method your team has approved, then point DNS or the load balancer at the production ingress. Keep the previous system available for a rollback period agreed in advance. The step is done when the production smoke tests pass, the first real pipelines complete and the platform owner signs the cutover record.

Differences by where the stateful services run

This is the Cloud Native Hybrid pattern in its most common form. GitLab's stateless services (webservice, Sidekiq workers, Registry and similar components) run as pods, while PostgreSQL, Redis and Gitaly run on virtual machines that your team builds, patches and backs up. The Helm chart or Operator is configured to point at those external endpoints rather than deploying stateful pods of its own.

  • Chart configuration: disable the bundled PostgreSQL and Redis subcharts and set external host, port and credential references, including Gitaly storage entries that point at the VM addresses.
  • Network paths: open the database, Redis and Gitaly ports only from the cluster node or pod CIDR ranges, and confirm that DNS names resolve the same way from inside the cluster.
  • Operations: your team owns VM patching, database failover, Redis availability and Gitaly storage capacity. Backups for these services run outside the cluster, so restore procedures must be tested on the VMs themselves.
  • Version coupling: check that the PostgreSQL and Redis versions you run on VMs are supported by the GitLab release you plan to install, and confirm the current list in the GitLab documentation.
  • Upgrade effort: stateful VMs are upgraded on their own schedule, so plan them against the required upgrade stops at x.2, x.5, x.8 and x.11.

Before building, confirm which stateful services your user count requires and who will hold the on-call duty for them.

What drives GitLab on Kubernetes effort and how to keep it down

This table lists the main factors that change the work of a GitLab on Kubernetes deployment, how each one raises effort and what keeps it under control. Read each row as a decision to settle before build starts, since most of the effort grows from late changes to user count, storage layout or chart values. The main takeaway is that fixing the reference architecture, keeping external services in a known layout and limiting custom chart values early reduces both build and run effort.

DriverHow it raises effortHow to keep it down
User count and reference architectureThe user count sets which GitLab reference architecture applies, which sets node counts, sizing and whether high availability components are needed. Growing the user count after build usually means re-sizing stateful services and revisiting the layout.Fix the reference architecture from a confirmed user count and expected API request rate before build. Ask the vendor or your deployment partner to confirm the matching sizing in the reference architectures documentation for your version.
Gitaly and object storage volumeRepository data sits in Gitaly, and artifacts, LFS objects, packages and backups grow with use. Storage classes, volume resizing and backup targets that are chosen late can force data moves on a running instance.Estimate repository and artifact growth with the team that will use the instance, choose storage classes and object storage buckets before install, and set backup targets during build rather than after go-live.
External PostgreSQL, Redis and Gitaly servicesThe Cloud Native Hybrid layout runs stateful services outside Kubernetes, on VMs or managed services. Each external service needs its own provisioning, network rules, credentials, backups and monitoring, which adds work outside the cluster.Confirm which managed or VM-based services your organization already operates, and agree on owners, network paths and secret handling before build. Reuse existing database platform standards where the versions and supported configuration match.
Identity and TLS integrationSingle sign-on, group mapping, certificates for the external URL and internal trust chains each need coordination with identity and certificate owners. Delays here often hold up the first working login and the cutover date.Collect identity provider metadata, group names, certificate authority details and DNS ownership at the start. Test sign-in with a small pilot group before the broader rollout.
Runner placementRunners can be placed on the same cluster, on separate build nodes or on external capacity. Placement changes network access to registries, cache storage, privilege settings and the Runner version alignment work.Decide runner location and executor type early, keep Runner versions aligned with the GitLab version as the documentation advises, and plan runner isolation separately from the GitLab release process.
Customization of chart valuesEach custom value in the Helm chart or Operator custom resource must be documented, tested and re-applied at every upgrade. Heavy overrides make upgrades and troubleshooting slower and harder to hand over.Keep chart values minimal and version them in source control. Record why each override exists, and review the list before every upgrade stop.
Upgrade stops and release cadenceGitLab requires passage through upgrade stops, and Kubernetes deployments need chart and image versions to move together. Skipping planning for these steps leads to rushed upgrades on a live instance.Plan upgrade windows against the required upgrade stops listed in the upgrade paths documentation, and test each step in a non-production environment that matches the production layout.
Compliance evidenceAssessors often ask for configuration baselines, access reviews, backup restore results and patch records. Collecting this evidence after go-live takes extra effort and can reveal gaps in logging or ownership.Define the evidence list with your compliance lead before build, enable audit logging and backup restore testing during build, and store records in a location the assessor can access. DeployOpen prepares evidence for assessments but does not issue audit reports.
Team Kubernetes maturityA team new to Kubernetes needs time to operate ingress, persistent volumes, secrets and node upgrades alongside GitLab itself. Gaps in these skills increase the number of support questions and incidents during the first months.Assess the team's cluster skills before choosing the Kubernetes path. Where skills are thin, plan knowledge transfer and runbooks into the scope, or consider the Linux package if the team lacks cluster capacity.

Securing the cluster, secrets and external services for GitLab on Kubernetes

In a Cloud Native Hybrid layout, GitLab's stateless components run in Kubernetes while PostgreSQL, Redis, Gitaly and object storage sit outside the cluster. The controls below decide how credentials, network paths and runners are kept apart, so each one needs a deliberate decision before go-live.

Credentials for external services

Database, Redis and object storage credentials must reach the chart or Operator through Kubernetes Secrets, typically created from an external secrets manager or sealed secrets rather than entered in values files. Check that no password appears in the Helm values committed to version control, in CI job logs, or in rendered manifests kept in a repository. Confirm how rotation is performed without a full redeploy.

Namespace and network policy

Place GitLab in a dedicated namespace and use Kubernetes network policies to allow only the traffic the components need, such as web and Sidekiq pods reaching PostgreSQL, Redis and Gitaly on their service ports. Because stateful services run outside the cluster, the policies must also cover egress to those VMs or managed endpoints. Test the rules by confirming that unexpected pods are refused.

Service account scope

Each GitLab workload should run under its own service account with only the permissions its chart templates require. Review whether any component is granted cluster-wide rights, whether automatic token mounting is disabled where pods do not call the API, and who can read the secrets referenced by those accounts. Document the role bindings so an auditor can trace them.

Runner isolation on the same cluster

If GitLab Runner executes jobs on the same cluster, the Kubernetes executor's job pods can reach the same network and service accounts as the platform unless you separate them. Plan a dedicated namespace for runners, restrictive network policy, no access to GitLab's secrets, and a clear rule for which projects may use shared runners. Confirm the Runner version is aligned with GitLab, as the Runner documentation advises.

TLS for internal traffic

Traffic between the ingress, GitLab components and external PostgreSQL, Redis and Gitaly should be encrypted, not only the public edge. Decide where certificates are issued and renewed, which certificate authority the chart trusts, and how custom CA bundles are mounted into each component. Confirm that each external service enforces TLS and that certificate expiry is monitored.

Application hardening and NIST alignment

Cluster and secrets controls do not cover application settings, CI/CD configuration, gitlab.rb or the operating system. Work through the separate hardening topic for those. GitLab's hardening documentation includes guidance mapped to NIST SP 800-53, which GitLab describes as a work in progress to be rolled out gradually, so confirm the current state of each mapped control with GitLab before relying on it for an assessment.

How to verify GitLab on Kubernetes works and fails safely

Verification should prove three things before you call a GitLab on Kubernetes deployment ready: every workload is healthy, GitLab can reach each external dependency it relies on, and a developer can complete real work end to end. Start with pod health and readiness across the GitLab components the chart deploys, including Webservice, Sidekiq, Gitaly-facing workloads and the Toolbox. Check the Kubernetes events and container restart counts as well as the status fields, because a pod can report Running while it restarts in a loop. Confirm that the external PostgreSQL, Redis and Gitaly endpoints are reached from the GitLab pods using the same hostnames, ports, TLS settings and credentials your production values will use. The GitLab administration health checks and the Toolbox checks are a reasonable starting point, but confirm the exact commands and their output with the version you install, since they change between releases.

Next, test the paths your users will take. Push and clone a repository over HTTPS and over SSH, using a test user whose authentication matches your identity setup, and confirm that the SSH host key shown to clients matches the one you published. Create a merge request, then run a CI pipeline that executes on a runner registered to this instance. Use a project that exercises artifacts and the container registry if you have enabled them, because those paths use object storage and separate ingress rules that a simple clone never touches. Record which runner tags, executor and image the job used. A pipeline that passes on a runner you started by hand, outside the cluster, proves less than one that passes on the runner your teams will depend on.

Then test recovery. Restart one stateless pod, such as a Webservice or Sidekiq replica, and confirm that requests continue to succeed during and after the restart. Drain one worker node with kubectl drain in a non-production cluster and watch whether pods reschedule, whether PodDisruptionBudgets block the drain, and how long user-facing requests are interrupted. Do not expect this to exercise Gitaly, PostgreSQL or Redis, because those sit outside the cluster in this layout. Their recovery depends on the storage platform or managed service you chose, so verify that behavior with that platform's own tests.

The failure test matters most. In staging, remove one external dependency for a controlled period, for example by blocking network access from the GitLab pods to Redis or by stopping a Gitaly node, and record exactly how the instance reports it. Note what the web interface shows, which health endpoints change, what appears in the logs of each component, whether queued Sidekiq jobs accumulate, and whether a push or pipeline fails cleanly or hangs. Decide in advance what each signal means for your on-call team and which alert should fire. Restore the dependency and confirm the instance recovers without manual cleanup. Write the observed behavior down, because it becomes the baseline for your runbook.

A backup restore test is the only way to prove recoverability. Health checks and a successful pipeline show that the system works now, not that you can rebuild it after data loss. Restore a recent backup into a separate environment, confirm repositories, issues, users and artifacts match the source, and time the restore so you know whether it meets your recovery objectives. Remember that secrets and configuration files, such as the Rails secret and the keys GitLab uses to encrypt stored data, must be saved separately from the database and repository backups, or a restored instance cannot read its own data. The backup topic covers the tool, storage choices and restore procedure in detail. Schedule this test on a regular basis and treat a failed restore as a defect in your deployment.

Common questions about GitLab on Kubernetes cost and effort

What drives the cost of deploying GitLab on Kubernetes?

The cost is driven by scope, the size of the user base and how many stateful services you run outside the cluster. Main cost components: discovery and architecture design, the Helm chart or Operator configuration, external PostgreSQL, Redis and Gitaly storage, identity integration, backup and restore testing, runner setup and handover documentation. One-time work covers design, build and validation. Recurring costs cover cloud or data center infrastructure, licenses for the tier you choose, runner compute, backup storage and the admin time spent on upgrades. Ask any quote to separate fixed-scope build work from ongoing support, and to list which stateful services are in scope and which are your responsibility.

Can our own team deploy GitLab on Kubernetes without outside help?

Yes, a team with solid Kubernetes and database operations experience can do it alone, but the work is broader than the chart install. The chart or Operator gets pods running quickly; the harder parts are external PostgreSQL, Redis and Gitaly placement, object storage, TLS, backup and restore, and planning each upgrade stop. Questions to answer honestly: Who owns the stateful services outside the cluster? Who will test restores? Who reads release notes before each monthly update? If those owners are already staffed and trained, an internal build is realistic. If not, a fixed-scope partner engagement can cover design and handover while your team takes over operations.

How long does a GitLab on Kubernetes project take?

Duration depends on scope, not on the Kubernetes version alone. The main variables are the user count, which sets the reference architecture you need; whether identity, runners, backups and integrations are in the first release; and how many environments must be validated before production. Migration of repositories and CI from another platform adds time, and so does a required approval process for infrastructure changes. Ask for the timeline in the written scope, with each phase tied to a deliverable, and confirm which items are assumed to be provided by your team, such as cluster access, DNS and object storage.

What do we need to provide for the engagement to succeed?

The engagement needs a named technical owner, access to a target Kubernetes cluster and the cloud or data center accounts that host it, and a decision on where stateful services will run. You will also need to provide DNS and TLS certificates, identity provider details if you use SSO, a storage target for backups and a test window for restore exercises. Lead time on these items often sets the schedule more than the build itself. List them in the scope document so gaps are visible before work starts.

Which Kubernetes skills does the team need to run GitLab on it?

Your team needs working knowledge of Kubernetes workloads, namespaces, persistent volumes, ingress, secrets and Helm releases, plus the ability to read pod logs and events during an incident. Stateful services need separate skills. The GitLab reference architectures state that PostgreSQL and Redis inside Kubernetes are not supported, and the Cloud Native Hybrid layout runs them on VMs or managed services. Your team therefore also needs database and storage operations skills. Confirm with GitLab's current reference architecture documentation which components are supported on Kubernetes for your chosen size before assigning ownership.

When is the Linux package a better choice than Kubernetes?

The Linux package is often the better choice when your organization has no Kubernetes platform team, or when the instance is a single application with simple scaling needs. GitLab describes the Linux package as the most mature and scalable installation method, and it bundles PostgreSQL, Redis and Sidekiq. Choose Kubernetes when your platform team already runs and patches clusters, you want the GitLab components managed the same way as other services, and you can operate the external stateful services. Make the decision on operational capacity, not on preference for containers.

Should we pick the Helm chart or the GitLab Operator?

Pick the Helm chart if your team already manages releases with Helm and wants direct control over values files and templating. Pick the Operator if your platform team prefers declarative custom resources and reconciliation loops, and already runs Operators for other workloads. Both are supported installation methods listed by GitLab, so the choice is about your tooling and skills, not the product outcome. Whichever you choose, record the decision, the values or custom resources in version control and the process for changing them, because that becomes the basis for every upgrade.

What happens to our instance during a GitLab version upgrade?

GitLab ships a minor release monthly and patch releases twice a month, and it requires upgrades to pass through required upgrade stops. Since GitLab 17.5 these fall at versions x.2, x.5, x.8 and x.11, for example 18.2, 18.5, 18.8, 18.11, 19.2, 19.5, 19.8 and 19.11. Upgrading past a stop without stopping there is not supported, so plan a path from your current version to the next stop. Bug fixes go only to the current stable release, while security fixes also reach the previous two monthly releases. Test each step in a non-production environment, confirm the database migrations finish, and take a backup before each change.

What to monitor, back up, upgrade and document after go-live

Go-live is the start of the operating work, and for a Kubernetes deployment that work is split across two layers. The stateless GitLab services run as pods on the cluster, while PostgreSQL, Redis, Gitaly storage and object storage live outside it in the Cloud Native Hybrid layout. Monitoring has to cover both sides. Watch pod restarts and readiness for Webservice, Sidekiq, Gitaly-facing components and the registry, and watch node memory and disk pressure, because a node that starts evicting pods will look like an application fault. Then check the external services directly: PostgreSQL connections, replication lag and storage, Redis memory and latency, and the disk usage and I/O on the Gitaly volumes. Confirm with your platform team which of these metrics the GitLab charts expose and which need separate exporters.

Backups need to cover the external PostgreSQL database and the object storage buckets together, because GitLab's backup tool does not hold everything in one place. Take the database snapshot and the object storage copy at a consistent point, then record that pairing. Separately, store the GitLab secrets (the Kubernetes secrets that hold the Rails secret, database and Redis credentials, and the encryption keys for CI variables and two-factor data), your chart values files and the Operator custom resource definitions in version control or a protected vault. A restored database without the matching secrets cannot decrypt stored values. Restore tests should be scheduled and written down, and they should cover a full rebuild in an empty namespace, not just a file listing. The backup and restore topic describes the procedure.

Upgrades on this layout follow two rules. GitLab ships a minor release on the third Thursday of each month, and it requires upgrades to pass through required upgrade stops at x.2, x.5, x.8 and x.11, for example 19.2, 19.5, 19.8 and 19.11. Plan chart or Operator version changes against those stops, and check the matching chart version for each GitLab release before you move. Bug fixes are backported only to the current stable release, while security fixes also reach the two previous monthly releases, so staying close to a supported version matters for patches. Run each upgrade in a non-production copy first, and keep the upgrade path, rollback point and database snapshot in the change record. The upgrades topic covers the sequence in detail.

The runbook is the document that makes the rest workable. For each stateful service, record where it runs (managed or VM-hosted PostgreSQL, Redis, Gitaly nodes, object storage bucket and region), who owns it, who is on call, where its credentials and backups are kept, and how it is restored. Add the chart and Operator versions in use, the upgrade stop plan, the alert routes and the escalation contacts for your cloud or data center team. Review the runbook after each upgrade and each restore test. If the high availability design changes the number of Gitaly or database nodes, update the record the same day. Ask your implementation partner to deliver the runbook as part of the handover, and confirm who keeps it current after the engagement ends.

How DeployOpen scopes, builds and hands over GitLab on Kubernetes

DeployOpen plans, builds, documents and supports self-managed GitLab on Kubernetes inside your own cloud accounts, data centers or isolated networks. We start by confirming with you whether the Helm chart or the GitLab Operator fits your environment, and whether the Linux package is the better route instead.

How we scope

  • Engagements are fixed-scope, with scope, deliverables and timelines agreed in writing before work starts.
  • The written scope states which installation method, reference architecture and Cloud Native Hybrid layout apply to your user count and API load.
  • Scope confirms where PostgreSQL, Redis and Gitaly run outside Kubernetes, since GitLab does not support running those stateful components inside it.

How we build

  • Builds deploy stateless GitLab components on Kubernetes and connect them to externally hosted PostgreSQL, Redis and Gitaly services.
  • We configure ingress, storage classes, secrets handling and identity connections, then test sign-in, repository access, merge requests and CI/CD jobs.
  • Runner registration, backup jobs and restore tests are included in the build plan so the platform is verifiable before go-live.

How we hand over

  • Handover includes documentation of the deployed chart or Operator version, values files, network paths and external service dependencies.
  • Runbooks cover backup and restore steps, including the secrets and configuration files that must be saved separately from database dumps.
  • Your team receives the upgrade plan, including the required upgrade stops at versions x.2, x.5, x.8 and x.11, and the steps to check before each one.

How we support

  • Ongoing support, upgrades and continuous testing are available as retainers after handover.
  • Retainers can cover monthly minor releases, patch releases and the required upgrade stops, planned against the written scope.
  • Support scope, response expectations and what is excluded should be confirmed in writing as part of the retainer agreement.

Sources and further reading

Talk to our team.

Tell us what you're working on, whether it's a deployment, an audit, a security test or a cyber range. You'll speak with an engineer who can help you scope it.

  • 30-minute call: free, with no obligation.
  • NDA on request: we can sign before you share details.
  • Clear next steps: a scope and plan after the call.