GVKun编程网logo

Docker 日常使用及问题(docker基本使用)

15

想了解Docker日常使用及问题的新动态吗?本文将为您提供详细的信息,我们还将为您解答关于docker基本使用的相关问题,此外,我们还将为您介绍关于167dockerdocker构建nginx容器系列

想了解Docker 日常使用及问题的新动态吗?本文将为您提供详细的信息,我们还将为您解答关于docker基本使用的相关问题,此外,我们还将为您介绍关于167 docker docker构建nginx容器系列问题 docker registry docker run docker toolbo、CentOS 7 安装 Docker-machine 及日常使用、Docker in Docker(实际上是 Docker outside Docker): /var/run/docker.sock、Docker windows 安装及问题处理的新知识。

本文目录一览:

Docker 日常使用及问题(docker基本使用)

Docker 日常使用及问题(docker基本使用)

docker 安装

# Docker requires a 64-bit installation regardless of your CentOS version. Also, your kernel must be 3.10 at minimum, which CentOS 7 runs.
# Centos 6安装docker 链接:“www.centoscn.com/image-text/install/2014/1128/4202.html”
sudo tee /etc/yum.repos.d/docker.repo <<-''EOF''
[dockerrepo]
name=Docker Repository
baseurl=https://yum.dockerproject.org/repo/main/centos/$releasever/
enabled=1
gpgcheck=1
gpgkey=https://yum.dockerproject.org/gpg
EOF

yum install docker-engine
service docker start

docker 使用

# 搜索查看可以使用的镜像
docker search centos
# 拉取需要的镜像
docker pull centos:latest
# 查看本地镜像列表
docker images
# 查看网络状态
docker network ls
# 查看容器信息
docker inspect webhack

# 拷贝一个现存容器中的文件到本地
docker cp aaa39fe1e7af:/etc/redis.conf ./
# 查看一个容器的运行日志
docker logs -f 容器名orID
# 查看一个容器的root密码, 因为Docker容器启动时的root用户的密码是随机分配的。所以,通过这种方式就可以得到redmine容器的root用户的密码了。(没测试成功)
docker logs <容器名orID> 2>&1 | grep ''^User: '' | tail -n1

# 批量删除构建失败的容器
# 先停止容器运行再删除,否则会挂掉...
docker ps -a  | awk ''{print $1}'' | xargs docker stop
docker ps -a  | awk ''{print $1}'' | xargs docker rm
# 然后删除无用的镜像文件
docker rmi image_id

# 存出构建好的镜像文件
docker save -o honey.tar honey:v1
# 载入现有镜像到docker
docker load --input honey.tar
docker < honey.tar.gz
# 导出容器
docker export id > honey.tar
# 导入容器
cat honey.tar | docker import - honey:latest

# 启动一个容器的bash终端
docker run -a stdin -a stdout -t centos:6.6 /bin/bash
# 基于centos7的容器没有/bin/bash命令。。。。很乱

# 基于Dockerfile构建一个镜像文件
docker build -t honey:v1 .

# 挂载本地文件或目录到容器中,容器中对文件的修改和宿主机中对文件的修改都会同步到容器和宿主机中,最好的方式是挂载映射目录,因为编辑文件时可能会造成文件 inode 的改变,从 Docker 1.1 .0起,这会导致报错误信息。
# 参见:https://yeasy.gitbooks.io/docker_practice/content/data_management/volume.html
# 挂载文件时,可能会出现本地文件权限是root或者是权限比较大的文件目录,而挂载到容器中后,容器中的低权限或其他用户将无法对文件目录进行修改,解决方法是将本地的文件目录设置为777权限
docker run --net=host -v /home/docker/snmp/conf/supervisord.conf:/etc/supervisord.conf -v /home/docker/snmp/log:/home/log -it snmp:v3 supervisord

# 把容器放到后台运行并打印出容器的id
docker run -d

# 退出容器后即删除容器,不能与-d共用
docker run --rm -it 容器ID

# 提交修改后的容器为新的镜像
docker commit 容器ID 镜像ID

