在 Kubernetes 集群中部署 Jenkins

Deploy Jenkins in Kubernetes cluster

我是 Kubernetes 的新手,正在尝试在集群中部署 Jenkins,但 pod 正在挂起。

我需要 jenkins 访问 kubernetes,包括访问 docker 和 kubectl 命令,以便与我的微服务持续集成。

有了这个示例 yaml 文件,我可以通过 Minikube 在本地机器(我的笔记本)上启动一个 jenkins 实例。

但现在我正在尝试使用云集群作为我研究领域的一部分。

我接受改进建议。

正如我所说:我只是想上传一个jenkins实例,通过它我可以不断地集成我的微服务。

这些是我的配置和日志。

我的错误是什么?

apiVersion: rbac.authorization.k8s.io/v1beta1
kind: ClusterRoleBinding
metadata:
  name: jenkins-rbac
subjects:
  - kind: ServiceAccount
    name: default
    namespace: default
roleRef:
  kind: ClusterRole
  name: cluster-admin
  apiGroup: rbac.authorization.k8s.io
---
kind: PersistentVolume
apiVersion: v1
metadata:
  name: jenkins
  labels:
    type: local
spec:
  capacity:
    storage: 2Gi
  accessModes:
    - ReadWriteOnce
  hostPath:
    path: "/data/jenkins/"
---
kind: PersistentVolumeClaim
apiVersion: v1
metadata:
  name: jenkins-claim
spec:
  accessModes:
    - ReadWriteMany
  resources:
    requests:
      storage: 2Gi
---
apiVersion: v1
kind: Service
metadata:
  name: jenkins
  labels:
    app: jenkins
spec:
  ports:
    - port: 80
      targetPort: 8080
      nodePort: 32256
  selector:
    app: jenkins
    tier: jenkins
  type: NodePort
---
apiVersion: extensions/v1beta1
kind: Deployment
metadata:
  name: jenkins
  labels:
    app: jenkins
spec:
  strategy:
    type: Recreate
  template:
    metadata:
      labels:
        app: jenkins
        tier: jenkins
    spec:
      containers:
      - image: sammubr/jenkins
        name: jenkins
        securityContext:
          privileged: true
        ports:
        - containerPort: 8080
          name: jenkins
        volumeMounts:
        - name: jenkins-persistent-storage
          mountPath: /var/jenkins_home
        - name: docker
          mountPath: /var/run/docker.sock
      volumes:
      - name: docker
        hostPath:
          path: /var/run/docker.sock
      - name: jenkins-persistent-storage
        persistentVolumeClaim:
          claimName: jenkins-claim

然后kubectl --context do-sfo2-teste-cluster apply -f jenkins.yaml

但始终处于待定状态:

samuel@samuel-Inspiron-5548:~/Documentos/teste/jenkins$ kubectl get all
NAME                           READY   STATUS    RESTARTS   AGE
pod/jenkins-5dc7fbd78d-9wxfl   0/1     Pending   0          8m34s

NAME                 TYPE        CLUSTER-IP     EXTERNAL-IP   PORT(S)        AGE
service/jenkins      NodePort    10.245.30.47   <none>        80:32256/TCP   8m34s
service/kubernetes   ClusterIP   10.245.0.1     <none>        443/TCP        79m

NAME                      READY   UP-TO-DATE   AVAILABLE   AGE
deployment.apps/jenkins   0/1     1            0           8m35s

NAME                                 DESIRED   CURRENT   READY   AGE
replicaset.apps/jenkins-5dc7fbd78d   1         1         0       8m35s
samuel@samuel-Inspiron-5548:~/Documentos/teste/jenkins$ kubectl describe pod/jenkins-5dc7fbd78d-9wxfl
Name:               jenkins-5dc7fbd78d-9wxfl
Namespace:          default
Priority:           0
PriorityClassName:  <none>
Node:               <none>
Labels:             app=jenkins
                    pod-template-hash=5dc7fbd78d
                    tier=jenkins
Annotations:        <none>
Status:             Pending
IP:                 
Controlled By:      ReplicaSet/jenkins-5dc7fbd78d
Containers:
  jenkins:
    Image:        sammubr/jenkins
    Port:         8080/TCP
    Host Port:    0/TCP
    Environment:  <none>
    Mounts:
      /var/jenkins_home from jenkins-persistent-storage (rw)
      /var/run/docker.sock from docker (rw)
      /var/run/secrets/kubernetes.io/serviceaccount from default-token-5wdgs (ro)
Conditions:
  Type           Status
  PodScheduled   False 
