Docker镜像压缩与优化操作

现如今docker如此受人追捧,主要是因为它的轻量化、可以快速部署以及资源的利用。但是一个docker images质量的好与坏,主要取决于Dockerfile编写的质量。同样功能的镜像,但是不同的Dockerfile build出来的镜像大小是不一样的,这是因为docker是由一层一层的只读层累积起来的,而这每一层就是Dockerfile中的每一条指令,所以Docker image的大小完全取决于Dockerfile中的每条指令生成的中间层的大小,

下面我们来举一个小例子来详细说明dockerimage的形成。

我们有一个Dockerfile:

FROM Ubuntu:14.04
ADD run.sh /
VOLUME /data
CMD [“./run.sh”]

这个简单的Dockerfile主要做的事情是:基于Ubuntu:14.04系统将run.sh放在根目录下,设置卷挂载点,然后在image启动的时候run脚本run.sh。

下图就是形成的docker image:

很明显,由图我们可以看到,四条指令分别形成四个层,假设Ubuntu:14.04是150MB,run.sh是1MB的话,那么FROM Ubuntu:14.04层的大小就是150MB,ADD run.sh /层的大小即为1MB,而VOLUME /data层和CMD [“./run.sh”]由于没有加入文件等数据,也没有在系统中生成数据,所以该层的大小为0。

所以整个image的大小就是151MB。在知道了docker image生成的原理之后,下面我们就来聊一下docker镜像的优化与压缩。

需要说明的一点就是:层数的多少在某些情况下是不会决定image的大小的,只有当Dockerfile中出现:

RUN yum install ***

RUN yum uninstall ***

的时候镜像是可以压缩优化的,因为上面这两句是安装一个工具,然后卸载掉,正常情况下我们感觉这样一安装一卸载大小就为0了,但是在docker image中不是这样的,RUN yum uninstall ***这一层只能是令上一层不可见,但是上一层的大小是不会变化的,所以,如果想达到0的效果,我们就需要将这两层压缩成一层,也就是这样写:

RUN yum install *** && \

yumuninstall ***

这样就会达到压缩镜像的效果。

所以,压缩镜像主要有两点:

1、选择一个较小的原镜像,也就是FROM后面的那个镜像尽量要小。

2、根据实际情况对Dockerfile中的层进行合并,具体情况就是如上述所说的情况,要知道并不是随便合并层就会达到效果的。

补充知识:如何将anaconda+jupyter build成docker镜像

最近由于业务的需求,要build一个jupyter的image来提供服务,因为docker的轻量化可以很方便的迁移。

下面来介绍一下我所做的操作,以及我踩的坑:

首先来安装anaconda,有python2和3版本的,版本不同但是build的过程是一样的,有两种方式,第一种,你可以通过Dockerfile的方式来build image,但是在运行Anaconda2-5.0.1-Linux-x86_64.sh脚本的时候无法实现交互,所以,我才用了docker commit的方式来执行,但是事实证明也可以通过Dockerfile的方式来build,您只需要在本机上先运行了Anaconda2-5.0.1-Linux-x86_64.sh的脚本,并将生成的文件夹就是anaconda2 ADD到image中相应的位置,并且修改环境变量,将PATH加进去即可。

下面以python2为例来说:

1. 从anaconda官网上下载运行脚本Anaconda2-5.0.1-Linux-x86_64.sh,其中在下载的时候要注意你的系统的是32位还是64位。

2. 将脚本scp到基础镜像中,安装解压指令bzip2

yum install bzip2

3. 运行脚本(一路输入yes)

sh Anaconda2-5.0.1-Linux-x86_64.sh

4. 更新anaconda

conda update anaconda

5. 安装jupyter

conda install jupyter

6. 创建登录密码

root@localhost ~]# ipython

Python 3.5.2 (default, Aug 4 2017, 02:13:48)
Type 'copyright', 'credits' or 'license' for more information
IPython 6.1.0 -- An enhanced Interactive Python. Type '?' for help.

In [1]: from notebook.auth import passwd
In [2]: passwd()
Enter password:
Verify password:
Out[2]: 'sha1:5311cd8b9da9:70dd3321fccb5b5d77e66080a5d3d943ab9752b4'

7. 生成配置文件

jupyter notebook --generate-config --allow-root

注意:在这一步的时候有可能会遇见编码错误:UnicodeEncodeError:'ascii'codec can't encode characters in position...

处理的方法是:在anaconda2文件夹中的lib>python2.7>site.py更改:

if 0:
 # Enable to support locale aware default string encodings.
 import locale
 loc = locale.getdefaultlocale()
 if loc[1]:
 encoding = loc[1]
#将上述代码段中if后面的0改成1,保存,重新启动anaconda。 

8. 修改配置文件:

vi ~/.jupyter/jupyter_notebook_config.py

添加以下内容:

