Over the last years GitLab became one of the most popular and powerful open source git source code platform. From pure source code repository to a DevOps platform, it’s interesting to see how GitLab has evolved and this is reflected in the technological choices made by the technical teams. GitLab can be deployed on Cloud or On-premise environments in multiple ways; automatically (packages) manually (compile all sources)…. https://about.gitlab.com/install/

This blog post aims to explain how to deploy GitLab in Kubernetes but also serves as a customer feedback where we are using GitLab deployed on Kubernetes in production.


  • a Kubernetes cluster up and running
  • an ingress controller configured for external access

In our example, we will use Google Kubernetes Engine (GKE) and Nginx as ingress controller. 

Helm installation

If you already have Helm client and Tiller installed on your cluster, you can skip to the next section.
You can install Helm using the following commands:

➜ curl -o get_helm.sh https://raw.githubusercontent.com/kubernetes/helm/master/scripts/get
chmod 700 get_helm.sh

➜ ./get_helm.sh
helm installed into /usr/local/bin/helm
tiller installed into /usr/local/bin/tiller
Run 'helm init' to configure helm.

All installation methods and the documentation can be found here: https://helm.sh/docs/intro/install/

Installing Tiller

➜ helm init
Creating /Users/meb/.helm
Creating /Users/meb/.helm/repository
Creating /Users/meb/.helm/repository/cache
Creating /Users/meb/.helm/repository/local
Creating /Users/meb/.helm/plugins
Creating /Users/meb/.helm/starters
Creating /Users/meb/.helm/cache/archive
Creating /Users/meb/.helm/repository/repositories.yaml
Adding stable repo with URL: https://kubernetes-charts.storage.googleapis.com
Adding local repo with URL:
$HELM_HOME has been configured at /Users/meb/.helm.

Tiller (the Helm server-side component) has been installed into your Kubernetes Cluster.


Deploy GitLab with Helm

Storage Class

Let’s first create a storage class in our cluster, GitLab will be able to store data.

cat > pd-ssd-storage.yaml <<EOF
apiVersion: storage.k8s.io/v1
kind: StorageClass
  name: pd-ssd
provisioner: kubernetes.io/gce-pd
  type: pd-ssd
kubectl apply -f pd-ssd-storage.yaml

Once done we can install GitLab chart using Helm.

Install the GitLab chart

The GitLab chart requires custom configuration so that it can leverage the external data stores that you previously provisioned.

Download the configuration file template:

wget https://raw.githubusercontent.com/terraform-google-modules/terraform-google-gke-gitlab/master/values.yaml.tpl

After customisation, the final values.yaml file should contains the following:

# Values for gitlab/gitlab chart on GKE
  edition: ce
    domain: xip.io
    https: true
    gitlab: {}
    externalIP: #Replace by your Nginx Ingress ExternalIP
    ssh: ~
      name: gitlab.xip.io 
      https: true
      name: gitlab-registry.xip.io
      https: true
      name: gitlab-minio.xip.io
      https: true
    enabled: true
  ## doc/charts/globals.md#configure-ingress-settings
    configureCertmanager: false
    class: "nginx"
    enabled: true
      enabled: true
  install: false
  enabled: false
  install: true
  install: true
  install: true
  install: true
  enable: true

Install the chart by using the following Helm commands:

helm repo add gitlab https://charts.gitlab.io/
helm install -f values.yaml --version 2.3.7 -n gitlab gitlab/gitlab

Verify your deployment

Pod status:

