Docker 快速入门,安装数据库 Dockerfile使用 制作ubuntu-flask镜像

开始

四、Docker 的三个基本概念

1.镜像(images):一个特殊的文件系统

操作系统分为内核空间和用户空间。对于 Linux 而言,内核启动后,会挂载 root 文件系统为其提供用户空间支持。而 Docker 镜像(Image),就相当于是一个 root 文件系统

Docker 镜像是一个特殊的文件系统,除了提供容器运行时所需的程序、库、资源、配置等文件外,还包含了一些为运行时准备的一些配置参数(如匿名卷、环境变量、用户等)

镜像不包含任何动态数据,其内容在构建之后也不会被改变。

Docker 设计时,就充分利用 Union FS 的技术,将其设计为分层存储的架构。 镜像实际是由多层文件系统联合组成。

镜像构建时,会一层层构建,前一层是后一层的基础。每一层构建完就不会再发生改变,后一层上的任何改变只发生在自己这一层。

比如,删除前一层文件的操作,实际不是真的删除前一层的文件,而是仅在当前层标记为该文件已删除。

在最终容器运行的时候,虽然不会看到这个文件,但是实际上该文件会一直跟随镜像。(这点非常类似Git,每次commit都会仅仅修改本次的提交,不会修改之前的commit)

因此,在构建镜像的时候,需要额外小心,每一层尽量只包含该层需要添加的东西,任何额外的东西应该在该层构建结束前清理掉。

分层存储的特征还使得镜像的复用、定制变的更为容易。甚至可以用之前构建好的镜像作为基础层,然后进一步添加新的层,以定制自己所需的内容,构建新的镜像。

2. 容器:镜像运行时的实体

镜像(Image)和容器(Container)的关系,就像是面向对象程序设计中的类和实例一样,镜像是静态的,容器是动态的

容器可以被创建、启动、停止、删除、暂停等

容器的实质是进程,但与直接在宿主执行的进程不同,容器进程运行于属于自己的独立的命名空间。前面讲过镜像使用的是分层存储,容器也是如此。

容器存储层的生存周期和容器一样,容器消亡时,容器存储层也随之消亡。因此,任何保存于容器存储层的信息都会随容器删除而丢失(用大白话描述:容器运行过程中存储的数据,在容器停止时就没有了)

按照 Docker官方的建议,容器不应该向其存储层内写入任何数据 ,容器存储层要保持无状态化。

所有的文件写入操作,都应该使用数据卷(Volume)、或者绑定宿主目录,在这些位置的读写会跳过容器存储层,直接对宿主(或网络存储)发生读写,其性能和稳定性更高。

数据卷的生存周期独立于容器,容器消亡,数据卷不会消亡。因此, 使用数据卷后,容器可以随意删除、重新 run,数据却不会丢失。

3. 仓库:存放镜像文件的地方

仓库:

镜像构建完成后,可以很容易的在当前宿主上运行,但是, 如果需要在其他服务器上使用这个镜像,我们就需要一个集中的存储、分发镜像的服务,Docker Registry 就是这样的服务。

一个 Docker Registry 中可以包含多个仓库(Repository);每个仓库可以包含多个标签(Tag);每个标签对应一个镜像。

所以说,仓库是 Docker 用来集中存放镜像文件的地方,类似于我们之前常用的代码仓库。

Docker Registry 是开放给用户使用、允许用户管理镜像的 Registry 服务。一般这类公开允许用户免费上传、下载公开的镜像,并可能提供收费服务供用户管理私有镜像。

最常使用的 Registry 公开服务是官方的Docker Hub ,这也是默认的 Registry,并拥有大量的高质量的官方镜像,网址为:hub.docker.com

在国内访问 Docker Hub 可能会比较慢,国内也有一些云服务商提供类似于 Docker Hub 的公开服务。

除了使用公开服务外,用户还可以在本地搭建私有 Docker Registry 。Docker 官方提供了 Docker Registry 镜像,可以直接使用做为私有 Registry 服务。

开源的 Docker Registry 镜像只提供了 Docker Registry API 的服务端实现,足以支持 Docker 命令,不影响使用。但不包含图形界面,以及镜像维护、用户管理、访问控制等高级功能。

版本:

通常,一个仓库会包含同一个软件不同版本的镜像,而标签就常用于对应该软件的各个版本

我们可以通过<仓库名>:<标签>的格式来指定具体是这个软件哪个版本的镜像。如果不给出标签,将以latest 作为默认标签。

4. 一句话总结

镜像:已经打包好的 Docker 应用,有点类似于一个程序的安装包。

镜像仓库:存储镜像的服务器

容器:有了镜像我们就可以创建容器了,容器就是运行着的镜像,一个镜像可以同时创建多个容器,容器之间的隔离的。

下载Docker Desktop

Download Docker Desktop | Docker

linux

sudo apt update 
sudo apt install apt-transport-https ca-certificates curl gnupg-agent software-properties-common -y 