# Docker 挂载数据卷的默认权限是读写,用户也可以通过 :ro 指定为只读。
docker run -d -P --name web -v /src/webapp:/opt/webapp:ro

docker export 和 docker save 的区别

# export用于持久化容器(不是镜像),会丢失历史和元数据,无法回滚到以前的层
docker ps -a
docker export 容器ID > export.tar
# 导入
cat export.tar | docker import - export:v1

# save用于持久化镜像(不是容器),有历史所有的操作,可以会滚
docker save 镜像ID > image.tar
# 导入
docker load < image.tar

Dockerfile 使用过程中的一些问题

# WORKDIR  指构建容器时容器内部的目录
WORKDIR /home
# COPY  复制本地文件到服务器的目录,无法复制操作容器内的文件
COPY soft/jdk-7u79-linux-x64.rpm /home
# RUN   运行服务器中的命令
RUN rpm -ivh jdk-7u79-linux-x64.rpm
# 切换目录
WORKDIR redis-3.2.0
WORKDIR src/
# 此时的目录为/home/redis-3.2.0/src
RUN pwd
# 容器内部的复制命令,无法操作本地文件
RUN cp redis-cli /usr/bin
# 默认调用的是sh -c apt-get install 某些情况下易出现问题
CMD apt-get install
# 所见即所得,按照自己想要的方式执行 调用exec from
CMD ["apt-get install"]

# 指定容器运行时的用户名或UID,后续的RUN也会使用指定的用户执行命令
# 虽然使用nobody权限的用户启动容器执行命令比较安全,但是对于yum这种则无法执行
# 解决方法是使用supervisord启动执行的程序的时候指定启动的用户权限组进行执行启动
USER nobody

# 创建一个可以从本地或者其他容器挂载的挂载点,如果服务器不存在就自动创建
# 和-v创建卷的区别https://segmentfault.com/q/1010000004107293
VOLUME ["/data"]

CMD RUN 的区别

CMD 容器启动时执行的命令,可被docker run中的命令重写覆盖,每个Dockerfile仅最后一条CMD指令生效
RUN 容器构建时运行的命令
ENTRYPOINT,表示镜像在初始化时需要执行的命令,不可被docker run中的命令重写覆盖,需谨记

# ENTRYPOINT/CMD都只能在文件中存在一次,并且最后一个生效 多个存在,只有最后一个生效,其它无效!
需要初始化运行多个命令,彼此之间可以使用 && 隔开,但最后一个须要为无限运行的命令,需切记!
# ENTRYPOINT/CMD,一般两者可以配合使用,比如:
ENTRYPOINT ["/usr/sbin/sshd"]
CMD ["-D"]

# 在Docker daemon模式下,无论你是使用ENTRYPOINT,还是CMD,最后的命令,一定要是当前进程需要一直运行的,才能够防容器退出。
# 以下无效方式:
ENTRYPOINT service tomcat7 start #运行几秒钟之后,容器就会退出
 CMD service tomcat7 start #运行几秒钟之后,容器就会退出

# 这样有效:
ENTRYPOINT service tomcat7 start && tail -f /var/lib/tomcat7/logs/catalina.out
# 或者
CMD service tomcat7 start && tail -f /var/lib/tomcat7/logs/catalina.out

# 这样也有效:
ENTRYPOINT ["/usr/sbin/sshd"]
 CMD ["-D"]

错误解决

# 报错“tar (child): Error is not recoverable: exiting now”这类错误的时候
# 注意检查是否指定了WORKDIR

Docker 相关资源

常用docker命令,及一些坑:http://blog.csdn.net/wsscy2004/article/details/25878363
Docker使用Dockerfile构建镜像 :http://my.oschina.net/u/1861837/blog/649015
Docker学习总结之Run命令介绍:http://www.cnblogs.com/vikings-blog/p/4238062.html
Docker学习笔记之二,基于Dockerfile搭建JAVA Tomcat运行环境:http://www.blogjava.net/yongboy/archive/2013/12/16/407643.html
Dockerfile reference:https://docs.docker.com/engine/reference/builder/
Docker — 从入门到实践(非常不错):https://yeasy.gitbooks.io/docker_practice/content/

