在构建、共享和运行Docker容器安全应用程序时,您需要考虑一些Docker安全最佳实践。Docker是一个用于构建、共享和运行容器化应用程序的开源平台。您可以轻松构建包含您的应用程序的Docker映像,在您的团队内外共享它们,并使用一个命令运行您的应用程序。看起来很容易,对吧?但是,确实如此。您可能已经知道Docker是什么以及它是如何工作的。因此,我们不会详细介绍它。本博客将介绍使用Docker平台时要考虑的12大Docker安全最佳实践。为什么需要保护Dockerfile、容器?容器化因应用程序可以部署在任何地方的灵活性而风靡全球。但是,这也引入了一些安全漏洞。Docker和Docker容器使得构建、共享和部署应用程序变得非常容易,这使得部署后发现、检测、报告和修复安全问题变得困难。通过将安全性转移到左侧,可以防止和最小化大部分开销。因此,从Dockerfile到Docker容器的所有内容都必须得到保护,以确保Docker容器的安全。Docker安全性的12大最佳实践从一开始就通过各种规程提高Docker容器的安全性,从编写Dockerfile到运行Docker容器。让我们继续看看可以确保Docker容器安全的12大Docker安全最佳实践。1.使用Docker映像使您的Docker主机和Docker引擎保持最新Docker容器在主机上可用的Docker引擎上运行。这些主机可以是Linux/Mac或Windows。Docker引擎可以是可用版本之一。使用最新的稳定版本至关重要,它更新了以前版本中的已知问题。这同样适用于主机操作系统。例如,截至2021年12月27日,如果您使用Ubuntu作为主机操作系统,则可以使用Ubuntu20.04LTS而不是Ubuntu16.04LTS,对于DockerEngine,您可以使用20.10.11。查找Docker发行说明以获取更多信息,并检查Docker支持的操作系统平台。安装更新或补丁非常重要,因为每个补丁都解决了CVE-2021-41092等漏洞。这个特定的补丁修复了一个错误,即用于从CLI登录docker注册表的凭据被发送到“registry-1.docker.io”而不是预期的私有注册表;这通常是由于错误配置的配置文件(通常是`~/.docker/config.json`)列出了`credsStore`或`credHelpers`。UbuntuOS发布周期请参考下方截图。2.避免在Dockerfile指令中存储机密数据Dockerfile包含创建Docker镜像的指令。COPY、RUN、ADD、CMD、ENTRYPOINT等。这些是一些命令指令,可能是Dockerfile的一部分。我们还可以根据需要使用ENV和ARGS在运行时或构建时设置变量。您可以使用ENV或ARGS指令在Docker容器中使用环境变量。设置环境变量时,您应该注意不要将机密、凭据、密码等分配给Dockerfile中的变量,也不要在任何命令中对它们进行硬编码。将此视为Dockerfile安全最佳实践之一,因为忽略它可能会导致潜在的安全威胁,并可能使您损失很多钱。例如,如果您在Dockerfile中硬编码数据库的密码或连接详细信息,将它们分配给环境变量,然后将您的Dockerfile上传到公共存储库,那么任何有权访问该存储库的人都可以获得这些凭据和访问详细信息或连接到一个数据库。FROMmysql:5.7ENVDATABASE_USERNAME=admin#<-可以设置用户名ENVDATABASE_PASSWORD=mypassword@!@#$#<-避免不惜一切代价设置密码3.避免使用不受信任的镜像仓库镜像仓库是存放Docker镜像的地方.它可以是私人的或公共的。DockerHub是Docker官方基于云的Docker镜像注册表,它是安装时的默认注册表。如果您不配置任何注册表,图像将从这个公共存储库中提取。当您从任何公共注册表中提取Docker镜像时,请注意来源,因为您可能不知道它们是谁构建的、它们是如何构建的,或者它们是否值得信赖。每当您从不受信任的发布者处提取图像时,请不要忘记验证源注册表和用于构建图像的Dockerfile。此外,您的Dockerfile的基础映像,即FROM指令。FROM#<-在使用之前验证基础镜像4.谨防递归复制当为需要将文件从本地计算机复制到DockerImage的应用程序编写Dockerfile时,您应该注意使用COPY复制的内容操作说明。您的本地计算机上可能存在包含机密数据或保密信息的文件。因此,如果将这些文件复制到Docker镜像中,任何有权访问容器的人都可以从容器中获取这些文件。因此,仅复制容器中需要的文件而不是复制所有内容非常重要,如下面的说明所示,以提高Docker容器的安全性。你可以试试。码头工人。它可以帮助排除与模式匹配的文件和目录,并避免使用ADD或COPY将大文件或敏感文件不必要地发送到图像。例如,在下面的COPY指令中,当前位置的所有文件将被复制到Docker镜像中。因此,您应该始终避免“复制”。./”,并且应该在COPY指令中将文件名明确指定为“COPYpackage.json./”FROMnode:12.18.4-alpineWORKDIR/appENVPATH/app/node_modules/.bin:$PATHCOPY../#<-避免这种COPY指令5.在开发期间扫描图像Docker图像是从Dockerfiles构建的,其中包含使用基础图像、安装包、启动应用程序等的说明。Dockerfiles也可能包含不正确的硬编码凭据。那么,如果您使用的基础镜像存在一些漏洞,并且Dockerfile中硬编码的凭据从使用该Dockerfile构建的镜像创建的容器中泄露了怎么办?扫描镜像是识别Docker镜像中已知安全漏洞的过程,以便您可以在将它们推送到DockerHub或任何其他注册表之前修复它们。您现在可以直接从DockerDesktopCLI运行Snyk漏洞扫描,因为Snyk和Docker已经合作。例如,您可以通过提供用于创建镜像的Dockerfile来获取有关Docker镜像的详细报告。dockerscan--filePATH_TO_DOCKERFILEDOCKER_IMAGE6.使用固定标签实现不变性在Docker中,图像具有标签。Docker镜像最常见和默认的标签是“最新”。因此,如果您不为图像分配标签,默认情况下它将具有“最新”标签。可以使用相同的标签发布多个图像,即Docker图像标签不是不可变的。所以这非常重要-更喜欢为您的图像使用更具体的标签,这样您每次都能获得相同的图像。最好在您的私有存储库中保留图像的副本。使用DockerContentTrust(DCT)将数字签名用于客户端或运行时验证特定图像标签的完整性和发布者。访问官方文档以了解更多信息。例如,假设Dev1提取myimage:latestimag,在他/她的计算机上运行该应用程序的1.1版,并发现该应用程序可以顺利运行。后来,Dev2拉取同一个镜像myimage:latest,在自己的电脑上运行应用,发现应用坏了。在这里,您确定它们都运行相同版本的应用程序吗?答案是否定的,因为在Dev2拉取镜像myimage:latest之前,Dev3进行了更改并推送了同名myimage:latest应用程序的不稳定版本1.2。现在,当他们部署镜像myimage:latest时,它将指向应用程序的不稳定版本1.2,这会破坏生产环境。7.LintDockerfile市场上有各种Dockerfilelinter,可用于确保Dockerfile遵循Dockerfile安全最佳实践。如果生成警告,Linters可以帮助您停止构建过程;他们遍历您的Dockerfile并在Dockerfile不遵循最佳实践时发出警告。您可以利用Hadolint,这是一个用于验证内联bash和lintingDockerfile的开源项目。8.限制容器资源默认情况下,在主机上运行的Docker容器可以利用所有RAM和CPU。在Docker容器受损的情况下,攻击者可能会尝试使用主机资源来执行恶意活动。此外,如果特定容器开始使用主机上的所有资源,则驻留在同一位置的其他容器可能会因资源不可用而受到影响。为避免这种情况,建议对Docker容器设置资源限制,以便它们使用的资源不会超过分配给它们的资源,并有助于提供Docker容器安全性。例如,如果主机有1个CPU,下面的第一个命令将保证容器每秒最多使用50%的CPU,第二个命令将容器的内存使用限制为1GB。CPU限制dockerrun-it--cpus=".5"ubuntu/bin/bash内存限制dockerrun-it--memory="1g"ubuntu/bin/bash9.不要使用名称/var/runUNIXdomainsocketcommunicationfor/docker.sock公开DockerDaemonSocketDocker,这是DockerAPI的主要入口点。任何人如果有权访问Docker守护程序套接字,也可以获得root访问权限。因此,允许任何用户写入/var/run/docker.sock或将套接字暴露给容器对系统的其余部分来说是一个很大的Docker容器安全风险,因为这会赋予它root权限。因此,切勿在Docker容器内挂载/var/run/docker.sock。例如,永远不要使用“-v/var/run/docker.sock:/var/run/docker.sock”之类的选项运行dockerrun命令,并将其视为Docker安全最佳实践之一,可以帮助您保持系统安全保护。10.以非root用户身份运行容器大多数镜像过于宽松,根据sysdig.com的2021年容器安全和使用报告,58%的容器以root用户身份运行。这不被认为是Dockerfile最佳实践;应该避免,因为在极少数情况下,您确实需要以root身份在容器中运行您的进程。为确保您没有使用root用户,请始终使用用户名指定“USER”指令。在Docker容器中使用非root用户可确保缓解容器运行时中的潜在漏洞并确保Docker容器安全。例如,始终尝试使用非根用户在容器中创建和运行您的应用程序进程。您需要的非root用户可能不存在;因此,您必须先创建一个才能使用它。FROMalpine:3.12RUNadduser-Dnon-root-user&&chown-Rnon-root-user/myapp-data#<-创建用户USERnon-root-user#<-使用非root用户11。保持Docker在整个Dockerfile构建过程中保持图像尽可能小会创建许多仅在构建期间需要的工件。需要这些包来编译或运行单元测试、临时文件、机密等的依赖项。将这些工件保留在基础映像中会增加Docker映像的大小,这会减慢下载时间并随着更多包的出现而增加攻击面加载。因此,Docker支持多阶段构建的原因之一。此功能允许您在构建过程中使用大量临时图像,同时仅保留最新图像和复制到其中的数据。因此,您有两个图像:图1:第一个图像是一个大图像,其中包含创建应用程序和运行测试所需的许多依赖项。图2:就库的大小和数量而言,图像非常小且轻,只有在生产中运行程序所需的工件副本。通过这种方式,您可以使用多阶段构建来构建Docker镜像,从而减小镜像的大小并避免安装不必要的库,从而增加潜在安全风险的可能性。12.使用最新的Docker镜像。由于定期发现新的安全漏洞,因此保持最新的安全补丁是Docker安全最佳实践。因此,使用经常更新的基础镜像并在其之上构建自己的镜像非常重要。不必总是使用最新版本,它可能包含重大更改,但您应该有一个版本控制策略。以下是基本映像需要考虑的几点。坚持使用更有可能获得安全更新的稳定或长期支持版本。在您的基础映像版本达到其使用寿命并且不再接收更新之前,请准备好删除旧版本并迁移。定期重建您的镜像并使用类似的技术从基础发行版中获取最新的软件包结论我们都知道“预防胜于治疗”,Docker也是如此。它的安全性不能简单地被忽视,因为这可能会导致一场巨大的灾难。我们现在知道为什么Docker容器安全性至关重要以及为什么它必须到位。将安全性左移对于改善Docker环境和减少管理开销至关重要。上面提到的前12条建议侧重于Dockerfile安全最佳实践和Docker容器安全最佳实践,将帮助您保护Docker容器和Docker环境。与经验丰富的团队一起保护您的Docker容器。
