Featured image of post Docker Desktop for MacのHyperKit VMに入る

Docker Desktop for MacのHyperKit VMに入る

コンテナのログファイルが見たい

Docker Desktop for MacでDockerのホストOSに入ってコンテナのログファイルが確認したかったんだけど詰まったのでメモ.


まとめ

特権コンテナnsenterを実行するのがかんたん.

# 特権コンテナを実行してホストOSに入る
$ docker run -it --rm --privileged --pid=host justincormack/nsenter1

環境

やりかた

Macにはない?

Linux上でDockerコンテナを実行したときのログファイルはホストOSの/var/lib/docker/containers/<ContainerID>に吐き出されるんだけど,
Docker Desktop for Macで動かしたコンテナのログを見ようとしてもそんなディレクトリがそもそもmacOS上に存在しない…

# hellp-worldの実行
$ docker container run hello-world

Hello from Docker!
This message shows that your installation appears to be working correctly.

To generate this message, Docker took the following steps:
 1. The Docker client contacted the Docker daemon.
 2. The Docker daemon pulled the "hello-world" image from the Docker Hub.
    (amd64)
 3. The Docker daemon created a new container from that image which runs the
    executable that produces the output you are currently reading.
 4. The Docker daemon streamed that output to the Docker client, which sent it
    to your terminal.

To try something more ambitious, you can run an Ubuntu container with:
 $ docker run -it ubuntu bash

Share images, automate workflows, and more with a free Docker ID:
 https://hub.docker.com/

For more examples and ideas, visit:
 https://docs.docker.com/get-started/

# コンテナIDの確認
$ docker container ls -a
CONTAINER ID        IMAGE               COMMAND             CREATED             STATUS                      PORTS               NAMES
f9a220a39165        hello-world         "/hello"            17 seconds ago      Exited (0) 16 seconds ago                       busy_matsumoto
$ docker container inspect f9a220a39165 -f {{.Id}}
f9a220a391654fd66c8094a2965da6e1255ffb97c6db047d0aef1985d2e49659

# ディレクトリがない
$ ls /var/lib/docker/containers/f9a220a391654fd66c8094a2965da6e1255ffb97c6db047d0aef1985d2e49659
ls: /var/lib/docker/containers/f9a220a391654fd66c8094a2965da6e1255ffb97c6db047d0aef1985d2e49659: No such file or directory
$ ls /var/lib/docker/containers
ls: /var/lib/docker/containers: No such file or directory

これはDocker Desktop for MacDockermacOS上で直接動作しているわけではなく,
macOS上に構築されたHyperKit VMの上で動作している1ため.

VMに入る

じゃあHyperKit VMに入ればいいじゃんという話.

ちょっと調べると

  • ~/Library/Containers/com.docker.docker/Data/vms/0/ttyscreenで呼び出す
  • 特権コンテナを立ち上げてnsenterでホストOSに入る

といった方法2が出てきた.

…が, 自分の環境だとscreenを実行してもCannot exec '/Users/uzimihsr/Library/Containers/com.docker.docker/Data/vms/0/tty': No such file or directoryと表示されて落ちてしまった.

# どうして...
$ screen ~/Library/Containers/com.docker.docker/Data/vms/0/tty
[screen is terminating]

# そもそもttyコマンドが見当たらない
$ ls ~/Library/Containers/com.docker.docker/Data/vms/0/tty
ls: /Users/uzimihsr/Library/Containers/com.docker.docker/Data/vms/0/tty: No such file or directory

なんかIssueに似た症状のコメント3も上がってるので, 自分だけじゃないはず…🤔

回避方法もよくわかんなかったのでscreenを使う方法は諦めて,
特権コンテナ4を使う方法を試してみる.

# 特権コンテナを使ってホストOS(VM)に入る
$ docker run -it --rm --privileged --pid=host justincormack/nsenter1
/ # hostname
docker-desktop
/ # uname -a
Linux docker-desktop 5.4.39-linuxkit #1 SMP Fri May 8 23:03:06 UTC 2020 x86_64 Linux

VMに入れたっぽい…!

目的のコンテナログも表示できる.

