k8s部署jenkins,并且配置动态生成slave

一. 部署jenkins

1.deploy.yaml

---
apiVersion: apps/v1
kind: Deployment
metadata:
  name: jenkins2
  namespace: kube-ops
spec: 
  selector:
    matchLabels:
      app: jenkins2
  template:
    metadata:
      labels:
        app: jenkins2
    spec:
      terminationGracePeriodSeconds: 10
      serviceAccount: jenkins2
      containers:
      - name: jenkins
        image: jenkins/jenkins:lts
        imagePullPolicy: IfNotPresent
        ports:
        - containerPort: 8080
          name: web
          protocol: TCP
        - containerPort: 50000
          name: agent
          protocol: TCP
        resources:
          limits:
            cpu: 1000m
            memory: 1Gi
          requests:
            cpu: 500m
            memory: 512Mi
        livenessProbe:
          httpGet:
            path: /login
            port: 8080
          initialDelaySeconds: 60
          timeoutSeconds: 5
          failureThreshold: 12
        readinessProbe:
          httpGet:
            path: /login
            port: 8080
          initialDelaySeconds: 60
          timeoutSeconds: 5
          failureThreshold: 12
        volumeMounts:
        - name: jenkinshome
          subPath: jenkins2
          mountPath: /var/jenkins_home
      securityContext:
        fsGroup: 1000
      volumes:
      - name: jenkinshome
        persistentVolumeClaim:
          claimName: opspvc

---
apiVersion: v1
kind: Service
metadata:
  name: jenkins2
  namespace: kube-ops
  labels:
    app: jenkins2
spec:
  selector:
    app: jenkins2
  type: NodePort
  ports:
  - name: web
    port: 8080
    targetPort: web
    nodePort: 30002
  - name: agent
    port: 50000
    targetPort: agent

2.创建ns

kubectl create namespace kube-ops

3.创建pvc

---
kind: PersistentVolumeClaim
apiVersion: v1
metadata:
  name: opspvc
  namespace: kube-ops
spec:
  accessModes:
    - ReadWriteMany
  resources:
    requests:
      storage: 20Gi

4.创建rbac

另外我们这里还需要使用到一个拥有相关权限的 serviceAccount:jenkins2,我们这里只是给 jenkins 赋予了一些必要的权限,当然如果你对 serviceAccount 的权限不是很熟悉的话,我们给这个 sa 绑定一个 cluster-admin 的集群角色权限也是可以的,当然这样具有一定的安全风险:(rbac.yaml)

apiVersion: v1
kind: ServiceAccount
metadata:
  name: jenkins2
  namespace: kube-ops

---

kind: ClusterRole
apiVersion: rbac.authorization.k8s.io/v1beta1
metadata:
  name: jenkins2
rules:
  - apiGroups: ["extensions", "apps"]
    resources: ["deployments"]
    verbs: ["create", "delete", "get", "list", "watch", "patch", "update"]
  - apiGroups: [""]
    resources: ["services"]
    verbs: ["create", "delete", "get", "list", "watch", "patch", "update"]
  - apiGroups: [""]
    resources: ["pods"]
    verbs: ["create","delete","get","list","patch","update","watch"]
  - apiGroups: [""]
    resources: ["pods/exec"]
    verbs: ["create","delete","get","list","patch","update","watch"]
  - apiGroups: [""]
    resources: ["pods/log"]
    verbs: ["get","list","watch"]
  - apiGroups: [""]
    resources: ["secrets"]
    verbs: ["get"]

---
apiVersion: rbac.authorization.k8s.io/v1beta1
kind: ClusterRoleBinding
metadata:
  name: jenkins2
  namespace: kube-ops
roleRef:
  apiGroup: rbac.authorization.k8s.io
  kind: ClusterRole
  name: jenkins2
subjects:
  - kind: ServiceAccount
    name: jenkins2
    namespace: kube-ops

5.排错

创建pod后可能会报权限错误,这是因为默认的镜像使用的是 jenkins 这个用户,而我们通过 PVC 挂载到 nfs 服务器的共享数据目录下面却是 root 用户的,所以没有权限访问该目录,要解决该问题,也很简单,我只需要在 nfs 共享数据目录下面把我们的目录权限重新分配下即可:

chown -R 1000 /data/k8s/jenkins2

等到服务启动成功后,我们就可以根据任意节点的 IP:30002 端口就可以访问 jenkins 服务了,可以根据提示信息进行安装配置即可:

