小集装箱挑战:建立6KB集装箱HTTP服务器

2021-04-22 15:15:37

类别:标签:TL;我设置的DR才能构建我能够做一些有用的东西的最小的容器图像。通过利用多级构建,划痕基础图像和基于微小的组装的HTTP服务器,我能够将其降至6.32KB!

容器通常被吹捧为银弹,以解决与操作软件相关的每一个挑战。虽然我喜欢容器,但我经常在野外遇到包含各种问题的容器图像。一个常见的问题是大小,图像有时在多个GB时计时!

正因为如此,我决定挑战自己和他人建立最小的图像。

容器应在选择的端口上为HTTP提供文件的内容

不允许卷安装(也称为“Marek规则”😜)

要获得基线图像大小,我们可以使用Node.js创建一个简单的服务器index.js:

const fs =要求(" fs"); const http =要求(' http'); const server = http。 createserver((req,res)=> {res。写点(200,{' content-type':' text / html'})fs。Creeateadstream('索引.html')。管道(RES)})服务器。侦听(端口,主机名,()=> {控制台。日志(`server:http://0.0.0.0:8080 //0.0.0.0);

用于降低图像尺寸的最简单和最明显的策略之一是使用较小的基础图像。官方节点映像具有SLIM变体(仍然基于Debian,但预先安装较少的依赖项)和基于Alpine Linux的Alpine变体。

使用节点:14-SLIM和Node:14- alpine,因为基础图像分别将图像尺寸降至167MB和116MB。

由于Docker图像是附加的,所以每个层都在接下来的情况下,我们可以做的是,我们可以做的是让节点.js解决方案变小。

要将事物带到下一个级别,我们可以转移到编译的语言,运行时依赖性更少。有各种各样的选择,但对于建立网络服务,Golang是一个受欢迎的选择。

包主要导入(" fmt"" log"" net / http")func main(){fileServer:= http。 fileserver(http.dir(" ./&# 34;))http。把手(" /",fileserver)fmt。 printf("在端口8080 \ n&#34的启动服务器,如果err:= http。 Histendsdserve(":8080",nil); err!= nil {log。致命(err)}}

此处的问题是Golang基础图像的安装很多依赖项,在构建Go软件时非常有用,但不需要运行软件。

Docker有一个名为多级构建的功能,可以轻松地在环境中构建所有必要的依赖项,然后将结果的可执行文件复制到其他图像中。

这与各种原因有用,但最明显的是图像尺寸!通过重构DockerFile如下:

###来自golang的阶段###:1.14-高山作为BuilderCopy。 .RUN Go Build -o Server。 ###运行阶段###来自Alpine:3.12Copy --from = Builder / Go / Server ./servercopy inders.html index.htmlcmd [" ./服务器" ]

13 MB并不是太糟糕,但仍然有几个技巧我们可以玩,让它变小。

有一个称为划痕的基础图像,它显式为空,具有零大小。因为划痕内部没有内部,所以任何由它构建的图像必须带来所有必要的依赖项。

要使用我们的GO基于服务器实现此可能,我们需要将一些标志添加到编译步骤中,以确保必要的库静态链接到可执行文件中:

###来自golang的阶段###:1.14作为BuilderCopy。 .run go build \ -ldflags" -linkmode外部-extldflags -static" \ -a server.go ###运行阶段### from scratchcopy --from = builder / go / server ./servercopy index.html index.htmlcmd [" ./服务器" ]

具体来说,我们将链接模式设置为外部并将 - 将天标传递给外部链接器。

以一种小于10MB的图像,以像Go的语言写入的东西,几乎是任何情况都很小...但我们可以越小! GitHub用户Nemasu全功能HTTP服务器在Github上编写的Github命名为Assmttpd。

容器中所需的只是在运行提供的Make Release Recipe之前将一些构建依赖性安装到Ubuntu基础映像中:

###来自Ubuntu的Build Stage ### .run使释放### Run Stage ###从ScratchCopy --from = Builder / Asmttpd / Asmttpdcopy / web_root/index.html / web_root/index.htmlcmd [" / asmttpd&#34 ;,#34; / web_root&#34 ;," 8080" ]

然后将生成的ASMTTPD可执行文件复制到划痕图像中并用CMD调用。这导致图像尺寸仅为6.34KB! 🥳

希望您从初始943MB节点943MB Node.js拍摄此旅程一直享受这个微小的6.34KB装配图像,并学习了一些技术,您可以应用于使您的容器图像更小。