Docker Desktopの代替案を探していたところMultipassがかなり良い感じだったので構築方法を記載しておきます。
Multipassとは
Multipassは手軽・高速にUbuntu環境を作成する仮想環境で、Linux, Windows, Macで動作します。
ホスト環境
この内容を実施するとホストのMacには以下の影響があります。
- Docker Desktopを使わない。
- Mac上で
docker
コマンドを使うとMultipass上のdockerが使用されます。 - Ubuntu構築用にCPU,メモリ,ストレージ等のリソースが必要です。
- Homebrewで
multipass
,docker
,docker-compose
をインストールします。 -
~/.ssh
ディレクトリのconfig
ファイルに必要な記述を追記します。 -
~/.ssh
ディレクトリにsshファイルを作成します。 - Ubuntuにホームディレクトリをマウントします(任意)。
- Docker Desktopのように各種アクセス先はlocalhostではなく
任意の名前.local
でアクセスが出来るようになります。localhostと切り分けができるので個人的にはこちらの方が好みです。 - MultipassがHypreKitを利用しているので他の仮想化アプリケーションは無くても構いません。(任意で別の仮想化アプリケーションを利用する方法もあるようです)
参考
https://medium.com/@gourneau_38759/docker-engine-with-multipass-on-macos-dc44ff09ffb2
必要なパッケージをインストール
# もし、homebrewでdocker desktop及びdockerがインストールしてある場合は以下を実行で一旦削除
# brew uninstall --force docker docker-machine docker-compose
brew install multipass docker docker-compose
SSHファイル作成
multipass_docker
という任意の名前でSSHファイルを作成します。
your_email@example.com
の箇所は必ず書き換えてください。メールアドレスである必要はありません。
ssh-keygen -t rsa -b 4096 -C "your_email@example.com" -f ~/.ssh/multipass_docker
# your_email@example.comは以下のようにuuidgenを使ってランダムな文字列を使っても良い
# ssh-keygen -t rsa -b 4096 -C "$(uuidgen)" -f ~/.ssh/multipass_docker
chmod 600 ~/.ssh/multipass_docker
chmod 600 ~/.ssh/multipass_docker.pub
yamlファイル作成
Ubuntu構成用に以下のコマンドをターミナルで入力してファイルを作成する。
# 作成した.pubファイルを変数に読み込む
AUTHORIZED_KEYS=$(cat ~/.ssh/multipass_docker.pub )
# ヒアドキュメントでファイルを作成する
cat > ./multipass_docker.yaml << _EOF_
---
locale: en_US.UTF8
timezone: Asia/Tokyo
package_upgrade: true
users:
- name: ubuntu
sudo: ALL=(ALL) NOPASSWD:ALL
ssh-authorized-keys:
- ${AUTHORIZED_KEYS}
packages:
- docker
- avahi-daemon
- apt-transport-https
- ca-certificates
- curl
- gnupg
- lsb-release
runcmd:
- sudo curl -fsSL https://get.docker.com | sudo bash
- sudo systemctl enable docker
- sudo systemctl enable -s HUP ssh
- sudo groupadd docker
- sudo usermod -aG docker ubuntu
_EOF_
構築
以下の様式でMultipassを使ったUbuntuを構築します。
multipass launch -c CPU -m メモリ量 -d ストレージ容量 -n 任意の名前 20.04 --cloud-init ./multipass_docker.yaml
以下のコマンドでUbuntuを構築します。今回はdocker
という名前のマシンで作成しており、これ以降docker.local
で直接アクセス出来るようになります。
docker
という名前は任意ですので、他の名前でもかまいません。その際はアクセス先が任意の名前.local
になります。
multipass launch -c 2 -m 4G -d 40G -n docker 20.04 --cloud-init ./multipass_docker.yaml
構築できたか確認
# SSH接続をする。
# 念の為、以下を実行してログイン記録を削除。
ssh-keygen -R docker.local
# sshファイルを使用してMultipassのインスタンスにログイン
ssh -i ~/.ssh/multipass_docker ubuntu@docker.local
# Multipassのインスタンスにログイン出来たら以下を実行してdockerがインストールされているか確認
docker info
# 確認出来たらインスタンスから出る
exit
# SSH接続が出来ることが確認出来たら構成用に使用したyamlファイルは不要になるので削除する。
rm ./multipass_docker.yaml
# 設定内容の確認
multipass info docker
# 一覧表
multipass ls
~/.ssh/configファイルに追記
ssh ubuntu@docker.local
コマンドでログイン出来るように~/.ssh/config
ファイルに以下を追記します。無い場合は新しく作成しましょう。
Host docker.local
HostName docker.local
IdentityFile ~/.ssh/multipass_docker
User ubuntu
Port 22
ログイン出来るか確認
multipass shell
multipass
コマンドで以下を実行することでログイン出来ます。
multipass shell docker
# 確認出来たらインスタンスから出る
exit
sshでログイン
# 念の為、以下を実行してログイン記録を削除。
ssh-keygen -R docker.local
# ubuntuにログイン
ssh ubuntu@docker.local
# ログイン出来ることを確認出来たらインスタンスから出る。
exit
.zshrcに追記
環境変数DOCKER_HOST
にUbuntuのアクセス先を記述することで、ホスト側でのdocker
コマンドはUbuntuのものを使うように設定できます。.zshrc
の末尾にでも追記しておくことで、ログイン時に設定されるようにしておきましょう。
# multipass docker
export DOCKER_HOST="ssh://ubuntu@docker.local"
[任意]ホームディレクトリをMultipass上にマウントする
作業しやすいようにホームディレクトリをUbuntu上にマウントします。
1回マウントしたらホストを再起動してもマウントし続けます。
# ホームをUbuntu上の同じ名前の階層(/Users/ユーザ名)にマウントする
multipass mount ${HOME} docker:${HOME}
# アンマウント
# multipass unmount docker:${HOME}
この作業は任意ですが、していない場合、docker上でDockerfile
やdocker-compose.yaml
と同階層のファイルをマウントしようとしてもMultipassの内部しか見えていない状態なので以下のようなエラーになります。
user@mac docker % docker-compose up
[+] Running 1/0
⠿ Container docker-xxxx-1 Created 0.0s
Attaching to docker-xxxx-1
Error response from daemon: invalid mount config for type "bind": bind source path does not exist: /Users/***
テスト
nginxを使ってみる
docker run --name nginx_test -d -p 8080:80 nginx
# 以下で削除
# docker stop $(docker ps -aqf "name=nginx_test")
# docker rm $(docker ps -aqf "name=nginx_test")
アクセス
この場合URLはhttp://docker.local:8080
です。
外部からのアクセス
外部からアクセスするにはmultipass ls
もしくはmultipass info docker
でIPv4
項目を参照しましょう。
削除
multipassの削除は、delete
で一次削除、purge
で完全削除の2段階です。
delete
でゴミ箱に入れて、purge
でゴミ箱を空にする感じです。
# 削除は以下
multipass delete docker
multipass purge
エラー対応
Operation not permitted
ホスト側のファイルを扱おうとした際にこのようなエラーが表示されることがあります。
解決策は、システム環境設定
のプライバシー
タブのフルディスクアクセス
の一覧にあるmultipassd
にチェックを入れることです。