kubectl get pods -n gitlab -o wide
NAME                                        READY   STATUS      RESTARTS   AGE   IP          NODE                                    NOMINATED NODE   READINESS GATES
gitlab-gitaly-0                             1/1     Running     0          1d   gke-jx-dbi-default-pool-01891a7e-2g7j              
gitlab-gitlab-exporter-7cf6b77d78-89f46     1/1     Running     0          1d   gke-jx-dbi-default-pool-01891a7e-1rb5              
gitlab-gitlab-shell-c548bd566-g6p7b         1/1     Running     0          1d   gke-jx-dbi-default-pool-01891a7e-2g7j              
gitlab-gitlab-shell-c548bd566-plg4t         1/1     Running     0          1d   gke-jx-dbi-default-pool-01891a7e-1rb5              
gitlab-migrations.1-tf5jl                   0/1     Completed   0          1d   gke-jx-dbi-default-pool-01891a7e-2g7j              
gitlab-minio-75567fcbb6-j9z9z               1/1     Running     0          1d   gke-jx-dbi-default-pool-01891a7e-2g7j              
gitlab-minio-create-buckets.1-2c8th         0/1     Completed   0          1d   gke-jx-dbi-default-pool-01891a7e-2g7j              
gitlab-postgresql-66d8d9574b-r66fm          2/2     Running     0          1d   gke-jx-dbi-default-pool-01891a7e-1rb5              
gitlab-prometheus-server-6fb685b9c7-q4jl5   2/2     Running     0          1d   gke-jx-dbi-default-pool-01891a7e-2g7j              
gitlab-redis-7668c4d476-nqddk               2/2     Running     0          1d   gke-jx-dbi-default-pool-01891a7e-2g7j              
gitlab-registry-5675459cbd-gjnx6            1/1     Running     0          1d   gke-jx-dbi-default-pool-01891a7e-2g7j              
gitlab-registry-5675459cbd-rpcn2            1/1     Running     0          1d   gke-jx-dbi-default-pool-01891a7e-1rb5              
gitlab-sidekiq-all-in-1-5fdc8f5868-8fnxl    1/1     Running     1          1d    gke-jx-dbi-default-pool-01891a7e-2g7j              
gitlab-task-runner-5cb689799-pzz5r          1/1     Running     0          1d   gke-jx-dbi-default-pool-01891a7e-2g7j              
gitlab-unicorn-9f9bf8574-cjqdh              2/2     Running     0          1d    gke-jx-dbi-default-pool-01891a7e-1rb5              
gitlab-unicorn-9f9bf8574-mfqrn              2/2     Running     0          1d   gke-jx-dbi-default-pool-01891a7e-715p              


kubectl get svc -n gitlab
NAME                       TYPE        CLUSTER-IP     EXTERNAL-IP   PORT(S)             AGE
gitlab-gitaly              ClusterIP   None                   8075/TCP,9236/TCP   1d
gitlab-gitlab-exporter     ClusterIP           9168/TCP            1d
gitlab-gitlab-shell        ClusterIP           22/TCP              1d
gitlab-minio-svc           ClusterIP            9000/TCP            1d
gitlab-postgresql          ClusterIP           5432/TCP            1d
gitlab-prometheus-server   ClusterIP           80/TCP              1d
gitlab-redis               ClusterIP           6379/TCP,9121/TCP   1d
gitlab-registry            ClusterIP           5000/TCP            1d
gitlab-unicorn             ClusterIP           8080/TCP,8181/TCP   1d

Ingress resources:

kubectl get ing -n gitlab
NAME              HOSTS                          ADDRESS          PORTS     AGE
gitlab-minio      gitlab-minio.xip.io     80, 443   1d
gitlab-registry   gitlab-registry.xip.io   80, 443   1d
gitlab-unicorn    gitlab.   80, 443   1d

Connect to GitLab Web UI

Once your GitLab instance is up and running, log int to it as follows:

1. Get the URL for your GitLab server:

export GITLAB_HOSTNAME=$(kuexport GITLAB_HOSTNAME=$(kubectl get ingresses.extensions gitlab-unicorn \
    -o jsonpath='{.spec.rules[0].host}')
echo "Your GitLab URL is: https://${GITLAB_HOSTNAME}"

Your GitLab URL is: https://gitlab.

2. Get the root password:

kubectl get secret gitlab-gkubectl get secret gitlab-gitlab-initial-root-password \
    -o go-template='{{.data.password}}' | base64 -d && echo

Visit the GitLab URL in your browser from step 1 and log in as the root user with the password from step 2. Below the screenshot from the login page.

Thumbnail [60x60]