詳解SpringBoot(2.3)應用製作Docker鏡像(官方方案)

来源:https://www.cnblogs.com/bolingcavalry/archive/2020/06/08/13063508.html
-Advertisement-
Play Games

關於《SpringBoot-2.3容器化技術》系列 《SpringBoot-2.3容器化技術》系列,旨在和大家一起學習實踐2.3版本帶來的最新容器化技術,讓咱們的Java應用更加適應容器化環境,在雲計算時代依舊緊跟主流,保持競爭力; 全系列文章分為主題和輔助兩部分,主題部分如下: 《體驗Spring ...


關於《SpringBoot-2.3容器化技術》系列

《SpringBoot-2.3容器化技術》系列,旨在和大家一起學習實踐2.3版本帶來的最新容器化技術,讓咱們的Java應用更加適應容器化環境,在雲計算時代依舊緊跟主流,保持競爭力;

全系列文章分為主題和輔助兩部分,主題部分如下:

  1. 《體驗SpringBoot(2.3)應用製作Docker鏡像(官方方案)》
  2. 《詳解SpringBoot(2.3)應用製作Docker鏡像(官方方案)》
  3. 《掌握SpringBoot-2.3的容器探針:基礎篇》
  4. 《掌握SpringBoot-2.3的容器探針:深入篇》
  5. 《掌握SpringBoot-2.3的容器探針:實戰篇》

輔助部分是一些參考資料和備忘總結,如下:

  1. 《SpringBoot-2.3鏡像方案為什麼要做多個layer》
  2. 《設置非root賬號不用sudo直接執行docker命令》
  3. 《開發階段,將SpringBoot應用快速部署到K8S》

本篇簡介

前文,咱們快速體驗了官方推薦的docker鏡像製作方案,但也產生了幾個疑問:

  1. SpringBoot-2.3版本推薦的鏡像構建方案和舊版本比有什麼不同?
  2. pom.xml中spring-boot-maven-plugin插件新增的參數,到底做了什麼?
  3. Dockerfile中,java -Djarmode=layertools -jar application.jar extract這個操作啥意思?

本篇的目標就是解答上述問題,在尋找答案的過程中不斷補全知識點,提升自己;

關鍵知識點:鏡像layer

前文多次提到的鏡像layer到底是什麼,為什麼會有多層layer?有必要先把這個知識點夯實了,請參考文章《SpringBoot-2.3鏡像方案為什麼要做多個layer》

老版本SpringBoot的官方方案

