docker容器常用命令
最近打算突破一下docker的知识,买了一门课程,这里同步做一下笔记。
获取镜像
# 查询镜像
docker search centos
# 拉取指定版本的镜像
docker pull centos:6.9
# 拉取最新的镜像版本:latest
docker pull centos
查询镜像
# 查询本机的所有镜像,并显示详细信息
docker images
# 查询本机的所有镜像,只显示镜像ID
docker images -q
# 查看镜像的详细信息(对外端口、容器启动时执行的命令、环境变量、工作目录等等)
docker inspect ID/name:tag
删除镜像
# 删除指定镜像
docker rmi IID
# 删除所有镜像
docker rmi `docker images -q`
# 同上
docker rmi $(docker images -q)
# 强制删除镜像(一些相互依赖的镜像通过上面的命令无法删除)
docker rmi -f IID
导入导出镜像
# 导出本地镜像为tar文件
docker image save nginx >/opt/nginx.tar.gz
# 从tar文件加载镜像
docker image load -i /opt/nginx.tar.gz
启动容器
# 启动交互式容器(/bin/sh、/bin/bash、bash),执行exit后容器就退出了,可以使用ctrl+p+q
docker run -it --name="n1" 3fe2fe0dab2e /bin/bash
# 启动守护式容器
docker run -d -p 8080:80 --name="n1" nginx
# 启动容器,并执行一个命令(执行的命令必须是前台持续性的,不能是执行完就结束的命令,否则容器就会推出)
docker run -d -p 8080:80 --name="n1" nginx cd /usr1;python manager.py runserver 0.0.0.0:8080
# 停止正在运行容器
docker stop 容器ID/名称
# 启动已经停止的容器
docker start 容器ID/名称
# 重启容器,不会使容器中已有的修改失效
docker restart 容器ID/名称
进入容器
# 进入容器的已有交互界面,退出时应该使用ctrl+p+q,否则容器会关闭
docker attach 容器ID
# 进入当前运行容器,并创建一个新的交互式界面,退出时不会关闭容器(推荐做法)
docker exec -it 容器ID|容器名称 /bin/bash
# 不进入容器执行命令(查看根目录列表,并显示在控制台)
docker exec 容器ID ls /
# 不进入容器,向容器中安装vim,并后台安装,不在前台展示
docker exec -d 容器ID apt-get install vim
查询容器
# 查询当前正在运行的容器
docker ps
# 查询所有存在的容器,包括已退出的
docker ps -a
# 查询容器ID
docker ps -q
# 查询容器详细信息(端口映射、IP地址、磁盘绑定等信息)
docker inspect 容器ID/名称
删除容器
# 删除已退出的容器
docker rm 容器ID/名称
# 强制删除容器,包括正在运行的
docker rm -f 容器ID/名称
容器网络
指定映射(docker 会自动添加一条iptables规则来实现端口映射)
-p hostPort:containerPort
-p ip:hostPort:containerPort
-p ip::containerPort(随机端口)
-p hostPort:containerPort/udp
-p 81:80 –p 443:443
随机映射
docker run -p 80(随机端口)
容器其他操作
# 查看容器中正在运行的进程
docker top 容器ID/名称
# 拷贝文件或目录
docker cp 宿主机目录/文件 容器ID:/usr1/test
docker cp 容器ID:/usr1/test 宿主机目录/文件
# 查询容器正在运行的日志
docker logs 容器ID/名称
# 实时显示容器中运行日志
docker logs -f 容器ID/名称
# 将容器实时日志输出到文件,可以配合ELK进行日志收集
docker logs -f testxx > /var/log/xxx.log 2>1&
容器持久化存储
# 挂载数据卷 -v 宿主机目录或文件:容器中目录或文件
docker run -d -v ./test:/test --name='n1' nginx
数据卷容器
# 启动一个容器作为数据卷
docker run -it --name "my_volumes" -v /opt/Volume/conf:/usr/local/nginx/conf nginx /bin/bash
# 跳出容器
ctrl p q
# 使用上面的数据卷容器作为新容器的数据卷,相当于新容器挂载了/opt/Volume/conf目录
docker run -d -p 8085:80 --volumes-from my_volumes --name "n85" nginx
docker run -d -p 8086:80 --volumes-from my_volumes --name "n86" nginx
基于容器制作镜像
# 查询正在运行的容器
docker ps
# 将容器制作为镜像(如果要提交到私有镜像库,新镜像名称必须携带私有库的域名,例如:xxx.com
docker commit 容器ID xxx.com/my_container:v1
# 将容器提交到私有镜像库
docker push xxx.com/my_container:v1
# 修改镜像名称(想要将公共镜像推送到私有镜像库,必须修改其名称,前面加上私有库的域名)
docker tag old_container_name xxx.com/new_container_name:latest
优点:制作方便,只要进入容器,安装好环境,就可以制作一个新的镜像,并部署到其他环境。
缺点:容器内新增的服务必须在启动后,再进入容器启动一次服务,但是可以通过启动时执行指定命令来解决这个问题
基于Dockerfile制作镜像
- FROM命令
FROM 镜像ID:标签
# 必须指定镜像和标签,作为基础镜像,此命令是必须的
FROM centos:latest
- RUN命令
# RUN 执行shell命令,多条命令使用&&连接,也可以使用多行RUN,但是docker镜像是分层制作的
# 在dockerfile中每一条执行命令都创建一层,所以我们尽量创建少的层,把能够合并的命令放在一
# 层中
RUN cd /opt && mkdir code && yum install -y vim && yum install -y wget
以上命令就是切换到/opt目录,创建一个code子目录,安装vim和wget
- CMD命令
使用镜像启动容器时默认的运行命令,如果在docker run的时候,在后面带上自定义命令,那么这个命令就会被替换掉,导致容器启动的时候不会执行,所以一般我们不用这个
CMD ["/usr/sbin/sshd", "-D"]
- ENTRYPOINT
和上面的CMD命令相似,但是不会被启动容器时的自定义命令替换掉,一定会执行;还有一个用法是在docker run后面的自定义命令可以作为ENTRYPOINT的命令参数传入
ENTRYPOINT ["/usr/sbin/sshd", "-D"]
- COPY命令
从主机拷贝文件到容器中
COPY init.sh /opt/
- ADD命令
和copy命令类似,拷贝文件到镜像中,但是对于压缩文件(含有tar的)拷贝过去会直接解压
ADD xxx.tar.gz /var/www/html
- EXPOSE命令
指定容器要对外暴露的端口
EXPOSE 80
EXPOSE 3306
- VOLUME命令
在dockerfile中声明了VOLUME绑定目录并不会在容器启动的时候帮我们自动绑定目录,那么VOLUME和-v有什么区别呢?假设我们在dockerfile中声明了
VOLUME ['/data', '/etc/proc']
那么我们使用不同的命令启动时
# 如果在run容器的时候,没有指定-v,那么此时会创建一个匿名卷,并且绑定到/var/lib/docker/volumes(docker安装目录下的volumes中)
docker run -d --name='cent1' my_centos
# 如果在run的时候,指定了-v,那么就会覆盖匿名卷
docker run -d -v ./data:/data -v ./proc:/etc/proc --name='cent1' my_centos
所以如果一个镜像制作的时候使用了VOLUME,那么每次启动都会在宿主机上创建一个数据目录,如果这个目录里存在的东西很多,那么时间长了,我们就会发现宿主机上空间越来越小,即使你重启容器也不行。所以要了解这个性质,针对性的清理docker目录。
- WORKDIR
相当于cd命令,区别是在dockerfile中使用了WORKDIR后,在它下面的语句,工作目录都变成了WORKDIR指定的目录
WORKDIR /code
- ENV
在dockerfile中设置环境变量,主要为了在执行docker run的时候可以通过-e参数修改环境变量,这样也可以使镜像更加通用。例如MySQL安装时要指定用户名、密码、绑定IP,如果直接在容器里面安装,那么我们如果要修改的话,必须登录到容器中,进行修改重启。但是在dockerfile中指定了ENV变量,那么在docker run的时候就可以修改这些设置。
ENV MYSQL_USERNAME = 'root'
# 使用时用以下方式获取
${MYSQL_USERNAME}
下面给一个简单的dockerfile例子
FROM centos:latest
# 替换yum源
COPY CentOS-Base.repo /etc/yum.repos.d/CentOS-Base.repo
# 配置pip文件
COPY pip.conf ~/.pip/
RUN yum clean all && yum makecache && yum update -y && yum install -y vim && yum install -y wget
RUN yum install -y python38 && yum install -y python38-setuptools && yum install -y python38-pip && # 配置pip文件
# 切换到目录/ftp
WORKDIR /ftp
# 将init.sh文件拷贝到镜像的/ftp目录下
COPY init.sh .
# 执行启动命令
ENTRYPOINT ["/bin/bash", "init.sh"]
在当前目录下创建dockerfile文件,并使用docker build命令制作镜像
# -t 后面是新的镜像标签, .表示使用当前目录下的dockerfile文件
docker build -t my_images/centos:latest .
搭建私有镜像库
在很多企业中,都不能肆意的访问外网,那这样是不是docker就没法愉快的使用了呢?我们通常下载镜像都是从docker hub官方仓库下载的,如果在企业内部搭建一个私有镜像库,那是不是就能像外网一样使用docker了呢,docker官方为我们提供了非常简单的搭建私有库的方式:
docker run -d -p 5000:5000 --restart=always --name docker_registry -v /opt/registry:/var/lib/registry registry
# --restart=always docker服务启动时,容器就启动
# -v 将镜像存储地址映射到宿主机,防止丢失
好了,通过以上命令我们的私有镜像库就搭建好了,是不是很简单呢?那么怎么使用呢?
- 修改配置文件
vim /etc/docker/daemon.json
{
"insecure-registries": ["xx.xx.xx.xx:5000"]
}
- 重启docker服务
systemctl restart docker
- 推送本地镜像到私有镜像库
修改镜像名称,添加私有镜像库地址为前缀,然后push到镜像库
docker tag nginx:latest xx.xx.xx.xx:5000/nginx:latest
docker push xx.xx.xx.xx:5000/nginx:latest
- 在其他机器上pull
docker pull xx.xx.xx.xx:5000/nginx:latest
- 使用utl_file走选择性数据导出(r2笔记95天)
- 使用Linux命令发送邮件(r2笔记94天)
- 如何用python轻松破解wifi密码( 源码 )
- 海量数据迁移之通过shell估算数据量 (r2笔记93天)
- 使用sklearn进行数据挖掘
- 批量转换分区表为普通表(r2笔记92天)
- 使用sklearn做特征工程
- 【专业技术】CSS作用及用法
- 生产环境sql语句调优实战第六篇(r2笔记91天)
- 关于分区表的move操作(r2笔记90天)
- 简单分析oracle的数据存储(r2笔记89天)
- 机器学习线性分类算法:感知器原理
- 通过shell脚本来查看Undo中资源消耗高的sql(r2笔记88天)
- 关于分页查询的优化思路(r3笔记第7天)
- JavaScript 教程
- JavaScript 编辑工具
- JavaScript 与HTML
- JavaScript 与Java
- JavaScript 数据结构
- JavaScript 基本数据类型
- JavaScript 特殊数据类型
- JavaScript 运算符
- JavaScript typeof 运算符
- JavaScript 表达式
- JavaScript 类型转换
- JavaScript 基本语法
- JavaScript 注释
- Javascript 基本处理流程
- Javascript 选择结构
- Javascript if 语句
- Javascript if 语句的嵌套
- Javascript switch 语句
- Javascript 循环结构
- Javascript 循环结构实例
- Javascript 跳转语句
- Javascript 控制语句总结
- Javascript 函数介绍
- Javascript 函数的定义
- Javascript 函数调用
- Javascript 几种特殊的函数
- JavaScript 内置函数简介
- Javascript eval() 函数
- Javascript isFinite() 函数
- Javascript isNaN() 函数
- parseInt() 与 parseFloat()
- escape() 与 unescape()
- Javascript 字符串介绍
- Javascript length属性
- javascript 字符串函数
- Javascript 日期对象简介
- Javascript 日期对象用途
- Date 对象属性和方法
- Javascript 数组是什么
- Javascript 创建数组
- Javascript 数组赋值与取值
- Javascript 数组属性和方法
- grafana-zabbix插件安装和配置zabbix mysql
- grafana使用教程之API key
- Grafana使用教程之安装
- Java基础数据类型之包装类equals和==详解
- SCP不用密码传输文件
- Java 使用Collections.reverse对list集合进行降序排序
- Liquibase异常 mysql数据库 Cannot add foreign key constraint
- Linux获取文件最后修改时间
- Crontab脚本无法正常执行问题
- Python 输入时间字符串以分钟单位计算时间差
- Linux下执行bcp指令
- Python 处理时间差
- Zabbix发送带附件的邮件
- CentOs7下Zabbix安装教程——zabbix agent安装和前端配置
- CentOs7下Zabbix安装教程——zabbix server安装