docker補充

Docker最初是dotcloud 公司創始人Solomon Hykes 在法國期間發起的一個公司內部的項目,在2013年3月1以Apache 2.0授權協議開源,主要項目代碼在GiHub 上進行維護,Docker 項目後來還加入了Linux 基金會,併成立推動開放容器聯盟。

Docker 使用的是Google公司推出的Go語言進行開發實現,基於Linux內核的cgroup,namespace,以及AUFS類的Union FS等技術,對進程進行封裝隔離,屬於操作系統層面的虛擬化技術,由於隔離的進程獨立於宿主和其他的隔離的進程,因此也稱其爲容器。

跟普通虛擬機進行比較,傳統的虛擬機技術在虛擬出一套硬件後,在其上運行一個完整的操作系統,在該系統上面再運行所需要的進程,而容器內核的應用進程直接運行於宿主機的內核,容器內沒有自己的內核,而且也沒有進行硬件虛擬,因此容器要比傳統虛擬機更爲輕便。

在使用Docker 包括三個基本的概念,鏡像,容器,倉庫,該三個概念就是Docker的整個生命週期。

Docker 引擎是一個包含以下主要組件的客戶端服務器應用程序,一種服務器,它是一種稱爲守護進程並且長時間運行的程序,REST API 用於指定程序可以用來與守護進程通信的接口,並指示它做什麼,還是一個有命令行界面工具的客戶端。

在使用docker的時候,我們需要知道Docker的架構,Docker使用客戶端 - 服務器 (c/s)架構模式,使用遠程的api 來管理和創建Docker容器,Docker 容器通過docker 鏡像來創建。在docker中,docker容器和鏡像的關係類似於對象和類的關係

鏡像(images) docker 鏡像 是用於創建docker容器的模版

容器(container) 容器是獨立運行的一個或一組應用

客戶端(client )Docker 客戶端通過命令行或者其他工具使用Docker API,便可於Docker 的守護進程進行通信

主機(Host)一個物理或者虛擬機的機器用於執行Docker 守護進程和容器

倉庫 (Registry) Docker 倉庫用於保存鏡像,可以理解爲代碼控制中的代碼倉庫,Docker Hub 提供了大量的Docker 鏡像集合提供使用

Docker Machine Docker Machine 是一個簡化Docker 安裝的命令行工具,通過一個簡單的命令行即可在相應的平臺上安裝Docker 的 分層存儲(重點)

 因爲鏡像包含操作 系統完整的root 文件系統,其提及往往是龐大的,因爲在Docker 在設計的時候,就充分利用了Union FS (聯合安裝)的技術,將其設計分曾存儲的架構,所以嚴格來說,鏡像並非是一個像iso那樣的打包文件,鏡像只是一個虛擬的概念,其實際體現並非由一個文件組成,而是由一組文件組成,或者說,是由多層文件系統聯合組成。鏡像在構建的時候,會一層層的構建,前一層是後一層的基礎(因爲鏡像是由多個文件組成,只有當基礎的文件將上面文件所需要的環境構建成功之後,上層的文件才能構建成功),每一層構建完就不會再發生改變,後一層上的任何改變之後發生在自己的這一層,比如,刪除前一層的文件的操作,實際不是真的刪除前一層的文件,而是僅在當前層標記爲該文件已經刪除,但是實際上該文件會一直跟隨鏡像,因此,在構建鏡像的時候,需要額外小心,每一層儘量只包含該層需要添加的東西,任何額外的東西應該在該層構建結束前清理掉,分層存儲的特徵使得鏡像得意複用,定製變的更爲容易,甚至可以用之前構建好的鏡像作爲基礎層,然後再進一步添加新的層,以定製自己所需要的內容,構建新的鏡像。

Docker 容器

容器的實質是進程,但與直接在宿主執行的進程不同,容器進程運行在屬於自己的獨立的 命名空間 , 因此容器可以擁有自己的 root 文件系統,自己的網絡配置,自己的進程空間,甚至自己的ID 空間,容器內的進程是運行在一個隔離的環境裏的,使用起來沒,就好像是在一個獨立與宿主機的系統操做一樣,這種特性使得容器封裝的應用比直接在宿主機運行更加安全(沙箱機制)。

前面講解的鏡像是使用的分層存儲,容器也是如此,每一個容器運行的時候,是以鏡像爲基礎,在其上創建一個當前容器的存儲層,我們可以稱爲這個爲容器運行時讀寫爲準備的存儲層爲容器存儲層。

容器存儲層的生存週期和容器一樣,當容器消亡時,容器存儲層也隨之消亡,因此,任何個保存與容器存儲層的信息的信息都會隨着容器的刪除而丟失。