SpringBoot-2.2.0.RELEASE版本為例,官方文檔(
https://docs.spring.io/spring-boot/docs/2.2.0.RELEASE/reference/pdf/spring-boot-reference.pdf)給出的做法如下:

  1. 將SpringBoot工程編譯構建,在target目錄得到jar;
  2. 在target目錄新建dependency文件夾;
  3. 將jar解壓到dependency文件夾;
  4. 編寫Dockerfile文件,內容如下:
FROM openjdk:8-jdk-alpine
VOLUME /tmp
ARG DEPENDENCY=target/dependency
COPY ${DEPENDENCY}/BOOT-INF/lib /app/lib
COPY ${DEPENDENCY}/META-INF /app/META-INF
COPY ${DEPENDENCY}/BOOT-INF/classes /app
ENTRYPOINT ["java","-cp","app:app/lib/*","com.example.MyApplication"]
  1. 可見,官方推薦的做法是將整個jar文件解壓,在Dockerfile中多次用COPY命令分別複製,這樣做的好處顯而易見:多個layer,如果鏡像的新版本中只修改了應用代碼,那麼下載鏡像時只會下載/app這個layer,其他部分直接使用本地緩存,這是docker鏡像的常規優化手段;
  2. 上述方案有個小問題:麻煩!!!
  3. 於是2.3.0.RELEASE版本做了些優化,讓事情變得簡單些;

2.3.0.RELEASE版本方案和舊版的區別

2.3.0.RELEASE版本構建Docker的步驟如下:

  1. pom.xml中的spring-boot-maven-plugin插件增加一個配置項;
    2.編譯構建生成jar;
  2. 編寫Dockerfile,裡面用到了多階段構建(multi-stage builds),用工具從jar中提取拆分後,再多次執行COPY命令將拆分後的內容放入鏡像,達到多個layer的目的;

因此,2.3.0.RELEASE版本和舊版本相比有如下變化:

  1. pom.xml中多了個參數;
  2. 構建好jar後,無需自己解壓jar;
  3. Dockefile內容不一樣,舊版是手動解壓jar,再在Dockerfile分別複製,2.3.0.RELEASE是通過java命令從jar中提取出各部分內容

搞清楚了新舊版本的區別,咱們繼續研究下一個問題吧;

pom.xml中spring-boot-maven-plugin插件新增的參數

  1. pring-boot-maven-plugin插件新增參數如下圖所示:

在這裡插入圖片描述
2. 上述參數有啥用?我這邊編譯構建了兩次jar,第一次有上述參數,第二次沒有,將兩次生成的jar解壓後對比,發現用了上述參數後,生成的jar會多出下圖紅框中的兩個文件:

在這裡插入圖片描述

  1. 看看layers.idx文件的內容,如下圖:

在這裡插入圖片描述

  1. 上圖中的內容分別是什麼意思呢?官方已給出了詳細解釋,如下圖紅框:

在這裡插入圖片描述

  1. 綜上所述,layers.idx文件是個清單,裡面記錄了所有要被覆制到鏡像中的信息,接下來看看如何使用layers.idx文件,這就涉及到jar包中新增的另一個文件:spring-boot-jarmode-layertools-2.3.0.RELEASE.jar

spring-boot-jarmode-layertools工具

  1. 前面已經介紹過jar中除了layers.idx,還多了個文件:spring-boot-jarmode-layertools-2.3.0.RELEASE.jar ,來看看這個文件的用處;
  2. 進入工程的target目錄,這裡面是編譯後的jar文件(我這裡文件名為dockerlayerdemo-0.0.1-SNAPSHOT.jar),註意此時的spring-boot-maven-plugin插件是帶上了下圖紅框中的參數的:

在這裡插入圖片描述

  1. 執行以下命令:
java -Djarmode=layertools -jar dockerlayerdemo-0.0.1-SNAPSHOT.jar list
  1. 得到結果如下圖所示,是layers.idx文件的內容:

在這裡插入圖片描述

  1. 來看看官方對這個layertools的解釋,list參數的作用上面我們已經體驗過了,重點是紅框中的extract參數,它的作用是從jar中提取構建鏡像所需的內容:

在這裡插入圖片描述

  1. 看到這裡,您是否想到了《體驗SpringBoot(2.3)應用製作Docker鏡像(官方方案)》中Dockerfile的內容,請看下圖的紅框和紅字,是否有種恍然大悟的感覺:jar構建生成清單layers.idx,Dockerfile中根據清單從jar提取文件放入鏡像:

在這裡插入圖片描述

至此,三個問題都已經找到了答案,小結一下:

SpringBoot-2.3.0.RELEASE推薦的鏡像構建方案和舊版本相比有什麼不同

  1. pom.xml中的spring-boot-maven-plugin插件增加一個配置項;
  2. 構建好jar後,舊版本要自己解壓jar,新版不需要;
  3. 新版本的jar中,多了個文件清單layers.idx和鏡像文件處理工具spring-boot-jarmode-layertools-2.3.0.RELEASE.jar
  4. 舊版的Dockefile內容:因為前面解壓好了,所有在Dockerfile里直接複製前面解壓的內容,這裡就有個風險:前一步解壓和當前複製的文件位置要保證一致;
  5. 新版的Dockerfile內容:使用工具spring-boot-jarmode-layertools-2.3.0.RELEASE.jar,根據的layers.idx內容從jar中提取文件,複製到鏡像中;
  6. 新版的Dockerfile中,由於使用了分階段構建,因此從jar提取文件的操作不會保存到鏡像的layer中;

pom.xml中spring-boot-maven-plugin插件新增的參數,到底做了什麼

spring-boot-maven-plugin插件新增的參數,使得編譯構建得到jar中多了兩個文件,如下圖所示:

在這裡插入圖片描述

Dockerfile中,java -Djarmode=layertools -jar application.jar extract這個操作啥意思

  1. java -Djarmode=layertools -jar application.jar extract的作用是從jar中提取文件,這些文件是docker鏡像的一部分;
  2. 上述操作的參數是extract,另外還有兩個參數,官方解釋它們的作用如下:

在這裡插入圖片描述

至此,問題已全部澄清,相信您對SpringBoot-2.3.0.RELEASE官方的鏡像構建方案也足夠瞭解了,最後是我根據自己的認識畫的流程圖,幫助您快速理解整個構建流程:

在這裡插入圖片描述

歡迎訪問我的GitHub

歡迎關註我的公眾號:程式員欣宸

在這裡插入圖片描述

https://github.com/zq2599/blog_demos


您的分享是我們最大的動力!

-Advertisement-
Play Games
更多相關文章
  • 持久化 RDB方式 Redis實現快照的過程 AOF方式 操作系統緩存 RDB與AOF 複製 主從資料庫 主從複製的意義 安全 持久化 Redis通過將數據存儲在記憶體中而獲得了極快的速度,但為了保證Redis在重啟後數據不丟失,需要將數據從記憶體持久化到硬碟中。 持久化的方式有兩種,二者可以只用一種, ...
  • 安裝mysql yum repository wget -i -c http://dev.mysql.com/get/mysql57-community-release-el7-10.noarch.rpm yum -y install mysql57-community-release-el7-10 ...
  • 近期新接觸sqlserver、oracle資料庫,發現指定返回記錄總數居然都和mysql不同: Mysql:select XXX where XXX limit N Sqlserver: select TOP N XXX Oracle:select XXXX where rownum < (N+1) ...
  • 常用操作 1.查看創建表參數 提取完整的DDL: SELECT DBMS_METADATA.GET_DDL('TABLE','table_name') FROM DUAL; 2.指定返回記錄數 select XXX from XXX where rownum<n 3.查詢指定列的所有值且每個值只顯示 ...
  • 這是一次本地壓力測試,由於預設Oracle 10g的資料庫最大連接數是150。但是要程式的壓力測試要用到300。 於是我參考網上資料,執行下麵兩行命令,修改最大連接數後,重啟oracle伺服器,就發生了錯誤提示oracle無法登陸。 step 1: 修改最大連接數 # 查詢 當前最大連接數selec ...
  • 1.背景環境 本文章來自最近做的項目模塊的思考和總結,主要講思路不涉及過多的基礎和實現細節。 需求:統計出來納稅人名稱、行業、近一年業務量(辦稅服務廳、電子稅務局、自助渠道),近一年業務量top5(辦稅服務廳、電子稅務局、自助渠道)、近一年納稅金額、近一年申報數、近一年用票數。支持根據所屬稅務機關分 ...
  • 列表標簽 無序列表: 無序列表是一個項目的列表,此列項目使用粗體圓點(典型的小黑圓圈)進行標記。 無序列表使用 <ul> 標簽 <ul> <li>劉備</li> <li>關羽</li> <li>孫尚香</li> <li>諸葛亮</li> <li>劉禪</li> </ul> 有序列表: 有序列表也是一 ...
  • # 從零開始的前端生活-理解content(二) 應用 清除浮動 偽元素加content最常見的應用是清除浮動帶來的影響 .clear::after{ content:''; display:table; clear:both; } 字元內容的生成 content還可以插入Unicode字元(萬國 ...
一周排行
    -Advertisement-
    Play Games
  • 移動開發(一):使用.NET MAUI開發第一個安卓APP 對於工作多年的C#程式員來說,近來想嘗試開發一款安卓APP,考慮了很久最終選擇使用.NET MAUI這個微軟官方的框架來嘗試體驗開發安卓APP,畢竟是使用Visual Studio開發工具,使用起來也比較的順手,結合微軟官方的教程進行了安卓 ...
  • 前言 QuestPDF 是一個開源 .NET 庫,用於生成 PDF 文檔。使用了C# Fluent API方式可簡化開發、減少錯誤並提高工作效率。利用它可以輕鬆生成 PDF 報告、發票、導出文件等。 項目介紹 QuestPDF 是一個革命性的開源 .NET 庫,它徹底改變了我們生成 PDF 文檔的方 ...
  • 項目地址 項目後端地址: https://github.com/ZyPLJ/ZYTteeHole 項目前端頁面地址: ZyPLJ/TreeHoleVue (github.com) https://github.com/ZyPLJ/TreeHoleVue 目前項目測試訪問地址: http://tree ...
  • 話不多說,直接開乾 一.下載 1.官方鏈接下載: https://www.microsoft.com/zh-cn/sql-server/sql-server-downloads 2.在下載目錄中找到下麵這個小的安裝包 SQL2022-SSEI-Dev.exe,運行開始下載SQL server; 二. ...
  • 前言 隨著物聯網(IoT)技術的迅猛發展,MQTT(消息隊列遙測傳輸)協議憑藉其輕量級和高效性,已成為眾多物聯網應用的首選通信標準。 MQTTnet 作為一個高性能的 .NET 開源庫,為 .NET 平臺上的 MQTT 客戶端與伺服器開發提供了強大的支持。 本文將全面介紹 MQTTnet 的核心功能 ...
  • Serilog支持多種接收器用於日誌存儲,增強器用於添加屬性,LogContext管理動態屬性,支持多種輸出格式包括純文本、JSON及ExpressionTemplate。還提供了自定義格式化選項,適用於不同需求。 ...
  • 目錄簡介獲取 HTML 文檔解析 HTML 文檔測試參考文章 簡介 動態內容網站使用 JavaScript 腳本動態檢索和渲染數據,爬取信息時需要模擬瀏覽器行為,否則獲取到的源碼基本是空的。 本文使用的爬取步驟如下: 使用 Selenium 獲取渲染後的 HTML 文檔 使用 HtmlAgility ...
  • 1.前言 什麼是熱更新 游戲或者軟體更新時,無需重新下載客戶端進行安裝,而是在應用程式啟動的情況下,在內部進行資源或者代碼更新 Unity目前常用熱更新解決方案 HybridCLR,Xlua,ILRuntime等 Unity目前常用資源管理解決方案 AssetBundles,Addressable, ...
  • 本文章主要是在C# ASP.NET Core Web API框架實現向手機發送驗證碼簡訊功能。這裡我選擇是一個互億無線簡訊驗證碼平臺,其實像阿裡雲,騰訊雲上面也可以。 首先我們先去 互億無線 https://www.ihuyi.com/api/sms.html 去註冊一個賬號 註冊完成賬號後,它會送 ...
  • 通過以下方式可以高效,並保證數據同步的可靠性 1.API設計 使用RESTful設計,確保API端點明確,並使用適當的HTTP方法(如POST用於創建,PUT用於更新)。 設計清晰的請求和響應模型,以確保客戶端能夠理解預期格式。 2.數據驗證 在伺服器端進行嚴格的數據驗證,確保接收到的數據符合預期格 ...