參考資料
- Windows Docker Desktop設置中文
- 【Docker 】Docker Desktop for Windows(WSL 2)安裝
- WSL 2 上的 Docker 遠程容器入門
目錄
- 一. 環境配置
- 1.1 安裝WSL
- 1.2 安裝配置 Docker Desktop
- 1.3 VS Code 插件安裝
- 1.4 下載項目,配置Dockerfile
- 二. 常用Docker命令簡介
- 2.1 Dockerfile打包鏡像
- 2.2 image鏡像
- 2.2.1 `docker image ls` 查看所有鏡像
- 2.2.2 `docker image rm 鏡像ID` 刪除指定鏡像
- 2.3 container容器
- 2.3.1 `docker run` 創建并啟動容器
- 2.3.2 `docker container ls --all` 查看所有容器
- 2.3.3 容器的停止
- 2.3.3.1 `docker stop`
- 2.3.3.2 `docker container stop`
- 2.3.4 容器的刪除
- 2.3.4.1 `docker rm`
- 2.3.4.2 `docker container rm`
- 2.3.5 `docker exec`進入容器內部
- 2.3.6 `docker container start` 啟動一個既存的容器
- 2.3.7 `docker container logs` 查看 docker 容器的輸出
- 2.3.8 `docker container cp` 復制容器內的文件到本地
- 2.4 registry倉庫
- 2.4.1 `docker pull` 鏡像拉取
- 2.4.2 `docker push` 鏡像推送
- 三. docker-compose
- 3.1 遇到的問題
- 3.2 `docker-compose.yml` 配置文件
- 3.3 `docker-compose build` 構建鏡像
- 3.4 數據遷移
- 3.5 `docker-compose up` 運行容器
一. 環境配置
1.1 安裝WSL
?詳情請參考下面這篇博客
Linux Windows之wsl安裝使用簡介
1.2 安裝配置 Docker Desktop
?從官網下載安裝Docker Desktop
- ※因為
Docker Desktop
依賴于wsl,所以需要先安裝wsl - https://www.docker.com/products/docker-desktop/
?安裝完成之后,進行如下配置
- 指定Docker鏡像的磁盤存儲位置
- 指定對應的wsl
?當我們的wsl和docker都配置完成之后,使用下面的命令應該能看到docker的版本和wsl的掛載目錄
apluser@FengYeHong-HP:~$ docker --version
Docker version 28.1.1, build 4eba377
apluser@FengYeHong-HP:~$
apluser@FengYeHong-HP:~$ ls -l /mnt/wsl/
drwxr-xr-x 4 root root 100 Jun 11 20:06 docker-desktop
drwxr-xr-x 3 root root 60 Jun 11 20:06 docker-desktop-bind-mounts
-rw-r--r-- 1 root root 198 Jun 11 20:06 resolv.conf
1.3 VS Code 插件安裝
?Docker
擴展
- 提供對Dockerfile的語法檢測,代碼高亮,自動補全
- 可以通過菜單運行各種Docker命令
- 可以在左側面板中看到我們創建的所有鏡像,容器等
?Dev Containers
擴展
- 支持在容器中打開代碼項目
- 自動配置開發環境,通過
.devcontainer
目錄定義語言版本、依賴、插件等 - 調試支持,支持容器內調試(Node.js、Python、C++ 等)
1.4 下載項目,配置Dockerfile
?執行下面的git命令,下載示例項目
git clone https://github.com/mattwojo/helloworld-django.git
?下載完成之后,移動到示例項目的根目錄,應該會看到這樣的目錄
apluser@FengYeHong-HP:helloworld-django$ ls -l
total 148
-rw-r--r-- 1 apluser apluser 483 Jun 11 20:48 Dockerfile
-rw-r--r-- 1 apluser apluser 131072 Jun 7 16:56 db.sqlite3
drwxr-xr-x 4 apluser apluser 4096 Jun 7 09:38 hello
-rwxr-xr-x 1 apluser apluser 667 Jun 7 09:38 manage.py
-rw-r--r-- 1 apluser apluser 16 Jun 7 09:38 requirements.txt
drwxr-xr-x 3 apluser apluser 4096 Jun 7 09:38 web_project
二. 常用Docker命令簡介
?所有的命令都可以通過docker --help
查看
2.1 Dockerfile打包鏡像
?在項目的根目錄下手動創建一個Dockerfile
文件,創建之后的目錄如下
apluser@FengYeHong-HP:helloworld-django$ ls -l
total 148
-rw-r--r-- 1 apluser apluser 196 Jun 7 16:54 Dockerfile
-rw-r--r-- 1 apluser apluser 131072 Jun 7 16:56 db.sqlite3
drwxr-xr-x 4 apluser apluser 4096 Jun 7 09:38 hello
-rwxr-xr-x 1 apluser apluser 667 Jun 7 09:38 manage.py
-rw-r--r-- 1 apluser apluser 16 Jun 7 09:38 requirements.txt
drwxr-xr-x 3 apluser apluser 4096 Jun 7 09:38 web_project
apluser@FengYeHong-HP:helloworld-django$
apluser@FengYeHong-HP:helloworld-django$ cat Dockerfile
# 安裝python環境, 指定基礎鏡像
FROM python:3.11-slim
# 創建一個名為 app 的工作目錄
WORKDIR /app
# 將當前目錄下的 requirements.txt 復制到app工作目錄中
COPY requirements.txt .# 運行pip命令, 安裝python項目所需的依賴
RUN pip install --no-cache-dir -r requirements.txt
# 將當前目錄下的所有內容都復制到app工作目錄中
COPY . /app# 指定8000端口
EXPOSE 8000
# 啟動python項目
CMD ["python", "manage.py", "runserver", "0.0.0.0:8000"]
-t
參數用來指定 image 文件的名字,后面還可以用冒號指定標簽。如果不指定,默認的標簽就是latest
。- 最后的那個
.
表示Dockerfile
文件所在的路徑,因為當前路徑在Dockerfile
文件所在的目錄,所示是一個.
。
docker image build -t helloworld-django .
# 或者
docker image build -t helloworld-django:0.0.1 .
2.2 image鏡像
2.2.1 docker image ls
查看所有鏡像
apluser@FengYeHong-HP:~$ docker image ls
REPOSITORY TAG IMAGE ID CREATED SIZE
helloworld-django latest 51fedeaf85ff 2 days ago 363MB
hello-world latest 0b6a027b5cf3 4 months ago 20.4kB
2.2.2 docker image rm 鏡像ID
刪除指定鏡像
apluser@FengYeHong-HP:~$ docker image rm 51fedeaf85ff
Untagged: helloworld-django:latest
Deleted: sha256:51fedeaf85ffdc569edae785cce00602eb90b4a7a12766c6f671a517f0c4f199
apluser@FengYeHong-HP:~$
apluser@FengYeHong-HP:~$ docker image ls
REPOSITORY TAG IMAGE ID CREATED SIZE
hello-world latest 0b6a027b5cf3 4 months ago 20.4kB
2.3 container容器
2.3.1 docker run
創建并啟動容器
-it
:容器的 Shell 映射到當前的 Shell,然后你在本機窗口輸入的命令,就會傳入容器--rm
:容器一旦停止就會自動刪除(僅在臨時測試時使用)-p
:容器的 8000 端口映射到本機的 8100 端口helloworld-django:latest
:指定要啟動的容器
apluser@FengYeHong-HP:~$ docker run -it --rm -p 8100:8000 helloworld-django:latest
Watching for file changes with StatReloader
Performing system checks...System check identified no issues (0 silenced).You have 18 unapplied migration(s). Your project may not work properly until you apply the migrations for app(s): admin, auth, contenttypes, sessions.
Run 'python manage.py migrate' to apply them.
June 14, 2025 - 00:12:19
Django version 3.2.25, using settings 'web_project.settings'
Starting development server at http://0.0.0.0:8000/
Quit the server with CONTROL-C.
?容器啟動之后,在瀏覽器中就可以看到如下所示的界面
2.3.2 docker container ls --all
查看所有容器
docker container ls
:查看正在運行的容器docker container ls --all
:查看正在所有容器,包括已經停止運行的容器
?docker ps
的作用和docker container
相同,只不過從語義化上看來,docker container
更好。
2.3.3 容器的停止
2.3.3.1 docker stop
?docker stop 容器ID
:停止正在運行的容器。注意:停止運行的容器并不會被刪除。
docker stop <容器ID或名稱>
會向容器發送SIGTERM
信號,讓其優雅退出,如果在默認的 10 秒內還沒退出,則發送SIGKILL
強制終止。docker kill <容器ID或名稱>
會立即強制終止容器(不等待)
apluser@FengYeHong-HP:~$ docker container ls
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
d32995d7a305 helloworld-django:latest "python manage.py ru…" 22 minutes ago Up 22 minutes 0.0.0.0:8100->8000/tcp kind_bassi
apluser@FengYeHong-HP:~$
apluser@FengYeHong-HP:~$ docker stop d32995d7a305
d32995d7a305
2.3.3.2 docker container stop
apluser@FengYeHong-HP:~$ docker container ls
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
783e1ad29407 helloworld-django:latest "python manage.py ru…" 16 minutes ago Up 16 minutes 0.0.0.0:8100->8000/tcp reverent_lalande
apluser@FengYeHong-HP:~$
apluser@FengYeHong-HP:~$ docker container stop 783e1ad29407
783e1ad29407
2.3.4 容器的刪除
2.3.4.1 docker rm
?如果你不只是要停止容器,還想連容器一起刪除(比如臨時容器),可以用docker rm -f
, -f
相當于先 stop
再 rm
apluser@FengYeHong-HP:~$ docker container ls
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
4c07319bbebc helloworld-django:latest "python manage.py ru…" 11 seconds ago Up 9 seconds 0.0.0.0:8100->8000/tcp infallible_sammet
apluser@FengYeHong-HP:~$
apluser@FengYeHong-HP:~$ docker rm -f 4c07319bbebc
4c07319bbebc
2.3.4.2 docker container rm
?語義化更好
apluser@FengYeHong-HP:~$ docker container ls --all
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
6380b917ff0c helloworld-django:latest "python manage.py ru…" 44 seconds ago Up 42 seconds 0.0.0.0:8100->8000/tcp determined_boyd
f0e58479ba3d helloworld-django "python manage.py ru…" 54 minutes ago Exited (0) 54 minutes ago vigorous_leavitt
cca37d72e4ba helloworld-django "python manage.py ru…" 54 minutes ago Exited (0) 54 minutes ago musing_franklin
f51614fe80d9 helloworld-django:latest "python manage.py ru…" 55 minutes ago Exited (0) 54 minutes ago unruffled_franklin
bb11c3bbaf5f helloworld-django "python manage.py ru…" 56 minutes ago Exited (0) 56 minutes ago relaxed_banach
apluser@FengYeHong-HP:~$
apluser@FengYeHong-HP:~$ docker container rm bb11c3bbaf5f
bb11c3bbaf5f
apluser@FengYeHong-HP:~$
2.3.5 docker exec
進入容器內部
apluser@FengYeHong-HP:~$ docker container ls
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
783e1ad29407 helloworld-django:latest "python manage.py ru…" 12 seconds ago Up 11 seconds 0.0.0.0:8100->8000/tcp reverent_lalande
apluser@FengYeHong-HP:~$
apluser@FengYeHong-HP:~$ docker exec -it 783e1ad29407 bash
root@783e1ad29407:/app# ls -l
total 20
-rw-r--r-- 1 root root 483 Jun 11 11:48 Dockerfile
-rw-r--r-- 1 root root 0 Jun 13 23:58 db.sqlite3
drwxr-xr-x 4 root root 4096 Jun 7 00:38 hello
-rwxr-xr-x 1 root root 667 Jun 7 00:38 manage.py
-rw-r--r-- 1 root root 16 Jun 7 00:38 requirements.txt
drwxr-xr-x 3 root root 4096 Jun 7 00:38 web_project
2.3.6 docker container start
啟動一個既存的容器
?docker run
的方式會創建并啟動一個容器,同樣的命令運行兩次,就會生成兩個一模一樣的容器文件。
如果希望重復使用容器,就要使用docker container start
命令,它用來啟動已經生成、已經停止運行的容器文件。
2.3.7 docker container logs
查看 docker 容器的輸出
?docker 容器的輸出,即容器里面 Shell 的標準輸出。如果
docker run
命令運行容器的時候,沒有使用-it參數docker container start
直接啟動既存容器時
就要用這個命令查看輸出。
2.3.8 docker container cp
復制容器內的文件到本地
?將容器內的requirements.txt
文件復制到本地的指定路徑中
apluser@FengYeHong-HP:~$ docker exec -it f0e58479ba3d bash
root@f0e58479ba3d:/app#
root@f0e58479ba3d:/app# ls -l
total 20
-rw-r--r-- 1 root root 483 Jun 11 11:48 Dockerfile
-rw-r--r-- 1 root root 0 Jun 13 23:58 db.sqlite3
drwxr-xr-x 4 root root 4096 Jun 7 00:38 hello
-rwxr-xr-x 1 root root 667 Jun 7 00:38 manage.py
-rw-r--r-- 1 root root 16 Jun 7 00:38 requirements.txt
drwxr-xr-x 3 root root 4096 Jun 7 00:38 web_project
root@f0e58479ba3d:/app#
root@f0e58479ba3d:/app# exit
exit
apluser@FengYeHong-HP:~$ docker container cp f0e58479ba3d:/app/requirements.txt /home/apluser/work/
Successfully copied 2.05kB to /home/apluser/work/
apluser@FengYeHong-HP:~$
apluser@FengYeHong-HP:~$ ls -l /home/apluser/work/requirements.txt
-rw-r--r-- 1 apluser apluser 16 Jun 7 09:38 /home/apluser/work/requirements.txt
2.4 registry倉庫
?Docker Registry
是 Docker 提供的鏡像倉庫服務,用于 存儲、分發和管理 Docker 鏡像。可使用 Docker Registry 來
:
- 上傳(push)鏡像
- 下載(pull)鏡像
- 搭建私有鏡像倉庫
Docker Registry
常與 docker login
, docker push
, docker pull
命令配合使用。
2.4.1 docker pull
鏡像拉取
?鏡像拉取語法:docker pull <registry>/<倉庫>:<標簽>
# 從docker的官網倉庫拉取nginx鏡像
docker pull nginx:latest
# 從私人倉庫拉取鏡像
docker pull myregistry.com:5000/myimage:latest
2.4.2 docker push
鏡像推送
?在推送鏡像之前,你需要為鏡像添加倉庫地址和標簽。
# docker tag <本地鏡像ID或名稱> <registry>/<鏡像名稱>:<標簽>
docker tag myapp:latest myregistry.com:5000/myapp:latest
?向指定的倉庫推送鏡像
# docker push <registry>/<鏡像名稱>:<標簽>
docker push myregistry.com:5000/myapp:latest
三. docker-compose
3.1 遇到的問題
💦當我們直接使用docker run -it --rm -p 8100:8000 helloworld-django:latest
命令創建并運行容器的時候,django
工程會出現下面的提示,原因就在于我們在并沒有進行數據遷移。
You have 18 unapplied migration(s). Your project may not work properly until you apply the migrations for app(s): admin, auth, contenttypes, sessions.
Run 'python manage.py migrate' to apply them.
?我們可以通過下面的方式進行數據遷移
docker run -it \
-v $(pwd)/db.sqlite3:/app/db.sqlite3 \
-w /app \
helloworld-django \
python manage.py migrate
💥注意,在此案例中數據遷移之后的有數據的db.sqlite3
文件并不在容器中,而是在本地的路徑下。
因此,之后真正啟動容器的時候,必須要將本地目錄下的db.sqlite3
文件掛載到容器中才行,也就是說容器中的程序讀取的是本地目錄中的db.sqlite3
文件
?使用掛載的數據的同時,啟動容器
-v /主機路徑文件:/容器路徑文件
這會讓容器內部使用主機上的文件,從而讓db.sqlite3
的內容得以持久保存。-w /app
設置容器內的工作目錄是/app
,這個要與你 Dockerfile 中 WORKDIR 設置一致(通常也是/app
)
docker run -it -p 8100:8000 \
-v $(pwd)/db.sqlite3:/app/db.sqlite3 \
-w /app \
helloworld-django
💦但是輸入這么長的命令,不僅繁瑣,還很容器出錯,有沒有什么更好的辦法?
3.2 docker-compose.yml
配置文件
?將命令行中的配置命令,通過yml
文件的方式簡化到配置文件中
apluser@FengYeHong-HP:helloworld-django$ ls -l
total 152
-rw-r--r-- 1 apluser apluser 483 Jun 11 20:48 Dockerfile
-rw-r--r-- 1 apluser apluser 131072 Jun 14 14:49 db.sqlite3
-rw-r--r-- 1 apluser apluser 259 Jun 14 15:14 docker-compose.yml
drwxr-xr-x 4 apluser apluser 4096 Jun 7 09:38 hello
-rwxr-xr-x 1 apluser apluser 667 Jun 7 09:38 manage.py
-rw-r--r-- 1 apluser apluser 16 Jun 7 09:38 requirements.txt
drwxr-xr-x 3 apluser apluser 4096 Jun 7 09:38 web_project
apluser@FengYeHong-HP:helloworld-django$
apluser@FengYeHong-HP:helloworld-django$ cat docker-compose.yml
services:web:image: helloworld-djangobuild:context: .dockerfile: Dockerfileports:- "8100:8000"volumes:- ./db.sqlite3:/app/db.sqlite3working_dir: /appcommand: python manage.py runserver 0.0.0.0:8000
3.3 docker-compose build
構建鏡像
3.4 數據遷移
?docker-compose run web python manage.py migrate
- 執行命令進行數據遷移
- 此處的
web
應當和docker-compose.yml
文件中的services
對應的名稱相同
💥需要注意的是,這種 docker-compose run
會啟動一個一次性容器,它不會被 docker-compose up
管理到。
3.5 docker-compose up
運行容器
# --remove-orphans 在啟動的時候,刪除被遺漏的容器
docker-compose up --remove-orphans
# 在后臺啟動容器
docker-compose up -d
?如下圖所示,容器啟動成功,頁面也能正常訪問。