后期更新问题

后期持续性的更新确实是个头疼的问题,不知道有没有类似github pages那种同步的功能会不会出现...

167 docker docker构建nginx容器系列问题 docker registry docker run docker toolbo

167 docker docker构建nginx容器系列问题 docker registry docker run docker toolbo

docker构建nginx容器系列问题


background : 最近为小伙伴们筹划docker系列的技术分享,研究了一会docker相关技术, 在此记录一下构建nginx容器时候的坑

1.nginx服务器根目录问题

docker 官方镜像提供的nginx基于debian/jessie平台,其文件结构和ubuntu中的nginx中并不相同

eg:

run一个niginx容器

<span>//80端口被占用,so...</span>
$ sudo docker run <span>-it</span><span>-p</span><span>800</span>:<span>800</span> nginx
$ sudo docker ps 

CONTAINER ID        IMAGE               COMMAND                  CREATED             STATUS              PORTS                                   NAMES
<span>1801</span>a32aab54        nginx               <span>"nginx -g ''daemon off"</span><span>2</span> minutes ago       Up <span>2</span> minutes        <span>80</span>/tcp, <span>443</span>/tcp, <span>0.0</span><span>.0</span><span>.0</span>:<span>800</span><span>-&gt;</span><span>800</span>/tcp   berserk_kare
登录后复制

进入容器内部

<span>$ </span>sudo docker exec -it <span>1801</span>a32aab54 /bin/bash
root<span>@1801a32aab54</span><span>:/</span><span># </span>
登录后复制

查看nginx目录

<span># cd /etc/nginx/</span>
conf<span>.d</span>/         koi-utf         mime<span>.types</span>      nginx<span>.conf</span>      uwsgi_params    
fastcgi_params  koi-win         modules/        scgi_params     win-utf  
登录后复制

可以看到不仅没有熟悉的 /sites-available,也没有 /sites-enabled

继续查看nginx配置

<span># cat /conf.d/default.conf</span><span>server</span> {
    listen       <span>80</span>;
    server_name  localhost;

    <span>#charset koi8-r;</span><span>#access_log  /var/log/nginx/log/host.access.log  main;</span>    location / {
        root   /usr/share/nginx/html;
        <span>index</span><span>index</span>.html <span>index</span>.htm;
    }

    <span>#error_page  404              /404.html;</span><span># redirect server error pages to the static page /50x.html</span><span>#</span>
    error_page   <span>500</span><span>502</span><span>503</span><span>504</span>  /<span>50</span>x.html;
    location = /<span>50</span>x.html {
        root   /usr/share/nginx/html;
    }
    <span>#...省略php-fpm配置,好长..</span>
}
登录后复制

根目录配置: root /usr/share/nginx/html;

测试

<span># cd /usr/share/nginx/html</span><span># touch index.html</span><span># echo "test nginx in docker" &gt;index.html</span>
登录后复制

php-fpm配置相关

'').addClass(''pre-numbering'').hide(); $(this).addClass(''has-numbering'').parent().append($numbering); for (i = 1; i '').text(i)); }; $numbering.fadeIn(1700); }); });

以上就介绍了167 docker docker构建nginx容器系列问题,包括了docker,nginx方面的内容,希望对PHP教程有兴趣的朋友有所帮助。

CentOS 7 安装 Docker-machine 及日常使用

CentOS 7 安装 Docker-machine 及日常使用

CentOS 7.6.1810 安装 Docker-machine 0.16.0 

其它系统安装说明请访问:官方文档

Centos 7 系统请使用如下代码:

$ base=https://github.com/docker/machine/releases/download/v0.16.0 &&
  curl -L $base/docker-machine-$(uname -s)-$(uname -m) >/tmp/docker-machine &&
chmod +x /tmp/docker-machine && sudo install /tmp/docker-machine /usr/bin/docker-machine

Check the installation by displaying the Machine version:

$ docker-machine version
docker-machine version 0.16.0, build 9371605