sudo apt-get remove docker docker.io containerd runc -y 

curl -fsSL https://download.docker.com/linux/ubuntu/gpg | sudo apt-key add - 

sudo add-apt-repository "deb [arch=amd64] https://download.docker.com/linux/ubuntu $(lsb_release -cs) stable" 

sudo apt update 
sudo apt install docker-ce docker-ce-cli containerd.io -y

Docker 配置加速器

Linux 用户配置加速器
针对安装了 Docker 的 Linux 用户,您可以参考以下配置步骤:

修改 /etc/docker/daemon.json 文件并添加上 registry-mirrors 键值

{
    "registry-mirrors": ["https://registry.docker-cn.com"]
}

win10

对于使用 Windows 10 的用户,在任务栏托盘 Docker 图标内右键菜单选择 Settings,打开配置窗口后在左侧导航菜单选择 Docker Engine,在右侧像下边一样编辑 json 文件,之后点击 Apply & Restart 保存后 Docker 就会重启并应用配置的镜像地址了。

{
  "registry-mirrors": [
    "https://hub-mirror.c.163.com",
    "https://mirror.baidubce.com"
  ]
}

验证docker是否正常工作


1. 打开终端
2. 输入命令

docker run hello-world

docker run -it ubuntu bash

-it:交互模式:在窗口中运行Ubuntu这个容器,运行bash软件

一个容器适合运行单一程序

使用Docker

一、运行终端
打开终端,输入docker images ,如果运行正常,表示docker已经可以在本电脑上使用了

image-20191118102525668

二、docker常用命令

指令说明
docker images查看已下载的镜像
docker rmi 镜像id删除已下载的镜像 rm 镜像名称:标签名
docker search 镜像从官方仓库(hub.docker.com)查找镜像
docker pull 镜像名称:标签名标签名默认是 latest,代表最新版本。
docker run创建容器
docker ps列出运行中的容器(运行中)process status
docker ps -a列出所有的容器(运行、未运行)
docker rm 容器名称删除停止的容器
docker rm -f 容器名称删除运行中的容器
docker start 容器名称启动容器
docker stop 容器名称停止容器
docker restart 容器名称重启容器
docker exec执行容器中的指令


如果在使用过程中有疑惑的地方,可以使用帮助文档查看

Docker 运行MySql

1. 拉取MySql镜像
 

docker pull mysql:5.5

 下载完成后,我们就可以在本地镜像列表里看到名为 mysql ,标签为5.5的镜像

2. 使用MySql镜像
运行容器

docker run -d --name=mysql -p 3306:3306 -e MYSQL_ROOT_PASSWORD=123456 mysql:5.5

命令说明:

--name=mysql:为容器指定一个名称为mysql
-p 3306:3306:将容器的(后面的3306) 3306 端口映射到主机的(前面的3306) 3306端口。
-d:后台运行容器,并返回容器ID。
-e MYSQL_ROOT_PASSWORD=123456:初始化 root 用户的密码为123456。
mysql:5.5 要使用的镜像的名称
注意:

如果本地已经使用了3306端口,那么可以容器的3306端口映射到本机端口的3307或者其他的

docker run -d --name=mysql -p 3307:3306 -e MYSQL_ROOT_PASSWORD=123456 mysql:5.5

运行效果:

 3. 连接数据库

docker run -it -p 12345:3306 -e MYSQL_ROOT_PASSWORD=root mysql:5.5
虚拟机输入  ipconfig,第一个 IPv4 地址 是本地虚拟机的ip地址
192.168.50.129

Docker常用命令说明

4.1 Docker pull 命令

docker pull : 从镜像仓库中拉取或者更新指定镜像

语法

docker pull [OPTIONS] NAME[:TAG|@DIGEST]

OPTIONS说明:

-a :拉取所有 tagged 镜像

实例

  • 从Docker Hub下载MySql 8.0.1版镜像

      docker pull mysql:8.0.1
    
  • 从Docker Hub下载REPOSITORY为mysql的所有版本的镜像

      docker pull -a mysql

4.2 Docker images 命令

docker images : 列出本地镜像

语法

docker images [OPTIONS] [REPOSITORY[:TAG]]

OPTIONS说明:

  • -a :列出本地所有的镜像(含中间映像层,默认情况下,过滤掉中间映像层)
  • --digests :显示镜像的摘要信息
  • -f :显示满足条件的镜像
  • --format :指定返回值的模板文件
  • --no-trunc :显示完整的镜像信息
  • -q :只显示镜像ID

实例

  • 查看本地所有镜像列表

      docker images
    

  • 列出本地镜像中镜像名为ubuntu的镜像列表

      docker images  ubuntu

4.3 Docker tag 命令

docker tag : 标记本地镜像,将其归入某一仓库

语法

docker tag [OPTIONS] IMAGE[:TAG] [REGISTRYHOST/][USERNAME/]NAME[:TAG]

