曾經嘗試過在 Web 應用程式中使用 Docker 磁碟區進行熱重載嗎?如果你有跟我一樣可怕的經歷,你會喜歡 Docker 剛剛發布的最新功能:docker-compose watch!讓我向您展示如何升級現有專案以獲得出色的 Docker 開發設置,您的團隊實際上會喜歡使用它 🤩
TL;DR:看看這個 docker-compose 檔案和 官方文件
讓我們開始吧!
Docker 剛剛發布了Docker Compose Watch 和Docker Compose Version 2.22 #2220).有了這個新功能,您可以使用“docker-compose watch”代替“docker-compose up”,並自動將本機原始程式碼與 Docker 容器中的程式碼同步,而無需使用磁碟區!
讓我們透過使用我之前寫過的 來看看它在實際專案中的工作原理。
在這個專案中,我有一個帶有前端、後端以及一些用於 UI 和資料庫的附加庫的 monorepo。
├── apps
│ ├── api
│ └── web
└── packages
├── database
├── eslint-config-custom
├── tsconfig
└── ui
兩個應用程式(「api」和「web」)都已經進行了docker 化,而Dockerfile 位於專案的根目錄中(1, 2)
docker-compose.yml
檔案如下所示:
services:
web:
build:
dockerfile: web.Dockerfile
ports:
- "3000:3000"
depends_on:
- api
api:
build:
dockerfile: api.Dockerfile
ports:
- "3001:3000"from within the Docker network
這已經相當不錯了,但如您所知,在開發過程中使用它是一個 PITA。每當您更改程式碼時,您都必須重建 Docker 映像,即使您的應用程式可能支援開箱即用的熱重載(或使用 Nodemon 如果不)。
為了改善這一點,Docker Compose Watch 引入了一個新屬性,稱為「watch」。 watch 屬性包含一個所謂的 rules 列表,每個規則都包含它們正在監視的 path 以及一旦路徑中的文件發生更改就會執行的 action。
如果您希望在主機和容器之間同步資料夾,您可以新增:
services:
web: # shortened for clarity
build:
dockerfile: web.Dockerfile
develop:
watch:
- action: sync
path: ./apps/web
target: /app/apps/web
每當主機上的路徑“./apps/web/”中的檔案發生變更時,它將同步(複製)到容器的“/app/apps/web”。目標路徑中的附加應用程式是必要的,因為這是我們在 Dockerfile 中定義的「WORKDIR」。如果您有可熱重新加載的應用程式,這可能是您可能會使用的主要內容。
如果您有需要編譯的應用程式或需要重新安裝的依賴項,還有一個名為 rebuild 的操作。它將重建並重新啟動容器,而不是簡單地在主機和容器之間複製檔案。這對你的 npm 依賴關係非常有幫助!讓我們補充一下:
services:
web: # shortened for clarity
build:
dockerfile: web.Dockerfile
develop:
watch:
- action: sync
path: ./apps/web
target: /app/apps/web
- action: rebuild
path: ./package.json
target: /app/package.json
每當我們的 package.json 發生變化時,我們都會重建整個 Dockerfile 以安裝新的依賴項。
除了同步和重建之外,中間還有一些稱為同步+重新啟動的操作。此操作將首先同步目錄,然後立即重新啟動容器而不重建。大多數框架通常都有無法熱重載的設定檔(例如「next.config.js」)(僅同步是不夠的),但也不需要緩慢重建。
這會將您的撰寫文件更改為:
services:
web: # shortened for clarity
build:
dockerfile: web.Dockerfile
develop:
watch:
- action: sync
path: ./apps/web
target: /app/apps/web
- action: rebuild
path: ./package.json
target: /app/package.json
- action: sync+restart
path: ./apps/web/next.config.js
target: /app/apps/web/next.config.js
一如既往,沒有免費午餐和一些警告😬
新的“watch”屬性的最大問題是路徑仍然非常基本。文件指出,尚不支援 Glob 模式,如果您想具體說明,這可能會導致「大量」規則。
以下是一些有效和無效的範例:
✅ 應用程式/網路
這將會符合./apps/web
中的所有檔案(例如./apps/web/README.md
,還有./apps/web/src/index.tsx
)
❌ build/**/!(*.spec|*.bundle|*.min).js
遺憾的是(還沒?) 支持 Glob
❌ ~/下載
所有路徑都是相對於專案根目錄的!
如果您對 Docker 設定仍然不滿意,還有很多方法可以改進它!
協作是軟體開發的重要組成部分,孤島工作可能會嚴重損害您的團隊。緩慢的 Docker 建置和複雜的設定沒有幫助!為了解決這個問題並促進協作文化,您可以使用 Docker 擴展,例如 Livecycle立即與您的隊友分享您本地的docker-compose 應用程式。由於您已經在使用 Docker 和 docker-compose,因此您需要做的就是安裝 Docker 桌面擴充並點擊共享切換按鈕。然後,您的應用程式將透過隧道連接到網路,您可以與您的團隊分享您的唯一 URL 以獲取回饋!如果您想查看 Livecycle 的更多用例,我在這篇文章中寫了更多相關內容:)
像往常一樣,確保您的 Dockerfile 遵循最佳實踐,尤其是在多階段建置和快取方面。雖然這可能會使編寫初始 Dockerfile 變得更加困難,但它將使您的 Docker 應用程式在開發過程中使用起來更加愉快。
建立一個基本的“.dockerignore”檔案並將依賴項安裝與程式碼建置分開還有很長的路要走!
一如既往,我希望你今天學到新東西了!如果您在設定 Docker 專案時需要任何協助,或者您有任何其他回饋,請告訴我
乾杯,喬納斯:D
原文出處:https://dev.to/code42cate/say-goodbye-to-docker-volumes-j9l