🚀

いい感じに好きなコマンドが実行できる VS Code 拡張を作った(Commando)

2023/03/04に公開

VS Code 拡張を作ったので、その話をします。
GitHub Actions で自動テスト & デプロイするおまけ付き

Commando

どんなもの?

シェルとかのコマンドをいい感じに実行できる VS Code の拡張機能です。
tasks.json と異なり、出力ウィンドウに結果を表示できたりするので邪魔になりにくいです。
地味にローカライズ対応しています。誰か外国語詳しい人が追加してくれると嬉しい。

Commando

以下のような感じで設定するとコマンドパレットから実行できます。

settings.json
{
  "commando.commands": [
    {
      "name": "Hello World",
      "description": "はろーわーるどを表示する",
      "cmd": "echo \"Hello World\""
    }
  ],
}

コマンドパレットじゃ使いにくい?
キーバインドからも実行できます。

keybindings.json
{
  "key": "ctrl+t",
  "command": "commando.execute",
  "args": {
    "name": "Hello World"
  }
}

キーバインドすらもめんどくさい?
ファイルを保存時に実行なんてこともできますよ。

settings.json
{
  "commando.commands": [
    {
      "name": "Hello World",
      "description": "はろーわーるどを表示する",
      "cmd": "echo \"Hello World\"",
      "executeOnSavePattern": ".*\\.txt"
    }
  ],
}

なんか他にも欲しい機能があったら教えてください。

インストール

VS Code で Commando で検索するか、以下のリンクからインストールしてください。
https://marketplace.visualstudio.com/items?itemName=SeeLog.commando

他のオプション

  • executeInTerminal: コマンドをターミナルで実行するかどうか。デフォルトは falsefalse の場合は出力ウィンドウに結果が出るのでエコです。
  • autoClear: 名前の通り自動で出力系のクリア
  • autoFocus: 名前の通り自動で出力ウィンドウにフォーカス

プレースホルダーも使えます。

  • ${commandName}: コマンド名 e.g. "Super Command"
  • ${workspaceFolder}: ワークスペースのフルパス e.g. "/home/ubuntu/hoge/.vscode/settings.json"
  • ${workspaceFolderBasename}: ワークスペースフォルダの名前 e.g. "workspace"
  • ${homeDir}: ホームディレクトリ的なところ e.g. "/home/ubuntu"
  • ${tmpDir}: テンポラリディレクトリ的なところ e.g. "/tmp/hogehoge/"
  • ${platform}: OS のプラットフォーム e.g. "linux"
  • ${file}: ファイルのフルパス e.g. "/home/ubuntu/hoge/.vscode/settings.json"
  • ${fileBasename}: ファイル名 e.g. "settings.json"
  • ${fileExtname}: ファイルの拡張子 e.g. ".json"
  • ${fileBasenameWithoutExt}: 拡張子抜きのファイル名 e.g. "settings"
  • ${fileDirName}: ファイルの親のフルパス e.g. "/home/ubuntu/hoge/.vscode"
  • ${relativeFile}: ワークスペースフォルダから見たファイルの相対パス e.g. ".vscode/settings.json"
  • ${lineNumber}: 今の行番号 e.g. "5"
  • ${lineNumbers}: マルチカーソル版行番号 e.g. "5 5"
  • ${columnNumber}: 今の列番号 e.g. "26"
  • ${columnNumbers}: マルチカーソル版行番号 e.g. "26 32"
  • ${selectedText}: 選択しているテキスト e.g. "Hello"
  • ${selectedTexts}: マルチカーソル版の選択しているテキスト e.g. "Hello World"

GitHub Actions 的なお話

https://github.com/SeeLog/commando

GitHub Actions を使って自動テスト & デプロイしています。

自動テスト

https://github.com/SeeLog/commando/pull/2

パブリックリポジトリだと無料らしいので macOS でも CI を回しています。
Ubuntu の場合だけ /usr/bin/Xvfb :99 -screen 0 1024x768x24 みたいなことをしてあげると、GUI が動くようになるので VS Code のテストができます。

Windows と macOS はなんかそういうのいらないっぽいです。

.github/workflows/test.yml
name: Test VSCode extension

on:
  push:
    branches:
      - main
  pull_request:
    branches:
      - main

jobs:
  test:
    name: Test on ${{ matrix.os }}
    runs-on: ${{ matrix.os }}
    timeout-minutes: 10
    strategy:
      matrix:
        os: [ubuntu-latest, windows-latest, macos-latest]
        node:
          - 19
    steps:
      - name: Checkout
        uses: actions/checkout@v3
      - name: Install Node ${{ matrix.node }}
        uses: actions/setup-node@v3
        with:
          node-version: ${{ matrix.node }}
      - run: /usr/bin/Xvfb :99 -screen 0 1024x768x24 > /dev/null 2>&1 & echo "Starting Xvfb..."
        shell: bash
        if: ${{ success() && matrix.os == 'ubuntu-latest' }}
      - name: Install dependencies
        run: npm ci
      - name: Run test
        # pretest run compile and lint automatically
        run: npm run test
        env:
          DISPLAY: ":99.0"

自動デプロイ

タグを打つと自動でデプロイされます。
こっちはプルリク1発でうまく動かせなかったので、コードを貼ります。
https://github.com/SeeLog/commando/blob/main/.github/workflows/deploy.yml

事前に VS Code Extension をアップロードするためのトークンを取っておきます。
そして、リポジトリの Settings > Secrets and variables で VSCE_TOKEN という名前でトークンを登録します。
間違ってもトークンを deploy.yml に書いちゃダメです。

.github/workflows/deploy.yml
name: Deploy Extension
on:
  push:
    tags:
      - v*

jobs:
  upload-artifact:
    runs-on: ubuntu-latest
    steps:
      - name: Checkout
        uses: actions/checkout@v3
      - name: Install Node 19
        uses: actions/setup-node@v3
        with:
          node-version: 19
      - name: Install vsce
        run: npm install -g vsce
      - name: Install dependencies
        run: npm ci
      - name: Run build
        run: vsce package
      - name: Upload artifact
        uses: actions/upload-artifact@v3
        with:
          name: extension
          path: "*.vsix"
  publish:
    needs: upload-artifact
    runs-on: ubuntu-latest
    if: success() && startsWith(github.ref, 'refs/tags/v')
    steps:
      - name: Download artifact
        uses: actions/download-artifact@v3
      - name: Install vsce
        run: npm install -g vsce
      - name: Publish
        run: vsce publish --packagePath $(find . -iname *.vsix)
        env:
          VSCE_PAT: ${{ secrets.VSCE_PAT }}

v から始まるタグを打つと自動でデプロイされます。
デプロイは複数の OS からやらなくても良いと思うので Ubuntu でやってます。

npx の方の vsce だとなんかうまく動かなかったので、npm install で vsce をグローバルにインストールしています。

Discussion