1

在我的 OS X 主机上,我使用启用了 Kubernetes 并使用 Kubernetes 编排的 Docker CE (18.06.1-ce-mac73 (26764))。在这台主机上,我可以使用这个简单的 docker-compose 文件 (kube-compose.yml) 运行堆栈部署以将容器部署到 Kubernetes:

version: '3.3'
services:
  web:
    image: dockerdemos/lab-web
    volumes:
      - "./web/static:/static"
    ports:
      - "9999:80"

这个命令行从包含撰写文件的目录运行:

docker stack deploy --compose-file ./kube-compose.yml simple_test

但是,当我尝试从我的 Jenkins 容器中运行相同的命令时,Jenkins 会返回:

该节点不是集群管理器。使用“docker swarm init”或“docker swarm join”将此节点连接到swarm,然后重试

我不希望为 swarm 初始化 Jenkins 容器中的 docker 客户端,因为我没有在主机上使用 Docker swarm。

Jenkins 容器在 docker-compose 中定义,以包含到 docker 主机套接字端点的卷挂载:

version: '3.3'
services:
  jenkins:
    # contains embedded docker client & blueocean plugin
    image: jenkinsci/blueocean:latest
    user: root
    ports:
      - "8080:8080"
      - "50000:50000"
    volumes:
      - ./jenkins_home:/var/jenkins_home
      # run Docker from the host system when the container calls it.
      - /var/run/docker.sock:/var/run/docker.sock
      # root of simple project
      - .:/home/project
    container_name: jenkins

我还按照本指南使用 socat 代理对 docker 主机的请求:https ://github.com/docker/for-mac/issues/770和这里:Docker-compose: deploying service in multiple hosts

最后,我使用以下 Jenkins 定义 (Jenkinsfile) 来调用堆栈以部署在我的主机上。Jenkins 安装了 Jenkins docker 插件:

node {
    checkout scm

    stage ('Deploy To Kube') {
        docker.withServer('tcp://docker.for.mac.localhost:1234') {
            sh 'docker stack deploy app --compose-file /home/project/kube-compose.yml'
        }
    }      
}

我还尝试将 withServer 签名更改为:

docker.withServer('unix:///var/run/docker.sock')

我得到相同的错误响应。但是,我能够从 Jenkins 容器远程登录到 docker 主机,所以我知道它是可以访问的。另外,正如我之前提到的,我知道消息说要运行 swarm init,但我没有部署到 swarm。

我检查了 Jenkins 容器中 docker 客户端的版本,它与我在主机上使用的版本相同(不过是 Linux 变体):

Docker 版本 18.06.1-ce,构建 d72f525745

这是我描述的代码:https ://github.com/ewilansky/localstackdeploy.git

请让我知道是否可以从 Jenkins 容器中做我希望做的事情。所有这些的目的是提供一个简单、可移植的管道演示,部署到 Kubernetes 是最后一步。我知道这不是在本地开发环境之外的任何地方都可以采用的方法。

4

1 回答 1

1

在 Jenkins Docker 插件或 Kubernetes Docker Stack Deploy 命令可以支持我描述的远程部署方案之前,这是一种对我来说效果很好的方法。

我现在使用 Jenkins 容器中的 Kubernetes 客户端 kubectl。为了最大限度地减少 Jenkins 容器的大小增加,我只将 Kubernetes 客户端添加到基于 Alpine Linux 构建的 jenkinsci/blueocean 映像中。这个 DockerFile 显示了添加:

FROM jenkinsci/blueocean
USER root
RUN curl -LO https://storage.googleapis.com/kubernetes-release/release/v1.12.0/bin/linux/amd64/kubectl
RUN chmod +x ./kubectl
RUN mv ./kubectl /usr/local/bin/kubectl
RUN mkdir /root/.kube
COPY kube-config /root/.kube/config

我采用了这种方法,它增加了大约 100 mb 的图像大小,而不是获取 Alpine Linux Kubernetes 包,这在我的测试中几乎使图像大小增加了一倍。当然,Kubernetes 包包含所有 Kubernetes 组件,但我只需要 Kubernetes 客户端。这类似于 docker 客户端驻留在 Jenkins 容器中以便在主机上运行 Docker 命令的要求。

请注意,在 DockerFile 中有对 Kuberenetes 配置文件的引用:

kube-config /root/.kube/config

我从主机(运行 Docker for Mac 的计算机)上的 Kubernetes 配置文件开始。我相信如果您在 Docker for Mac 中启用 Kubernetes,Kubernetes 客户端配置将出现在 ~/.kube/config 中。如果没有,请单独安装 Kubernetes 客户端工具。在您将通过 DockerFile 复制到 Jenkins 容器的 Kubernetes 配置文件中,只需更改服务器值,使 Jenkins 容器指向 Docker for Mac 主机:

    server: https://docker.for.mac.localhost:6443

如果您使用的是 Windows 机器,我认为您可以使用 docker.for.win.localhost。此处对此进行了讨论:https ://github.com/docker/for-mac/issues/2705和此处描述的其他方法:https ://github.com/docker/for-linux/issues/264 。

重组 Jenkins 容器后,我可以使用 kubectl 为我的应用程序创建部署和服务,该应用程序现在在 Kubernetes Docker for Mac 主机中运行。就我而言,这是我添加到 Jenkins 文件中的两个命令:

 stage ('Deploy To Kube') {
    sh 'kubectl create -f /kube/deploy/app_set/sb-demo-deployment.yaml'
}
stage('Configure Kube Load Balancer') {
    sh 'kubectl create -f /kube/deploy/app_set/sb-demo-service.yaml'
}

Kubernetes 容器部署有很多选项。就我而言,我只需要在负载均衡器后面部署我的 Web 应用程序(带有副本)。所有这些都在 kubectl 调用的两个 yaml 文件中定义。这比 docker stack deploy 更复杂一些,但达到了相同的最终结果。

于 2018-10-25T15:10:57.170 回答