下载 completion script:docker-machine-prompt.bash      docker-machine-wrapper.bash    docker-machine.bash 将其放在 /etc/bash_completion.d 目录下

bash 文件下载地址

编辑 /root/.bashrc 文件如下

vim /root/.bashrc
PS1=''[\u@\h \W$(__docker_machine_ps1)]\$ ''

若出现如下错误

请在 /root/.bashrc 添加如下代码

source /etc/bash_completion.d/docker-machine-wrapper.bash
source /etc/bash_completion.d/docker-machine-prompt.bash
source /etc/bash_completion.d/docker-machine.bash

 

并重新 source 下 bashrc

source /root/.bashrc

安装完成。

通过 docker-machine 在其它 host 创建 docker,创建 machine 要求能够无密码登录远程主机,所以需要先通过如下命令将 ssh key 拷贝到 192.168.1.206. 可查 官方文档

ssh-keygen                         #生成密钥,生成位置/root/.ssh/

ssh-copy-id root@192.168.1.206       #复制公钥至远程目标
ssh 192.168.1.206		              #远程目标

vim /etc/ssh/sshd.config       #配置远程主机

PubkeyAuthentication yes                #打开此行注释

service sshd restart       #重启ssh服务
setenfoce 0                #官方并没有提示关闭远程主机的selinux,但是我关闭了
systemctl stop firewalld         #关闭远程主机的防火墙
systemctl disable firewalld       #禁止开机启动

一切准备就绪,执行 docker-machine create 命令创建 docker (此处为计算机名,可以是 elk,zabbix,mysql 等有意义的名字)

docker-machine create -d generic --generic-ip-address=192.168.1.234 --generic-ssh-key ~/.ssh/id_rsa --generic-ssh-user=root docker  #虚机使用此行
# docker-machine create --driver generic --generic-ip-address=192.168.1.206 elk  #cloudman ubuntu16.0.4使用

执行 docker-machine ls查看安装完成的docker

docker-machine ls

  

远程到目标主机并查看 docker daemon 的具体配置

 

vim /etc/systemd/system/docker.service.d/10-machine.conf      #针对centos 7.6.1810
# vim  /etc/systemd/system/docker.service              #针对ubuntu 16.0.4

  1. -H tcp://0.0.0.0:2376 使 docker daemon 接受远程连接。

  2. --tls* 对远程连接启用安全认证和加密。

查看远程主机 docker 的 env 环境

docker-machine env docker

eval $(docker-machine env docker)   #通过docker-machine管理192.168.1.234上的docker

看到命令行提示符已经变了,其原因是我们之前在 $HOME/.bashrc 中配置了 PS1=''[\u@\h \W$(__docker_machine_ps1)]\$ '',用于显示当前 docker host。

eval $(docker-machine env zabbix)            #切换到 zabbix
docker-machine upgrade docker zabbix          #批量执行更新 machine 的 docker 到最新版本
docker-machine config docker               #查看machine 的 docker daemon 配置

stop/start/restart 是对 machine 的操作系统操作,而 不是 stop/start/restart docker daemon

docker-machine scp docker:/tmp/a zabbix:/tmp/b    #在不同的host之间拷贝数据

以上是通过 docker-machine 远程其它主机安装 docker,及一些常用操作

 

下面是如何通过 docker-machinet 删除之前安装 docker. 官网文档 

Remove a machine. This removes the local reference and deletes it on the cloud provider or virtualization management platform.

$ docker-machine rm --help

Usage: docker-machine rm [OPTIONS] [arg...]

Remove a machine

Description:
   Argument(s) are one or more machine names.

Options:

   --force, -f    Remove local configuration even if machine cannot be removed, also implies an automatic yes (`-y`)
   -y        Assumes automatic yes to proceed with remove, without prompting further user confirmation

Examples

$ docker-machine ls
NAME   ACTIVE   URL          STATE     URL                         SWARM   DOCKER   ERRORS
bar    -        virtualbox   Running   tcp://192.168.99.101:2376           v1.9.1
baz    -        virtualbox   Running   tcp://192.168.99.103:2376           v1.9.1
foo    -        virtualbox   Running   tcp://192.168.99.100:2376           v1.9.1
qix    -        virtualbox   Running   tcp://192.168.99.102:2376           v1.9.1