初始化的密码我们可以在 jenkins 的容器的日志中进行查看,也可以直接在 nfs 的共享数据目录中查看:

cat /data/k8s/jenkins2/secrets/initAdminPassword

然后选择安装推荐的插件即可。

二. 配置

接下来我们就需要来配置 Jenkins,让他能够动态的生成 Slave 的 Pod。

1.安装kubernetes plugin

点击 Manage Jenkins -> Manage Plugins -> Available -> Kubernetes plugin 勾选安装即可。

2.填写 Kubernetes 和 Jenkins 配置信息

注意 namespace,我们这里填 kube-ops,然后点击Test Connection,如果出现 Connection test successful 的提示信息证明 Jenkins 已经可以和 Kubernetes 系统正常通信了,然后下方的 Jenkins URL 地址:http://jenkins2.kube-ops.svc.cluster.local:8080,格式为:服务名.namespace.svc.cluster.local:8080

3.配置 Pod Template

其实就是配置 Jenkins Slave 运行的 Pod 模板,命名空间我们同样是用 kube-ops,Labels写slave-jnlp, 这里的标签也非常重要,对于后面执行 Job 的时候需要用到该值

首先构建slave自定义镜像

Dockerfile文件内容如下, 镜像中包含了docker, kubectl命令

FROM jenkins/inbound-agent:4.11-1-jdk11
  
LABEL AUTHOR HONG

COPY kubectl /usr/local/bin/kubectl

USER root

RUN apt-get update \
        && apt upgrade -y \
        && apt install -y curl vim wget gnupg apt-transport-https lsb-release ca-certificates \
        && wget -O /usr/share/keyrings/docker.asc http://mirrors.aliyun.com/docker-ce/linux/debian/gpg \
        && echo "deb [signed-by=/usr/share/keyrings/docker.asc] http://mirrors.aliyun.com/docker-ce/linux/debian $(lsb_release -sc) stable" > /etc/apt/sources.list.d/docker.list \
        && apt update -y \
        #&& apt-cache madison docker-ce \
        && apt-get install -y docker-ce \
        && usermod -a -G docker jenkins
        #&& sed -i '/^root/a\jenkins    ALL=(ALL:ALL) NOPASSWD:ALL' /etc/sudoers

WORKDIR /home/jenkins

USER jenkins

ENTRYPOINT ["jenkins-slave"]

这里生成镜像标签名jenkins/slave:v3.0

然后填写模板如下

1)填写标签和镜像名

2)挂载两个主机目录

一个是/var/run/docker.sock,该文件是用于 Pod 中的容器能够共享宿主机的 Docker,这就是大家说的 docker in docker 的方式,Docker 二进制文件我们已经打包到上面的镜像中了,需要修改node节点上的docker.sock权限为777,但是重启服务器后docker.sock的权限会丢失,处理方法如下

创建一个service文件/etc/systemd/system/docker-sock-permissions

[Unit]
Description=Set permissions for docker.sock
[Service]
ExecStart=/bin/chmod o+rw /var/run/docker.sock
RemainAfterExit=yes
[Install]
WantedBy=multi-user.target

设置权限及开机启动

 chmod 644 /etc/systemd/system/docker-sock-permissions.service
 systemctl enable docker-sock-permissions.service

另外一个目录是/root/.kube目录,我们将这个目录挂载到容器的/root/.kube目录下面,这是为了让我们能够在 Pod 的容器中能够使用 kubectl 工具来访问我们的 Kubernetes 集群,方便我们后面在 Slave Pod 部署 Kubernetes 应用。需要注意的是我们要从master节点上把.kube文件夹拷贝到node节点的/root目录下

3)设置生成的slave容器的存活时间

这里我们最好留空,slave作业完成后,相应的pod会立刻销毁,设置时间过长的话,任务结束后pod也会一直存在。

4)设置service account,这里的值就是我们部署jenkins时,deploy.yaml文件中的sa

注意点

1.slave镜像java版本,要和jenkins server中的java版本一样,进入server容器中,使用java --version查看版本发现版本号是11
测试使用jenkins/jnlp-slave:4.13.3-1-jdk11
这个镜像版本可以使用基本的bash命令,但是没有kubectl, docker这些命令

2.测试使用odavid/jenkins-jnlp-slave:latest 默认安装了docker

对照参考
https://segmentfault.com/a/1190000041897068?sort=votes

posted @ 2023-08-30 21:04  坚强的小蚂蚁  阅读(719)  评论(0编辑  收藏  举报