c.NotebookApp.ip='*'
c.NotebookApp.password = u'sha1:5311cd8b9da9:70dd3321fccb5b5d77e66080a5d3d943ab9752b4' #注意这里的密钥是刚刚生成的那个
c.NotebookApp.open_browser = False
c.NotebookApp.port =8888 #随便指定一个端口,使用默认8888也可以

9.保存镜像

docker commit 容器ID 镜像名称

10. 启动images提供服务:

docker run --privileged -d -p 8889:8888 -v /sys/fs/cgroup:/sys/fs/cgroup --name jupyter jupyter2:v2 /usr/sbin/init

注意:centos7有一个大坑,就是你在关闭防火墙的时候,systemctl 无法使用,报错: Failed to get D-Bus connection : Operation not permitted

所以要用init来起,在Dockerfile中可以用CMD来使运行时启动。

11. 进入docker image

docker exec -it jupyter /bin/bash

12.关闭防火墙

systemctl stop firewalls.service

13. 启动jupyter

jupyter notebook --notebook-dir=/root/ --allow-root

14.在浏览器输入服务器的IP+映射的端口号即可访问,完成~

以上这篇Docker镜像压缩与优化操作就是小编分享给大家的全部内容了,希望能给大家一个参考,也希望大家多多支持我们。

(0)