$ docker-machine rm baz
About to remove baz
Are you sure? (y/n): y
Successfully removed baz


$ docker-machine ls
NAME   ACTIVE   URL          STATE     URL                         SWARM   DOCKER   ERRORS
bar    -        virtualbox   Running   tcp://192.168.99.101:2376           v1.9.1
foo    -        virtualbox   Running   tcp://192.168.99.100:2376           v1.9.1
qix    -        virtualbox   Running   tcp://192.168.99.102:2376           v1.9.1


$ docker-machine rm bar qix
About to remove bar, qix
Are you sure? (y/n): y
Successfully removed bar
Successfully removed qix


$ docker-machine ls
NAME   ACTIVE   URL          STATE     URL                         SWARM   DOCKER   ERRORS
foo    -        virtualbox   Running   tcp://192.168.99.100:2376           v1.9.1

$ docker-machine rm -y foo
About to remove foo
Successfully removed foo 

Docker in Docker(实际上是 Docker outside Docker): /var/run/docker.sock

Docker in Docker(实际上是 Docker outside Docker): /var/run/docker.sock

在 Docker 容器里面使用 docker run/docker build

Docker 容器技术目前是微服务/持续集成/持续交付领域的第一选择。而在 DevOps 中,我们需要将各种后端/前端的测试/构建环境打包成 Docker 镜像,然后在需要的时候,Jenkins 会使用这些镜像启动容器以执行 Jenkins 任务。

为了方便维护,我们的 CI 系统如 Jenkins,也会使用 Docker 方式部署。 Jenkins 任务中有些任务需要将微服务构建成 Docker 镜像,然后推送到 Harbor 私有仓库中。 或者我们所有的 Jenkins Master 镜像和 Jenkins Slave 镜像本身都不包含任何额外的构建环境,执行任务时都需要启动包含对应环境的镜像来执行任务。

我们的 Jenkins Master、Jenkins Slaves 都是跑在容器里面的,该如何在这些容器里面调用 docker run 命令启动包含 CI 环境的镜像呢? 在这些 CI 镜像里面,我们从源码编译完成后,又如何通过 docker build 将编译结果打包成 Docker 镜像,然后推送到内网仓库呢?

答案下面揭晓。

一、原理说明:/var/run/docker.sock

Docker 采取的是 Client/Server 架构,我们常用的 docker xxx 命令工具,只是 docker 的 client,我们通过该命令行执行命令时,实际上是在通过 client 与 docker engine 通信。

我们通过 apt/yum 安装 docker-ce 时,会自动生成一个 systemd 的 service,所以安装完成后,需要通过 sudo systemctl enable docker.service 来启用该服务。 这个 Docker 服务启动的,就是 docker engine,查看 /usr/lib/systemd/system/docker.service,能看到有这样一条语句:

ExecStart=/usr/bin/dockerd -H fd:// --containerd=/run/containerd/containerd.sock

默认情况下,Docker守护进程会生成一个 socket(/var/run/docker.sock)文件来进行本地进程通信,因此只能在本地使用 docker 客户端或者使用 Docker API 进行操作。 sock 文件是 UNIX 域套接字,它可以通过文件系统(而非网络地址)进行寻址和访问。

因此只要以数据卷的形式将 docker 客户端和上述 socket 套接字挂载到容器内部,就能实现 "Docker in Docker",在容器内使用 docker 命令了。具体的命令见后面的「示例」部分。

要记住的是,真正执行我们的 docker 命令的是 docker engine,而这个 engine 跑在宿主机上。所以这并不是真正的 "Docker in Docker".

二、示例

在容器内部使用宿主机的 docker,方法有二:

  1. 命令行方式:将 /usr/bin/docker 映射进容器内部,然后直接在容器内部使用这个命令行工具 docker
    • 需要的时候,也可以将 /etc/docker 文件夹映射到容器内,这样容器内的 docker 命令行工具也会使用与宿主机同样的配置。
  2. 编程方式:在容器内部以编程的方式使用 docker
    • 通过 python 使用 docker: 在 Dockerfile 中通过 pip install docker 将 docker client 安装到镜像中来使用

