<ruby id="bdb3f"></ruby>

    <p id="bdb3f"><cite id="bdb3f"></cite></p>

      <p id="bdb3f"><cite id="bdb3f"><th id="bdb3f"></th></cite></p><p id="bdb3f"></p>
        <p id="bdb3f"><cite id="bdb3f"></cite></p>

          <pre id="bdb3f"></pre>
          <pre id="bdb3f"><del id="bdb3f"><thead id="bdb3f"></thead></del></pre>

          <ruby id="bdb3f"><mark id="bdb3f"></mark></ruby><ruby id="bdb3f"></ruby>
          <pre id="bdb3f"><pre id="bdb3f"><mark id="bdb3f"></mark></pre></pre><output id="bdb3f"></output><p id="bdb3f"></p><p id="bdb3f"></p>

          <pre id="bdb3f"><del id="bdb3f"><progress id="bdb3f"></progress></del></pre>

                <ruby id="bdb3f"></ruby>

                ThinkChat2.0新版上線,更智能更精彩,支持會話、畫圖、視頻、閱讀、搜索等,送10W Token,即刻開啟你的AI之旅 廣告
                >注意:如果您是初學者,您可以暫時跳過后面的內容,直接學習 [容器](../container) 一節。 ## 利用 commit 理解鏡像構成 注意: `docker commit` 命令除了學習之外,還有一些特殊的應用場合,比如被入侵后保存現場等。但是,不要使用 `docker commit` 定制鏡像,定制鏡像應該使用 `Dockerfile` 來完成。如果你想要定制鏡像請查看下一小節。 鏡像是容器的基礎,每次執行 `docker run` 的時候都會指定哪個鏡像作為容器運行的基礎。在之前的例子中,我們所使用的都是來自于 Docker Hub 的鏡像。直接使用這些鏡像是可以滿足一定的需求,而當這些鏡像無法直接滿足需求時,我們就需要定制這些鏡像。接下來的幾節就將講解如何定制鏡像。 回顧一下之前我們學到的知識,鏡像是多層存儲,每一層是在前一層的基礎上進行的修改;而容器同樣也是多層存儲,是在以鏡像為基礎層,在其基礎上加一層作為容器運行時的存儲層。 現在讓我們以定制一個 Web 服務器為例子,來講解鏡像是如何構建的。 ```bash $ docker run --name webserver -d -p 80:80 nginx ``` 這條命令會用 `nginx` 鏡像啟動一個容器,命名為 `webserver`,并且映射了 80 端口,這樣我們可以用瀏覽器去訪問這個 `nginx` 服務器。 如果是在 Linux 本機運行的 Docker,或者如果使用的是 Docker for Mac、Docker for Windows,那么可以直接訪問:<http://localhost>;如果使用的是 Docker Toolbox,或者是在虛擬機、云服務器上安裝的 Docker,則需要將 `localhost` 換為虛擬機地址或者實際云服務器地址。 直接用瀏覽器訪問的話,我們會看到默認的 Nginx 歡迎頁面。 <img src="_images/images-mac-example-nginx.png" width="80%" > 現在,假設我們非常不喜歡這個歡迎頁面,我們希望改成歡迎 Docker 的文字,我們可以使用 `docker exec` 命令進入容器,修改其內容。 ```bash $ docker exec -it webserver bash root@3729b97e8226:/# echo '<h1>Hello, Docker!</h1>' > /usr/share/nginx/html/index.html root@3729b97e8226:/# exit exit ``` 我們以交互式終端方式進入 `webserver` 容器,并執行了 `bash` 命令,也就是獲得一個可操作的 Shell。 然后,我們用 `<h1>Hello, Docker!</h1>` 覆蓋了 `/usr/share/nginx/html/index.html` 的內容。 現在我們再刷新瀏覽器的話,會發現內容被改變了。 <img src="_images/images-create-nginx-docker.png" width="80%" > 我們修改了容器的文件,也就是改動了容器的存儲層。我們可以通過 `docker diff` 命令看到具體的改動。 ```bash $ docker diff webserver C /root A /root/.bash_history C /run C /usr C /usr/share C /usr/share/nginx C /usr/share/nginx/html C /usr/share/nginx/html/index.html C /var C /var/cache C /var/cache/nginx A /var/cache/nginx/client_temp A /var/cache/nginx/fastcgi_temp A /var/cache/nginx/proxy_temp A /var/cache/nginx/scgi_temp A /var/cache/nginx/uwsgi_temp ``` 現在我們定制好了變化,我們希望能將其保存下來形成鏡像。 要知道,當我們運行一個容器的時候(如果不使用卷的話),我們做的任何文件修改都會被記錄于容器存儲層里。而 Docker 提供了一個 `docker commit` 命令,可以將容器的存儲層保存下來成為鏡像。換句話說,就是在原有鏡像的基礎上,再疊加上容器的存儲層,并構成新的鏡像。以后我們運行這個新鏡像的時候,就會擁有原有容器最后的文件變化。 `docker commit` 的語法格式為: ```bash docker commit [選項] <容器ID或容器名> [<倉庫名>[:<標簽>]] ``` 我們可以用下面的命令將容器保存為鏡像: ```bash $ docker commit \ --author "Tao Wang <twang2218@gmail.com>" \ --message "修改了默認網頁" \ webserver \ nginx:v2 sha256:07e33465974800ce65751acc279adc6ed2dc5ed4e0838f8b86f0c87aa1795214 ``` 其中 `--author` 是指定修改的作者,而 `--message` 則是記錄本次修改的內容。這點和 `git` 版本控制相似,不過這里這些信息可以省略留空。 我們可以在 `docker image ls` 中看到這個新定制的鏡像: ```bash $ docker image ls nginx REPOSITORY TAG IMAGE ID CREATED SIZE nginx v2 07e334659748 9 seconds ago 181.5 MB nginx 1.11 05a60462f8ba 12 days ago 181.5 MB nginx latest e43d811ce2f4 4 weeks ago 181.5 MB``` 我們還可以用 `docker history` 具體查看鏡像內的歷史記錄,如果比較 `nginx:latest` 的歷史記錄,我們會發現新增了我們剛剛提交的這一層。 ```bash $ docker history nginx:v2 IMAGE CREATED CREATED BY SIZE COMMENT 07e334659748 54 seconds ago nginx -g daemon off; 95 B 修改了默認網頁 e43d811ce2f4 4 weeks ago /bin/sh -c #(nop) CMD ["nginx" "-g" "daemon 0 B <missing> 4 weeks ago /bin/sh -c #(nop) EXPOSE 443/tcp 80/tcp 0 B <missing> 4 weeks ago /bin/sh -c ln -sf /dev/stdout /var/log/nginx/ 22 B <missing> 4 weeks ago /bin/sh -c apt-key adv --keyserver hkp://pgp. 58.46 MB <missing> 4 weeks ago /bin/sh -c #(nop) ENV NGINX_VERSION=1.11.5-1 0 B <missing> 4 weeks ago /bin/sh -c #(nop) MAINTAINER NGINX Docker Ma 0 B <missing> 4 weeks ago /bin/sh -c #(nop) CMD ["/bin/bash"] 0 B <missing> 4 weeks ago /bin/sh -c #(nop) ADD file:23aa4f893e3288698c 123 MB ``` 新的鏡像定制好后,我們可以來運行這個鏡像。 ```bash docker run --name web2 -d -p 81:80 nginx:v2 ``` 這里我們命名為新的服務為 `web2`,并且映射到 `81` 端口。如果是 Docker for Mac/Windows 或 Linux 桌面的話,我們就可以直接訪問 <http://localhost:81> 看到結果,其內容應該和之前修改后的 `webserver` 一樣。 至此,我們第一次完成了定制鏡像,使用的是 `docker commit` 命令,手動操作給舊的鏡像添加了新的一層,形成新的鏡像,對鏡像多層存儲應該有了更直觀的感覺。 ### 慎用 `docker commit` 使用 `docker commit` 命令雖然可以比較直觀的幫助理解鏡像分層存儲的概念,但是實際環境中并不會這樣使用。 首先,如果仔細觀察之前的 `docker diff webserver` 的結果,你會發現除了真正想要修改的 `/usr/share/nginx/html/index.html` 文件外,由于命令的執行,還有很多文件被改動或添加了。這還僅僅是最簡單的操作,如果是安裝軟件包、編譯構建,那會有大量的無關內容被添加進來,如果不小心清理,將會導致鏡像極為臃腫。 此外,使用 `docker commit` 意味著所有對鏡像的操作都是黑箱操作,生成的鏡像也被稱為**黑箱鏡像**,換句話說,就是除了制作鏡像的人知道執行過什么命令、怎么生成的鏡像,別人根本無從得知。而且,即使是這個制作鏡像的人,過一段時間后也無法記清具體在操作的。雖然 `docker diff` 或許可以告訴得到一些線索,但是遠遠不到可以確保生成一致鏡像的地步。這種黑箱鏡像的維護工作是非常痛苦的。 而且,回顧之前提及的鏡像所使用的分層存儲的概念,除當前層外,之前的每一層都是不會發生改變的,換句話說,任何修改的結果僅僅是在當前層進行標記、添加、修改,而不會改動上一層。如果使用 `docker commit` 制作鏡像,以及后期修改的話,每一次修改都會讓鏡像更加臃腫一次,所刪除的上一層的東西并不會丟失,會一直如影隨形的跟著這個鏡像,即使根本無法訪問到。這會讓鏡像更加臃腫。
                  <ruby id="bdb3f"></ruby>

                  <p id="bdb3f"><cite id="bdb3f"></cite></p>

                    <p id="bdb3f"><cite id="bdb3f"><th id="bdb3f"></th></cite></p><p id="bdb3f"></p>
                      <p id="bdb3f"><cite id="bdb3f"></cite></p>

                        <pre id="bdb3f"></pre>
                        <pre id="bdb3f"><del id="bdb3f"><thead id="bdb3f"></thead></del></pre>

                        <ruby id="bdb3f"><mark id="bdb3f"></mark></ruby><ruby id="bdb3f"></ruby>
                        <pre id="bdb3f"><pre id="bdb3f"><mark id="bdb3f"></mark></pre></pre><output id="bdb3f"></output><p id="bdb3f"></p><p id="bdb3f"></p>

                        <pre id="bdb3f"><del id="bdb3f"><progress id="bdb3f"></progress></del></pre>

                              <ruby id="bdb3f"></ruby>

                              哎呀哎呀视频在线观看