Codespacesとdevcontainerのメモ
Codespaces と devcontainer の違い
Codespacesはdevcontainerを使っているものの、実際には devcontainer.json や docker-compose.yml に色々とマージしてから devcontainer を起動しているので、 Codespaces の設定としての devcontainer.json がそのまま VSCode の devcontainer として動くとは限らない。
一番の違いは workspaceFolder。
Codespaces は /workspaces/<リポジトリ名>
をチェックアウトし、 /workspace
をバインドマウントする。そして workspaceFolder
が設定されてない場合は /workspaces/<リポジトリ名>
を workspaceFolder に設定する。
もちろん workspaceFolder
を指定しない devcontainer.json を使ってVSCodeでコンテナを使おうとするとエラーになるので、 Codespaces でも独自 devcontianer でも使える devcontainer.json を使いたい場合は /workspaces
以外のディレクトリを用意してそこを workspaceFolder に設定するのが良い。
workspaceFolder がなくてもエラーにならない?
workspaceFolder がない devcontainer.json を含むリポジトリを、 VSCode で Open in container すると、 /workspaces/<ディレクトリ名>
が workspace になる。
前に試した時が誤認だったのか、その後に何か変更があったのか。
Codespace の workspace のパーミッション
Codespace を起動して ls すると、ディレクトリに変な色がついている。パーミッションを見ると、otherにもwがついているのが原因ぽい。なぜ。。。
chmod -R o-w .
すると直るので、 postCreateCommand
あたりに書いておくといいだろう。
Rancher Desktop や colima を使った時のUID問題
Docker Desktop では bind mount をするときに、gRPC-FUSEの謎技術によって、ホストのディレクトリをbind mountするときにちゃんとコンテナないのユーザーのuid/gidに変換されている。(詳細不明)
colima や Rancher Desktop を使って devcontainer を使おうとした場合、一旦 Linux VM に sshfs や 9p を使ってマウントした後、さらにLinux上のdockerがbind mountする形になっている。そのため、コンテナ内のユーザーIDとbind mountしたホストのディレクトリのコンテナ内でのユーザーID(devcontainer用のイメージでは1000が一般的)が一致しない。そのためworkspaceフォルダーのオーナーが他人になり、作業ができない。
ホストのUIDとコンテナ内のUIDが一致しない問題は一般的なので、Linux版のdevcontainerではコンテナ内のUID/GIDをホストのUID/GIDに合わせる機能 "updateRemoteUserUID" が存在するが、mac版ではその動作はしない(しても、macのUIDとLinux VM内のUIDが一致してないと意味がない)
どうしてもmacOSでDocker Desktopを使わずにdevcontainerで作業したい場合は、 "updateRemoteUserUID" が実行している Dockerfile と同じことを手作業ですればいい。
ただし、実行がコンテナ作成後になるので、コンテナ作成中にUID 1000版で作られてしまったファイルのchownが必要になる。正直お勧めできない。
現実的に、 macOSユーザーが devcontainer を使いたい場合は次のようにするのがいいと思う。
- あきらめて Docker Desktop を買う
- Remote-SSH 等で Linux 上で devcontainer を動かす
- 性能は Docker Desktop on macOS より多分上
- 代わりに macOS 上で動くRemote非対応デスクトップアプリでそのファイルを編集するのはあきらめる
features の python
features で python 環境のセットアップができる。python自体のインストールに加えて、pipxとかblackとかいろいろインストールしている。具体的に何をするのかはソース参照。
で、Pythonのインストール方法は優先順で、システムのPython、Oryxを使ったバイナリインストール、ソースからビルド、になっている。
ソースからビルドする場合はもちろん起動速度が遅くなる(オプションで最適化を有効にしたらさらに遅くなる)ので、頻繁にCodespaceを使うならprebuildの設定をしておいた方がいいだろう。
Oryxを使いたい場合は、Oryxもfeaturesでインストールできる。featuresのインストール順が自動でOryx優先になるかわからないので、手動でOryxを先にインストールさせた方がいいだろう。 (overrideFeatureInstallOrder オプション)
ただ、僕が試した時点では Ubuntu 22.04 に Oryx が対応してないのでソースからインストールになってしまった。Ubuntu 22.04ではシステムのPythonが3.10だったので、それを使うなら Oryx はいらない。
他の言語の feature もチラ見した感じだとソースからビルドするものがあるので、そういう場合は features の代わりに apt, conda, nix, Homebrew などのパッケージマネージャーの利用も考えた方がいいかもしれない。
Linux上でもバイナリをサクッとインストールできる言語はいいですね。