仕組み
一度VSCode Remote Containersを開いた後 cat ~/Library/Application\ Support/Code/storage.json
の
windowsState
> lastActiveWindow
> folder
を見ると以下のような感じになっているのが分かります。
"windowsState": {
"lastActiveWindow": {
"folder": "vscode-remote://dev-container%2B2f557365722f6e616d652f646576656c6f702f70726f6a656374/usr/src",
"backupPath": "...",
"remoteAuthority": "dev-container+2f557365722f6e616d652f646576656c6f702f70726f6a656374",
"uiState": {
"mode": 1,
"x": 0,
"y": 23,
"width": 3440,
"height": 1417
}
},
"openedWindows": []
},
この folder
のURLが分かれば
$ code --folder-uri vscode-remote://dev-container%2B2f557365722f6e616d652f646576656c6f702f70726f6a656374/usr/src
このように直接CLIから立ち上げる事が可能です。
2f557365722f6e616d652f646576656c6f702f70726f6a656374
の部分は16進数文字列
になっていて
これをデコードすると /User/name/develop/project
となります。また %2B
が含まれているのでURLエンコードされているのが分かります。
最後の /usr/src
は devcontainer.json
の workspaceFolder
で指定したパスになります。
これらを踏まえて全体のURL構成要素としては
"vscode-remote://" + URI.encode_www_form_component("dev-container+" + "/User/name/develop/project".unpack('H*')) + "/usr/src"
となっているようです。
スクリプトの作成
パスを指定したらVSCode Remote Containersを起動する為のURLを生成してくれるスクリプトを書いてみます。
指定したパス配下の .devcontainer/devcontainer.json
の workspaceFolder
を読み込んで生成してます。
# frozen_string_literal: true
# !/usr/bin/env ruby
require 'json'
module VSCodeRemoteContainer
class Utility
def initialize
end
def generate_url(root_path)
folder = find_workspace_folder(root_path)
path = "dev-container+#{root_path.unpack('H*')[0]}"
puts "vscode-remote://#{URI.encode_www_form_component(path)}#{folder}"
end
def find_workspace_folder(root_path)
unless File.exist?("#{root_path}/.devcontainer/devcontainer.json")
puts 'Not found devcontainer.json file.'
return
end
config = JSON.parse(File.read("#{root_path}/.devcontainer/devcontainer.json"))
config['workspaceFolder']
end
end
end
VSCodeRemoteContainer::Utility.new.generate_url(*ARGV)
上記を main.rb
として保存し以下の様に実行するとURLが生成されます
$ ruby main.rb '/User/name/xxxx'
# => vscode-remote://dev-container%2B2f557365722f6e616d652f646576656c6f702f70726f6a656374/usr/src
AlfredのWorkflowsの作成
今回はghqと組み合わせて動作するWorkflowsを作成してみました。
動作イメージとして↓のようにリポジトリ名を指定して直接VSCodeをコンテナ内で起動しています。
Workflowsを作成するにあたって上記のスクリプトに追記しました。
module VSCodeRemoteContainer
class Utility
attr_accessor :bin_path
def initialize
@bin_path = ENV['GHQ_PATH'] || '/usr/local/bin'
end
def ghq_exists?
!`which #{@bin_path}/ghq`.empty?
end
def search
return unless ghq_exists?
result = []
`#{@bin_path}/ghq list --full-path`.split(/\R/).each do |d|
Dir.foreach(d) do |path|
next if ['.', '..'].include?(path)
file = File.join(d, path)
result << d if file.include?('.devcontainer')
end
end
result
end
end
end
やってる事は ghq
を使って対象のリポジトリ一覧をとってきて、
.devcontainer
ディレクトリがあるリポジトリだけを返すようにしてます。
出来上がったものは
https://gist.github.com/Slowhand0309/253bb296cd7acb089601d2b32da4723b
こちらに置いております。とりあえず作ってみた程度なので不具合等見つけたら
ご連絡頂けると助かります。
※ zsh
をベースに作ってますが、お使いのシェルでお好みで修正して頂ければ