Kubernetes 클러스터에서 GitLab CI/CD 사용
Offering: GitLab Self-Managed, GitLab Dedicated
GitLab CI/CD를 사용하여 Kubernetes 클러스터에 안전하게 연결, 배포 및 업데이트할 수 있습니다. 이를 위해 클러스터에 에이전트를 설치합니다. 클러스터에 대한 접근이 안전하도록 보장하기 위해: GitLab CI/CD를 사용하여 클러스터와 상호작용하려면 러너가 GitLab에 등록되어 있어야 합니다.
히스토리
- GitLab 17.0에서 에이전트 연결 공유 한도가 100에서 500으로 변경됨.
GitLab CI/CD를 사용하여 Kubernetes 클러스터에 안전하게 연결, 배포 및 업데이트할 수 있습니다.
이를 위해 클러스터에 에이전트를 설치합니다. 완료하면 Kubernetes 컨텍스트가 생성되고 GitLab CI/CD 파이프라인에서 Kubernetes API 명령을 실행할 수 있습니다.
클러스터에 대한 접근이 안전하도록 보장하기 위해:
- 각 에이전트는 별도의 컨텍스트(
kubecontext)를 가집니다. - 에이전트가 구성된 프로젝트와 권한을 부여한 추가 프로젝트만 클러스터에서 에이전트에 접근할 수 있습니다.
GitLab CI/CD를 사용하여 클러스터와 상호작용하려면 러너가 GitLab에 등록되어 있어야 합니다. 그러나 이 러너가 에이전트가 있는 클러스터에 있을 필요는 없습니다.
사전 요구 사항:
- GitLab CI/CD가 활성화되어 있는지 확인합니다.
GitLab CI/CD를 클러스터와 함께 사용#
GitLab CI/CD로 Kubernetes 클러스터를 업데이트하려면:
- 작동 중인 Kubernetes 클러스터가 있고 매니페스트가 GitLab 프로젝트에 있는지 확인합니다.
- 동일한 GitLab 프로젝트에서 Kubernetes용 GitLab 에이전트를 등록하고 설치합니다.
.gitlab-ci.yml파일을 업데이트하여 에이전트의 Kubernetes 컨텍스트를 선택하고 Kubernetes API 명령을 실행합니다.- 파이프라인을 실행하여 클러스터에 배포하거나 업데이트합니다.
Kubernetes 매니페스트가 포함된 여러 GitLab 프로젝트가 있는 경우:
- 자체 프로젝트 또는 Kubernetes 매니페스트를 보관하는 GitLab 프로젝트 중 하나에 Kubernetes용 GitLab 에이전트를 설치합니다.
- GitLab 프로젝트에서 에이전트 접근을 권한 부여합니다.
- 선택 사항. 보안 강화를 위해 가장(impersonation) 사용합니다.
.gitlab-ci.yml파일을 업데이트하여 에이전트의 Kubernetes 컨텍스트를 선택하고 Kubernetes API 명령을 실행합니다.- 파이프라인을 실행하여 클러스터에 배포하거나 업데이트합니다.
에이전트 접근 권한 부여#
Kubernetes 매니페스트가 있는 여러 프로젝트가 있는 경우 이러한 프로젝트가 에이전트에 접근할 수 있도록 권한을 부여해야 합니다. 개별 프로젝트, 그룹 또는 서브그룹에 대해 에이전트 접근 권한을 부여하면 모든 프로젝트가 접근할 수 있습니다. 보안 강화를 위해 가장(impersonation) 사용도 가능합니다.
권한 부여 구성이 전파되는 데 1~2분이 걸릴 수 있습니다.
에이전트에 접근하도록 프로젝트 권한 부여#
히스토리
Kubernetes 매니페스트를 보관하는 GitLab 프로젝트가 에이전트에 접근하도록 권한을 부여하려면:
-
상단 표시줄에서 검색 또는 이동을 선택하고 에이전트 구성 파일(
config.yaml)이 포함된 프로젝트를 찾습니다. -
config.yaml파일을 편집합니다.ci_access키워드 아래에projects속성을 추가합니다. -
id에 프로젝트 경로를 추가합니다.ci_access: projects: - id: path/to/project- 권한 부여된 프로젝트는 인스턴스 수준 권한 부여 애플리케이션 설정이 활성화되지 않은 한 에이전트 구성 프로젝트와 동일한 최상위 그룹 또는 사용자 네임스페이스를 가져야 합니다.
- 추가 계층을 수용하기 위해 동일한 클러스터에 추가 에이전트를 설치할 수 있습니다.
- 최대 500개의 프로젝트에 권한을 부여할 수 있습니다.
이러한 변경 후:
- 이제 모든 CI/CD 작업에는 공유된 모든 에이전트 연결에 대한 컨텍스트가 포함된
kubeconfig파일이 포함됩니다. kubeconfig경로는$KUBECONFIG환경 변수에서 사용할 수 있습니다.- CI/CD 스크립트에서
kubectl명령을 실행할 컨텍스트를 선택할 수 있습니다.
그룹의 프로젝트가 에이전트에 접근하도록 권한 부여#
그룹 또는 서브그룹의 모든 GitLab 프로젝트가 에이전트에 접근하도록 권한을 부여하려면:
-
상단 표시줄에서 검색 또는 이동을 선택하고 에이전트 구성 파일(
config.yaml)이 포함된 프로젝트를 찾습니다. -
config.yaml파일을 편집합니다.ci_access키워드 아래에groups속성을 추가합니다. -
id에 경로를 추가합니다:ci_access: groups: - id: path/to/group/subgroup- 권한 부여된 그룹은 인스턴스 수준 권한 부여 애플리케이션 설정이 활성화되지 않은 한 에이전트 구성 프로젝트와 동일한 최상위 그룹을 가져야 합니다.
- 추가 계층을 수용하기 위해 동일한 클러스터에 추가 에이전트를 설치할 수 있습니다.
- 권한 부여된 그룹의 모든 서브그룹도 개별적으로 지정하지 않고 동일한 에이전트에 접근할 수 있습니다.
- 최대 500개의 그룹에 권한을 부여할 수 있습니다.
이러한 변경 후:
- 이제 그룹과 서브그룹에 속한 모든 프로젝트가 에이전트에 접근하도록 권한이 부여됩니다.
- 이제 모든 CI/CD 작업에는 공유된 모든 에이전트 연결에 대한 컨텍스트가 포함된
kubeconfig파일이 포함됩니다. kubeconfig경로는$KUBECONFIG환경 변수에서 사용할 수 있습니다.- CI/CD 스크립트에서
kubectl명령을 실행할 컨텍스트를 선택할 수 있습니다.
GitLab 인스턴스의 모든 프로젝트가 에이전트에 접근하도록 권한 부여#
히스토리
- GitLab 17.11에서 도입됨.
사전 요구 사항:
- 관리자여야 합니다.
GitLab 인스턴스의 모든 프로젝트에 권한을 부여하도록 에이전트를 구성할 수 있게 하려면:
- 관리자 영역에서 설정 > 일반을 선택하고 Kubernetes용 GitLab 에이전트 섹션을 확장합니다.
- 인스턴스 수준 권한 부여 활성화를 선택합니다.
- 변경 사항 저장을 선택합니다.
- 애플리케이션 설정 업데이트
organization_cluster_agent_authorization_enabled를true로 설정합니다.
모든 GitLab 프로젝트에 접근하도록 에이전트에 권한을 부여하려면:
-
상단 표시줄에서 검색 또는 이동을 선택하고 에이전트 구성 파일(
config.yaml)이 포함된 프로젝트를 찾습니다. -
config.yaml파일을 편집합니다.ci_access키워드 아래에instance속성을 추가합니다:ci_access: instance: {}
에이전트 구성 파일에 이러한 변경을 한 후:
- 인스턴스의 모든 프로젝트의 모든 CI/CD 작업이 에이전트에 접근하도록 권한이 부여됩니다. 필요에 따라 접근을 허용하거나 제한하기 위해 RBAC와 함께 CI/CD 작업 가장을 사용할 수 있습니다. 자세한 내용은 가장을 사용하여 프로젝트 및 그룹 접근 제한을 참조하세요.
- 모든 CI/CD 작업에는 공유된 모든 에이전트 연결에 대한 컨텍스트가 포함된
kubeconfig파일이 포함됩니다. kubeconfig경로는$KUBECONFIG환경 변수에서 사용할 수 있습니다.- CI/CD 스크립트에서
kubectl명령을 실행할 컨텍스트를 선택할 수 있습니다.
.gitlab-ci.yml 파일을 업데이트하여 kubectl 명령 실행#
Kubernetes 명령을 실행하려는 프로젝트에서 프로젝트의 .gitlab-ci.yml 파일을 편집합니다.
script 키워드 아래의 첫 번째 명령에서 에이전트의 컨텍스트를 설정합니다.
<path/to/agent/project>:<agent-name> 형식을 사용합니다. 예시:
deploy:
image: debian:13-slim
variables:
KUBECTL_VERSION: v1.34
DEBIAN_FRONTEND: noninteractive
script:
# Follows https://kubernetes.io/docs/tasks/tools/install-kubectl-linux/#install-using-native-package-management
- apt-get update
- apt-get install -y --no-install-recommends apt-transport-https ca-certificates curl gnupg
- curl --fail --silent --show-error --location "https://pkgs.k8s.io/core:/stable:/${KUBECTL_VERSION}/deb/Release.key" | gpg --dearmor --output /etc/apt/keyrings/kubernetes-apt-keyring.gpg
- chmod 644 /etc/apt/keyrings/kubernetes-apt-keyring.gpg
- echo "deb [signed-by=/etc/apt/keyrings/kubernetes-apt-keyring.gpg] https://pkgs.k8s.io/core:/stable:/${KUBECTL_VERSION}/deb/ /" | tee /etc/apt/sources.list.d/kubernetes.list
- chmod 644 /etc/apt/sources.list.d/kubernetes.list
- apt-get update
- apt-get install -y --no-install-recommends kubectl
- kubectl config get-contexts
- kubectl config use-context path/to/agent/project:agent-name
- kubectl get pods
에이전트의 컨텍스트가 무엇인지 모르는 경우 에이전트에 접근하려는 CI/CD 작업에서 kubectl config get-contexts를 실행합니다.
Auto DevOps를 사용하는 환경#
Auto DevOps가 활성화된 경우 CI/CD 변수 KUBE_CONTEXT를 정의해야 합니다.
KUBE_CONTEXT의 값을 Auto DevOps가 사용할 에이전트의 컨텍스트로 설정합니다:
deploy:
variables:
KUBE_CONTEXT: path/to/agent/project:agent-name
서로 다른 Auto DevOps 작업에 서로 다른 에이전트를 할당할 수 있습니다. 예를 들어 Auto DevOps는 staging 작업에 하나의 에이전트를 사용하고 production 작업에 다른 에이전트를 사용할 수 있습니다.
여러 에이전트를 사용하려면 각 에이전트에 대해 환경 범위 CI/CD 변수를 정의합니다. 예시:
KUBE_CONTEXT라는 두 개의 변수를 정의합니다.- 첫 번째 변수의 경우:
environment를staging으로 설정합니다.- 값을 스테이징 에이전트의 컨텍스트로 설정합니다.
- 두 번째 변수의 경우:
environment를production으로 설정합니다.- 값을 프로덕션 에이전트의 컨텍스트로 설정합니다.
인증서 기반 연결과 에이전트 기반 연결이 모두 있는 환경#
인증서 기반 클러스터(더 이상 사용 중단됨)와 에이전트 연결이 모두 있는 환경에 배포하는 경우:
- 인증서 기반 클러스터의 컨텍스트를
gitlab-deploy라고 합니다. 이 컨텍스트는 항상 기본으로 선택됩니다. - 에이전트 컨텍스트는
$KUBECONFIG에 포함됩니다.kubectl config use-context <path/to/agent/project>:<agent-name>을 사용하여 선택할 수 있습니다.
인증서 기반 연결이 있을 때 에이전트 연결을 사용하려면 새 kubectl 구성 컨텍스트를 수동으로 구성할 수 있습니다. 예시:
deploy:
variables:
KUBE_CONTEXT: my-context # The name to use for the new context
AGENT_ID: 1234 # replace with your agent's numeric ID
K8S_PROXY_URL: https:///k8s-proxy/ # For agent server (KAS) deployed in Kubernetes cluster (for gitlab.com use kas.gitlab.com); replace with your URL
# K8S_PROXY_URL: https:///-/kubernetes-agent/k8s-proxy/ # For agent server (KAS) in Omnibus
# Include any additional variables
before_script:
- kubectl config set-credentials agent:$AGENT_ID --token="ci:${AGENT_ID}:${CI_JOB_TOKEN}"
- kubectl config set-cluster gitlab --server="${K8S_PROXY_URL}"
- kubectl config set-context "$KUBE_CONTEXT" --cluster=gitlab --user="agent:${AGENT_ID}"
- kubectl config use-context "$KUBE_CONTEXT"
# Include the remaining job configuration
자체 서명 인증서를 사용하는 KAS 환경#
자체 서명 인증서와 함께 KAS를 사용하는 환경을 사용하는 경우 인증서에 서명한 인증 기관(CA)을 신뢰하도록 Kubernetes 클라이언트를 구성해야 합니다.
클라이언트를 구성하려면 다음 중 하나를 수행합니다:
- PEM 형식의 KAS 인증서와 함께 CI/CD 변수
SSL_CERT_FILE을 설정합니다. --certificate-authority=$KAS_CERTIFICATE로 Kubernetes 클라이언트를 구성합니다. 여기서KAS_CERTIFICATE는 KAS의 CA 인증서가 있는 CI/CD 변수입니다.- 컨테이너 이미지를 업데이트하거나 러너를 통해 마운트하여 작업 컨테이너의 적절한 위치에 인증서를 배치합니다.
- 권장하지 않음.
--insecure-skip-tls-verify=true로 Kubernetes 클라이언트를 구성합니다.
가장을 사용하여 프로젝트 및 그룹 접근 제한#
히스토리
- GitLab 15.5에서 환경 티어에 대한 가장 지원을 추가하도록 변경됨.
기본적으로 CI/CD 작업은 클러스터에 에이전트를 설치하는 데 사용된 서비스 계정에서 모든 권한을 상속합니다. 클러스터에 대한 접근을 제한하려면 가장(impersonation)을 사용할 수 있습니다.
가장을 지정하려면 에이전트 구성 파일에서 access_as 속성을 사용하고 Kubernetes RBAC 규칙을 사용하여 가장된 계정 권한을 관리합니다.
다음을 가장할 수 있습니다:
- 에이전트 자체 (기본값).
- 클러스터에 접근하는 CI/CD 작업.
- 클러스터 내에 정의된 특정 사용자 또는 시스템 계정.
권한 부여 구성이 전파되는 데 1~2분이 걸릴 수 있습니다.
에이전트 가장#
에이전트는 기본적으로 가장됩니다. 에이전트를 가장하기 위해 특별히 할 일은 없습니다.
클러스터에 접근하는 CI/CD 작업 가장#
클러스터에 접근하는 CI/CD 작업을 가장하려면 access_as 키 아래에 ci_job: {} 키-값을 추가합니다.
에이전트가 실제 Kubernetes API에 요청할 때 다음과 같은 방식으로 가장 자격 증명을 설정합니다:
-
UserName은gitlab:ci_job:<job id>로 설정됩니다. 예:gitlab:ci_job:1074499489. -
Groups는 다음으로 설정됩니다:-
CI 작업에서 오는 모든 요청을 식별하기 위한
gitlab:ci_job. -
프로젝트가 속한 그룹 ID 목록.
-
프로젝트 ID.
-
이 작업이 속한 환경의 슬러그와 티어.
예: 다음 조건에서
group1/group1-1/project1의 CI 작업의 경우:- 그룹
group1의 ID는 23. - 그룹
group1/group1-1의 ID는 25. - 프로젝트
group1/group1-1/project1의 ID는 150. production환경 티어를 가진prod환경에서 실행 중인 작업.
- 그룹
그룹 목록은
[gitlab:ci_job, gitlab:group:23, gitlab:group_env_tier:23:production, gitlab:group:25, gitlab:group_env_tier:25:production, gitlab:project:150, gitlab:project_env:150:prod, gitlab:project_env_tier:150:production]입니다. -
-
Extra는 요청에 대한 추가 정보를 전달합니다. 가장된 ID에 대해 다음 속성이 설정됩니다:
| 속성 | 설명 |
|---|---|
agent.gitlab.com/id |
에이전트 ID를 포함합니다. |
agent.gitlab.com/config_project_id |
에이전트의 구성 프로젝트 ID를 포함합니다. |
agent.gitlab.com/project_id |
CI 프로젝트 ID를 포함합니다. |
agent.gitlab.com/ci_pipeline_id |
CI 파이프라인 ID를 포함합니다. |
agent.gitlab.com/ci_job_id |
CI 작업 ID를 포함합니다. |
agent.gitlab.com/username |
CI 작업이 실행 중인 사용자의 사용자 이름을 포함합니다. |
agent.gitlab.com/environment_slug |
환경의 슬러그를 포함합니다. 환경에서 실행 중인 경우에만 설정됩니다. |
agent.gitlab.com/environment_tier |
환경의 티어를 포함합니다. 환경에서 실행 중인 경우에만 설정됩니다. |
CI/CD 작업의 ID로 접근을 제한하기 위한 예시 config.yaml:
ci_access:
projects:
- id: path/to/project
access_as:
ci_job: {}
CI/CD 작업을 제한하는 예시 RBAC#
다음 RoleBinding 리소스는 모든 CI/CD 작업을 읽기 전용 권한으로 제한합니다.
apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRoleBinding
metadata:
name: ci-job-view
roleRef:
name: view
kind: ClusterRole
apiGroup: rbac.authorization.k8s.io
subjects:
- name: gitlab:ci_job
kind: Group
정적 ID 가장#
주어진 연결에 대해 가장에 정적 ID를 사용할 수 있습니다.
access_as 키 아래에 impersonate 키를 추가하여 제공된 ID를 사용하여 요청합니다.
ID는 다음 키로 지정할 수 있습니다:
username(필수)uidgroupsextra
자세한 내용은 공식 Kubernetes 문서를 참조하세요.
특정 환경으로 프로젝트 및 그룹 접근 제한#
히스토리
- GitLab 15.7에서 도입됨.
기본적으로 에이전트가 프로젝트에서 사용 가능한 경우 프로젝트의 모든 CI/CD 작업이 해당 에이전트를 사용할 수 있습니다.
특정 환경의 작업으로만 에이전트에 대한 접근을 제한하려면 ci_access.projects 또는 ci_access.groups에 environments를 추가합니다. 예시:
ci_access:
projects:
- id: path/to/project-1
- id: path/to/project-2
environments:
- staging
- review/*
groups:
- id: path/to/group-1
environments:
- production
이 예시에서:
project-1의 모든 CI/CD 작업이 에이전트에 접근할 수 있습니다.staging또는review/*환경을 가진project-2의 CI/CD 작업이 에이전트에 접근할 수 있습니다.*는 와일드카드이므로review/*는review아래의 모든 환경과 일치합니다.
production환경을 가진group-1의 프로젝트에 대한 CI/CD 작업이 에이전트에 접근할 수 있습니다.
보호된 브랜치로 에이전트 접근 제한#
히스토리
- GitLab 17.3에서
kubernetes_agent_protected_branches라는 플래그와 함께 도입됨. 기본적으로 비활성화됨. - GitLab 17.10에서 일반적으로 사용 가능. 기능 플래그
kubernetes_agent_protected_branches제거됨.
이 기능의 가용성은 기능 플래그에 의해 제어됩니다. 자세한 내용은 히스토리를 참조하세요. 이 기능은 테스트를 위해 사용할 수 있지만 프로덕션 사용을 위한 준비가 되지 않았습니다.
보호된 브랜치에서 실행되는 작업만 에이전트에 접근을 제한하려면:
-
ci_access.projects또는ci_access.groups에protected_branches_only: true를 추가합니다. 예시:ci_access: projects: - id: path/to/project-1 protected_branches_only: true groups: - id: path/to/group-1 protected_branches_only: true environments: - production
기본적으로 protected_branches_only는 false로 설정되어 있으며 에이전트는 보호되지 않은 브랜치와 보호된 브랜치 모두에서 접근할 수 있습니다.
추가 보안을 위해 이 기능을 환경 제한과 결합할 수 있습니다.
프로젝트에 여러 구성이 있는 경우 가장 구체적인 구성만 사용됩니다.
예를 들어 다음 구성은 example 그룹이 보호된 브랜치에만 접근을 허용하도록 구성되어 있더라도 example/my-project의 보호되지 않은 브랜치에 접근을 허용합니다:
# .gitlab/agents/my-agent/config.yaml
ci_access:
project:
- id: example/my-project # Project of the group below
protected_branches_only: false # This configuration supersedes the group configuration
environments:
- dev
groups:
- id: example
protected_branches_only: true
environments:
- dev
자세한 내용은 CI/CD에서 Kubernetes 접근을 참조하세요.
관련 항목#
- 자기 주도 클래스룸 워크샵 (AWS EKS 사용, 다른 Kubernetes 클러스터에도 사용 가능)
- Auto DevOps 구성
트러블슈팅#
~/.kube/cache에 쓰기 권한 부여#
kubectl, Helm, kpt, kustomize 같은 도구는 ~/.kube/cache에 클러스터에 대한 정보를 캐시합니다. 이 디렉토리가 쓰기 가능하지 않으면 도구는 각 호출 시마다 정보를 가져오므로 상호작용이 느려지고 클러스터에 불필요한 부하가 생성됩니다. 최상의 경험을 위해 .gitlab-ci.yml 파일에서 사용하는 이미지에서 이 디렉토리가 쓰기 가능한지 확인하세요.
TLS 활성화#
GitLab Self-Managed를 사용하는 경우 인스턴스가 TLS(전송 레이어 보안)로 구성되어 있는지 확인합니다.
TLS 없이 kubectl을 사용하려고 하면 다음과 같은 오류가 발생할 수 있습니다:
$ kubectl get pods
error: You must be logged in to the server (the server has asked for the client to provide credentials)
서버에 연결할 수 없음: 알 수 없는 기관이 서명한 인증서#
자체 서명 인증서와 함께 KAS를 사용하는 환경을 사용하는 경우 kubectl 호출 시 이 오류가 반환될 수 있습니다:
kubectl get pods
Unable to connect to the server: x509: certificate signed by unknown authority
작업이 KAS 인증서에 서명한 인증 기관(CA)을 신뢰하지 않기 때문에 오류가 발생합니다.
문제를 해결하려면 CA를 신뢰하도록 kubectl 구성을 참조하세요.
유효성 검사 오류#
kubectl 버전 v1.27.0 또는 v1.27.1을 사용하는 경우 다음 오류가 발생할 수 있습니다:
error: error validating "file.yml": error validating data: the server responded with the status code 426 but did not return more information; if you choose to ignore these errors, turn validation off with --validate=false
이 문제는 공유 Kubernetes 라이브러리를 사용하는 kubectl 및 기타 도구의 버그로 인해 발생합니다.
문제를 해결하려면 다른 버전의 kubectl을 사용하세요.
