---
title: "CI/CD : runner GitLab dans votre namespace"
description: "Déployer un runner GitLab dans votre namespace Kontainers : le gestionnaire s'authentifie via le ServiceAccount pré-provisionné, les jobs restent sans privilège."
source_url:
  html: https://docs.blackswift.cloud/exemples/gitlab-runner/
  md: https://docs.blackswift.cloud/exemples/gitlab-runner.md
---

# CI/CD : runner GitLab dans votre namespace

> Déployer un runner GitLab dans votre namespace Kontainers : le gestionnaire s'authentifie via le ServiceAccount pré-provisionné, les jobs restent sans privilège.

Héberger votre runner GitLab **dans votre namespace** a deux vertus : vos jobs
tournent au plus près de vos applications, et le **gestionnaire du runner**
s'authentifie via le ServiceAccount `bs-namespace-member` pré-provisionné —
aucun credential à créer pour faire tourner l'infrastructure de CI elle-même.

## Le principe : des privilèges au bon endroit

Un runner GitLab sur Kubernetes, ce sont deux étages :

| Étage | Rôle | ServiceAccount |
| --- | --- | --- |
| Le **gestionnaire** (pod permanent) | Crée et supervise un pod par job CI | `bs-namespace-member` — il a besoin de l'API |
| Les **pods de jobs** (éphémères) | Exécutent vos scripts (build, tests…) | `default` — **aucun droit API** |

C'est le moindre privilège : un job de build compromis (dépendance malveillante,
script tiers…) ne peut rien faire sur le cluster. Vos jobs de **déploiement**,
qui ont légitimement besoin de l'API, s'authentifient explicitement — voir plus
bas.

## Déployer le runner

Avec le [chart Helm officiel](https://docs.gitlab.com/runner/install/kubernetes/)
([Helm sur Kontainers](https://docs.blackswift.cloud/deployer/deployer-avec-helm.md)) :

```yaml
# values-runner.yaml
gitlabUrl: https://gitlab.com/        # ou votre instance (Froggit…)

rbac:
  create: false                        # on n'a pas les droits de créer des rôles…
serviceAccount:
  create: false
  name: bs-namespace-member            # …et pas besoin : celui-ci est fourni
                                       # (gestionnaire uniquement — les pods de
                                       # jobs restent sur le SA default)

concurrent: 2

runners:
  config: |
    [[runners]]
      [runners.kubernetes]
        namespace = "{{ .Release.Namespace }}"
        cpu_request = "100m"
        memory_request = "256Mi"
        memory_limit = "256Mi"
        ephemeral_storage_request = "1Gi"
        ephemeral_storage_limit = "2Gi"

resources:
  requests: {cpu: 100m, memory: 128Mi}
  limits: {memory: 128Mi}
```

```bash
# Le token vient de GitLab : Settings › CI/CD › Runners › New project runner
kubectl create secret generic gitlab-runner-secret -n <namespace> \
  --from-literal=runner-token='glrt-…' --from-literal=runner-registration-token=''

helm repo add gitlab https://charts.gitlab.io
helm upgrade --install runner gitlab/gitlab-runner \
  -n <namespace> -f values-runner.yaml \
  --set runners.secret=gitlab-runner-secret
```

Le runner apparaît dans GitLab, et chaque job CI devient un pod dans votre
namespace — soumis aux mêmes [quotas](https://docs.blackswift.cloud/reference/quotas-et-limites.md) que le
reste (comptez-les dans votre budget de 20 pods).

## Un `.gitlab-ci.yml` qui déploie

Les pods de jobs n'ayant aucun droit API, le job de déploiement s'authentifie
avec un **[kubeconfig permanent](https://docs.blackswift.cloud/operer/ci-cd-avec-le-serviceaccount.md)**
stocké en variable CI (type *File*, masquée et protégée) :

```yaml
deploy:
  stage: deploy
  image: bitnami/kubectl:latest
  script:
    - export KUBECONFIG=$KUBE_CONFIG_FILE
    - kubectl set image deploy/boutique app=$CI_REGISTRY_IMAGE:$CI_COMMIT_SHORT_SHA
    - kubectl rollout status deploy/boutique --timeout=120s
  environment: production
  rules:
    - if: $CI_COMMIT_TAG
```

Seul ce job reçoit la variable : les jobs de build et de test du même pipeline
restent sans accès au cluster.

## Les contraintes à connaître

- **Pas de Docker-in-Docker privilégié** : la
  [politique de sécurité](https://docs.blackswift.cloud/reference/mutations-et-politiques.md#politiques-de-rejet)
  interdit les pods privilégiés. Pour construire des images dans la CI, utilisez
  [kaniko](https://github.com/GoogleContainerTools/kaniko), qui build sans
  privilèges :

  ```yaml
  build:
    stage: build
    image:
      name: gcr.io/kaniko-project/executor:debug
      entrypoint: [""]
    script:
      - /kaniko/executor --context $CI_PROJECT_DIR
        --destination $CI_REGISTRY_IMAGE:$CI_COMMIT_SHORT_SHA
  ```

- **Stockage éphémère limité à 2 Gi par conteneur** : les gros builds (caches
  npm/gradle…) peuvent le dépasser — montez un
  [PVC de cache](https://docs.blackswift.cloud/deployer/stockage-persistant.md) via
  `[runners.kubernetes.volumes.pvc]` si besoin ;
- **Runner d'équipe multi-environnements** : hébergez-le dans un namespace
  `tooling` — [le réseau intra-organisation](https://docs.blackswift.cloud/comprendre/isolation-reseau.md)
  permet à ses jobs de joindre dev et prod. Côté déploiement, créez un
  [kubeconfig permanent](https://docs.blackswift.cloud/operer/ci-cd-avec-le-serviceaccount.md) **par namespace
  cible** : une variable CI par environnement, des périmètres étanches.
