如何在Docker容器中運(yùn)行Docker 「3種方法」
Docker In Docker的用處
dockerIndocker的一個(gè)潛在用處是CI管道,在代碼成功構(gòu)建后,您需要在其中構(gòu)建docker鏡像并將其推送到容器鏡像倉庫。
使用VM構(gòu)建Docker映像非常簡單。但是,當(dāng)您計(jì)劃將基于 Jenkins docker的動態(tài)代理用于CI/CD管道時(shí),docker In docker是必備功能。
沙盒環(huán)境。
出于實(shí)驗(yàn)?zāi)康模谀谋镜亻_發(fā)工作站上。
在Docker容器中運(yùn)行Docker
在Docker中實(shí)現(xiàn)Docker的三種方法
通過掛載docker.sock(DooD方法)運(yùn)行docker
dind 方法
使用Nestybox sysbox Docker運(yùn)行時(shí)
讓我們詳細(xì)了解每個(gè)選項(xiàng)。確保在主機(jī)中安裝了docker來嘗試此設(shè)置。
方法1:使用[/var/run/docker.sock]的Docker中運(yùn)行Docker
什么是/var/run/docker.sock?
/var/run/docker.sock是默認(rèn)的Unix套接字。套接字用于在同一主機(jī)上的進(jìn)程之間進(jìn)行通信。Docker守護(hù)程序默認(rèn)情況下偵聽docker.sock。如果您在運(yùn)行Docker守護(hù)程序的主機(jī)上,則可以使用/ var/run/docker.sock管理容器。
例如,如果您運(yùn)行以下命令,它將返回docker engine的版本。
- curl --unix-socket /var/run/docker.sock http://localhost/version
現(xiàn)在您已經(jīng)了解了什么是docker.sock,讓我們看看如何使用在docker中運(yùn)行docker。
要在docker內(nèi)部運(yùn)行docker,要做的只是在默認(rèn)Unix套接字docker.sock作為卷的情況下運(yùn)行docker 。
例如,
- docker run -v /var/run/docker.sock:/var/run/docker.sock \ -ti docker-image
請注意:如果您的容器可以訪問docker.sock,則意味著它具有對docker守護(hù)程序的更多特權(quán)。因此,在實(shí)際項(xiàng)目中使用時(shí),請了解并使用安全隱患。
現(xiàn)在,從容器中,您應(yīng)該能夠執(zhí)行docker命令來構(gòu)建鏡像并將其推送到鏡像倉庫。在這里,實(shí)際的docker操作發(fā)生在運(yùn)行docker容器的VM主機(jī)上,而不是在容器內(nèi)部進(jìn)行。意思是,即使您正在容器中執(zhí)行docker命令,也指示Docker客戶端通過以下docker.sock方式連接到VM主機(jī)docker-engine。
此方法實(shí)際上在容器內(nèi)部創(chuàng)建一個(gè)子容器。僅當(dāng)您確實(shí)要在容器中包含容器和圖像時(shí)才使用此方法。否則,我建議您使用第一種方法。為此,您只需要使用帶有dind標(biāo)簽的官方docker鏡像即可。該dind映像使用Docker所需的實(shí)用程序進(jìn)行制作以在Docker容器中運(yùn)行。
方法3:使用Sysbox運(yùn)行時(shí)的Docker中的Docker
方法1和2在安全方面有一些缺點(diǎn),因?yàn)樵谔貦?quán)模式下運(yùn)行容器。Nestybox嘗試通過使用sysbox Docker運(yùn)行時(shí)來解決該問題。
如果使用Nestybox sysbox運(yùn)行時(shí)創(chuàng)建容器,則它可以在能夠運(yùn)行systemd,docker,kubernetes的容器內(nèi)創(chuàng)建虛擬環(huán)境,而無需特權(quán)訪問基礎(chǔ)主機(jī)系統(tǒng)。解釋sysbox需要足夠的理解力,因此我不在本文的討論范圍之內(nèi)。請參考此頁面以全面了解sysbox。
步驟1:安裝sysbox運(yùn)行時(shí)環(huán)境。請參閱此頁面以獲取有關(guān)安裝sysbox運(yùn)行時(shí)的最新官方說明。
第2步:一旦擁有sysbox運(yùn)行時(shí)可用,您要做的就是使用sysbox運(yùn)行時(shí)標(biāo)志啟動docker容器,如下所示。在這里,我們使用的是官方docker dind映像。
- docker run --runtime=sysbox-runc --name sysbox-dind -d docker:dind
步驟3:現(xiàn)在將exec會話帶到sysbox-dind容器。
- docker exec -it sysbox-dind /bin/sh
現(xiàn)在,您可以嘗試使用Dockerfile構(gòu)建映像,如先前方法所示。
關(guān)鍵注意事項(xiàng)
僅在必要時(shí)在Docker中使用Docker。在將任何工作流程遷移到Docker-in-Docker方法之前,請進(jìn)行足夠的測試。
在特權(quán)模式下使用容器時(shí),請確保您已獲得企業(yè)安全團(tuán)隊(duì)有關(guān)計(jì)劃執(zhí)行的必要批準(zhǔn)。
在帶有kubernetes容器的Docker中使用Docker時(shí),存在一些挑戰(zhàn)。請參閱此博客以了解更多信息。
如果您打算使用Nestybox(Sysbox),請確保已通過企業(yè)架構(gòu)師/安全團(tuán)隊(duì)的測試和批準(zhǔn)。
常見問題
這是Docker問題中一些經(jīng)常問到的Docker。
在Docker中運(yùn)行Docker安全嗎?
使用docker.sock和dind方法在docker中運(yùn)行docker的安全性較差,因?yàn)樗哂袑ocker守護(hù)程序的完全特權(quán)
如何在Jenkins中的docker中運(yùn)行docker?
您可以使用Jenkins動態(tài)docker代理設(shè)置并將docker.sock安裝到代理容器,以從代理容器內(nèi)執(zhí)行docker命令。