相关推荐

  • supervisor下的Dockerfile的多服务镜像封装操作

    编写Dockerfile文件 配置yum源 cd /tmp/docker vim Dockerfile FROM rhel7 EXPOSE 80 22 # 向外暴露80和22的端口 COPY dvd.repo /etc/yum.repos.d/dvd.repo && yum install -y httpd openssh-server openssh-clients supervisor && yum clean all && ssh-keygen -q

  • Docker镜像分析工具dive原理解析

    今天推荐一个这样的开源工具,用于探索 Docker 镜像,各层内容以及发现缩小 Docker/OCI 镜像大小的方法.这个工具就是:dive. 工具地址:https://github.com/wagoodman/dive,Star 数:22k+. 这个工具可以清晰得看到镜像每一层都包含哪些内容,方便你分析是否有必要,如下图所示. 特性 该工具的主要特性包括: 按层显示 Docker 镜像内容: 指出每一层的变化: 评估 "镜像的效率": 快速的构建/分析周期: 和 CI 集成: 支持多

  • docker镜像访问本地elasticsearch端口操作

    使用docker stack部署的镜像服务,进入镜像之后,理论上,应该可以通过下面的指令访问本地的elasticsearch服务 curl 本机ip/9200 但是却提示拒绝访问. 后来本机使用上述指令查看之后发现,本机也是拒绝访问. 之后发现,9200端口的elasticsearch服务,是通过打洞的方式连接的远程服务器上的elasticsearch服务,只能通过下面指令访问端口 curl 127.0.0.1:9200 如果想要通过本机ip访问9200端口,则需要在打洞指令的后面加上 -g.

  • dockerfile制作apache镜像的方法

    一.Docker镜像 1.1 docker镜像 应用的是发布的标准格式 支撑一个docker容器的运行 1.2 docker镜像的创建方法 基于已有的镜像创建 基于本地模板创建 基于Dockerfile创建 Docker镜像是分层的结构 ①Dockerfile中的每个指令都会创建一个新的镜像层 ②镜像层将被缓存和复用 ③当Dockerfile的指令修改了,复制的文件变化了,或者构建镜像时指定的变量不同了,对应的镜像层缓存就会失效 ④某一层的镜像缓存失效之后,它之后的镜像层缓存都会失效 ⑤镜像层是

  • Docker如何制作自己镜像并上传dockerhub

    1.首先注册自己的dockerhub账号,注册地址:https://hub.docker.com 2.在linux服务器登录自己的账号:docker login --username=qiaoyeye 3.在https://hub.docker.com/上先找到自己想要的镜像 4.拉取镜像到本地:docker pull centos 5.本地准备jdk和tomcat软件,解压后放入服务器 6.新建Dockerfile文件,注意区分大小写 #----------------------------

  • Docker镜像压缩与优化操作

    现如今docker如此受人追捧,主要是因为它的轻量化.可以快速部署以及资源的利用.但是一个docker images质量的好与坏,主要取决于Dockerfile编写的质量.同样功能的镜像,但是不同的Dockerfile build出来的镜像大小是不一样的,这是因为docker是由一层一层的只读层累积起来的,而这每一层就是Dockerfile中的每一条指令,所以Docker image的大小完全取决于Dockerfile中的每条指令生成的中间层的大小, 下面我们来举一个小例子来详细说明docker

  • 理解Docker(2):Docker 镜像详细介绍

    本系列文章将介绍Docker的有关知识: (1)Docker 安装及基本用法 (2)Docker 镜像 (3)Docker 容器的隔离性 - 使用 Linux namespace 隔离容器的运行环境 (4)Docker 容器的隔离性 - 使用 cgroups 限制容器使用的资源 (5)Docker 网络 对于每个软件,除了它自身的代码以外,它的运行还需要有一个运行环境和依赖.不管这个软件是象往常一样运行在物理机或者虚机之中,还是运行在现在的容器之中,这些都是不变的.在传统环境中,软件在运行之前也

  • 构建Golang应用最小Docker镜像的实现

    我通常使用docker运行我的 golang 程序,在这里分享一下我构建 docker 镜像的经验.我构建 docker 镜像不仅优化构建后的体积,还要优化构建速度. 示例应用 首先贴出代码例子,我们假设要构建一个 http 服务 package main import ( "fmt" "net/http" "time" "github.com/gin-gonic/gin" ) func main() { fmt.Printl

  • 详解六种减小Docker镜像大小的方法

    我从2017年做Vulhub开始,一直在和一个麻烦的问题做斗争:在编写Dockerfile的时候, 如何减小 docker build 生成的镜像大小 ?这篇文章就给大家总结一下我自己使用过的六种减小镜像大小的方法. 1. 使用Alpine Linux Alpine Linux是一个基于BusyBox和Musl Libc的Linux发行版,其最大的优势就是小.一个纯的基础Alpine Docker镜像在压缩后仅有2.67MB. 不少Docker官方镜像都有Alpine版本,比如PHP: 比较之下

  • Docker 镜像分层及dockerfile 编写技巧

    docker镜像分层 分层介绍 Dockerfile中的每个指令都会创建一个新的镜像层 镜像层将被缓存和复用 当Dockerfile的指令修改了,复制的文件变化了,或者构建镜像时指定的变量不同了,对应的镜像层缓存就会失效 某一层的镜像缓存失效之后,它之后的镜像层缓存都会失效 镜像层是不可变的,如果在某一层中添加一个文件,然后在下一层中删除它,则镜像中依然会包含该文件 Docker镜像原理 Docker镜像是由特殊的文件系统叠加而成 ·最底端是bootfs,并使用宿主机的bootfs ·第二层是r

  • Docker镜像的迁移与备份及Dockerflie 使用方法详解

    目录 一.迁移与备份 1. 容器保存为镜像 2. 镜像备份 3. 镜像恢复与迁移 二.Dockerflie 1. 认识 Dockerfile 2. Dockerfile 常用命令 3. 使用 Dockerfile 构建镜像 一.迁移与备份 迁移和备份主要有三个操作命令将容器保存为镜像.备份镜像(将镜像导出为一个文件).镜像的迁移与恢复.迁移与备份在实际操作 Docker 的过程中使用的是非常多的,比如要将一台服务器的镜像迁移到另外一台服务器,就么可以先将镜像保存为一个文件,然后将文件拷贝至另一台

  • 详解Docker镜像的基本操作方法

    目录 一.获取镜像 二.运行镜像 三.列出镜像 四.镜像大小 五.删除本地镜像 一.获取镜像 之前我们提到过 Docker 官⽅提供了⼀个公共的镜像仓库:Docker Hub,我们就可以从这上⾯获取镜像,获取镜像的命令:docker pull,格式为: $ docker pull [选项] [Docker Registry 地址[:端⼝]/]仓库名[:标签] Docker 镜像仓库地址:地址的格式⼀般是 <域名/IP>[:端⼝号],默认地址是 Docker Hub. 仓库名:这⾥的仓库名是两段

  • 创建Web项目的Docker镜像实例讲解

    最近做个项目,创建web项目的Docker镜像,经过一番折腾终于做出来了,这里记录下,也希望读者能少走点弯路!以下就是资料整理! 基于Java,Mongodb,Tomcat的Supplierprofile项目 禁用selinux vi etc/selinux/config SELINUX=disabled SELINUXTYPE=targeted 运行镜像 Docker run -i --privileged=true -v /home/centos:/usr/local/file -d -p

  • 详解docker使用阿里云Docker镜像库加速(修订版)

    官方镜像下载实在是慢,于是开通了阿里云开发者帐号, 阿里的文档是错误的, 复制代码 代码如下: sudo sed -i "s|ExecStart=/usr/bin/docker daemon|ExecStart=/usr/bin/docker daemon --registry-mirror=https://pee6w651.mirror.aliyuncs.com|g" /etc/systemd/system/docker.service 这一句改为 复制代码 代码如下: sudo s

  • 详解制作各种docker镜像

    做了一个星期的镜像,收货颇多,现在整理记录下来,当做工作笔记吧.把常用的几个镜像的Dockerfile分享下. 制作基础docker镜像 第一步:设置Docker镜像源 复制代码 代码如下: yum install -y yum-priorities && rpm -ivh http://dl.fedoraproject.org/pub/epel/6/x86_64/epel-release-6-8.noarch.rpm && rpm --import /etc/pki/rp

随机推荐