容器的启动方式也有两种,如下:

1. 直接通过 docker 命令启动

示例命令如下:

docker run --name <name> \
    -v /var/run/docker.sock:/var/run/docker.sock \
    -v /usr/bin/docker:/usr/bin/docker \
    --user root \
    <image-name>:<tag>

**必须以 root 用户启动!(或者其他有权限读写 /var/run/docker.sock 的用户)**然后,在容器内就能正常使用 docker 命令,或者访问宿主机的 docker api 了。

2. 使用 docker-compose 启动

docker-compose.yml 文件内容如下:

version: ''3.3''
services:
  jenkins-master:
    image: jenkinsci/blueocean:latest
    container_name: jenkins-master
    environment:
      - TZ=Asia/Shanghai  # 时区
    ports:
      - "8080:8080"
      - "50000:50000"
    volumes:
      - ./jenkins_home:/var/jenkins_home  # 将容器中的数据映射到宿主机
      - /usr/bin/docker:/usr/bin/docker  # 为容器内部提供 docker 命令行工具(这个随意)
      - /var/run/docker.sock:/var/run/docker.sock  # 容器内部通过 unix socket 使用宿主机 docker engine
    user: root  # 必须确保容器以 root 用户启动!(这样它才有权限读写 docker.socket)
    restart: always

然后通过 docker-compose up -d 即可后台启动容器。

Docker 中的 uid 与 gid

通过上面的操作,我们在容器内执行 docker ps 时,还是很可能会遇到一个问题:权限问题

如果你容器的默认用户是 root,那么你不会遇到这个问题,因为 /var/run/docker.sock 的 onwer 就是 root.

但是一般来说,为了限制用户的权限,容器的默认用户一般都是 uid 和 gid 都是 1000 的普通用户。这样我们就没有权限访问 /var/run/docker.sock 了。

解决办法:

方法一(不一定有效):在构建镜像时,最后一层添加如下内容:

# docker 用户组的 id,通常都是 999
RUN groupadd -g 999 docker \
    && usermod -aG docker <your_user_name>

这样我们的默认用户,就能使用 docker 命令了。

P.S. 999 不一定是 docker 用户组,所以上述方法某些情况下可能失效。这时还是老老实实通过 docker run -u root 启动容器吧。(或者在 docker-compose.yml 中添加 user: root 属性)

参考

  • Docker in Docker - 王柏元

Docker windows 安装及问题处理

Docker windows 安装及问题处理

下载地址可以是 docker 官网或者阿里的镜像地址,在 runoob 中可以找到。

安装过程不在赘述,安装过程中需要安装虚拟机,会提示是否同意安装一个 “通用串行总线控制器”,同意并接受即可安装,否则安装之后的 toolbox 没有虚拟机是无法使用的,安装之后

打开这个窗口,新建一个自己的虚拟机,如未安装无法使用 toolbox quickstart,,安装完虚拟就启动看看是否有问题,这里发现的问题为 "0x00000000 指令引用的内存 0x00000000,该内存不能为 written"。就这个问题网上大神给出解答为系统有未注册的 dll 文件,必须注册所有 dll 文件,方法是在命令提示符下输入

for %1 in (%windir%\system32\*.dll) do regsvr32.exe /s %1

这里已经亲自尝试过,是好用的执行命令之后需要一会儿,等到全部执行完,在打开虚拟机就不会报错,toolbox quickstart 也能正常使用。

我们今天的关于Docker 日常使用及问题docker基本使用的分享就到这里,谢谢您的阅读,如果想了解更多关于167 docker docker构建nginx容器系列问题 docker registry docker run docker toolbo、CentOS 7 安装 Docker-machine 及日常使用、Docker in Docker(实际上是 Docker outside Docker): /var/run/docker.sock、Docker windows 安装及问题处理的相关信息,可以在本站进行搜索。

本文标签: