docker使用
1. docker初探
1.1 hello world
sudo docker run hello-world
运行hello world首先会看到Hello from Docker!
,然后得到以下提示:
hello-world流程To generate this message, Docker took the following steps:(docker按照下面的步骤,产生了这条消息)
- The Docker client contacted the Docker daemon.(Docker客户端联系Docker守护进程)
- The Docker daemon pulled the "hello-world" image from the Docker Hub.(amd64)(Docker守护进程从Docker仓库拉取“hello-world”镜像)
- The Docker daemon created a new container from that image which runs the executable that produces the output you are currently reading.(Docker守护进程通过拉取下来的镜像创建了一个容器,这个容器运行命令生成你读到的内容)
- The Docker daemon streamed that output to the Docker client, which sent it to your terminal.(Docker守护进程将生成的内容发送到Docker客户端,Docker客户端再将其发送到终端,即我们的屏幕)
1.2 Docker简介
一个按照docker模式构建的app,结构如下:
- Stack(堆栈层:服务的交互)
- Services(服务层:负责容器在生产中的行为方式)
- Container(应用层:容器即这个应用程序)
也可以使用别人构建好的app,就像运行一个hello-world一样。
1.3 Docker用法
1.3.1 搜索docker镜像
sudo docker search [镜像名]
或者去官网查:http://index.docker.io/
eg:
renz@renz-ubuntu:~$ sudo docker search tutorial
NAME DESCRIPTION STARS OFFICIAL AUTOMATED
learn/tutorial 36
georgeyord/reactjs-tutorial This is the backend of the React comment b... 5 [OK]
chris24walsh/flask-aws-tutorial Runs a simple flask webapp demo, with the ... 1 [OK]
...
1.3.2 下载docker镜像
sudo docker pull [选项] [Docker Registry地址]<仓库名>:<标签>
eg:
sudo docker pull learn/tutorial
1.3.3 在docker容器中运行指令
容器 进程 资源(文件系统、系统类库、shell环境)
sudo docker run learn/tutorial echo "hello world"
1.3.4 在容器中安装程序
sudo docker run learn/tutorial apt-get install -y ping
1.3.5 保存对容器的修改
sudo docker commit [ID号] learn/ping
使用docker ps -l
获取ID号
1.3.6 检查运行中的镜像
docker inspect [ID号]
1.3.7 简单用法的总结
## 查看Docker版本
docker --version
docker version
docker info
## 运行Docker镜像
docker run hello-world
## 查看Docker镜像
docker image ls
## 查看Docker容器(running, all, all in quiet mode)
docker container ls
docker container ls -all
docker container ls -a -q
1.4. Docker容器
了解了Docker的用法,我们可以试着制作一个app。不使用Docker的时候,我们需要事前准备app的环境,但是使用Docker,我们只需要找到已有的镜像(别人活着自己制作的包含了我们app所需要的运行时环境、配置等),拉取然后在上面制作自己的镜像就可以了。
这些镜像的定义可以通过Dockerfile
来设置
1.4.1 Dockerfile
创建一个新的文件夹,cd
到其中,然后创建一个名为Dockerfile的文件,内容如下:
# Use an official Python runtime as a parent image
FROM python:2.7-slim
# Set the working directory to /app
WORKDIR /app
# Copy the current directory contents into the container at /app
ADD . /app
# Install any needed packages specified in requirements.txt
RUN pip install --trusted-host pypi.python.org -r requirements.txt
# Make port 80 available to the world outside this container
EXPOSE 80
# Define environment variable
ENV NAME World
# Run app.py when the container launches
CMD ["python", "app.py"]
另外常见两个文件如下,放置在和Dockerfile同一个目录下。
requirements.txt
Flask
Redis
app.py
from flask import Flask
from redis import Redis, RedisError
import os
import socket
# Connect to Redis
redis = Redis(host="redis", db=0, socket_connect_timeout=2, socket_timeout=2)
app = Flask(__name__)
@app.route("/")
def hello():
try:
visits = redis.incr("counter")
except RedisError:
visits = "<i>cannot connect to Redis, counter disabled</i>"
html = "<h3>Hello {name}!</h3>" \
"<b>Hostname:</b> {hostname}<br/>" \
"<b>Visits:</b> {visits}"
return html.format(name=os.getenv("NAME", "world"), hostname=socket.gethostname(), visits=visits)
if __name__ == "__main__":
app.run(host='0.0.0.0', port=80)
pip install --trusted-host pypi.python.org -r requirements.txt
安装了Python要用到的Flask库和Redis库,应用程序打印环境变量NAME
和socker.gethostname()
的输出;由于我们仅安装了Python库而没有完整的安装Redis,所以会抛出异常(except RedisError)
1.4.2 构建app
确保你新建的文件夹里有三个文件:
- Dockerfile
- app.py
- requirements.txt
通过build命令创建一个新的镜像并为该镜像创建一个tag(即标签)
docker build -t friendlyhello .
通过docker image ls
查看你本地Docker镜像库。
1.4.3 运行app
使用-p
参数将本机的4000端口映射到容器中定义的80端口:
docker run -p 4000:80 friendlyhello
1.4.4 分享镜像
这里主要介绍将镜像上传到docker hub:cloud.docker.com
1.4.4.1 登录
docker login
登录进已有的账号
1.4.4.2 Tag the image
语法:
docker tag image username/repository:tag
eg.:
docker tag image renz2048/rzdost:part2
对了,你需要在cloud.docker.com里先创建你自己的repository(仓库)。
上传打过标签的镜像到仓库:
docker push username/repository:tag
hub-repository.PNG
可以看到目前我的rzdost里已经有我的part2镜像了
1.4.5 本节常用镜像
docker build -t friendlyhello . # Create image using this directory's Dockerfile
docker run -p 4000:80 friendlyhello # Run "friendlyname" mapping port 4000 to 80
docker run -d -p 4000:80 friendlyhello # Same thing, but in detached mode
docker container ls # List all running containers
docker container ls -a # List all containers, even those not running
docker container stop <hash> # Gracefully stop the specified container
docker container kill <hash> # Force shutdown of the specified container
docker container rm <hash> # Remove specified container from this machine
docker container rm $(docker container ls -a -q) # Remove all containers
docker image ls -a # List all images on this machine
docker image rm <image id> # Remove specified image from this machine
docker image rm $(docker image ls -a -q) # Remove all images from this machine
docker login # Log in this CLI session using your Docker credentials
docker tag <image> username/repository:tag # Tag <image> for upload to registry
docker push username/repository:tag # Upload tagged image to registry
docker run username/repository:tag # Run image from a registry
1.5 服务层
1.5.1 前提条件
- 安装Docker version 1.13或者更高
- 获得Docker Compose,linux版本下的安装参考5.2节
- 确保已经将制作好的镜像(例:friendlyhello)保存在docker hub中
- 确保你的镜像能够部署正常。运行以下命令来测试:
将参数替换成你自己的
docker run -p 80:80 username/repo:tag
然后访问http://localhost/(我在虚拟机中测试的,因此也可在主机访问虚拟机的IP)。
1.5.2 什么是服务
Services are really just “containers in production”
。一个服务只运行一个镜像,确定了该镜像的运行方式-使用哪个端口,容器需要运行多少个副本以便服务有足够的容量等等。
通过docker-compose.yml文件可以定义、运行一个服务:
version: "3"
services:
web:
# replace username/repo:tag with your name and image details
image: username/repo:tag
deploy:
replicas: 5
resources:
limits:
cpus: "0.1"
memory: 50M
restart_policy:
condition: on-failure
ports:
- "80:80"
networks:
- webnet
networks:
webnet:
(将文件中的username/repo:tag替换成你自己的参数)
这个.yml文件告诉docker做以下事情:
- 从远程仓库中取出上传的镜像(renz2048/rzdost:part2)
- 运行该镜像的5个实例作为一个名为web的服务,限制每个服务最多使用10%的CPU和50MB的RAM。
- 如果一个失败,立即重新启动容器
- 将主机上的80端口映射到web的端口80
- 指示web容器通过一个被称为webnet的负载均衡网络共享端口80
- 使用默认设置(这是一个负载平衡覆盖网络)定义webnet网络。
1.5.3 运行新的负载均衡app
设置app的名字为getstartedlab:
docker swarm init
docker stack deploy -c docker-compose.yml getstartedlab
获取service id:
docker service ls
通过docker stack rm
关闭应用程序:
docker stack rm getstartedlab
关闭群:
docker swarm leave --force
1.5.4 本节总结
docker stack ls # List stacks or apps
docker stack deploy -c <composefile> <appname> # Run the specified Compose file
docker service ls # List running services associated with an app
docker service ps <service> # List tasks associated with an app
docker inspect <task or container> # Inspect task or container
docker container ls -q # List container IDs
docker stack rm <appname> # Tear down an application
docker swarm leave --force # Take down a single node swarm from the manager
1.6 集群Swarms
2. 再探docker()
2.1 运行
以ubuntu docker registry为基础启动一个容器,启动其内的bash
并进行交互式操作:
root@ubuntu-14-dev:~# docker run -it --rm ubuntu bash
root@ae4bb548e9ea:/# cat /etc/os-release
NAME="Ubuntu"
VERSION="16.04.3 LTS (Xenial Xerus)"
ID=ubuntu
ID_LIKE=debian
PRETTY_NAME="Ubuntu 16.04.3 LTS"
VERSION_ID="16.04"
HOME_URL="http://www.ubuntu.com/"
SUPPORT_URL="http://help.ubuntu.com/"
BUG_REPORT_URL="http://bugs.launchpad.net/ubuntu/"
VERSION_CODENAME=xenial
UBUNTU_CODENAME=xenial
-
-it
:-i
交互式操作,-t
终端 -
--rm
: