🐺

VS Code複数バージョン・複数環境の共存ガイド(Remote WSL/Dev Containers/SSHと拡張機能の干渉を防ぐ)

に公開

はじめに

「前編の続き」として当記事をかきはじめてますけど
当記事の話題は、VS Code関係で、複数の開発案件で
環境が干渉しないで、独立的に共存して、同時に作業できるには
どうすれば、という話題に、一貫してなっています。
「前編の記事」の詳細を知らなくても、その話題については、
拾って、理解できるような記述内容にはなっていると思います。

まず、普段使いの最新版のVS Codeと、VS Code ポータブル版を活用して Dev Containers を独立、共存させた事例を用いての説明をしたいため、以前書いた記事を、前編として、「前編の続き」として当記事をかきはじめることにした。

前編はこちら:
https://zenn.dev/tazzae999jp/articles/b166b7fd73b3bf

前編の記事では、
いろいろな諸事情があり、とあるレガシー環境の保守開発のためにローカルに下記の環境を作った

  • CentOS 7.2 + Python 2.7.5 の「本番相当」環境を Dev Containers で再現する
  • そのコンテナの中に 古い debugpy を直接インストールする
  • Windows 側では ポータブル版 VS Code(1.63.2) を使って、そのコンテナにだけ接続してデバッグする

という構成を作りました。

同時に、普段使いの 最新版 VS Code(code . で起動する通常版) も残したまま、

  • 「古い環境をいじるためのポータブル版 VS Code」
  • 「日常開発用の最新版 VS Code」

共存させて使う という運用をした。

この記事では、

  • そもそも Remote WSL / Dev Containers がどんな仕組みで動いているか
  • なぜ前編のように「ポータブル版 VS Code」と「通常版 VS Code」を干渉させずに共存できたのか
  • 逆に、どこを共有しているから完全には独立ではないのか

を、できるだけ WSL2 や Remote WSL が初めての人でも追えるレベル で図解していきます。


1. 前編のおさらい:何をした環境だったのか

まず、前編の記事の構成を 1 枚の図でざっくり振り返ります。

  • Windows 11 上で動いている VS Code が「リモート」に接続する
  • リモート先は、Docker Desktop / Rancher Desktop 上の Dev Container (CentOS 7.2)
  • コンテナの中には、古い本番環境に合わせた
    • Python 2.7.5
    • 古い debugpy
      などをインストール
  • 「この古い環境にだけ接続する専用クライアント」として、ポータブル版 VS Code(1.63.2)を使う

という構図です。

【図1】

補足)
「 Ubuntu (※1) 」
「 Ubuntu (※2) 」
は、同一のディストリビューションだとして、考えてください。
2枚の図に分けて書いてますが、それは、
mermaidで↑の図を書いてますが、私が個人的に、mermaidで図を書くスキルが不足していてて、
2つに図を分けないとうまく描けなかった。
本当は、図を1個にして、「 Ubuntu 」が一個だけの図にしたかった。
「 Ubuntu 」から「 CentOS 7.2 Dev Container 」のコンテナに
矢印がつながっているのは、
大元が、「 ポータブル版 VS Code 1.63.2 」の流れだけである。
大元が、「 通常版 VS Code (最新) 」からの流れの時は、
「 Ubuntu 」から「 CentOS 7.2 Dev Container 」のコンテナに
矢印がつながっていない
その様子を、1個の図で視覚的、感じ取れるようにうまく描くための、
mermaidでの作図のスキルが私には無くて、上記のように2枚の図にしました。
苦肉の策で、この諸事情を、この文章で補足説明することにしました。

ここでポイントだったのは、

  • 通常版 VS Code(code .)は 普段使いの開発用
  • ポータブル版 VS Code(1.63.2)は 「古い debugpy コンテナ専用」

と、役割をきっちり分けたことです。

なぜ、普段使いの最新版VS Code環境と干渉せず、互いに独立で共存できたのかを、先に、ざっくり結論を示します。

ここで、もう少しだけ先回りして結論だけざっくり書いておきます(細かい仕組みは後述の「4. VS Code Server はリモートでどこに入るのか」と「5. どこまでが『独立』で、どこからが『共有』なのか」で説明します)。

  • 古い debugpy や Python 拡張は、WSL2 側の ~/.vscode-server には一切インストールしていない

    補足) たしかに、一旦、Remote WSL2でWSL2に接続してはいるが、
    古い debugpy や Python 拡張のインストールは、WSL2側はスルーした。
    コンテナ側に対してビルドプロセスの終盤で、コンテナに対してインストールする形で
    構築していた。

  • 代わりに、「特定の Dev Container 内の」 vscode ユーザーのホームディレクトリ配下 (~/.vscode-server) にだけ入れている
    ★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★
    ★ 前編の記事では、ここの拡張機能のインストールで特殊なやり方してます。★
    ★ その詳細は、後述します。★
    ★ 詳しくは、後述の説明を参照してください ★
    ★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★
  • Dev Container はコンテナごとにファイルシステムとホームディレクトリが完全に独立しているので、
    このコンテナに対する VS Code Server +拡張は、そのコンテナ専用の閉じた世界 になっている
  • 一方、普段使いの最新版 VS Code(code .)が使う Remote WSL 側の ~/.vscode-server とは、リモート側の場所レベルでそもそも分かれている

つまり、拡張機能がインストール先が、
ローカル(Windows)側の VS Code が通常版とポータブル版で分かれているだけでなく、リモート(WSL / Dev Container)側も物理的に別だったからこそ、前編の構成ではきれいに共存・独立が実現できていた、というのが大きなポイントです。

↑↑の文章にて、

  ★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★
  ★ 前編の記事では、ここの拡張機能のインストールで特殊なやり方してます。★
  ★ その詳細は、後述します。★
  ★ 詳しくは、後述の説明を参照してください ★
  ★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★★

と記載させていただいた箇所がありますが、その説明をここに書きます

そうしないと、↑↑の説明の流れの腰を折ってしまってわかりにくいと思いましたので
ここでまとめて説明します。

前編の記事の
https://zenn.dev/tazzae999jp/articles/b166b7fd73b3bf
で、
.devcontainer/devcontainer.json

  "postCreateCommand": "",
  "postStartCommand":  "bash -lc '/opt/setup-extensions.sh --block'",
  "postAttachCommand": "",

で、setup-extensions.sh が動くように指定してます
前編の記事で、setup-extensions.shの実装も書いてますが、
古いバージョンの拡張機能をDev Container側に特殊な方法でインストールしてます
署名なしの古いバージョンの拡張機能のため、普通のやり方ではインストールできなかったことと
インストールが完了するまで、待つよう制御するなど対処が入ってます
この待つ制御が入ってないと、先にRebuild without cache reopenのプロセスが
完了して結局、コンテナに該当の拡張機能がインストールできてない状況になりました。
これを防ぐため、インストールが完全に完了してから、
Rebuild without cache reopenのプロセスが進んで、完了する
という制御に仕向ける必要があったのです。
署名ありが要求される以前の古いバージョンなので仕方がなかったからです。
通常であれば、そんなことする必要ありません。
.devcontainer/devcontainer.jsonでコンテナにインストールしたい
拡張の識別子を書けば自動でインストールしてくれます。
下記の例のように拡張機能の識別子や必要ならバージョン指定もできます。

// .devcontainer/devcontainer.json の例
{
  "name": "my-devcontainer",
  "image": "mcr.microsoft.com/devcontainers/base:ubuntu",

  "customizations": {
    "vscode": {
      "extensions": [
        // ★ この拡張は特定バージョンに固定
        "ms-dotnettools.csdevkit@1.11.11",

        // ★ この拡張は常にその時点の最新版
        "ms-python.python",

        // ★ この拡張は“インストールリストから除外”
        "-ms-vscode.cpptools"
      ],
      "settings": {
        // 拡張の自動更新を止めたい場合(後述)
        "extensions.autoUpdate": false,
        "extensions.autoCheckUpdates": false
      }
    }
  }
}

上記で、
extensions.autoUpdate: false
で、拡張の自動更新を無効化。
extensions.autoCheckUpdates: false
で、更新チェック自体も止める。
の指定をして、Dev Container環境での拡張機能のバージョン固定できます。
開発案件ごとにバージョン固定するのは重要です。
ターゲットの本番環境にあわせて固定しておいて、開発作業をする必要があるからです。
★ devcontainer.jsonもgitの資産とすることで、git cloneしたら、使える拡張機能も
★ チームメンバーで共通みたいに、環境同期ができるということです。
まとめると、
今回みたいに署名なしの時代にまで、遡らなければならないほどの
古いバージョンの拡張機能をインストールしなければならない特殊な状況でなければ、
通常は、Dev Container環境に拡張機能をインストールするのは、
かなり楽に設定できる。ということは、ご認識いただきたく思います。

以上



2. Windows ローカルの VS Code は「どこに何を保存しているか」

まずは Windows 側だけ に絞って、

  • 通常版 VS Code
  • ポータブル版 VS Code(複数あったとして)

がそれぞれ どこに設定や拡張機能を保存しているか を整理します。

2-1. 通常版 VS Code の保存場所

Windows に普通にインストーラから入れた VS Code は、ざっくりいうと:

  • 設定ファイルC:\Users\<ユーザー名>\AppData\Roaming\Code
  • 拡張機能C:\Users\<ユーザー名>\.vscode\extensions

のような場所に保存されます。

2-2. ポータブル版 VS Code の保存場所

一方、公式がサポートしている 「ポータブルモード」 では、

  • Code.exe と同じ階層に data フォルダを置く
  • その中に
    • data\user-data … 設定
    • data\extensions … 拡張機能
      などが全部入る

という挙動になります。

つまり、ポータブル版 VS Code ごとに data フォルダが 1 個ずつあるイメージです。

【図2】

ここから分かる大事な点は:

  • 通常版 VS Code の設定・拡張は「ユーザープロファイル配下」の固定フォルダ
  • ポータブル版 VS Code の設定・拡張は「exe を展開した先の data フォルダ」

にそれぞれ保存されるので、

「インストール先のフォルダが違うポータブル版 VS Code どうし」
「通常版 VS Code とポータブル版 VS Code」

は、Windows ローカルの設定・拡張に関しては完全に独立している、ということです。

だから前編のように、

  • 通常版 VS Code … ふつうの開発用
  • ポータブル版 VS Code … 古い debugpy 用 Dev Container 専用

という 役割分担をしても、お互いの設定・拡張はぶつからないのです。

ただし、
WSL2側への拡張機能が保存されることがあります
詳しく言うと、後述の「~/.vscode-server/bin/<commit-id>/」
のところです。VS Codeのバージョンが同じだと<commit-id>が同じになります
この<commit-id>は、VS CodeのコミットIDです(= VS Codeのバージョンかと)
VS Codeの拡張機能によりけりなんですけど、
Windows領域への保存だけでいいものもあります。
WSL2側への保存も発生するものがあります。
VS Codeを「Remote WSL」でWSL2側に接続した状況で、拡張機能の中には
Ubuntuにもインストール などのボタンが出てくるものがあります。
そのボタンを押したときに、「~/.vscode-server/bin/<commit-id>/」に
インストールされることになると思います。
しかも、この「~/.vscode-server/bin/<commit-id>/」の
「~」記号ですが、ログインユーザのホームディレクトリですよね
そのログインユーザに関しては、
/etc/wsl.confで[User]のセクションでdefault=で指定されたユーザ
( 初期では、このユーザはUbuntuをインストール時に入力した初期ユーザです )
ユーザがログインユーザであるときしか、
「Remote WSL」はうまく動かないんです。
他のユーザでUbuntuにログインしても、「Remote WSL」はエラーになります
他のユーザで、code .でVS Codeを起動しても、「Remote WSL」でWSL2に接続時に
エラーになります。
/etc/wsl.confで[User]のセクションでdefault=で指定された
ユーザのホームディレクトリ配下の.vscode-serverフォルダ配下の一択になる
仕様となっています。その話は、
https://zenn.dev/neruneko/articles/ba513a3889f26b
の記事、参照のこと。
とにかく、うまくやるためには、まず、前提となる基礎知識が必要でしょう。
これ以後、基礎知識の説明になっています。
まずは、「Remote WSL って何?」という基礎知識から後続で説明しています。


3. 「Remote WSL って何?」をざっくりイメージから理解する

ここからが本題です。
Remote WSL / Dev Containers / Remote SSH は、まとめて Remote Development ファミリーと呼ばれます。

ざっくりしたイメージは:

  1. Windows 側で VS Code を起動する(これは「見た目の本体」)
  2. 接続先の WSL2 / コンテナ / SSH サーバー側に、
    「VS Code Server」という小さなプログラムをインストールする
  3. この VS Code Server が、
    • ファイルの読み書き
    • 拡張機能の実行
    • デバッグ実行(debugpy など)
      リモート側で担当する

という構造になっています。

【図3】

Remote WSL と Remote SSH と Dev Containers の違いは、

  • 「リモート側が WSL2 なのか? SSH サーバーなのか? コンテナなのか?」

という 場所の違い だけで、

  • 「VS Code Server をその場所に入れて、VS Code からしゃべる」

という基本構造は同じです。

ただし、Remote WSL の場合にだけの特殊事情として、
/etc/wsl.confで[User]のセクションでdefault=で指定されたユーザ
( 初期では、このユーザはUbuntuをインストール時に入力した初期ユーザです )
ユーザがログインユーザであるときしか、
「Remote WSL」はうまく動かないんです。
他のユーザでUbuntuにログインしても、「Remote WSL」はエラーになります
他のユーザで、code .でVS Codeを起動しても、「Remote WSL」でWSL2に接続時に
エラーになります。
/etc/wsl.confで[User]のセクションでdefault=で指定された
ユーザのホームディレクトリ配下の.vscode-serverフォルダ配下の一択になる
仕様となっています。その話は、
https://zenn.dev/neruneko/articles/ba513a3889f26b
の記事、参照のこと。


4. VS Code Server はリモートでどこに入るのか

次に、「VS Code Server 自体がどのフォルダにインストールされるのか」を見ていきます。

4-1. リモート側のホームディレクトリ配下に .vscode-server ができる

Remote WSL や Remote SSH で接続すると、

  • リモートユーザーのホームディレクトリ(例:/home/vscode)の下に
  • ~/.vscode-server/ というフォルダが作られます。

その中身は、だいたいこんな感じです:

  • ~/.vscode-server/bin/<commit-id>/ … VS Code Server 本体一式
  • ~/.vscode-server/extensions/ … リモート拡張機能
  • ~/.vscode-server/data/ … キャッシュや一部設定

【図4】

ここで出てきた <commit-id> が重要です。

4-2. <commit-id> は「VS Code のビルドごとに一意」

VS Code にはバージョン番号(例:1.63.2)がありますが、内部的にはさらに細かい コミット ID(git のハッシュ)でビルドを識別しています。

  • 通常版 VS Code(例:1.63.2 stable)
  • ポータブル版 VS Code(1.63.2 の ZIP 版)

のように、同じバージョンの VS Code であれば、内部的には 同じ <commit-id> になります。

VS Code が Remote WSL などに接続するときは、

  • 「いま起動している VS Code の <commit-id>」を見て
  • ~/.vscode-server/bin/<commit-id>/ が存在しなければインストール
  • 存在すれば、それをそのまま使う

という挙動になります。

つまり、リモート側の VS Code Server 本体は、「リモートユーザー」+「VS Code の commit-id」ごとに 1 セットです。


5. どこまでが「独立」で、どこからが「共有」なのか

ここまでの要素を組み合わせて、
冒頭の 2 つの話題(話題その1 / 話題その2)を整理し直します。

5-1. 話題その1:なぜ前編の構成はきれいに共存できたのか

前編の構成を、要素に分解してみます。

  • Windows 側
    • 通常版 VS Code(最新版) … 日常開発用
    • ポータブル版 VS Code(1.63.2) … 古い debugpy Dev Container 専用
  • Remote 側
    • Dev Container (CentOS 7.2)
      • Python 2.7.5
      • 古い debugpy(コンテナ内に直接インストール)

このとき、干渉しなかった理由は:

  1. Windows ローカルの設定・拡張が完全に分かれていた
    • 通常版 VS Code … %APPDATA%\Code, %USERPROFILE%\.vscode\extensions
    • ポータブル版 VS Code … ポータブルフォルダ\data\user-data, ポータブルフォルダ\data\extensions
  2. 古い debugpy は WSL2 ではなく「特定の Dev Container 内」にだけ入れた
    • 通常版 VS Code は、別のプロジェクトや別のコンテナに接続
    • ポータブル版 VS Code だけが「古い debugpy コンテナ」に接続

ここで Remote Development ファミリーの中でも、前編の構成が「Dev Containers だけ」を使っていたことを、もう一段はっきり書いておきます。

  • 古い debugpy や Python 拡張は、WSL2 の ~/.vscode-server には一切インストールしていない
  • 代わりに、Dev Container 内の vscode ユーザー(コンテナ内ホーム)配下の ~/.vscode-server にだけ入れている
  • Dev Container は 1 個のコンテナごとに 独立したファイルシステムとホームディレクトリ を持つので、
    「このコンテナに対する VS Code Server +拡張」は、そのコンテナ専用の閉じた世界 になる

つまり、前編の構成では

  • 普段使いの最新版 VS Code(code .)+ Remote WSL 側の ~/.vscode-server
  • ポータブル版 VS Code 1.63.2 + 特定の Dev Container 内の ~/.vscode-server

という 「リモート側の場所」自体も完全に分けていた ため、
Remote WSL / Dev Containers / Remote SSH が同じ仕組みで動くことを踏まえても、
読者が「Dev Container 内にだけ古い debugpy を閉じ込めた構成なんだ」と明確にイメージできるようにしておくのがポイントです。

つまり、

  • 「Windows 側」はインストール先フォルダが違うので完全に独立
  • 「Remote 側」も、そもそも接続しているコンテナが違うので、実質的に干渉しない

という二重の分離が効いていた、というわけです。

5-2. 話題その2:複数の VS Code が「同じリモート」に接続する場合

ここから少し難しくなります。

たとえば、次のような状態を考えます:

  • 通常版 VS Code … バージョン 1.90.x
  • ポータブル版 VS Code A … バージョン 1.80.x
  • ポータブル版 VS Code B … バージョン 1.63.2

この 3 つが、同じ WSL2 ディストリ(例: Ubuntu-24.04-my)の同じユーザー に Remote WSL で接続したとき、
リモート側のフォルダ構成はどうなるでしょうか。

イメージはこんな感じです。

【図5】

この図から読み取れるポイントは:

  • VS Code Server 本体(bin/<commit-id>/)は、commit-id ごとに別フォルダでインストールされる
  • しかし extensions/ はユーザーごとに 1 箇所だけ
    → どの VS Code から接続しても、ここに入っている拡張を共有して使う

下記の質問1、質問2が気になった。
そして、その回答もセットで下記に示す。

  • 質問1:

    ポータブル版 VS Code がすべてバージョン違いなら、共存できるか?
    → 「VS Code Server 本体は共存できる(bin はバージョンごとに分かれる)」という意味では YES
    → ただし 拡張 (~/.vscode-server/extensions) は共有される ので、「完全に独立」ではなく「一部共有」

  • 質問2:

    ポータブル版 VS Code の置き場所が違っても、バージョン(commit-id)が同じなら干渉するか?
    YES。commit-id が同じなら、同じ bin/<commit-id> と同じ extensions/ を見る

という整理になります。


6. まとめ:この記事のゴールと実践パターン集

この記事のゴールは、「前編の続き」として:

  • Windows ローカルの VS Code(通常版/ポータブル版)が、どこに設定・拡張を保存しているか
  • Remote WSL / Dev Containers / Remote SSH で VS Code Server がどこに入るか
  • どこまでが独立で、どこから先は共有されるのか

を、WSL2 初心者でも追えるレベルで図と一緒に整理することでした。

最後に、この記事だけ読めば「実際にどう分ければいいか」まで分かるように、具体的なパターンとしてまとめ直します。


WSL2 環境で Remote WSL を使うときのポイントは、次の 2 つです。

  • ディストリごとに default user は 1 人だけ/etc/wsl.conf[user] default=
  • Remote WSL 拡張は、その default user だけを前提に動く

この制約の上で、VS Code Server(~/.vscode-server)を分ける代表的なパターンは 2 つあります。

パターンA:WSL2 ディストリを分ける(教科書的で安全)

  1. 通常開発用ディストリ
    • 例:Ubuntu-24.04-my-dev
    • default user:vscode
    • 通常の案件、通常の Python / Node / PHP などはこちらで作業する。
  2. レガシー案件用ディストリ
    • 例:Ubuntu-24.04-my-legacy
    • default user:vscode(名前は同じでも、別ディストリなのでホームは完全に別)
    • 古い Python 2.7.5 や、古い debugpy など「他案件に混ぜたくないもの」はここに閉じ込める。

この構成だと:

  • Ubuntu-24.04-my-dev 側には ~/.vscode-server(通常案件用)
  • Ubuntu-24.04-my-legacy 側には別の ~/.vscode-server(レガシー案件用)

ができて、物理的に別ファイルシステムなので、拡張や VS Code Server の中身は完全に分離されます。

メリット

  • 教科書的でシンプル。WSL2 の仕様に素直に乗っている。
  • 万が一レガシー案件で変な拡張を入れても、通常案件側には一切影響しない。

デメリット

  • ディストリを増やすぶん、ディスクをそれなりに消費する。
  • バックアップ・エクスポート対象のディストリが増える。

ディスク容量がきつくてディストリを増やしたくない場合、
「ホーム直下の ~/.vscode-server だけを、案件ごとに差し替える」という現実解があります。

手順の骨格は、別記事:

で詳しく書いていますが、ここでは要点だけを整理します。

  1. いま使っている ~/.vscode-server を退避
    mv ~/.vscode-server ~/.vscode-server-main
    
  2. レガシー案件用の VS Code Server 領域を作る
    mkdir ~/.vscode-server-python2.7.5-remote-debug
    # ここに古い ms-python.python-2021.9.... や debugpy を展開しておく
    
  3. ホーム直下の ~/.vscode-server実体ではなく symlink にする
    ln -s ~/.vscode-server-main ~/.vscode-server
    
  4. 通常案件で作業するときは、この symlink を ~/.vscode-server-main に向けておく。
  5. Python 2.7.5 レガシー案件のフォルダでは、my_code 関数のようなシェル関数を用意しておき、
    実行前に次のようなことを自動でやらせる:
    • ~/.vscode-server の symlink を ~/.vscode-server-python2.7.5-remote-debug に向け替える
    • 古い VS Code Server プロセスを pkill -f vscode-server で止める
    • その状態で code . を起動する

こうしておくと:

  • 通常案件フォルダで code .~/.vscode-server-main を使う
  • レガシー案件フォルダで my_code .~/.vscode-server-python2.7.5-remote-debug を使う

という形で、**同じ WSL2 ディストリ内でも VS Code Server/拡張のセットを案件ごとに分けて運用できます。

注意点

  • symlink の指し先を切り替えるのは、あくまで「ハック寄り」のテクです。
    公式ドキュメントは「~/.vscode-server を別ディスクに mv して symlink にする」までは想定していますが、
    実体を複数用意して案件ごとに切り替える運用はサポート対象外です。
  • 切り替え時に VS Code Server のプロセスが生きていると、古いパスを握ったままになる可能性があるので、
    かならず pkill -f vscode-server などで一度止めてから起動するのが安全です。

WSL2 での結論としては:

  • ディスクに余裕があるならディストリ分割(パターンA)
  • ディスクが厳しいなら symlink ハック(パターンB)を慎重に使う

という 2 段構えで設計すると、無理なく運用できるはずです。


6-2. Remote SSH のユーザー分離パターン(素直で壊れにくい)

Remote SSH の場合は、WSL2 と違って ユーザーごとにホームディレクトリが完全に分かれます
VS Code Server もホーム直下の ~/.vscode-server を使うので、ユーザーを分けるだけで自然に分離されます。

基本の考え方はシンプルです。

  1. 通常案件用ユーザー
    • 例:user_main
    • ホーム:/home/user_main
    • 対応する VS Code Server:/home/user_main/.vscode-server
  2. レガシー案件用ユーザー
    • 例:user_legacy
    • ホーム:/home/user_legacy
    • 対応する VS Code Server:/home/user_legacy/.vscode-server

接続するときは:

  • 通常案件のとき:ssh user_main@host → Remote SSH で user_main に接続
  • レガシー案件のとき:ssh user_legacy@host → Remote SSH で user_legacy に接続

と使い分けるだけで、

  • VS Code Server 本体(bin/<commit-id>
  • extensions/ 以下の拡張群

もすべてユーザー単位で分かれます。

メリット

  • OS のユーザー分離にそのまま乗っているので、ハックが一切要らない。
  • 事故ったら「レガシー用ユーザーごと消す」という割り切りもできる。

デメリット

  • サーバー側で複数ユーザーを管理する手間が増える(権限・ディスク quota など)。

6-3. Dev Containers の分離パターン(コンテナごとに閉じ込める)

Dev Containers(Remote - Containers)は、Docker コンテナ内に VS Code Server をインストールして使います。
コンテナは OS レベルでファイルシステムが分離されるので、

  • コンテナA:/home/vscode/.vscode-server(通常案件用)
  • コンテナB:/home/vscode/.vscode-server(レガシー案件用)

という形で、同じパスでも「別世界」として扱われます。

実際の分け方は、だいたい次のイメージです。

  1. 通常案件用 DevContainer
    • devcontainer.json と Dockerfile で、
      • 通常版の Python / Node / PHP
      • 通常版の debugpy
        を入れたコンテナを定義する。
  2. レガシー案件用 DevContainer
    • 別の devcontainer.json と Dockerfile で、
      • Python 2.7.5 や古い debugpy
        を入れたコンテナを定義する。
  3. VS Code からは
    • 通常案件フォルダ → 通常用 DevContainer で「Open in Container」
    • レガシー案件フォルダ → レガシー用 DevContainer で「Open in Container」

と開くだけで、VS Code Server/拡張がコンテナごとに完全分離されます。

メリット

  • コンテナ単位で依存を全部閉じ込められるので、「最悪コンテナを捨てる」でやり直しが効く。
  • WSL2 ディストリや SSH ユーザーを増やさなくても、プロジェクトごとにわかりやすく分けられる。

デメリット

  • Docker / Dev Containers の知識が前提になる。
  • イメージのビルド・pull でディスクとネットワークをそこそこ使う。

補足)
モダンな開発案件だけをしてるのであれば、
普段使いの最新版のVS Codeだけを一択で使用して
上記のように開発案件ごとにDev Container環境をわけて
互いに、共存・独立です
前編の記事 では、古いバージョンの拡張を利用しなければならない
諸事情があり、それに伴い、古いバージョンのVS Codeが必要になり
ポータブル版の古いバージョンのVS Codeを、それ専用に使うことで
普段使いの最新版のVS Codeに影響させない配慮の上で、
Dev Container環境を利用するという、特殊な合わせ技であったことを
補足しておきます。


6-4. 全体としてどう設計するか(まとめ)

ここまでの話を、ざっくり整理するとこうなります。

  • ローカル(Windows)の VS Code

    • 通常版とポータブル版は、インストール先フォルダが違えば「互いに独立した VS Code」として扱える。
    • 前編の記事の構成では、「普段使いの最新版 VS Code」と「レガシー案件専用ポータブル版 VS Code」を分けたのがポイント。
  • WSL2

    • ディストリを増やせば、VS Code Server も含めて環境が丸ごと分かれる。
    • ディスクが厳しいなら、~/.vscode-server symlink ハックで案件ごとに VS Code Server セットを切り替える、という現実的な選択肢もある。
  • Remote SSH

    • ユーザーごとに ~/.vscode-server が独立するので、ユーザー分離がそのまま安全な分離パターンになる。
  • Dev Containers

    • コンテナはそもそも独立した環境なので、「案件ごとにコンテナを分ける」だけで自然と分離される。

このまとめ記事では、

  • 「ローカル VS Code」と「リモート VS Code Server」の接続関係
  • どこまでが独立で、どこからが共有なのか
  • それを踏まえて 実際にどう分けて運用すればいいか

までを書き切ることを目標にしました。

ここまで読んだ人が、自分の PC / 自分の案件に合わせて、

  • 「WSL2 ディストリを増やすか」
  • ~/.vscode-server symlink ハックを使うか」
  • 「Remote SSH でユーザーを分けるか」
  • 「Dev Containers で案件ごとに閉じ込めるか」

を選べるようになっていれば、このシリーズの後編としては成功だと思っています。

Discussion