Image tag是不穩定的
Docker image的tag是不穩定的,這句話的意思是就算tag不變,其所代表的image並非一成不變,例如openjdk:8
在去年代表jdk 8u161今年則代表jdk 8u191。就算你使用openjdk:8u181
也不能保證這個image是不變的,爲什麼這麼說?
一個Docker image大致是由4部分組成的:
- 其依賴的基礎鏡像,由Dockerfile的
FROM
指令所指定 - 其所包含的軟件,在這個例子裏就是 openjdk 8u181
- Dockerfile的其他腳本
- 啓動入口,比如
docker-entrypoint.sh
就算軟件不發生變化,另外3個也是有可能發生變化的,而構建的新image的tag依然是openjdk:8u181
。而且要注意到一般採用的是軟件的版本號作爲tag,而不是commit、構建日期作爲tag。如果你是Java程序員,可以類比docker image tag爲maven的SNAPSHOT。
那這意味着什麼?
- 從docker image使用方角度,每次啓動之前都需要pull一下,確保使用了新的image
- 從docker image提供方角度,就算你的軟件版本已經凍結,你仍然需要定期構建image併發布倉庫上
針對穩定與非穩定版本的構建策略
和Maven的版本定義一樣,你的軟件應該分爲兩種:
- stable版,即一旦發佈其版本號對應的代碼不會再做修改
- snapshot版,又稱nightly-build版,即該版本號對應的代碼是不穩定的
對於stable版,你應該定期對其構建image。比如你有版本1.0、1.1、1.2,那你應該定期從軟件倉庫中下載這三個版本的構建物,然後對爲它們構建image。以Maven舉例,定期從Maven倉庫下載它們的Jar,然後爲它們構建image。記得確保docker build
添加了--pull
選項。
對於snapshot版,你應該將構建image的過程融入到軟件的構建過程中。以Maven爲例,使用spotify-dockerfile-plugin,mvn clean install dockerfile:build dockerfile:push
。
不論是stable版還是snapshot版,都應該利用CI/CD工具(如Jenkins)將image構建工作自動化。