## 以下すべて特権コンテナ(ホストOS)内で実行
# コンテナのログファイルを探す
$ ls /var/lib/docker/containers/f9a220a391654fd66c8094a2965da6e1255ffb97c6db047d0aef1985d2e49659
checkpoints                                                                hosts
config.v2.json                                                             mounts
f9a220a391654fd66c8094a2965da6e1255ffb97c6db047d0aef1985d2e49659-json.log  resolv.conf
hostconfig.json                                                            resolv.conf.hash
hostname

# ログファイルの表示
$ cat /var/lib/docker/containers/f9a220a391654fd66c8094a2965da6e1255ffb97c6db047d0aef1985d2e49659/f9a220a391654fd66c8094a2965da6e1255ffb97c6db047d0aef1985d2e49659-json.log
{"log":"\n","stream":"stdout","time":"2020-12-15T12:25:05.3727159Z"}
{"log":"Hello from Docker!\n","stream":"stdout","time":"2020-12-15T12:25:05.3727757Z"}
{"log":"This message shows that your installation appears to be working correctly.\n","stream":"stdout","time":"2020-12-15T12:25:05.372871Z"}
{"log":"\n","stream":"stdout","time":"2020-12-15T12:25:05.3728948Z"}
{"log":"To generate this message, Docker took the following steps:\n","stream":"stdout","time":"2020-12-15T12:25:05.3729341Z"}
{"log":" 1. The Docker client contacted the Docker daemon.\n","stream":"stdout","time":"2020-12-15T12:25:05.3729571Z"}
{"log":" 2. The Docker daemon pulled the \"hello-world\" image from the Docker Hub.\n","stream":"stdout","time":"2020-12-15T12:25:05.3729785Z"}
{"log":"    (amd64)\n","stream":"stdout","time":"2020-12-15T12:25:05.372997Z"}
{"log":" 3. The Docker daemon created a new container from that image which runs the\n","stream":"stdout","time":"2020-12-15T12:25:05.3730192Z"}
{"log":"    executable that produces the output you are currently reading.\n","stream":"stdout","time":"2020-12-15T12:25:05.3731413Z"}
{"log":" 4. The Docker daemon streamed that output to the Docker client, which sent it\n","stream":"stdout","time":"2020-12-15T12:25:05.3731663Z"}
{"log":"    to your terminal.\n","stream":"stdout","time":"2020-12-15T12:25:05.3732665Z"}
{"log":"\n","stream":"stdout","time":"2020-12-15T12:25:05.3732845Z"}
{"log":"To try something more ambitious, you can run an Ubuntu container with:\n","stream":"stdout","time":"2020-12-15T12:25:05.3733071Z"}
{"log":" $ docker run -it ubuntu bash\n","stream":"stdout","time":"2020-12-15T12:25:05.3733248Z"}
{"log":"\n","stream":"stdout","time":"2020-12-15T12:25:05.373345Z"}
{"log":"Share images, automate workflows, and more with a free Docker ID:\n","stream":"stdout","time":"2020-12-15T12:25:05.3733674Z"}
{"log":" https://hub.docker.com/\n","stream":"stdout","time":"2020-12-15T12:25:05.3733901Z"}
{"log":"\n","stream":"stdout","time":"2020-12-15T12:25:05.3734126Z"}
{"log":"For more examples and ideas, visit:\n","stream":"stdout","time":"2020-12-15T12:25:05.3734351Z"}
{"log":" https://docs.docker.com/get-started/\n","stream":"stdout","time":"2020-12-15T12:25:05.3734587Z"}
{"log":"\n","stream":"stdout","time":"2020-12-15T12:25:05.3734814Z"}

# コンテナから出る
$ exit

Docker Desktop for Macで動かしたDockerコンテナの標準出力の内容がログファイルとして閲覧できた.

やったぜ.

おわり

Docker Desktop for MacDockerを動かしているVMに入り, コンテナのログファイルを閲覧することができた.

DockerがそもそもMacOSで直接動作していないことを理解できてなかったので, 勉強になった…

HyperKitじゃなくてVirtualBoxmacOS上にVMを立ててDockerを動かす方法もあるみたいなので, 余裕があれば試してみたい.

おまけ

おもちゃが棚の下にはいっちゃったねこ