|
一、示例
测试环境基于文档docker深入2-熟悉v1.11和找不同.txt
目标熟悉使用jenkins镜像从 github 拉取代码构建镜像
-------------------------------------------------------
---------------------- n36.test -----------------------
github
↓
jenkins(docker) 172.17.0.13
slave_36 172.17.0.1
↓
execute shell on salve host slave_36
↓
---------------- build image(slave_36) ----------------
↓
---------------- run container(slave_36) --------------
↓
---------------- push to local registry ---------------
-------------------------------------------------------
二、在 docker 环境中配置 jenkins 镜像
1、获取
[Jack@n36 jenkins-test]$ docker pull jenkins
2、运行
[Jack@n36 jenkins-test]$ mkdir /data/docker/jenkins-test
[Jack@n36 jenkins-test]$ docker run -d --restart=always -p 8080:8080 -p 50000:50000 -v /data/docker/jenkins-test:/var/jenkins_home --name jenkins_36 jenkins
3、配置 jenkins 主服务器的ssh key用于后续增加 salve 节点时使用 public key 来验证。
1)获取 container 的IP
[Jack@n36 jenkins-test]$ docker inspect -f '{{ .NetworkSettings.IPAddress }}' jenkins_36
172.17.0.13
2)进入 container生成 ssh key
[Jack@n36 jenkins-test]$ docker exec -it jenkins_36 /bin/bash
jenkins@7da65fcf10ef:/$ ssh-keygen -t rsa -b 2048 -C 'jenkins@docker'
jenkins@7da65fcf10ef:/$ cat ~/.ssh/id_rsa.pub
ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAABAQCyvJ8+M2qmxI0lUYt0XWzSQoz7BVttQ/MeFeQlaL+Cf1Wf5WQgP01niDNOiPNEZohSBd9Q6Fc6j2uLWjMot76IGRaQDDPbqvtVs+WHiqFiiTjz/NOIDzS0QsQq4uJau5a+m/mYLqcH3piAwvMGGOOFWtJXPtmpUX31zz0KbO8FnQigYq0vemsKnGw/lezxMbc0WlOesDX1WVtPPgSzWPlwpC3hVYhIVQqjeBVCTrg1tuNG1voyhOwEg6MvPHUrxpWxcYfDj/rM2O6UKSxUjbMCL0LE5gLSsc2iCo9pk8i9/eiMM4S5nWo0Obdv9PG1dQO698DRQMvHzkSZ8hU91LV1 jenkins@docker
3)将上述 id_rsa.pub 的内容拷贝到目标机器(本例是172.17.0.1)
创建一个用户 jenkins 并加入 docker 组用于后续的场景。
[root@n36 ~]# useradd jenkins
[root@n36 ~]# usermod -a -G docker jenkins
[root@n36 ~]# su jenkins
[jenkins@n36 root]$ cd ~
[jenkins@n36 ~]$ cat .ssh/authorized_keys
ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAABAQCyvJ8+M2qmxI0lUYt0XWzSQoz7BVttQ/MeFeQlaL+Cf1Wf5WQgP01niDNOiPNEZohSBd9Q6Fc6j2uLWjMot76IGRaQDDPbqvtVs+WHiqFiiTjz/NOIDzS0QsQq4uJau5a+m/mYLqcH3piAwvMGGOOFWtJXPtmpUX31zz0KbO8FnQigYq0vemsKnGw/lezxMbc0WlOesDX1WVtPPgSzWPlwpC3hVYhIVQqjeBVCTrg1tuNG1voyhOwEg6MvPHUrxpWxcYfDj/rM2O6UKSxUjbMCL0LE5gLSsc2iCo9pk8i9/eiMM4S5nWo0Obdv9PG1dQO698DRQMvHzkSZ8hU91LV1 jenkins@docker
注意这个文件的权限默认创建的文件是权限位是664将导致ssh时被拒绝。
[jenkins@n36 ~]$ ls -l .ssh/authorized_keys
-rw-rw-r-- 1 jenkins jenkins 396 Jun 30 10:17 .ssh/authorized_keys
设置该文件的权限位为644
[jenkins@n36 ~]$ chmod 644 .ssh/authorized_keys
[jenkins@n36 ~]$ ls -l .ssh/authorized_keys
-rw-r--r-- 1 jenkins jenkins 396 Jun 30 10:17 .ssh/authorized_keys
4)测试从 jenkins 主节点 ssh 登录到 slave 节点的连通性
jenkins@7da65fcf10ef:/$ ssh jenkins@172.17.0.1
Enter passphrase for key '/var/jenkins_home/.ssh/id_rsa':
Last login: Thu Jun 30 10:45:02 2016
[jenkins@n36 ~]$ exit
logout
Connection to 172.17.0.1 closed.
jenkins@7da65fcf10ef:/$
符合预期。
4、登录
访问http://IP:8080/
访问后的首要步骤
选择菜单“Jenkins-系统管理-Configure Global Security”
先增加一个管理员帐号密码设置一下安全选项。
在插件管理页面安装git插件。
5、增加一个节点slave_36专门用于执行 docker bulid 任务
提示先手动 ssh 测试一下连通性。(如步骤3所示)
选择菜单“Jenkins-系统管理-管理节点-新建节点”
调整部分配置
------------------------------------------------------------------------------
Name: slave_36
远程工作目录: /home/jenkins
用法: 只允许运行绑定到这台机器的Job
启动方法: launch slave agents on unix machines via ssh
Host: 172.17.0.1
Credentials: (可选 ssh password 或 key 认证)
保存
------------------------------------------------------------------------------
三、在 jenkins 中配置一个任务
1、事先在github上创建一个示例仓库用于后续配置的任务的构建。
https://github.com/opera443399/docker-example-flask.git
2、创建一个任务
项目名称: docker-example-flask
(勾选)Restrict where this project can be run
-Label Expression: slave_36
源码管理:
(勾选)Git
Repositories
Repository URL:https://github.com/opera443399/docker-example-flask.git
构建:
Execute shell
Command:
------------------------------------------------------------------------------
if [ ! -f 'Dockerfile' ]; then
echo -e "\n\033[10;1;32m[WARN] `date`, Dockerfile not found!\033[0m\n"
exit 1
fi
old_image_id=$(docker images |grep example_flask |awk '{print $3}')
docker build -t example_flask .
new_image_id=$(docker images |grep example_flask |awk '{print $3}')
if [ "X${old_image_id}" == "X${new_image_id}" ]; then
## new == old
echo -e "\n\033[10;1;32m[WARN] `date`, the image is not changed.\033[0m\n"
elif [ ! -z ${old_image_id} ]; then
## remove the old one
docker ps -f ancestor="${old_image_id}"
docker rm -f `docker ps -f ancestor="${old_image_id}" -q`
docker rmi -f ${old_image_id}
# new
docker run -d -P --name j_test_web example_flask
docker ps -f ancestor="example_flask:latest"
else
# new
docker run -d -P --name j_test_web example_flask
docker ps -f ancestor="example_flask:latest"
fi
------------------------------------------------------------------------------
保存
3、开始构建(git源码有变更的场景)
控制台输出
Started by user admin
Building remotely on slave_36 (build) in workspace /home/jenkins/workspace/docker-example-flask
> git rev-parse --is-inside-work-tree # timeout=10
Fetching changes from the remote Git repository
> git config remote.origin.url https://github.com/opera443399/docker-example-flask.git # timeout=10
Fetching upstream changes from https://github.com/opera443399/docker-example-flask.git
> git --version # timeout=10
> git -c core.askpass=true fetch --tags --progress https://github.com/opera443399/docker-example-flask.git +refs/heads/*:refs/remotes/origin/*
> git rev-parse refs/remotes/origin/master^{commit} # timeout=10
> git rev-parse refs/remotes/origin/origin/master^{commit} # timeout=10
Checking out Revision ee7589867d808e37f25caa5ba57f7b37f0764830 (refs/remotes/origin/master)
> git config core.sparsecheckout # timeout=10
> git checkout -f ee7589867d808e37f25caa5ba57f7b37f0764830
> git rev-list 3cf4b71d1fbafdad58409a923400029560fab1b7 # timeout=10
[docker-example-flask] $ /bin/sh -xe /tmp/hudson6257354915828167074.sh
+ '[' '!' -f Dockerfile ']'
++ docker images
++ grep example_flask
++ awk '{print $3}'
+ old_image_id=705df122c6f4
+ docker build -t example_flask .
Sending build context to Docker daemon 151.6 kB
Step 1 : FROM python:2.7
---> a047e3d0ae2b
Step 2 : MAINTAINER PC
---> Using cache
---> 226defd54560
Step 3 : ADD . /code
---> e29eabdfcf6c
Removing intermediate container 9c54acc4b169
Step 4 : WORKDIR /code
---> Running in e29cc3197baf
---> e477c42451fa
Removing intermediate container e29cc3197baf
Step 5 : RUN pip install -r requirements.txt
---> Running in 7484819fb9f9
Collecting flask (from -r requirements.txt (line 1))
Downloading Flask-0.11.1-py2.py3-none-any.whl (80kB)
Collecting Jinja2>=2.4 (from flask->-r requirements.txt (line 1))
Downloading Jinja2-2.8-py2.py3-none-any.whl (263kB)
Collecting Werkzeug>=0.7 (from flask->-r requirements.txt (line 1))
Downloading Werkzeug-0.11.10-py2.py3-none-any.whl (306kB)
Collecting click>=2.0 (from flask->-r requirements.txt (line 1))
Downloading click-6.6.tar.gz (283kB)
Collecting itsdangerous>=0.21 (from flask->-r requirements.txt (line 1))
Downloading itsdangerous-0.24.tar.gz (46kB)
Collecting MarkupSafe (from Jinja2>=2.4->flask->-r requirements.txt (line 1))
Downloading MarkupSafe-0.23.tar.gz
Building wheels for collected packages: click, itsdangerous, MarkupSafe
Running setup.py bdist_wheel for click: started
Running setup.py bdist_wheel for click: finished with status 'done'
Stored in directory: /root/.cache/pip/wheels/b0/6d/8c/cf5ca1146e48bc7914748bfb1dbf3a40a440b8b4f4f0d952dd
Running setup.py bdist_wheel for itsdangerous: started
Running setup.py bdist_wheel for itsdangerous: finished with status 'done'
Stored in directory: /root/.cache/pip/wheels/fc/a8/66/24d655233c757e178d45dea2de22a04c6d92766abfb741129a
Running setup.py bdist_wheel for MarkupSafe: started
Running setup.py bdist_wheel for MarkupSafe: finished with status 'done'
Stored in directory: /root/.cache/pip/wheels/a3/fa/dc/0198eed9ad95489b8a4f45d14dd5d2aee3f8984e46862c5748
Successfully built click itsdangerous MarkupSafe
Installing collected packages: MarkupSafe, Jinja2, Werkzeug, click, itsdangerous, flask
Successfully installed Jinja2-2.8 MarkupSafe-0.23 Werkzeug-0.11.10 click-6.6 flask-0.11.1 itsdangerous-0.24
---> 2f1766774e10
Removing intermediate container 7484819fb9f9
Step 6 : EXPOSE 5000
---> Running in 0afc7dfd706c
---> d4be934c4b82
Removing intermediate container 0afc7dfd706c
Step 7 : CMD python app.py
---> Running in 80143492c06f
---> 8a7e04e40099
Removing intermediate container 80143492c06f
Successfully built 8a7e04e40099
++ docker images
++ grep example_flask
++ awk '{print $3}'
+ new_image_id=8a7e04e40099
+ '[' X705df122c6f4 == X8a7e04e40099 ']'
+ '[' '!' -z 705df122c6f4 ']'
+ docker ps -f ancestor=705df122c6f4
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
d6cdb6752542 705df122c6f4 "/bin/sh -c 'python a" 12 minutes ago Up 12 minutes 0.0.0.0:32792->5000/tcp j_test_web
++ docker ps -f ancestor=705df122c6f4 -q
+ docker rm -f d6cdb6752542
d6cdb6752542
+ docker rmi -f 705df122c6f4
Deleted: sha256:705df122c6f45fd7d14872216df5ac748e7ccd8aeb574c692d6f3ef8e68d3612
Deleted: sha256:0479bb5f6b9bce43653428f5ed230846178e52d929e6a0817ccbb25bbb318e50
Deleted: sha256:efe1492bdf6ab159c1357c04b519e98bd33c17bfd57f1b24384ea7c786b34dd8
Deleted: sha256:5aae0d93bb57f7b4bf4c7151c203f5e0e194a8688c20a756db77d6bda1be216c
Deleted: sha256:933f0804c45e0cd9722280731315f4dcea31a7fc6a48ebf579e161cf28f79347
Deleted: sha256:0c9e6c88927096de37cdbcef1a9de5c9dc45ab1e80a9389d7106b0961874cf15
Deleted: sha256:b6c6b2b55c9e2eaf123777072efa77f35953706a29a93dadaf1ba18ac59a7d34
+ docker run -d -P --name j_test_web example_flask
da59337bc9a72416f1304bf96109ef69cb5a62097a93a12fd267330bc1871136
+ docker ps -f ancestor=example_flask:latest
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
da59337bc9a7 example_flask "/bin/sh -c 'python a" 1 seconds ago Up Less than a second 0.0.0.0:32793->5000/tcp j_test_web
Finished: SUCCESS
4、验证
image构建完毕后
[jenkins@n36 docker-example-flask]$ docker images
REPOSITORY TAG IMAGE ID CREATED SIZE
example_flask latest 8a7e04e40099 About a minute ago 694.6 MB
测试的container的状态
[jenkins@n36 docker-example-flask]$ docker ps -f ancestor=example_flask:latest
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
da59337bc9a7 example_flask "/bin/sh -c 'python a" 1 seconds ago Up Less than a second 0.0.0.0:32793->5000/tcp j_test_web
[jenkins@n36 docker-example-flask]$ curl 172.17.0.1:32793
Hello World! [docker-example-flask]
变更过程符合预期。
5、再次构建(git源码无变更的场景)
控制台输出
Started by user admin
Building remotely on slave_36 (build) in workspace /home/jenkins/workspace/docker-example-flask
> git rev-parse --is-inside-work-tree # timeout=10
Fetching changes from the remote Git repository
> git config remote.origin.url https://github.com/opera443399/docker-example-flask.git # timeout=10
Fetching upstream changes from https://github.com/opera443399/docker-example-flask.git
> git --version # timeout=10
> git -c core.askpass=true fetch --tags --progress https://github.com/opera443399/docker-example-flask.git +refs/heads/*:refs/remotes/origin/*
> git rev-parse refs/remotes/origin/master^{commit} # timeout=10
> git rev-parse refs/remotes/origin/origin/master^{commit} # timeout=10
Checking out Revision ee7589867d808e37f25caa5ba57f7b37f0764830 (refs/remotes/origin/master)
> git config core.sparsecheckout # timeout=10
> git checkout -f ee7589867d808e37f25caa5ba57f7b37f0764830
> git rev-list ee7589867d808e37f25caa5ba57f7b37f0764830 # timeout=10
[docker-example-flask] $ /bin/sh -xe /tmp/hudson288315631585112422.sh
+ '[' '!' -f Dockerfile ']'
++ docker images
++ grep example_flask
++ awk '{print $3}'
+ old_image_id=8a7e04e40099
+ docker build -t example_flask .
Sending build context to Docker daemon 151.6 kB
Step 1 : FROM python:2.7
---> a047e3d0ae2b
Step 2 : MAINTAINER PC
---> Using cache
---> 226defd54560
Step 3 : ADD . /code
---> Using cache
---> e29eabdfcf6c
Step 4 : WORKDIR /code
---> Using cache
---> e477c42451fa
Step 5 : RUN pip install -r requirements.txt
---> Using cache
---> 2f1766774e10
Step 6 : EXPOSE 5000
---> Using cache
---> d4be934c4b82
Step 7 : CMD python app.py
---> Using cache
---> 8a7e04e40099
Successfully built 8a7e04e40099
++ docker images
++ grep example_flask
++ awk '{print $3}'
+ new_image_id=8a7e04e40099
+ '[' X8a7e04e40099 == X8a7e04e40099 ']'
++ date
+ echo -e '\n\033[10;1;32m[WARN] Thu Jul 7 17:30:12 CST 2016, the image is not changed.\033[0m\n'
[10;1;32m[WARN] Thu Jul 7 17:30:12 CST 2016, the image is not changed.[0m
Finished: SUCCESS
6、再次验证
[jenkins@n36 docker-example-flask]$ docker images
REPOSITORY TAG IMAGE ID CREATED SIZE
example_flask latest 8a7e04e40099 16 minutes ago 694.6 MB
[jenkins@n36 docker-example-flask]$ docker ps -f ancestor=example_flask:latest
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
da59337bc9a7 example_flask "/bin/sh -c 'python a" 1 seconds ago Up 12 minutes 0.0.0.0:32793->5000/tcp j_test_web
未发生变更符合预期。
7、小结
1)在 jenkins 中添加 salve 节点然后在新的任务中配置好代码仓库在指定的节点上运行指定的脚本。
2)后续思路增加任务触发的条件并改进脚本验证镜像并 push 到 local registry 中然后在其他环境 pull 这个新的镜像。
ZYXW、参考
1、docker doc
https://github.com/jenkinsci/docker
https://hub.docker.com/_/jenkins/
2、jenkins
http://blog.nsfocus.net/jenkins-build-number-machines/
http://www.tuicool.com/articles/fq6rYnz
http://www.cnblogs.com/Leo_wl/p/4314792.html
https://segmentfault.com/a/1190000003732967
|
|
|