# Docker
说明
docker 学习笔记
# Docker 的基本命令
容器运行状态
docker stats
查看运行的容器
docer ps -a
停止所有容器
docker stop $(docker ps -a -q)
删除所有已经停止的容器
docker rm $(docker ps -a -q)
文件复制
从主机复制到容器
sudo docker cp host_path containerID:container_path
从容器复制到主机
sudo docker cp containerID:container_path host_path
# CICD
# 启动 runner:
$ docker run -d --name gitlab-runner --restart always \
-v /srv/gitlab-runner/config:/etc/gitlab-runner \
-v /var/run/docker.sock:/var/run/docker.sock \
gitlab/gitlab-runner:latest
一些容器运行时需要挂载**/var/run/docker.sock**文件。这个文件是什么呢?为什么有些容器需要使用它?简单地说,它是Docker守护进程(Docker daemon)默认监听的Unix域套接字(Unix domain socket),容器中的进程可以通过它与Docker守护进程进行通信。这里,便于runner跟docker的守护进程交互。
# 注册 runner
gitlab-runner register
--non-interactive \
--tls-ca-file=/etc/gitlab/ssl/gitlab.example.com.crt \
--url "http://218.28.35.120:19081/" \
--registration-token "EXY3_sPSpdVHXtMKYHej" \
--executor "docker" \
--docker-image node:latest \
--description "runner " \
--tag-list "run" \
--run-untagged \
--locked="false"
- --url 输入 gitlab 的服务 URL
- --registration-token 输入 gitlab-ci 的 Toekn
- --tls-ca-file 关于集成服务中对于这个 runner 的描述
- --tag-list 给这个 gitlab-runner 输入一个标记,这个 tag 非常重要,在后续的使用过程中需要使用这个 tag 来指定 gitlab-runner
- --run-untagged 是否运行在没有 tag 的 build 上面。在配置 gitlab-ci 的时候,会有很多 job,每个 job 可以通过 tags 属性来选择 runner。这里为 true 表示如果 job 没有配置 tags,也执行
- --locked 是否锁定 runner 到当前项目
- --executor 选择执行器,gitlab-runner 实现了很多执行器,可用在不同场景中运行构建,详情可见GitLab Runner Executors (opens new window),这里选用 Docker 模式
# runner 的基本命令
查看状态
gitlab-runner status
查看runner服务
gitlab-ci-multi-runner list
重启runner,发现他会自动去执行触发runner的任务
执行gitlab-ci-multi-runner restart
# 编写.gitlab-ci.yml
# docker镜像
image: node
# 依赖的docker服务
services:
- postgres
# 开始执行脚本前所需执行脚本
before_script:
- bundle install
# 脚本执行完后的钩子,执行所需脚本
after_script:
- rm secrets
# 该ci pipeline适合的场景
stages:
- build
- test
- deploy
# 定义的任务1
job1:
# 场景为构建
stage: build
# 所需执行的脚本
script:
- execute-script-for-job1
# 在哪个分支上可用
only:
- master
# 指定哪个ci runner跑该工作
tags:
- docker
# 解决 gitlab-runner 执行 docker 命令提示权限不足的问题
- 将 gitlab-runner 用户添加到 docker 组
sudo usermod -aG docker gitlab-runner
- 验证是否生效:
sudo -u gitlab-runner -H docker info
# 完整配置:
Dockerfile
FROM nginx
RUN mkdir /app
COPY /dist /app
COPY nginx.conf /etc/nginx/nginx.conf
打包完成后创建 nginx 镜像
步骤:
在镜像的根目录创建 app 文件夹
将打包后的文件复制过去 (/dist 指的是当前项目路径)
将项目中的 nginx 配置文件作为镜像的配置文件
nginx.conf
user nginx;
worker_processes 1;
error_log /var/log/nginx/error.log warn;
pid /var/run/nginx.pid;
events {
worker_connections 1024;
}
http {
include /etc/nginx/mime.types;
default_type application/octet-stream;
log_format main '$remote_addr - $remote_user [$time_local] "$request" '
'$status $body_bytes_sent "$http_referer" '
'"$http_user_agent" "$http_x_forwarded_for"';
access_log /var/log/nginx/access.log main;
sendfile on;
keepalive_timeout 65;
server {
listen 80;
server_name localhost;
location / {
root /app;
index index.html;
try_files $uri $uri/ /index.html;
}
error_page 500 502 503 504 /50x.html;
location = /50x.html {
root /usr/share/nginx/html;
}
}
}
gitlab-ci.yml
stages: # Stages 表示构建阶段,这里有两个阶段 install, deploy
- build
- deploy
project_build: # Jobs 表示构建工作,表示某个 Stage 里面执行的工作。
stage: build
only: # 定义了只有在被merge到了dev分支上 才会执行部署脚本。
- njx-dev
tags:
- vue
script:
- echo "=====开始依赖安装======"
- npm install --verbose --registry=https://registry.npm.taobao.org #安装依赖
- echo "=====开始打包======"
- npm run build
artifacts: # 将这个job生成的依赖传递给下一个job。需要设置dependencies
expire_in: 30 mins # artifacets 的过期时间,因为这些数据都是直接保存在 Gitlab 机器上的,过于久远的资源就可以删除掉了
paths: # 需要被传递给下一个job的目录。
- dist/
project_deploy:
stage: deploy
only:
- njx-dev
tags:
- vue
script:
- echo "=====开始部署======"
- ls
- docker build . -t finance-vue:lastest
- docker stop finance-vue-container
- docker rm finance-vue-container
- docker run -d -p 8084:80 --name finance-vue-container finance-vue:lastest
# - sudo cp -r dist/* /usr/local
# - sudo cd /usr/local
- ls
- echo "=====结束部署======"
# 修改 runner 详细配置
vi /etc/gitlab-runner/
concurrent = 4
check_interval = 0
[session_server]
session_timeout = 1800
[[runners]]
name = "myrunner with docker executor"
url = "http://${gitlabIP}" #gitlab地址
#特别注意,这个token不是小本本上的token!!!
token ="......"
executor = "docker"
[runners.docker]
host = ""
hostname = ""
privileged = false
tls_verify = false
disable_entrypoint_overwrite = false
oom_kill_disable = false
disable_cache = true
pull_policy = "if-not-present"
#这是runner的默认镜像;具体镜像maven:3-jdk-8在.gitlab-ci.yml中配置
image = "busybox:latest"
helper_image = "gitlab-runner-helper:x86_64-f100a208"
#映射maven配置
volumes = ["/home/v_in_docker/:/usr/share/maven/conf2/:rw"]
[runners.docker.sysctls]
"net.ipv4.ip_forward" = "1"
[runners.cache]
[runners.cache.s3]
[runners.cache.gc3]
12345678910111213141516171819202122232425262728293031
# [runners.docker.sysctls] 作用等效于
sudo vi /etc/sysctl.conf
#加一行:
net.ipv4.ip_forward=1
sudo sysctl -p
# runner 执行器为 docker 时发生的问题:
# 1、找不到 docker 命令
$ docker info /bin/bash: line 81: docker: command not found ERROR: Job failed: exit code 1
解决:在编写 gitlab-runner 的 docker-compose.yml 时候,加上挂载宿主机 docker 命令。实现docker in docker
privileged: true
volumes:
# 映射docker命令
- /var/run/docker.sock:/var/run/docker.sock
- /bin/docker:/bin/docker
# 2、没有 docker 权限
Got permission denied while trying to connect to the Docker
解决:
#则需要把将当前用户加入docker组
sudo gpasswd -a ${USER} docker
#或者将当前用户直接加到文件中
sudo echo "docker:x:994:${USER}" >> /etc/group
#查看docker用户组成员
cat /etc/group |grep docker
#重新启动docker服务
sudo systemctl restart docker
# 赋予权限
sudo chmod a+rw /var/run/docker.sock
before_script:
- docker info
- docker login -u "gitlab-ci-token" -p "$CI_BUILD_TOKEN" "$CI_REGISTRY"
# 容器
# 容器改名
docker rename <container name> <newcontainer name>
# 基本命令
命令 | 描述 |
---|---|
docker ps -a | 列出活动的容器 |
docker ps -l | |
docker start "container id" | 启动 |
docker stop "contaienr_name" | 停止 |
docker rm "contaienr name" | 删除容器 |
docker top "contaienr name" | 查看 WEB 应用程序容器的进程 |
docker inspect "contaienr name" | 查看 Docker 的底层信息 |
# 运行(创建)容器
$ docker run --name nginx-test -p 8080:80 -d nginx
$ docker run --name <your container name> -p <local port:container port> -d <image name>
容器名 本地端口:容器端口 镜像名
参数说明:
- --name nginx-test:容器名称
- -p 8080:80: 端口进行映射,将本地 8080 端口映射到容器内部的 80 端口
- **-d **: 设置容器在在后台一直运行
- --entrypoint=‘bash’:进入容器时所带的默认参数。$ docker exec -it nginx-test 等效与$ docker exec -it nginx-test bash
# 进入容器
$ docker exec -it nginx-test bash
$ docker exec -it <contaienr name>
参数说明:
--it:i 是交互模式,t 显示终端,是一个伪
tty
终端。-i 保证容器的
STDIN
(持久的标准输入)是开启的。-t 为创建的容器分配一个伪 tty 终端
bash:命令行交互
# 保存容器副本
docker commit -m="has update" -a="niu" <container id> <author>/<image name>:<tag>
例子
docker commit -m="has update" -a="runoob" e218edb10161 runoob/ubuntu:v2
参数说明:
- -m:提交的描述。
- -a:作者。
# 容器状态为 Exit(1)时的处理
1.第一步查看日志
docker logs -f <container name>
一般在这就能找到问题:可以看到是我们的配置文件有问题
[root@iz2ze7hl9oxqoqpukjw25 containers]# docker logs -f nginx2
nginx: [emerg] unknown directive "//显示索引" in /etc/nginx/nginx.conf:50
nginx: [emerg] unknown directive "//显示索引" in /etc/nginx/nginx.conf:50
nginx: [emerg] unexpected "}" in /etc/nginx/nginx.conf:52
nginx: [emerg] unknown directive "//显示索引" in /etc/nginx/nginx.conf:50
# 运行一些常用的容器
# redis
docker run -itd --name redis-test -p 3396:3396 redis
# mysql
docker run -itd --name mysql-niu -p 3306:3306 -e MYSQL_ROOT_PASSWORD=123456 mysql
yun install -y
############################################
# version : Docker version1.10.3, build 3999ccb-unsupported
# desc : 当前版本安装的ssh,wget,curl
############################################
FROM docker.io/centos
# 一次性安装vim,wget,curl,ssh server等必备软件
RUN yum install-y vim wget curl openssh-server sudo
RUN mkdir-p /var/run/sshd
# 安装supervisor工具
RUN yum install-y Python-setuptools
RUN easy_install supervisor
RUN mkdir-p /var/log/supervisor
# 将sshd的UsePAM参数设置成no
RUN sed-i 's/UsePAM yes/UsePAM no/g' /etc/ssh/sshd_config
RUN ssh-keygen -t rsa -f /etc/ssh/ssh_host_rsa_key
RUN ssh-keygen -t dsa -f /etc/ssh/ssh_host_dsa_key
# 添加root账户的密码为123456
RUN echo "root:123456" | chpasswd
# 添加测试用户admin,密码admin,并且将此用户添加到sudoers里
RUN useradd admin
RUN echo"admin:admin" | chpasswd
RUN echo"admin ALL=(ALL) ALL" >> /etc/sudoers
# 添加 supervisord 的配置文件,并复制配置文件到对应目录下面。(supervisord.conf文件和Dockerfile文件在同一路径)
COPY supervisord.conf/etc/supervisor/supervisord.conf
# 容器需要开放SSH 22端口
EXPOSE22
# 执行supervisord来同时执行多个命令,使用 supervisord 的可执行路径启动服务。
CMD ["/usr/bin/supervisord"]
supervisord.conf文件
# 配置文件包含目录和进程
# 第一段 supervsord 配置软件本身,使用 nodaemon 参数来运行。
# 第二段包含要控制的 2 个服务。每一段包含一个服务的目录和启动这个服务的命令。
[supervisord]
nodaemon=true
[program:sshd]
command=/usr/sbin/sshd -D
# 1 镜像源
setting > Docker Engine
{
"registry-mirrors": [
"https://registry.docker-cn.com",
"https://docker.mirrors.ustc.edu.cn"
],
"insecure-registries": [],
"debug": true,
"experimental": true
}
检查是否安装成功:
使用docker info
命令:
看到以下信息表示安装成功。
Registry Mirrors:
https://registry.docker-cn.com/
https://docker.mirrors.ustc.edu.cn/
几个速度比较快的镜像地址
Docker 官方中国区: https://registry.docker-cn.com
网易: http://hub-mirror.c.163.com
中科大: https://docker.mirrors.ustc.edu.cn
# 2 Docker 拉取 ubuntu 镜像
docker pull ubuntu
安装最新版本的 ubuntu 镜像
检查是否安装成功
docker images
命令
PS C:\Users\DELL> docker images
REPOSITORY TAG IMAGE ID CREATED SIZE
ubuntu latest 1d622ef86b13 47 hours ago 83.8MB
<none> <none> 10e305a20c54 5 months ago 377MB
golang 1.11-alpine e116d2efa2ab 8 months ago 345MB
# 3 在 ubuntu 镜像中安装 apt-get
- 备份
cp /etc/apt/sources.list /etc/apt/sources.list.bak
- 修改源(直接修改,未使用 vi 或者 vim 修改)
echo "">sources.list
echo "deb http://mirrors.163.com/ubuntu/ artful main restricted universe multiverse">>sources.list
echo "deb http://mirrors.163.com/ubuntu/ artful-security main restricted universe multiverse">>sources.list
echo "deb http://mirrors.163.com/ubuntu/ artful-updates main restricted universe multiverse">>sources.list
echo "deb http://mirrors.163.com/ubuntu/ artful-proposed main restricted universe multiverse">>sources.list
echo "deb http://mirrors.163.com/ubuntu/ artful-backports main restricted universe multiverse">>sources.list
echo "deb-src http://mirrors.163.com/ubuntu/ artful main restricted universe multiverse">>sources.list
echo "deb-src http://mirrors.163.com/ubuntu/ artful-security main restricted universe multiverse">>sources.list
echo "deb-src http://mirrors.163.com/ubuntu/ artful-updates main restricted universe multiverse">>sources.list
echo "deb-src http://mirrors.163.com/ubuntu/ artful-proposed main restricted universe multiverse">>sources.list
echo "deb-src http://mirrors.163.com/ubuntu/ artful-backports main restricted universe multiverse">>sources.list
在此https://www.jianshu.com/p/2072d1ab11db获取更多信息
# 4.保存修改后的容器
查看正在运行的容器docker ps
PS D:\dams-vue> docker ps
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
62ecc03257f8 youngniu/ubuntu "/bin/bash" 6 minutes ago Up 6 minutes admiring_shockley
进入正在运行的容器内
docker exec –it 3bd0eef03413(容器id) bash
查看被修改的容器:
docker ps -l
提交指定容器保存为新的镜像:
docker commit -m="some info" -a="author" <container id> <new image name>
查看本地所有镜像:
docker images
# 5 docker 运行 redis 容器
docker pull redis:latest 拉取镜像
docker images 查看是否拉去成功
docker run -itd --name redis-test -p 6379:6379 redis 运行redis容器
docker ps 查看是否运行成功
docker exec -it redis-test /bin/bash 进入到当前容器中
redis-cli 运行redis
# 6 常用命令
docker search mysql
# 7 安装 sqlserve
sudo docker run -e "ACCEPT_EULA=Y" -e "SA_PASSWORD=YourStrong@Passw0rd" -p 1433:1433 --name mssql -d mcr.microsoft.com/mssql/server:2017-latest
# 8 安装 vim
mv /etc/apt/sources.list /etc/apt/sources.list.bak
echo "deb http://mirrors.163.com/debian/ jessie main non-free contrib" >/etc/apt/sources.list
echo "deb http://mirrors.163.com/debian/ jessie-proposed-updates main non-free contrib" >>/etc/apt/sources.list
echo "deb-src http://mirrors.163.com/debian/ jessie main non-free contrib" >>/etc/apt/sources.list
echo "deb-src http://mirrors.163.com/debian/ jessie-proposed-updates main non-free contrib" >>/etc/apt/sources.list
apt-get update
apt-get install -y vim
# 使用Dockerfile制作tomcat-jdk镜像
# 1.下载文件
tomcat :https://tomcat.apache.org/download-90.cgi
jdk :http://www.oracle.com/technetwork/java/javase/downloads/jdk8-downloads-2133151.html
# 2.Dockerfile
# 指定操作的镜像
FROM centos:7
# 将 jdk 和 tomcat 添加到镜像centos的/usr/local/目录下
ADD jdk-8u141-linux-x64.tar.gz /usr/local/
ADD apache-tomcat-9.0.36.tar.gz /usr/local/
# 覆盖相关文件
#COPY server.xml /usr/local/apache-tomcat-8.5.50/conf/
# 添加环境变量
ENV JAVA_HOME /usr/local/jdk1.8.0_141
ENV CLASSPATH $JAVA_HOME/lib/dt.jar:$JAVA_HOME/lib/tools.jar
ENV CATALINA_HOME /usr/local/apache-tomcat-9.0.36
ENV PATH $PATH:$JAVA_HOME/bin:$CATALINA_HOME/lib:$CATALINA_HOME/bin
ENV TZ="Asia/Shanghai"
ENV JAVA_OPTS="\
-server \
-Xms3g \
-Xmx3g \
-Xmn512m \
-Xss512K \
-Dfile.encoding=UTF-8 \
-verbose:gc \
-XX:+UseConcMarkSweepGC \
-XX:MaxTenuringThreshold=10 \
-XX:+ExplicitGCInvokesConcurrent \
-XX:GCTimeRatio=19 \
-XX:+UseParNewGC \
-XX:+UseCMSCompactAtFullCollection \
-XX:CMSFullGCsBeforeCompaction=10 \
-XX:+CMSClassUnloadingEnabled \
-XX:+CMSParallelRemarkEnabled \
-XX:CMSInitiatingOccupancyFraction=50 \
-Xnoclassgc \
-XX:SoftRefLRUPolicyMSPerMB=0"
# 暴露8080端口
EXPOSE 8080
# 容器启动时运行tomcat
CMD /usr/local/apache-tomcat-9.0.36/bin/catalina.sh run
# 3.build
docker build -t youngniu/tomcat-9.0.36:v1 .
# 4.run
docker run -idt --name tomcat-isc -p 8100:8080 -v /home/tomcat-isc/webapps:/usr/local/tomcat/webapps -v /home/tomcat-isc/logs:/usr/local/tomcat/logs -v /home/tomcat-isc/conf:/usr/local/tomcat/conf tomcat-9.0.36:v1
说明:
* -d 后台运行
* --name mytomcat 容器名称 * -v /server/webapps:/usr/local/tomcat/webapps/ 挂载当前项目的运行目录到tomcat下的webapps * -e TZ="Asia/Shanghai" 设置时区 * --privileged=true 设置拥有容器中的真正的root权限 * -p 8080:8080 映射端口(宿主机port : 容器port) * tomcat-8.5.50:v1 镜像的名称
docker run -idt --name tomcat-isc -p 8100:8080 -v /home/tomcat-isc/webapps:/usr/local/tomcat/webapps -v /home/tomcat-isc/logs:/usr/local/tomcat/logs -v /home/tomcat-isc/conf:/usr/local/tomcat/conf tomcat:v1
# note
内省性
幂等性
Docker官方主页(http://www.docker.com/)。 DockerHub(http://hub.dockercom) Docker官方博客(http://blog.docker.com/) Docker官方文档(http://docs.docker.com/)。 Docker快速入门指南(http://www.docker.com/tryit/)。 Docker的Github源代码(https://github.com/docker/docker)。 Docker的IRC频道(irc.freenode.net)。
终端(terminal)=tty=文本的输入输出环境 控制台(console)=物理终端 shell=命令行解释器
# 使用tomcat容器部署项目
# 1.运行tomcat容器
docker run -idt -p 8081:8080 tomcat
-p 8081:8080
将本地8081端口映射到容器的8080端口
-d
diff的意思,官方解释:Inspect changes to files or directories on a container's filesystem。保存文件变更
# 2.进入tomcat容器
docker exec -it <container id> bash
初始化的tomcat /usr/local/tomcat/webapps
文件夹是空的,需要将/usr/local/tomcat/webapps.dist
文件中的内容复制到替换过去。
命令:
cd /usr/local/tomcat
rm webapps
rm <本地文件夹>
mv webapps.dist webapps
mv <文件> <更改名字>
这时才可以访问tomcat的欢迎页面
# 3.保存修改后的容器
语法:
docker commit -m="<comment>" -a="<author>" <container id> <author>/<new container name>:<tag>
例子
docker commit -m="has update" -a="runoob" e218edb10161 runoob/ubuntu:v2
# 4.把项目部署到tomcat
查看tomcat容器uuid
docker inspect -f '{{.Id}}' <container name>
得到:容器长uuid
fe3ce7d5fbc93c9cedafe362bd091a2ebed9babe610f52a3545ea85cd58a67a3
将本地文件复制到容器中
docker cp <local path> <container long id:contanier path>
例子
docker cp /usr/local/niu/apache-tomcat-9.0.24/webapps/dams fe3ce7d5fbc93c9cedafe362bd091a2ebed9babe610f52a3545ea85cd58a67a3:/usr/local/tomcat/webapps
# 5我的部署
# 6 挂载目录
/home/tomcat-isc/webapps
/usr/local/tomcat/webapps
/home/tomcat-isc/logs
/usr/local/tomcat/logs
docker run -idt --name tomcat-isc -p 8100:8080 -v /home/tomcat-isc/webapps:/usr/local/tomcat/webapps -v /home/tomcat-isc/logs:/usr/local/tomcat/logs youngniu/tomcat:niu