go 构建image图像_为Go应用程序设计源到图像的构建

go 构建image图像

在本系列中有关源到图像 (S2I)的第一篇文章中,我们检查了所需的文件,并讨论了S2I标准如何与任何编程语言(从Python到Ruby到Go)一起使用。 现在,让我们探索设计专门用于Go应用程序的S2I构建。 免责声明:尽管仍未正式将Go称为Golang,但我仍喜欢将其称为Golang。

Golang S2I文件

所有S2I环境的核心都始于定义为Dockerfile的配置文件。 我们的Golang构建器图像也不例外; 这个项目将需要一个Dockerfile 创建构建器,具有用于编译Go应用程序的逻辑的汇编脚本,用于启动应用程序的运行脚本(仅出于方便目的)以及用于保存已编译应用程序的save-artifacts脚本。

让我们看一下这些必需的文件,因为我们将它们用于构建器映像。

注意:所有引用的文件都在我的golang-s2i GitHub存储库中

Docker文件

这个Dockerfile不是很复杂。 该构建器映像将使用上游golang:1.12映像作为其基础,因此我们不必安装Go并设置环境。 必须设置两个环境变量以允许Go应用程序在容器环境中运行:

  • CGO_ENABLED = 0
  • GOOS = Linux

如果您想进一步了解为什么要使用它们,请查看Kelsey Hightower的出色文章“ 为静态Go二进制文件构建Docker映像 ”。

还需要在Dockerfile中设置GOCACHE = / tmp环境变量,以避免在以root以外的用户身份运行构建时避免写入错误。 这是OKD / OpenShift约定,以支持运行具有任意UID的容器 ,但这也是避免同时需要root特权进行构建的良好实践。 请查看Dan Walsh的文章“ 只是对容器中的root拒绝 ”,以了解为什么这是一件好事。

然后再设置两个环境变量:

  • STI_SCRIPTS_PATH = / usr / libexec / s2i
  • SOURCE_DIR = / go / src / app

第一个告诉S2I在哪里可以找到需要运行的脚本,第二个只是为了方便起见,所以我们的项目是DRY

在下一节中, 复制 S2I脚本(见下文)的制造商形象,创造和chmod$ SOURCE_DIR放在脚本将编译应用程序,以便后续操作发生在该目录中其设置为WORKDIR:


   
   
COPY . / s2i / bin / ${STI_SCRIPTS_PATH}
RUN mkdir -p $SOURCE_DIR \
      && chmod 0777 $SOURCE_DIR
WORKDIR $SOURCE_DIR

注意: $ SOURCE_DIR设置为/ go / src / app,因为父golang:1.12映像中的$ GOPATH变量设置为/ go

最后,如上所述,将USER 1001设置为放弃root特权并确保对随机UID的支持,并将CMD设置为S2I使用脚本:


   
   
USER 1001
CMD [ "/usr/libexec/s2i/usage" ]

此时,我们的Dockerfile应该看起来像我的GitHub存储库中的Dockerfile ,除了一些标签和注释。

组装

S2I使用汇编脚本来编译Go应用。

当S2I将应用程序代码复制到构建器映像中时,它将放置在/ tmp / src中 。 由于上游映像将GOPATH设置为/ go ,因此汇编脚本仅需要复制到该目录中:我们在映像中先前设置的$ SOURCE_DIR 。 然后,只需运行go get and go build即可 。 由于WORKDIR设置为同一目录,因此脚本将从此处运行:


   
   
#!/bin/bash -e

# Copy the src to the current directory - the WORKDIR/$SOURCE_DIR.
cp -Rf / tmp / src / . . /
go get -v
go build -v -o app -a -installsuffix cgo

使用-o app build标志运行go build命令,以便生成的二进制文件具有可预测的名称(特别是“ app”)。

这就是汇编脚本所需的全部内容,但是还可以在脚本的末尾包含go test -v ,以确保应用程序通过所有代码测试(因为如果任何测试失败,它将使映像构建失败)。

汇编脚本就是这样。 GitHub中的组装脚本包括一些命令,用于从先前的版本中复制工件,但其他方面是相同的。

如果S2I正在运行所生成图像生成的容器,则S2I使用运行脚本来执行该应用程序。 适当地,它只有两行:


   
   
#!/bin/bash
exec app

注意:如果应用程序需要参数,则需要对该脚本进行一些微调以传递这些参数(这就是为什么当应用程序本身只是“运行”脚本时,Go才包含该脚本的原因)。

保存工件

S2I不需要保存工件图像。 它的目的是重用以前构建的构件(例如:下载的PIP软件包或Ruby gem)并进行增量构建,以便可以更快地构建开发映像。 Golang构建器映像将使用它一点不同:允许我们提取已编译的二进制文件,以便可以将其包含在更苗条的运行时映像中(请参见下文)。

S2I期望save-artifacts脚本获取应用程序的所有文件和依赖项,并通过tar命令将它们流式传输到stdout,以便可以在另一端接收并保存它们。 从理论上讲这很容易,但是如果您不小心,可能会很棘手。 流到stdout的内容必须包含tar文件的内容; 我们必须小心以防止发送文本或其他内容。 我们需要将tar以外的所有其他输出通过管道传递到/ dev / null,以确保tar归档文件不会被其他数据破坏。

专家提示:如果我们尝试通过运行save-artifacts脚本作为容器的命令来手动将tar文件的内容从容器中流出来,则我们一定不要使用-i-t参数,因为tar拒绝流输出到伪终端。

在我们的例子中,由于构建器正在编译单个二进制文件,因此该脚本也只有两行,并且没有其他需要担心的输出:


   
   
#!/bin/sh -e
tar cf – app

现在,我们为Golang应用程序提供了功能齐全的S2I环境。 我们可以在命令行上解决这个问题。 如果您需要对所有这些文件进行复习,请返回并阅读本系列的第一篇文章 。 在下一篇文章中,我们将继续构建过程,并完成构建Go应用程序的工作流程。

翻译自: https://opensource.com/article/19/5/source-image-golang-part-2

go 构建image图像

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值