按照Docker 最佳實踐的要求,容器不應該向其存儲層內寫入任何數據,容器存儲層要保持無狀態化,所有的文件寫入操作,都應該由數據卷(Volume)或者綁定宿主機目錄,在這些位置的讀寫會跳過容器存儲層,直接對宿主(或網絡存儲)發生讀寫,其性能和穩定性更高。

數據卷的生命週期是獨立於容器的,容器的消亡,數據卷不會消亡,因此,使用數據卷後,容器的刪除或者重新運行之後,數據切不會丟失(數據卷就是把容器中的目錄映射到宿主機上面,在讀寫的時候,不會將數據保存到容器中,而是直接保存到宿主機上的映射的目錄中,當容器消亡,或者刪除時,宿主機上映射的文件中的數據並不會消失,當下次容器運行的時候,還是會將對應的文件進行映射,從而不會發生任何改變)

Docker倉庫

鏡像構建完成之後,可以很容易在當前的宿主機上面運行,但是,如果需要在其他的服務器上面使用這個鏡像,我們就需要一個集中的存儲,分佈鏡像的服務,Docker Registry 就是這樣的服務,一個Docker Registry 中可以含有多個倉庫(Reposutory),每個倉庫可以包含多個標籤,每個標籤對應一個鏡像。

通常,一個倉庫會包含同一個軟件不同版本的鏡像,而標籤就常用於對應軟件的各個版本,我們可以使用 倉庫名 : 標籤 的格式來指定具體的軟件是那個版本的鏡像,如果不給出標籤,將以latest 作爲默認標籤。例如:ubuntu:14.04

倉庫名經常以 兩段式路徑形式出現,比如 jwilder/nginx-proxy 前者往往以爲着Docker Registry 多用戶環境下的用戶名,後者則表示是對應的軟件名,但這並非絕對,取決於所使用的Docker Registry 的軟件或服務。

共有的Docker Registry 

最常用的就是GItHub ,在使用的時候需要配置一些加速器,來提供下載的速度。

私有的Docker Registry

自己發佈的項目大部分都是發佈到自己的私有倉庫中,可以在本地搭建私有倉庫,Docker 官網 提供了 Docker Registry 鏡像,可以直接使用作爲私有的Registry服務。

重點- 使用DockerFile 定製鏡像

鏡像的定製實際上就是定製每一層所添加的配置、文件,如果我們可以把每一層的修改、安裝、構建、操作的命令都寫到一個腳本,用這個腳本來構建、定製鏡像。

Dockerfile是一個文本文件,其內包含了一條條的指令,每一條指令構建一層,因此,每一條指令的內容,就是描述蓋層應當如何讓構建。

講解一下Dockerfile的指令

COPY:拷貝的指令,用於拷貝文件,用法於Linux的用法一致

ADD:跟COPY的用法一致,也是拷貝文件,但是該指令會自動的解壓縮到目標路徑中去,但是官網不提倡使用該方式,因爲該方式沒有copy的意思明確,並且add指令會使得鏡像構建緩存失效,從而降低鏡像的構建速度

CMD:CMD指令的格式和RUN類似,用來執行命令的,但是,在一個Dockerfile文件中,只能有一個CMD指令,該指令一般用於啓動程序使用,在實際操作中,一般爲CMD ["java" ,"-jar" ,"a.jar","--spring-profiles.active=pord"], 使用。

ENTRYPOINT : 目的是和CMD一樣的,都是在指定容器啓動的程序以及參數,ENTRYPOINT在運行時也可以代替,不過比CMD要略顯繁瑣,需要通過docker run 的參數 --entrypoint來指定。

當是定了ENTRYPOINT後,CMD的含義就發生了改變,不再是直接的運行其命令,而是將CMD的內容作爲參數傳遞給ENTRYPOINT指令,該指令也可以用來運行 .sh 後綴名的文件。

EVN:用於設置環境變量,無論是後面其他指令,如RUN 還是運行時的應用,都可以直接使用這裏定義的環境變量,

  例如:ENV NODE_VERSION 7.2.0 在後面使用的時候,可以直接使用 $NODE_VERSION 進行數據的獲取

EXPOSE:該指令用於暴露端口 宿主機端口:容器端口

WORKDIR:用來指定工作目錄,因爲在創建容器的時候,我們說過,一個容器是由很多層組成的,而且每層之間互不影響,後面的層是在前面基礎層的基礎上進行操作的,所以在操作每一層的時候,需要將當前目錄切換到當前層進行操作,如果不指定,在另外一個層中進行操作是會報錯的

 

 

 

 

 

 

 

 

 

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章