实例

将镜像registry.cn-hangzhou.aliyuncs.com/xavier/laravel标记为test/laravel:latest镜像

docker tag registry.cn-hangzhou.aliyuncs.com/xavier/laravel test/laravel
docker images  laravel

4.4 Docker rmi 命令

docker rmi : 删除本地一个或多个镜像

语法

docker rmi [OPTIONS] IMAGE [IMAGE...]

OPTIONS说明:

  • -f :强制删除;
  • --no-prune :不移除该镜像的过程镜像,默认移除;

什么是过程镜像:在构建新镜像的过程中产生的镜像或者依赖的镜像

实例

强制删除本地镜像mysql:5.5

docker rmi -f mysql:5.5 mysql:5.6

什么时候需要用强制删除呢?在你普通删除删不掉的时候

4.5 Docker run 命令

docker run :创建一个新的容器并运行一个命令

语法

docker run --name 容器名称 -d -p 主机端口:容器内端口 -e 环境变量 --link 其它容器名:容器中别名 镜像名称:标签名

OPTIONS说明:

  • -d: 后台运行容器,并返回容器ID;
  • -i: 以交互模式运行容器,通常与 -t 同时使用;
  • -t: 为容器重新分配一个伪输入终端,通常与 -i 同时使用;
  • --name="nginx-lb": 为容器指定一个名称;(给容器起名)
  • -e username="ritchie": 设置环境变量;
  • -m :设置容器使用内存最大值;
  • --link=[]: 添加链接到另一个容器;当要访问其它容器中的内容时,需要先链接才可以使用
  • -p: 开放一个端口或一组端口(绑定端口:电脑端口:容器端口)

实例

使用docker镜像nginx:latest以后台模式启动一个容器,并将容器命名为wuxidixi。且映射容器80端口到主机8000端口

docker run --name=wuxidixi -d  -p 80:80 nginx:latest

4.6 Docker start/stop/restart 命令

docker start :启动一个或多少已经被停止的容器

docker stop :停止一个运行中的容器

docker restart :重启容器

语法

docker start CONTAINER 
docker stop CONTAINER 
docker restart CONTAINER 

实例

停止运行中的容器

docker stop 容器id

启动已被停止的容器mysql

docker start 容器id

重启容器yigubigu

docker restart 容器id

docker  ps -a 所有容器
docker start 容器id
docker start -i 容器id (以交互模式运行)

4.7 Docker rm 命令

docker rm :删除一个或多个容器

语法

docker rm [OPTIONS] CONTAINER [CONTAINER...]

OPTIONS说明:

  • -f :通过SIGKILL信号强制删除一个运行中的容器
  • -l :移除容器间的网络连接,而非容器本身
  • -v :-v 删除与容器关联的卷

实例

s强制删除容器mysql

docker rm -f mysql

移除容器yigubigu对容器mysql的连接,连接名mysql

docker rm -l mysql

删除多个容器时,用空格隔开

删除容器nginx01,并删除容器挂载的数据卷

docker rm -v nginx01
docker ps // 查看所有正在运行容器
docker stop containerId // containerId 是容器的ID

docker ps -a // 查看所有容器
docker ps -a -q // 查看所有容器ID

docker stop $(docker ps -a -q) //  stop停止所有容器
 docker rm  $(docker ps -a -q)  删除所有停止的容器
docker  rm $(docker ps -a -q) //   remove删除所有容器

docker exec :运行一个容器,并运行这个容器其他命令

Docker exec命令用于在运行的Docker容器中执行命令。以下是一些常见的使用例子:

  1. 运行bash shell:

docker exec -it container_id /bin/bash

这个命令会在指定的容器中启动一个新的bash shell,允许你在容器内部进行交互操作。

  1. 查看容器中的环境变量:

docker exec container_id env

这个命令会列出在容器中定义的所有环境变。

  1. 查看容器中的文件:

docker exec container_id ls /path/to/directory

这个命令会列出容器中指定目录下的所有文件。

  1. 在容器中运行一个Python脚本:

docker exec container_id python /path/to/script.py

这个命令会在容器中运行指定的Python脚本。

  1. 在容器中安装软件:

docker exec container_id apt-get install -y package_name

这个命令会在容器中安装指定的软件包。

注意:在使用docker exec命令时,你需要确保目标容器正在运行。如果容器没有运行,你可以使用docker start命令来启动它。

总结

docker images----->查看本地所有的镜像
docker run镜像名字:版本  ---->创建一个容器且运行
-it--->交互模式
docker run -it 镜像名字:版本 ---->创建一个容器且运行默认的启动的程序
docker run -it 镜像名字:版本 [命令]  ---->创建一个容器且运行的是[命令]命令程序,而不是默认启动的程序
docker run-it ubuntu bash  --->创建一个容器且运行bash而不是默认启动的程序,注意bash是Ubuntu镜像中自带的而不是docker的
docker pull  镜像名字:版本  ---->下载一个镜像
docker pull  镜像名  ---->下载最新版
docker ps  查看正在运行的容器
docker ps -a 查看所有的容器