Volumes:
  docker:
    Type:          HostPath (bare host directory volume)
    Path:          /var/run/docker.sock
    HostPathType:  
  jenkins-persistent-storage:
    Type:       PersistentVolumeClaim (a reference to a PersistentVolumeClaim in the same namespace)
    ClaimName:  jenkins-claim
    ReadOnly:   false
  default-token-5wdgs:
    Type:        Secret (a volume populated by a Secret)
    SecretName:  default-token-5wdgs
    Optional:    false
QoS Class:       BestEffort
Node-Selectors:  <none>
Tolerations:     node.kubernetes.io/not-ready:NoExecute for 300s
                 node.kubernetes.io/unreachable:NoExecute for 300s
Events:
  Type     Reason            Age               From               Message
  ----     ------            ----              ----               -------
  Warning  FailedScheduling  7s (x8 over 10m)  default-scheduler  pod has unbound immediate PersistentVolumeClaims (repeated 2 times)

删除 PersistentVolume 定义文件中的引号 排队:

 hostPath:
    path: "/data/jenkins/"

正确的文件应该如下所示:

apiVersion: rbac.authorization.k8s.io/v1beta1
kind: ClusterRoleBinding
metadata:
  name: jenkins-rbac
subjects:
  - kind: ServiceAccount
    name: default
    namespace: default
roleRef:
  kind: ClusterRole
  name: cluster-admin
  apiGroup: rbac.authorization.k8s.io
---
kind: PersistentVolume
apiVersion: v1
metadata:
  name: jenkins
  labels:
    type: local
spec:
  capacity:
    storage: 2Gi
  accessModes:
    - ReadWriteOnce
  hostPath:
    path: /data/jenkins/
---
kind: PersistentVolumeClaim
apiVersion: v1
metadata:
  name: jenkins-claim
spec:
  accessModes:
    - ReadWriteMany
  resources:
    requests:
      storage: 2Gi
---
apiVersion: v1
kind: Service
metadata:
  name: jenkins
  labels:
    app: jenkins
spec:
  ports:
    - port: 80
      targetPort: 8080
      nodePort: 32256
  selector:
    app: jenkins
    tier: jenkins
  type: NodePort
---
apiVersion: extensions/v1beta1
kind: Deployment
metadata:
  name: jenkins
  labels:
    app: jenkins
spec:
  strategy:
    type: Recreate
  template:
    metadata:
      labels:
        app: jenkins
        tier: jenkins
    spec:
      containers:
      - image: sammubr/jenkins
        name: jenkins
        securityContext:
          privileged: true
        ports:
        - containerPort: 8080
          name: jenkins
        volumeMounts:
        - name: jenkins-persistent-storage
          mountPath: /var/jenkins_home
        - name: docker
          mountPath: /var/run/docker.sock
      volumes:
      - name: docker
        hostPath:
          path: /var/run/docker.sock
      - name: jenkins-persistent-storage
        persistentVolumeClaim:
          claimName: jenkins-claim

应用更改;

 $ kubectl apply -f your-config-file.yaml

有关 PersistentVolumesPersistentVolumeClaims 的更多信息,您可以在此处找到:persistent-volume.

正如@ortomala-lokni 之前提到的,您遇到了未绑定的 PersistentVolumeClaims 到声明的 PersitanceVolume 之前的问题,这最终导致 Jenkins Pod 无法启动。

在@ortomala-lokni 分享的 中对 SO 上的类似问题,可以阅读有关此错误的各种原因以及如何修复它们的信息。

在您的特定情况下,PVC 的需求与集群上实际配置的 PV 之间的不匹配是在 accessModes 中(ReadWriteOnce 与 ReadWriteMany)。

要解决您的问题,请相应地更新 'PersistentVolumeClaim' 定义,应该如下所示:

kind: PersistentVolumeClaim
apiVersion: v1
metadata:
  name: jenkins-claim
spec:
  accessModes:
    - ReadWriteOnce
  resources:
    requests:
      storage: 2Gi

注:
对于 Jenkins Pod 的单个副本,您不需要“ReadWriteMany”访问模式。这是因为根据您的 'jenkins' Deployment 的当前定义,Deployment 控制器在幕后创建了一个 ReplicaSet 对象,默认情况下确保只有 Jenkins Pod 的单个实例是 运行(= 仅简化单个实例Jenkins 服务器将立即写入此卷)。

请查找 here 另一个关于使用 helm 从头开始​​在 Kubernetes 上设置 Jenkins 的教程(推荐方式)。