docker stop 容器的id  ---->停止一个容器的运行(并没有删除,仅仅是停止运行)
docker start 容器的id  ---->将一个已经停止运行的容器再次运行起来
docker start -i 容器的id  ---->在将一个停止的容器运行起来的同时,指定交互模式

docker rm 容器的id  ---->删除已经停止运行的容器
docker rm $(docker ps -a -q)  --->删除所有停止运行的容器(慎用)
docker rm -f 容器的id  ---->强制删除容器(无论是否停止运行)
docker rmi 镜像的id  --->删除镜像的id(注意,如果这个镜像被被的容器正在使用包括停止运行的容器,那么此时先删除容器,再删除镜像)
docker search 名字  ---->搜索匹配的镜像(https://hub.docker.com)中搜索

docker exec 容器的id 容器中的命令(存在的程序)  ---->能够让正在运行中的容器,可以运行一个新的程序(命令)
docker run -d --name=mysql -p 3308:3306 -e MYSQL_ROOT_PASSWORD=123456 mysql:5.5
解释:
-d :后台运行,什么也看不见
--name : 给容器设置名字(如果重复的话就失败)
-p xxx:yyy  xxx是操作系统的端口 yyy是容器中用到的端口,作用是:将本机的XXX端口与容器中的yyy端口做映射
-e :environment的意思,就是给容器设置环境变量。用它可以将参数传递给容器

安装redis、MongoDB

redis图形化工具 AnotherRedisDesktopManager

GitHub - qishibo/AnotherRedisDesktopManager:

安装redis:

docker run -d --name redis-test -p 6379:6379 redis

安装MongoDB

docker run --name mongo-test -d -p 27017:27017 mongo

通过Docker安装MongoDB - 墨天轮

挂载硬盘


问题一

数据是保存在容器里的,如果容器删除了数据也就删除了

问题二

每次要修改容器时,必须要进入到容器中去修改,比如要修改my.cnf

为了能够保存(持久化)数据以及共享容器间的数据,Docker 提出了 Volume 的概念

可以使用 -v 这个参数,将容器中的一个目录或者文件 和主机上的目录和文件进行绑定,绑定之后,修改主机上的这个文件就相当于修改了容器中的文件,删除容器之后,绑定的目录和文件还在主机(不会被删除)

为了实现主机和容器之间的数据共享,我们可以在创建容器时添加 -v 参数:

docker run ... -v 主机目录:容器中的目录 ...
demo1
1.创建一个新容器,且设置共享路径

注意:创建时镜像名字放在最后

image-20191118145724861

2.真实电脑创建文件、文件夹,容器看到共享成功 image-20191118145907498

3.容器修改文件内容,真实电脑看到共享数据成功 image-20191118150045558

demo2
目的:重启docker容器看数据能否再次使用

1.退出容器

image-20191118150252608

2.修改真实电脑文件数据 image-20191118150310750

3.再次运行容器 image-20191118150402536

4.查看容器是否看到共享数据,结果成功 image-20191118150450264

demo3
目的:删除容器之后共享文件(夹)是否会丢失

1.退出、删除容器

image-20191118150653079

2.查看真实电脑文件依然在 image-20191118150711531

复制文件


我们可以使用 docker cp 指令向容器中复制文件,或者从容器中复制文件到主机

docker cp 源目录  目标目录
1.创建一个新的容器

image-20191118151011166

2.查看真实电脑路径下无文件(夹)

image-201911181511116533.从容器复制文件到真实电脑

image-20191118151226228

4.从真正电脑复制文件夹到容器

镜像制作与使用

有时,我们在一个容器中安装了需要的软件或者进行了较为复杂的配置,此时能否把这个容器制作成一个镜像呢?

答案:可以

这样我们就可以将这个镜像进行分享,从而让其他的开发者也直接可以使用

制作Ubuntu的镜像

基本的镜像->容器->在这个容器中安装你需要的软件->通过手段做成一个新镜像->传到仓库->别人可以从仓库中下载这个新的镜像->可以创建容器

1.使用commit制作镜像

1.下载一个需要的基本镜像
docker pull ubuntu:16.04
2.创建一个容器
docker run -it ubuntu:16.04
3,在容器中安装、配置满足你的需求
如果想要安装vi(编辑器),那么就得需要apt install vi,想要用apt
install 快速的安装软件的话,那么就得需要修改/etc/apt/sources.List文件
那么怎么改这个文件呢?

查看sources.list文件:cat /etc/apt/sources.list
3.1 在自己的电脑上编辑一个文件sources.list,然后写入新的更新源地址
3.2 通过docker cp sources.list 容器id:/home  将sources.List复制到容器中
3.3 在容器中将/home下的sources.List替换到/etc/apt下的sources.list文件

cd /home

cp sources.list /etc/apt/

3.4让更新源生效apt update
3.5安装vim
apt install vim

vim /etc/apt/sources.list

 我们可以直接使用 docker commit 指令将一个容器制作成一个镜像:

docker commit 容器名称 镜像名称:标签

docker commit -m "更新源清华,安装了vim编辑器" 40ffe8201 ubuntu_gai:1.0

上传镜像

4.将容器打包为镜像
docker commit-m"备注"容器的id镜像的名字:版本
5.上传
5.1先在https://hub.docker.com注册&登录
5.2在终端中docker login登录
5.3通过tag打标签
docker tag 镜像名:版本用户名/镜像名:版本
5.4推送到仓库
docker push用户名/镜像名:版本


制作好镜像之后,我们就可以把镜像上传到 docker 的仓库中

docker 的官方网站为注册用户提供了一个 docker 仓库,我们可以把我们自己的镜像放到 docker 官方的仓库上

一、注册账号
首先需要到 docker 官方网站上注册一个账号(如果注册不了,那么请自行百度科学上网)
二、登录
注册成功之后就可以登录,登录之后可以进入自己的仓库中

三、上传镜像
先在本地登录
执行以下指令进行登录(需要输入账号、密码)也可以用token登录:

docker login

打标签
登录成功之后,还需要为要上传的镜像打一个标签,注意这个标签必须要以 账号/ 开头:

docker tag 本地镜像:标签   账号/镜像名称:标签

比如,我的账号是 dong4716138 ,现在我要将本地的my_nginx:1.0上传到仓库中,那么首先我们对这个镜像打标签:

docker tag my_nginx:1.0 dong4716138/my_nginx:1.0
docker tag ubuntu_gai:1.0 qcbaskqenynotj/ubuntu_gai:1.0

上传
打完标签之后,我们就可以上传了:

docker push 账号/镜像:标签

docker push qcbaskqenynotj/ubuntu_gai:1.0

如:
docker push dong4716138/my_nginx:1.0

这个指令会将镜像上传到 my_nginx 这个仓库中

搜索是否可以下载指定版本的镜像

2.使用 Dockerfile 定制镜像(推荐)

1.找一个新的文件夹(这样的目的是:保证这个文件夹中是空的,如果不是空文件夹,那么在构建新的镜像时,会将这些没用的文件也上传打包到docker引擎中用)
2.创建一个新的文件Dockerfile
3.编辑Dockerfile文件
#检查本地是否有nginx:latest版本,如果有则创建容器,如果没有则先下载
FROM nginx
#在这个容器中运行-次命令,echo,.,是将index,html文件进行修改为<h1>Hello,Docker!</hl>
RUN echo,'sh1>Hello,Docker!</h1>'>/usr/share/nginx/html/index.html
#当上述的RUN命令执行完之后,docker会立刻进行打包为一个镜像(层)
4.用命令构建
docker build -t 新镜像名:版本

一、引入
从刚才的 docker commit 的学习中,我们可以了解到,镜像的定制实际上就是定制每一层所添加的配置、文件。如果我们可以把每一层修改、安装、构建、操作的命令都写入一个脚本,用这个脚本来构建、定制镜像,那么之前提及的无法重复的问题、镜像构建透明性的问题、体积的问题就都会解决。

这个脚本就是 Dockerfile

二、什么是Dockerfile
Dockerfile 是一个文本文件,其内包含了一条条的 **指令(Instruction)**,每一条指令构建一层,因此每一条指令的内容,就是描述该层应当如何构建。

下载nginx镜像

docker pull nignx

创建容器

docker run --rm -p 8002:80 nginx



说明:

--rm的作用是,当这个容器退出时,自动删除这个容器

使用浏览器访问8002端口 127.0.0.1:8002

四、使用Dockerfile
在一个空白目录中,建立一个文本文件,并命名为 Dockerfile:

$ mkdir my_nginx
$ cd my_nginx
$ touch Dockerfile
 

修改Dockerfile内容如下:

FROM nginx
RUN echo '<h1>Hello, Docker!</h1>' > /usr/share/nginx/html/index.html

#检查本地是否有nginx:latest版本,如果有则创建容器,如果没有则先下载
FROM nginx
#在这个容器中运行-一次命令,echo..,是将index.html文件进行修改为<h1>Hello,Docker!</h1>
RUN echo '<h1>Hello,Docker!</h1>'>/usr/share/nginx/html/index.html
#当上述的RUN命令执行完之后,docker会立刻进行打包为一个镜像(层)

> 覆盖 >>追加

docker run --rm -it -p 8002:80 nginx bash
echo '<h1>Hello, Docker!</h1>' > /usr/share/nginx/html/index.html
打开 127.0.0.1:8002

检查镜像的信息
docker inspect 镜像的名字:版本

Dockerfile参考手册

Dockerfile是一个包含用于组合映像的命令的文本文档。可以使用在命令行中调用任何命令。 Docker通过读取Dockerfile中的指令自动生成映像。

docker build命令用于从Dockerfile构建映像。可以在docker build命令中使用-f标志指向文件系统中任何位置的Dockerfile。

例:

docker build -f /path/to/a/Dockerfile

 

Dockerfile的基本结构

Dockerfile 一般分为四部分:基础镜像信息、维护者信息、镜像操作指令和容器启动时执行指令,’#’ 为 Dockerfile 中的注释。

Dockerfile文件说明

Docker以从上到下的顺序运行Dockerfile的指令。为了指定基本映像,第一条指令必须是FROM。一个声明以字符开头则被视为注释。可以在Docker文件中使用RUNCMDFROMEXPOSEENV等指令。

在这里列出了一些常用的指令。

FROM:指定基础镜像,必须为第一个命令

格式:
  FROM <image>
  FROM <image>:<tag>
  FROM <image>@<digest>
示例:
  FROM mysql:5.6
注:
  tag或digest是可选的,如果不使用这两个值时,会使用latest版本的基础镜像

MAINTAINER: 维护者信息

格式:
    MAINTAINER <name>
示例:
    MAINTAINER xxxxx
    MAINTAINER xxxxx@163.com
    MAINTAINER xxxxxx <xxxxxxx@163.com>

RUN:构建镜像时执行的命令

RUN用于在镜像容器中执行命令,其有以下两种命令执行方式:
shell执行
格式:
    RUN <command>
exec执行
格式:
    RUN ["executable", "param1", "param2"]
示例:
    RUN ["executable", "param1", "param2"]
    RUN apk update
    RUN ["/etc/execfile", "arg1", "arg1"]
注:
  RUN指令创建的中间镜像会被缓存,并会在下次构建中使用。如果不想使用这些缓存镜像,可以在构建时指定--no-cache参数,如:docker build --no-cache

ADD:将本地文件添加到容器中,tar类型文件会自动解压(网络压缩资源不会被解压),可以访问网络资源,类似wget

格式:
    ADD <src>... <dest>
    ADD ["<src>",... "<dest>"] 用于支持包含空格的路径
示例:
    ADD hom* /mydir/          # 添加所有以"hom"开头的文件
    ADD hom?.txt /mydir/      # ? 替代一个单字符,例如:"home.txt"
    ADD test relativeDir/     # 添加 "test" 到 `WORKDIR`/relativeDir/
    ADD test /absoluteDir/    # 添加 "test" 到 /absoluteDir/

COPY:功能类似ADD,但是是不会自动解压文件,也不能访问网络资源

CMD:构建容器后调用,也就是在容器启动时才进行调用。

格式:
    CMD ["executable","param1","param2"] (执行可执行文件,优先)
    CMD ["param1","param2"] (设置了ENTRYPOINT,则直接调用ENTRYPOINT添加参数)
    CMD command param1 param2 (执行shell内部命令)
示例:
    CMD echo "This is a test." | wc -
    CMD ["/usr/bin/wc","--help"]
注:
   CMD不同于RUN,CMD用于指定在容器启动时所要执行的命令,而RUN用于指定镜像构建时所要执行的命令。

ENV:设置环境变量

格式:
    ENV <key> <value>  #<key>之后的所有内容均会被视为其<value>的组成部分,因此,一次只能设置一个变量
    ENV <key>=<value> ...  #可以设置多个变量,每个变量为一个"<key>=<value>"的键值对,如果<key>中包含空格,可以使用\来进行转义,也可以通过""来进行标示;另外,反斜线也可以用于续行
示例:
    ENV myName John Doe
    ENV myDog Rex The Dog
    ENV myCat=fluffy

EXPOSE:指定于外界交互的端口

格式:
    EXPOSE <port> [<port>...]
示例:
    EXPOSE 80 443
    EXPOSE 8080
    EXPOSE 11211/tcp 11211/udp
注:
  EXPOSE并不会让容器的端口访问到主机。要使其可访问,需要在docker run运行容器时通过-p来发布这些端口,或通过-P参数来发布EXPOSE导出的所有端口

VOLUME:用于指定持久化目录

格式:
    VOLUME ["/path/to/dir"]
示例:
    VOLUME ["/data"]
    VOLUME ["/var/www", "/var/log/apache2", "/etc/apache2"]
注:
  一个卷可以存在于一个或多个容器的指定目录,该目录可以绕过联合文件系统,并具有以下功能:
1 卷可以容器间共享和重用
2 容器并不一定要和其它容器共享卷
3 修改卷后会立即生效
4 对卷的修改不会对镜像产生影响
5 卷会一直存在,直到没有任何容器在使用它

WORKDIR:工作目录,类似于cd命令

格式:
    WORKDIR /path/to/workdir
示例:
    WORKDIR /a  (这时工作目录为/a)
    WORKDIR b  (这时工作目录为/a/b)
    WORKDIR c  (这时工作目录为/a/b/c)
注:
  通过WORKDIR设置工作目录后,Dockerfile中其后的命令RUN、CMD、ENTRYPOINT、ADD、COPY等命令都会在该目录下执行。在使用docker run运行容器时,可以通过-w参数覆盖构建时所设置的工作目录。

**USER:**指定运行容器时的用户名或 UID,后续的 RUN 也会使用指定用户。使用USER指定用户时,可以使用用户名、UID或GID,或是两者的组合。当服务不需要管理员权限时,可以通过该命令指定运行用户。并且可以在之前创建所需要的用户

 格式:
  USER user
  USER user:group
  USER uid
  USER uid:gid
  USER user:gid
  USER uid:group

 示例:
  USER www

注:

  使用USER指定用户后,Dockerfile中其后的命令RUN、CMD、ENTRYPOINT都将使用该用户。镜像构建完成后,通过docker run运行容器时,可以通过-u参数来覆盖所指定的用户。

ARG:用于指定传递给构建运行时的变量

格式:
    ARG <name>[=<default value>]
示例:
    ARG site
    ARG build_user=www

以下是一个小例子:

# Base images 基础镜像
FROM centos

#MAINTAINER 维护者信息
MAINTAINER xxxxxx

#ENV 设置环境变量
ENV PATH /usr/local/nginx/sbin:$PATH

#ADD  文件放在当前目录下,拷过去会自动解压
ADD nginx-1.8.0.tar.gz /usr/local/  
ADD epel-release-latest-7.noarch.rpm /usr/local/  

#RUN 执行以下命令 
RUN rpm -ivh /usr/local/epel-release-latest-7.noarch.rpm
RUN yum install -y wget lftp gcc gcc-c++ make openssl-devel pcre-devel pcre && yum clean all
RUN useradd -s /sbin/nologin -M www

#WORKDIR 相当于cd
WORKDIR /usr/local/nginx-1.8.0 

RUN ./configure --prefix=/usr/local/nginx --user=www --group=www --with-http_ssl_module --with-pcre && make && make install

RUN echo "daemon off;" >> /etc/nginx.conf

#EXPOSE 映射端口
EXPOSE 80

#CMD 运行以下命令
CMD ["nginx"]

总结

最后用一张图解释常用指令的意义^-^

制作ubuntu-flask镜像

1.新建sources.list文件内容如下:

deb http://mirrors.aliyun.com/ubuntu/ focal main restricted
deb http://mirrors.aliyun.com/ubuntu/ focal-updates main restricted
deb http://mirrors.aliyun.com/ubuntu/ focal universe
deb http://mirrors.aliyun.com/ubuntu/ focal-updates universe
deb http://mirrors.aliyun.com/ubuntu/ focal multiverse
deb http://mirrors.aliyun.com/ubuntu/ focal-updates multiverse
deb http://mirrors.aliyun.com/ubuntu/ focal-backports main restricted universe multiverse
deb http://mirrors.aliyun.com/ubuntu/ focal-security main restricted
deb http://mirrors.aliyun.com/ubuntu/ focal-security universe
deb http://mirrors.aliyun.com/ubuntu/ focal-security multiverse

Dockerfile文件内容如下:

FROM ubuntu:20.04
COPY sources.list /etc/apt/sources.list
RUN apt-get update && apt-get install vim -y

 运行命令:

docker build -t ubuntu_flask:1.0 .

2. 安装Python3(ubuntu_flask:1.1)
Dockerfile_1.1文件内容如下:(从之前建立好的镜像,基础之上安装python3)

FROM ubuntu_flask:1.0
RUN apt-get install python3 -y


运行命令:(-f 指定Dockerfile是谁)

docker build -t ubuntu_flask:1.1 . -f Dockerfile_1.1

3. 安装pip3(ubuntu_flask:1.2)、安装flask需要的模块、包(ubuntu_flask:1.3)

开始构建

requirements.txt内容如下:(如果大家之前已经养成了用python虚拟换的好习惯,此时只需要切换虚拟环境然后pip freeze > requirements.txt就可以得到此文件,所以再次建议要用Python的虚拟环境)(> 覆盖)

click==8.1.3
colorama==0.4.6
Flask==2.2.3
itsdangerous==2.1.2
Jinja2==3.1.2
MarkupSafe==2.1.2
Werkzeug==2.2.3

Dockerfile1.2内容如下:

FROM ubuntu_flask:1.1
RUN apt-get install python3-pip -y

# 复制文件到容器
ADD requirements.txt /home

# 跳转到指定目录
WORKDIR /home

RUN pip3 install -r requirements.txt -i https://pypi.mirrors.ustc.edu.cn/simple/

命令:

docker build -t ubuntu_flask:1.2 . -f Dockerfile1.2

5. 编写测试flask项目(ubuntu_flask:1.3)

main.py内容如下:

from flask import Flask

# 创建flask对象
app = Flask(__name__)

a=1
@app.route('/')
def index():
    """
    处理一个页面的逻辑
    :return:
    """
    return f'hello flask  {a}'


if __name__ == '__main__':
    app.run(host='0.0.0.0', port=8899, debug=True)  # 如果是127.0.0.1那么意味着只能容器本身能访问,其他电脑不行

Dockerfile1.3内容如下:

FROM ubuntu_flask:1.2

# 进入到项目目录
WORKDIR /home

# 拷贝flask示例.py到工作目录(此时的.就是/home路径的意思,因为上面已经使用WORKDIR设置了)
COPY main.py .

# 对外暴露端口
EXPOSE 8899

# 运行测试项目
CMD ["python3","main.py"]

命令如下:

docker build -t ubuntu_flask:1.3 . -f Dockerfile1.3

6. 运行 & 测试

docker run --rm -it -p 8899:8899 ubuntu_flask:1.3


效果如下:

切换到Ubuntu20.04终于成功了 

1. 目的
上一节中已经完成了flask开发环境操作,但是发现有了很多次的Dockerfile才完成,这是很麻烦的,为了更加方便的操作使用,我们本小节将对上一节的之后进行升级为一个Dockerfile

2. 实现
将基础班中的5个Dockerfile文件合并为一个,名字叫做Dockerfile_2.0 适当修改后如下:

FROM ubuntu:20.04

# 复制国内更新源
COPY sources.list /etc/apt/sources.list

# 跳转到指定目录
WORKDIR /home

# 复制文件到容器
COPY requirements.txt .

# 安装vim、python3、pip3以及flask用的包
RUN apt-get update && apt-get install vim -y \
    && apt-get install python3 -y \
    && apt-get install python3-pip -y \
    && pip3 install -r requirements.txt -i https://pypi.tuna.tsinghua.edu.cn/simple

# 复制flask示例py文件
COPY main.py .

# 对外暴露端口
EXPOSE 8899

# 运行测试项目
CMD ["python3","main.py"]

命令:

docker build -t ubuntu_flask:2.0 . -f Dockerfile_2.0

常见问题

Docker卡在Docker Desktop stopped

1.检查虚拟机-设置-处理器-虚拟化引擎

 勾选前两项

2、再次启动Docker以后,如果卡在starting界面1.

点击TroubleShoot

 分别尝试这两个选项,点完后,发现出现了新的状态:Docker Desktop is Stopping.....

卸载Docker Desktop,重新安装,突然发现可以正常使用了

检查环境

解决Docker 一直starting 的办法_普通网友的博客-CSDN博客_docker desktop starting...

https://www.myfreax.com/how-to-install-and-use-docker-on-ubuntu-20-04/

  • 1
    点赞
  • 5
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
1. 首先需要安装DockerDocker Compose。可以使用以下命令在Ubuntu系统中安装它们: ``` sudo apt-get update sudo apt-get install docker.io sudo apt-get install docker-compose ``` 2. 创建一个新的项目目录: ``` mkdir myproject cd myproject ``` 3. 在该目录下创建一个名为docker-compose.yml的文件。可以使用nano或vim编辑器创建并编辑此文件: ``` nano docker-compose.yml ``` 或 ``` vim docker-compose.yml ``` 4. 将以下内容添加到docker-compose.yml文件中: ``` version: '3' services: web: build: . ports: - "5000:5000" ``` 这将创建一个名为web的服务,使用当前目录中的Dockerfile构建容器容器将映射到主机的端口5000上。 5. 创建一个名为Dockerfile的文件,并在其中添加以下内容: ``` FROM python:3.7-alpine WORKDIR /app COPY . /app RUN pip install -r requirements.txt CMD python app.py ``` 这将使用Python 3.7的Alpine镜像作为基础镜像,并在/app目录中复制当前目录中的所有文件。然后,它将安装requirements.txt文件中指定的所有依赖项,并使用CMD命令启动应用程序。 6. 在当前目录中创建一个名为app.py的Python文件,并在其中添加以下内容: ``` from flask import Flask app = Flask(__name__) @app.route('/') def hello_world(): return 'Hello, Docker Compose!' if __name__ == '__main__': app.run(debug=True, host='0.0.0.0') ``` 这将创建一个基本的Flask应用程序,当访问主页时,它将返回“Hello,Docker Compose!”消息。 7. 创建一个名为requirements.txt的文件,并在其中添加以下内容: ``` Flask==1.1.2 ``` 这将指定Flask 1.1.2作为应用程序的依赖项。 8. 在项目目录中运行以下命令,使用Docker Compose构建和启动容器: ``` sudo docker-compose up ``` 9. 浏览器中访问http://localhost:5000,将看到“Hello,Docker Compose!”消息。 这就完成了通过sudo docker-compose安装应用程序的过程。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值