タスクを介して外部ツールと統合する
ソフトウェアシステムのリンティング、ビルド、パッケージング、テスト、デプロイなどのタスクを自動化するための多くのツールが存在します。TypeScript Compiler、ESLint や TSLint のようなリンター、そして Make、Ant、Gulp、Jake、Rake、MSBuild のようなビルドシステムがその例です。
これらのツールは主にコマンドラインから実行され、ソフトウェア開発の内部ループ (編集、コンパイル、テスト、デバッグ) の内外でジョブを自動化します。開発ライフサイクルにおけるその重要性を考えると、VS Code 内からツールを実行し、その結果を分析できることは役立ちます。VS Code のタスクは、スクリプトを実行したりプロセスを開始したりするように構成できるため、既存の多くのツールをコマンドラインを入力したり新しいコードを書いたりすることなく VS Code 内から使用できます。ワークスペースまたはフォルダー固有のタスクは、ワークスペースの .vscode
フォルダーにある tasks.json
ファイルから構成されます。
拡張機能は、タスクプロバイダーを使用してタスクを提供することもでき、これらの提供されたタスクは tasks.json
ファイルで定義されたワークスペース固有の設定を追加できます。
注: タスクサポートは、ワークスペースフォルダーで作業している場合にのみ利用できます。単一ファイルを編集している場合は利用できません。
TypeScript Hello World
JavaScript にコンパイルしたいシンプルな "Hello World" TypeScript プログラムから始めましょう。
空のフォルダー "mytask" を作成し、tsconfig.json
ファイルを生成して、そのフォルダーから VS Code を起動します。
mkdir mytask
cd mytask
tsc --init
code .
次に、次の内容で HelloWorld.ts
ファイルを作成します。
function sayHello(name: string): void {
console.log(`Hello ${name}!`);
}
sayHello('Dave');
⇧⌘B (Windows、Linux では Ctrl+Shift+B) を押すか、グローバルメニューの ターミナル から ビルドタスクの実行 を実行すると、次のピッカーが表示されます。
最初の項目は TypeScript コンパイラを実行し、TypeScript ファイルを JavaScript ファイルに変換します。コンパイラが完了すると、HelloWorld.js
ファイルが存在するはずです。2番目の項目は、TypeScript コンパイラをウォッチモードで開始します。HelloWorld.ts
ファイルを保存するたびに、HelloWorld.js
ファイルが再生成されます。
TypeScript のビルドまたはウォッチタスクを既定のビルドタスクとして定義すると、ビルドタスクの実行 (⇧⌘B (Windows、Linux では Ctrl+Shift+B)) をトリガーしたときに直接実行されます。これを行うには、グローバルメニューの ターミナル から 既定のビルドタスクを構成 を選択します。これにより、利用可能なビルドタスクのピッカーが表示されます。tsc: build または tsc: watch を選択すると、VS Code が tasks.json
ファイルを生成します。以下に示されているものは、tsc: build タスクを既定のビルドタスクにします。
{
// See https://go.microsoft.com/fwlink/?LinkId=733558
// for the documentation about the tasks.json format
"version": "2.0.0",
"tasks": [
{
"type": "typescript",
"tsconfig": "tsconfig.json",
"problemMatcher": ["$tsc"],
"group": {
"kind": "build",
"isDefault": true
}
}
]
}
上記の tasks.json
の例は、新しいタスクを定義していません。VS Code の TypeScript 拡張機能によって提供される tsc: build タスクを既定のビルドタスクとして注釈付けしています。これで、⇧⌘B (Windows、Linux では Ctrl+Shift+B) を押すことで TypeScript コンパイラを実行できます。
タスクの自動検出
VS Code は現在、Gulp、Grunt、Jake、npm の各システムに対応するタスクを自動検出します。Maven および C# の dotnet
コマンドのサポートも追加するために、対応する拡張機能の作者と協力しています。Node.js をランタイムとして使用して JavaScript アプリケーションを開発している場合、通常は依存関係と実行するスクリプトを記述した package.json
ファイルを持っています。eslint-starter の例をクローンしている場合、グローバルメニューから タスクの実行 を実行すると、次のリストが表示されます。
まだ行っていない場合は、npm install
を実行して必要な npm モジュールをインストールします。次に、server.js
ファイルを開き、ステートメントの末尾にセミコロンを追加し (ESLint スターターはセミコロンなしのステートメントを想定していることに注意してください)、もう一度 タスクの実行 を実行します。今回は npm: lint タスクを選択します。使用する問題マッチャーを尋ねられたら、ESLint stylish を選択します。
タスクを実行すると、問題ビューに1つのエラーが表示されます。
さらに、VS Code は次の内容で tasks.json
ファイルを作成しました。
{
// See https://go.microsoft.com/fwlink/?LinkId=733558
// for the documentation about the tasks.json format
"version": "2.0.0",
"tasks": [
{
"type": "npm",
"script": "lint",
"problemMatcher": ["$eslint-stylish"]
}
]
}
これは、VS Code に npm lint スクリプトの出力を ESLint stylish フォーマットを使用して問題をスキャンするように指示します。
Gulp、Grunt、Jake の場合も、タスクの自動検出は同様に機能します。以下は、vscode-node-debug 拡張機能で検出されたタスクの例です。
ヒント: 'task' と入力し、Space、コマンド名 (この場合は 'task lint') を入力することで、クイックオープン (⌘P (Windows、Linux では Ctrl+P)) からタスクを実行できます。
タスクの自動検出は、次の設定を使用して無効にできます。
{
"typescript.tsc.autoDetect": "off",
"grunt.autoDetect": "off",
"jake.autoDetect": "off",
"gulp.autoDetect": "off",
"npm.autoDetect": "off"
}
カスタムタスク
ワークスペース内のすべてのタスクやスクリプトが自動検出できるわけではありません。環境を正しく設定するためにテストを実行するスクリプトがあるとします。そのスクリプトはワークスペース内のスクリプトフォルダーに保存されており、Linux と macOS では test.sh
、Windows では test.cmd
という名前です。グローバルメニューの ターミナル から タスクの構成 を実行し、テンプレートから tasks.json ファイルを作成 エントリを選択します。これにより、次のピッカーが開きます。
注: タスクランナーテンプレートのリストが表示されない場合、すでにフォルダー内に
tasks.json
ファイルが存在し、その内容がエディターで開かれている可能性があります。この例では、ファイルを閉じて削除するか、名前を変更してください。
自動検出のサポートをさらに強化しているため、このリストは将来的にはどんどん小さくなっていきます。独自のカスタムタスクを作成したいので、リストから その他 を選択します。これにより、タスクのスケルトンを含む tasks.json
ファイルが開きます。内容を次のように置き換えます。
{
// See https://go.microsoft.com/fwlink/?LinkId=733558
// for the documentation about the tasks.json format
"version": "2.0.0",
"tasks": [
{
"label": "Run tests",
"type": "shell",
"command": "./scripts/test.sh",
"windows": {
"command": ".\\scripts\\test.cmd"
},
"group": "test",
"presentation": {
"reveal": "always",
"panel": "new"
}
}
]
}
タスクのプロパティには次の意味があります。
- label: ユーザーインターフェイスで使用されるタスクのラベルです。
- type: タスクのタイプです。カスタムタスクの場合、
shell
またはprocess
のいずれかになります。shell
が指定されている場合、コマンドはシェルコマンド (例: bash、cmd、PowerShell) として解釈されます。process
が指定されている場合、コマンドは実行するプロセスとして解釈されます。 - command: 実際に実行するコマンドです。
- windows: Windows 固有のプロパティです。Windows オペレーティングシステムでコマンドが実行されるときに、デフォルトのプロパティの代わりに使用されます。
- group: タスクが属するグループを定義します。この例では、
test
グループに属します。テストグループに属するタスクは、コマンドパレットから テストタスクの実行 を実行することで実行できます。 - presentation: ユーザーインターフェイスでタスク出力がどのように処理されるかを定義します。この例では、出力が表示される統合ターミナルは
always
表示され、タスクが実行されるたびにnew
ターミナルが作成されます。 - options:
cwd
(現在の作業ディレクトリ)、env
(環境変数)、またはshell
(既定のシェル) のデフォルト設定を上書きします。オプションはタスクごとに設定できますが、グローバルにまたはプラットフォームごとに設定することもできます。ここで設定された環境変数は、タスクスクリプトまたはプロセス内からのみ参照でき、引数、コマンド、またはその他のタスク属性の一部である場合は解決されません。 - runOptions: タスクがいつ、どのように実行されるかを定義します。
- hide: タスクを「タスクの実行」クイックピックから非表示にします。これは、単独で実行できない複合タスクの要素に役立ちます。
tasks.json
ファイルで IntelliSense を使用して、タスクのプロパティと値の完全なセットを確認できます。サジェストのトリガー (⌃Space (Windows、Linux では Ctrl+Space)) でサジェストを表示し、ホバー時または 詳細... ('i') フライアウトで説明を読むことができます。
また、tasks.json スキーマを確認することもできます。
シェルコマンドは、スペースや $
のような特殊文字を含むコマンドや引数に関しては特別な処理が必要です。デフォルトでは、タスクシステムは次の動作をサポートしています。
- 単一のコマンドが指定された場合、タスクシステムはコマンドをそのまま基になるシェルに渡します。コマンドが正しく機能するためにクォーティングやエスケープが必要な場合、コマンドには適切な引用符またはエスケープ文字を含める必要があります。たとえば、名前にスペースを含むフォルダーのディレクトリを一覧表示するには、bash で実行されるコマンドは
ls 'folder with spaces'
のようにする必要があります。
{
"label": "dir",
"type": "shell",
"command": "dir 'folder with spaces'"
}
- コマンドと引数が指定されている場合、コマンドまたは引数にスペースが含まれていると、タスクシステムはシングルクォートを使用します。
cmd.exe
の場合、ダブルクォートが使用されます。以下のシェルコマンドは、PowerShell でdir 'folder with spaces'
として実行されます。
{
"label": "dir",
"type": "shell",
"command": "dir",
"args": ["folder with spaces"]
}
- 引数の引用符付け方法を制御したい場合、引数は値と引用符付けスタイルを指定するリテラルにすることができます。以下の例では、スペースを含む引数に対して引用符付けの代わりにエスケープを使用しています。
{
"label": "dir",
"type": "shell",
"command": "dir",
"args": [
{
"value": "folder with spaces",
"quoting": "escape"
}
]
}
エスケープの他に、以下の値がサポートされています。
- strong: シェルの強力な引用符付けメカニズムを使用します。これにより、文字列内のすべての評価が抑制されます。PowerShell、および Linux と macOS のシェルでは、シングルクォート (
'
) が使用されます。cmd.exe の場合、"
が使用されます。 - weak: シェルの弱い引用符付けメカニズムを使用します。これにより、文字列内の式 (例: 環境変数) が評価されます。PowerShell、および Linux と macOS のシェルでは、ダブルクォート (
"
) が使用されます。cmd.exe は弱い引用符付けをサポートしていないため、VS Code も"
を使用します。
コマンド自体にスペースが含まれている場合、VS Code はデフォルトでコマンドも強力に引用符で囲みます。引数と同様に、ユーザーは同じリテラルスタイルを使用してコマンドの引用符付けを制御できます。
ワークフローを構成するためのタスクプロパティは他にもあります。IntelliSense と ⌃Space (Windows、Linux では Ctrl+Space) を使用して、有効なプロパティの概要を確認できます。
グローバルメニューバーに加えて、タスクコマンドは コマンドパレット (⇧⌘P (Windows、Linux では Ctrl+Shift+P)) を使用してアクセスできます。「task」でフィルタリングすると、さまざまなタスク関連コマンドを確認できます。
複合タスク
dependsOn
プロパティを使用して、より単純なタスクから複合タスクを作成することもできます。たとえば、クライアントフォルダーとサーバーフォルダーを含むワークスペースがあり、両方にビルドスクリプトが含まれている場合、両方のビルドスクリプトを個別のターミナルで起動するタスクを作成できます。dependsOn
プロパティに複数のタスクをリストすると、デフォルトでは並行して実行されます。
tasks.json
ファイルは次のようになります。
{
"version": "2.0.0",
"tasks": [
{
"label": "Client Build",
"command": "gulp",
"args": ["build"],
"options": {
"cwd": "${workspaceFolder}/client"
}
},
{
"label": "Server Build",
"command": "gulp",
"args": ["build"],
"options": {
"cwd": "${workspaceFolder}/server"
}
},
{
"label": "Build",
"dependsOn": ["Client Build", "Server Build"]
}
]
}
"dependsOrder": "sequence"
を指定すると、タスクの依存関係は dependsOn
にリストされている順序で実行されます。"dependsOrder": "sequence"
とともに dependsOn
で使用されるすべてのバックグラウンド/ウォッチタスクには、それらが「完了」したときに追跡する問題マッチャーが必要です。次のタスクは、タスク Two、タスク Three、次にタスク One の順に実行します。
{
"label": "One",
"type": "shell",
"command": "echo Hello ",
"dependsOrder": "sequence",
"dependsOn": ["Two", "Three"]
}
ユーザーレベルのタスク
タスク: ユーザータスクを開く コマンドを使用して、特定のワークスペースやフォルダーに縛られないユーザーレベルのタスクを作成できます。他のタスクタイプはワークスペース情報を必要とするため、ここでは shell
および process
タスクのみを使用できます。
出力動作
タスクを実行するときに、統合ターミナルパネルの動作を制御したい場合があります。たとえば、エディターのスペースを最大化し、問題があると思われる場合にのみタスク出力を見たい場合があります。ターミナルの動作は、タスクの presentation
プロパティを使用して制御できます。次のプロパティを提供します。
- reveal: 統合ターミナルパネルが前面に表示されるかどうかを制御します。有効な値は次のとおりです。
always
- パネルは常に前面に表示されます。これがデフォルトです。never
- ユーザーは、表示 > ターミナル コマンド (⌃` (Windows、Linux では Ctrl+`)) を使用して、明示的にターミナルパネルを前面に表示する必要があります。silent
- 出力にエラーや警告がない場合にのみ、ターミナルパネルが前面に表示されます。
- revealProblems: このタスクの実行時に問題パネルが表示されるかどうかを制御します。
reveal
オプションよりも優先されます。デフォルトはnever
です。always
- このタスクが実行されるたびに、常に問題パネルを表示します。onProblem
- 問題が検出された場合にのみ、問題パネルを表示します。never
- このタスクが実行されても、問題パネルを一切表示しません。
- focus: ターミナルが入力フォーカスを受け取るかどうかを制御します。デフォルトは
false
です。 - echo: 実行されたコマンドがターミナルにエコーされるかどうかを制御します。デフォルトは
true
です。 - showReuseMessage: 「ターミナルはタスクによって再利用されます。閉じるには任意のキーを押してください」というメッセージを表示するかどうかを制御します。
- panel: ターミナルインスタンスがタスク実行間で共有されるかどうかを制御します。可能な値は次のとおりです。
shared
- ターミナルは共有され、他のタスク実行の出力は同じターミナルに追加されます。dedicated
- ターミナルは特定のタスク専用です。そのタスクが再度実行された場合、ターミナルは再利用されます。ただし、別のタスクの出力は別のターミナルに表示されます。new
- そのタスクのすべての実行は、新しいクリーンなターミナルを使用します。
- clear: このタスクが実行される前にターミナルがクリアされるかどうかを制御します。デフォルトは
false
です。 - close: タスクが終了したときに、タスクが実行されているターミナルが閉じられるかどうかを制御します。デフォルトは
false
です。 - group: スプリットペインを使用して、タスクが特定のターミナルグループで実行されるかどうかを制御します。同じグループ (文字列値で指定) のタスクは、新しいターミナルパネルの代わりにスプリットターミナルを使用して表示されます。
自動検出されたタスクのターミナルパネルの動作も変更できます。たとえば、上記の ESLint の例から npm: run lint の出力動作を変更したい場合は、presentation
プロパティを追加します。
{
// See https://go.microsoft.com/fwlink/?LinkId=733558
// for the documentation about the tasks.json format
"version": "2.0.0",
"tasks": [
{
"type": "npm",
"script": "lint",
"problemMatcher": ["$eslint-stylish"],
"presentation": {
"reveal": "never"
}
}
]
}
カスタムタスクと検出されたタスクの設定を組み合わせることもできます。npm: run lint タスクを設定し、カスタムの テストの実行 タスクを追加する tasks.json
は次のようになります。
{
// See https://go.microsoft.com/fwlink/?LinkId=733558
// for the documentation about the tasks.json format
"version": "2.0.0",
"tasks": [
{
"type": "npm",
"script": "lint",
"problemMatcher": ["$eslint-stylish"],
"presentation": {
"reveal": "never"
}
},
{
"label": "Run tests",
"type": "shell",
"command": "./scripts/test.sh",
"windows": {
"command": ".\\scripts\\test.cmd"
},
"group": "test",
"presentation": {
"reveal": "always",
"panel": "new"
}
}
]
}
実行動作
タスクの実行動作は runOptions
プロパティを使用して指定できます。
- reevaluateOnRerun: 最後のタスクを再実行 コマンドを通じてタスクが実行されるときに、変数がどのように評価されるかを制御します。デフォルトは
true
で、タスクが再実行されるときに変数が再評価されることを意味します。false
に設定すると、タスクの以前の実行で解決された変数値が使用されます。 - runOn: タスクがいつ実行されるかを指定します。
default
- このタスクは、タスクの実行 コマンドを通じて実行された場合にのみ実行されます。folderOpen
- このタスクは、それを含むフォルダーが開かれたときに実行されます。folderOpen
を含むタスクを含むフォルダーを初めて開くと、そのフォルダーでタスクを自動的に実行することを許可するかどうか尋ねられます。後で 自動タスクの管理 コマンドを使用して、自動タスクを許可 と 自動タスクを禁止 の間で決定を変更できます。
- instanceLimit - タスクを同時に実行できるインスタンスの数です。デフォルト値は
1
です。
自動検出されたタスクのカスタマイズ
前述のように、tasks.json
ファイルで自動検出されたタスクをカスタマイズできます。通常、これはプレゼンテーションプロパティを変更したり、タスクの出力をエラーや警告についてスキャンするために問題マッチャーをアタッチしたりするために行います。タスクの実行 リストから直接タスクをカスタマイズするには、右側の歯車アイコンを押して、対応するタスク参照を tasks.json
ファイルに挿入します。ESLint を使用して JavaScript ファイルをリンティングする次の Gulp ファイルがあるとします (ファイルは https://github.com/adametry/gulp-eslint から取得されています)。
const gulp = require('gulp');
const eslint = require('gulp-eslint');
gulp.task('lint', () => {
// ESLint ignores files with "node_modules" paths.
// So, it's best to have gulp ignore the directory as well.
// Also, Be sure to return the stream from the task;
// Otherwise, the task may end before the stream has finished.
return (
gulp
.src(['**/*.js', '!node_modules/**'])
// eslint() attaches the lint output to the "eslint" property
// of the file object so it can be used by other modules.
.pipe(eslint())
// eslint.format() outputs the lint results to the console.
// Alternatively use eslint.formatEach() (see Docs).
.pipe(eslint.format())
// To have the process exit with an error code (1) on
// lint error, return the stream and pipe to failAfterError last.
.pipe(eslint.failAfterError())
);
});
gulp.task('default', ['lint'], function() {
// This will only run if the lint task is successful...
});
グローバルメニューの ターミナル から タスクの実行 を実行すると、次のピッカーが表示されます。
歯車アイコンを押します。これにより、次の tasks.json
ファイルが作成されます。
{
// See https://go.microsoft.com/fwlink/?LinkId=733558
// for the documentation about the tasks.json format
"version": "2.0.0",
"tasks": [
{
"type": "gulp",
"task": "default",
"problemMatcher": []
}
]
}
通常、ここで問題マッチャー (この場合は $eslint-stylish
) を追加するか、プレゼンテーション設定を変更します。
問題マッチャーを使用したタスク出力の処理
VS Code は、問題マッチャーを使用してタスクからの出力を処理できます。問題マッチャーは、タスク出力テキストから既知の警告またはエラー文字列をスキャンし、それらをエディターと「問題」パネルにインラインで報告します。VS Code には、いくつかの問題マッチャーが「標準で」含まれています。
- TypeScript:
$tsc
は、出力内のファイル名が開いているフォルダーからの相対パスであると仮定します。 - TypeScript Watch:
$tsc-watch
は、ウォッチモードで実行されたときにtsc
コンパイラから報告された問題と一致します。 - JSHint:
$jshint
は、ファイル名が絶対パスとして報告されると仮定します。 - JSHint Stylish:
$jshint-stylish
は、ファイル名が絶対パスとして報告されると仮定します。 - ESLint Compact:
$eslint-compact
は、出力内のファイル名が開いているフォルダーからの相対パスであると仮定します。 - ESLint Stylish:
$eslint-stylish
は、出力内のファイル名が開いているフォルダーからの相対パスであると仮定します。 - Go:
$go
はgo
コンパイラから報告された問題と一致します。ファイル名が開いているフォルダーからの相対パスであると仮定します。 - CSharp and VB Compiler:
$mscompile
は、ファイル名が絶対パスとして報告されると仮定します。 - Lessc compiler:
$lessc
は、ファイル名が絶対パスとして報告されると仮定します。 - Node Sass compiler:
$node-sass
は、ファイル名が絶対パスとして報告されると仮定します。
独自のプロブレムマッチャーを作成することもできます。これについては後のセクションで説明します。
キーボードショートカットをタスクにバインドする
タスクを頻繁に実行する必要がある場合は、タスクのキーボードショートカットを定義できます。
たとえば、上記の テストの実行 タスクに Ctrl+H
をバインドするには、次の内容を keybindings.json
ファイルに追加します。
{
"key": "ctrl+h",
"command": "workbench.action.tasks.runTask",
"args": "Run tests"
}
変数の置換
タスク設定を作成する際には、アクティブなファイル (${file}
) やワークスペースのルートフォルダー (${workspaceFolder}
) のような、定義済みの一般的な変数のセットがあると便利です。VS Code は tasks.json
ファイル内の文字列での変数置換をサポートしており、定義済み変数の完全なリストは変数リファレンスで確認できます。
注: すべてのプロパティが変数置換を受け入れるわけではありません。具体的には、
command
、args
、options
のみが変数置換をサポートしています。
以下は、現在開いているファイルを TypeScript コンパイラに渡すカスタムタスク構成の例です。
{
"label": "TypeScript compile",
"type": "shell",
"command": "tsc ${file}",
"problemMatcher": ["$tsc"]
}
同様に、プロジェクトの設定を参照するには、名前の前に ${config: を付けます。たとえば、${config:python.formatting.autopep8Path}
は Python 拡張機能の設定 formatting.autopep8Path
を返します。
以下は、python.formatting.autopep8Path
設定で定義された autopep8 実行可能ファイルを使用して、現在のファイルで autopep8 を実行するカスタムタスク構成の例です。
{
"label": "autopep8 current file",
"type": "process",
"command": "${config:python.formatting.autopep8Path}",
"args": ["--in-place", "${file}"]
}
Python 拡張機能によって tasks.json
または launch.json
で使用される選択された Python インタープリターを指定したい場合は、${command:python.interpreterPath}
コマンドを使用できます。
単純な変数置換だけでは不十分な場合は、tasks.json
ファイルに inputs
セクションを追加することで、タスクのユーザーから入力を取得することもできます。
inputs
の詳細については、変数リファレンスを参照してください。
オペレーティングシステム固有のプロパティ
タスクシステムは、オペレーティングシステムに固有の値を定義する (たとえば、実行するコマンド) ことをサポートしています。これを行うには、オペレーティングシステム固有のリテラルを tasks.json
ファイルに記述し、そのリテラル内に対応するプロパティを指定します。
以下は、Node.js 実行可能ファイルをコマンドとして使用し、Windows と Linux で異なる扱いをする例です。
{
"label": "Run Node",
"type": "process",
"windows": {
"command": "C:\\Program Files\\nodejs\\node.exe"
},
"linux": {
"command": "/usr/bin/node"
}
}
有効なオペレーティングプロパティは、Windows の場合は windows
、Linux の場合は linux
、macOS の場合は osx
です。オペレーティングシステム固有のスコープで定義されたプロパティは、タスクまたはグローバルスコープで定義されたプロパティを上書きします。
グローバルタスク
タスクプロパティはグローバルスコープでも定義できます。存在する場合、それらは特定のタスクで使用されますが、異なる値で同じプロパティを定義する場合は上書きされます。以下の例では、すべてのタスクを新しいパネルで実行するように定義するグローバルな presentation
プロパティがあります。
{
// See https://go.microsoft.com/fwlink/?LinkId=733558
// for the documentation about the tasks.json format
"version": "2.0.0",
"presentation": {
"panel": "new"
},
"tasks": [
{
"label": "TS - Compile current file",
"type": "shell",
"command": "tsc ${file}",
"problemMatcher": ["$tsc"]
}
]
}
ヒント: グローバルスコープの
tasks.json
ファイルにアクセスするには、コマンドパレット (⇧⌘P (Windows、Linux では Ctrl+Shift+P)) を開き、タスク: ユーザータスクを開く コマンドを実行します。
PowerShell での文字エスケープ
デフォルトシェルが PowerShell の場合、またはタスクが PowerShell を使用するように構成されている場合、予期しないスペースと引用符のエスケープが表示されることがあります。この予期しないエスケープは、コマンドレットにのみ発生します。これは、VS Code がコマンドにコマンドレットが含まれているかどうかを認識しないためです。以下の例 1 は、PowerShell で機能しないエスケープが発生するケースを示しています。例 2 は、適切なエスケープを取得するための最良のクロスプラットフォームな方法を示しています。場合によっては、例 2 に従えないこともあり、その場合は例 3 に示すように手動でエスケープを行う必要があります。
"tasks": [
{
"label": "PowerShell example 1 (unexpected escaping)",
"type": "shell",
"command": "Get-ChildItem \"Folder With Spaces\""
},
{
"label": "PowerShell example 2 (expected escaping)",
"type": "shell",
"command": "Get-ChildItem",
"args": ["Folder With Spaces"]
},
{
"label": "PowerShell example 3 (manual escaping)",
"type": "shell",
"command": "& Get-ChildItem \\\"Folder With Spaces\\\""
}
]
タスク出力のエンコーディングの変更
タスクは頻繁にディスク上のファイルを扱います。これらのファイルがシステムエンコーディングとは異なるエンコーディングでディスクに保存されている場合、タスクとして実行されるコマンドにどのエンコーディングを使用するかを知らせる必要があります。これはオペレーティングシステムと使用されるシェルに依存するため、これを制御する一般的な解決策はありません。以下に、それを機能させるためのアドバイスと例を示します。
エンコーディングを調整する必要がある場合は、オペレーティングシステムで使用されているデフォルトエンコーディングを変更する、または少なくともシェルプロファイルファイルを調整して使用しているシェルに対して変更するのが理にかなっているかどうかを確認する必要があります。
特定のタスクのみを調整する必要がある場合は、エンコーディングを変更するために必要な OS 固有のコマンドをタスクのコマンドラインに追加します。次の例は、デフォルトのコードページが 437 の Windows 用です。このタスクはキリル文字を含むファイルの出力を表示するため、コードページ 866 が必要です。デフォルトシェルが cmd.exe
に設定されていると仮定すると、ファイルをリストするタスクは次のようになります。
{
// See https://go.microsoft.com/fwlink/?LinkId=733558
// for the documentation about the tasks.json format
"version": "2.0.0",
"tasks": [
{
"label": "more",
"type": "shell",
"command": "chcp 866 && more russian.txt",
"problemMatcher": []
}
]
}
タスクが PowerShell
で実行される場合、コマンドは chcp 866; more russian.txt
のように記述する必要があります。Linux および macOS では、locale
コマンドを使用してロケールを検査し、必要な環境変数を調整できます。
タスクの動作例
タスクの強力さを強調するために、VS Code がリンターやコンパイラのような外部ツールを統合するためにタスクをどのように使用できるかのいくつかの例を以下に示します。
TypeScript から JavaScript へのトランスパイル
TypeScript トピックには、TypeScript を JavaScript にトランスパイルし、VS Code 内から関連するエラーを監視するタスクを作成する例が含まれています。
Less および SCSS から CSS へのトランスパイル
CSS トピックでは、タスクを使用して CSS ファイルを生成する方法の例が提供されています。
問題マッチャーの定義
VS Code には、最も一般的な問題マッチャーのいくつかが「標準で」含まれています。しかし、世の中には多くのコンパイラやリンティングツールがあり、それらはすべて独自のエラーと警告のスタイルを生成するため、独自のプロブレムマッチャーを作成する必要があるかもしれません。
開発者が printf を prinft とタイプミスした helloWorld.c
プログラムがあります。gcc でコンパイルすると、次の警告が生成されます。
helloWorld.c:5:3: warning: implicit declaration of function ‘prinft’
出力内のメッセージをキャプチャし、VS Code に対応する問題を報告できる問題マッチャーを作成したいと考えています。問題マッチャーは正規表現に大きく依存しています。以下のセクションでは、正規表現に精通していることを前提としています。
ヒント: ECMAScript (JavaScript) フレーバーを持つ RegEx101 playground は、正規表現を開発およびテストするのに最適な方法であることがわかりました。
上記の警告 (およびエラー) をキャプチャするマッチャーは次のようになります。
{
// The problem is owned by the cpp language service.
"owner": "cpp",
// The file name for reported problems is relative to the opened folder.
"fileLocation": ["relative", "${workspaceFolder}"],
// The name that will be shown as the source of the problem.
"source": "gcc",
// The actual pattern to match problems in the output.
"pattern": {
// The regular expression. Example to match: helloWorld.c:5:3: warning: implicit declaration of function ‘printf’ [-Wimplicit-function-declaration]
"regexp": "^(.*):(\\d+):(\\d+):\\s+(warning|error):\\s+(.*)$",
// The first match group matches the file name which is relative.
"file": 1,
// The second match group matches the line on which the problem occurred.
"line": 2,
// The third match group matches the column at which the problem occurred.
"column": 3,
// The fourth match group matches the problem's severity. Can be ignored. Then all problems are captured as errors.
"severity": 4,
// The fifth match group matches the message.
"message": 5
}
}
ファイル、行、メッセージのプロパティは必須であることに注意してください。fileLocation
は、タスク出力によって生成され問題内で一致するファイルパスが absolute
(絶対パス) であるか relative
(相対パス) であるかを指定します。タスクが絶対パスと相対パスの両方を生成する場合は、autoDetect
ファイルの場所を使用できます。autoDetect
では、まずパスが絶対パスとしてテストされ、ファイルが存在しない場合はパスは相対パスであると見なされます。
severity
は、パターンに重大度が含まれていない場合に使用する問題の重大度を指定します。severity
の可能な値は、error
(エラー)、warning
(警告)、または info
(情報) です。
以下は、上記のコード (コメントは削除済み) を実際のタスク詳細で囲んだ完成した tasks.json
ファイルです。
{
"version": "2.0.0",
"tasks": [
{
"label": "build",
"command": "gcc",
"args": ["-Wall", "helloWorld.c", "-o", "helloWorld"],
"problemMatcher": {
"owner": "cpp",
"fileLocation": ["relative", "${workspaceFolder}"],
"source": "gcc",
"pattern": {
"regexp": "^(.*):(\\d+):(\\d+):\\s+(warning|error):\\s+(.*)$",
"file": 1,
"line": 2,
"column": 3,
"severity": 4,
"message": 5
}
}
}
]
}
VS Code 内で実行し、⇧⌘M (Windows、Linux では Ctrl+Shift+M) を押して問題のリストを取得すると、次の出力が得られます。
注: C/C++ 拡張機能には GCC 用の問題マッチャーが含まれているため、独自に定義する必要はありません。
パターン内で使用できるプロパティは他にもいくつかあります。これらは次のとおりです。
- location - 問題の場所が line または line,column または startLine,startColumn,endLine,endColumn の場合、汎用ロケーションマッチグループを使用できます。
- endLine - 問題の終了行の正規表現マッチグループインデックスです。コンパイラによって終了行の値が提供されない場合は省略できます。
- endColumn - 問題の終了列の正規表現マッチグループインデックスです。コンパイラによって終了列の値が提供されない場合は省略できます。
- code - 問題のコードの正規表現マッチグループインデックスです。コンパイラによってコード値が提供されない場合は省略できます。
ファイルのみをキャプチャする問題マッチャーを定義することもできます。これを行うには、オプションの kind
属性を file
に設定した pattern
を定義します。この場合、line
または location
プロパティを提供する必要はありません。
注:
kind
プロパティがfile
に設定されている場合、機能するパターンは少なくともfile
とmessage
のマッチグループを提供する必要があります。kind
プロパティが提供されていない場合、またはkind
プロパティがlocation
に設定されている場合、機能するパターンはline
またはlocation
プロパティも提供する必要があります。
注: 問題マッチャーは、与えられたコマンドからの出力のみを解析します。別のファイル (例: ログファイル) に書き込まれた出力を解析したい場合は、実行するコマンドが、実行を終了する前にその別のファイルから行を出力するようにしてください。
複数行の問題マッチャーの定義
一部のツールでは、特にスタイリッシュなレポーターを使用している場合、ソースファイルで見つかった問題を複数行にわたって表示します。ESLint がその例です。スタイリッシュモードでは、次のような出力を生成します。
test.js
1:0 error Missing "use strict" statement strict
✖ 1 problems (1 errors, 0 warnings)
私たちの問題マッチャーは行ベースなので、ファイル名 (test.js) を、実際の問題の場所とメッセージ (1:0 error Missing "use strict" statement) とは異なる正規表現でキャプチャする必要があります。
これを行うには、pattern
プロパティに問題パターンの配列を使用します。このようにして、一致させたい各行ごとにパターンを定義します。
次の問題パターンは、ESLint のスタイリッシュモードからの出力に一致しますが、次に解決する必要がある小さな問題がまだ1つあります。以下のコードには、ファイル名をキャプチャするための最初の正規表現と、行、列、重大度、メッセージ、およびエラーコードをキャプチャするための2番目の正規表現があります。
{
"owner": "javascript",
"fileLocation": ["relative", "${workspaceFolder}"],
"pattern": [
{
"regexp": "^([^\\s].*)$",
"file": 1
},
{
"regexp": "^\\s+(\\d+):(\\d+)\\s+(error|warning|info)\\s+(.*)\\s\\s+(.*)$",
"line": 1,
"column": 2,
"severity": 3,
"message": 4,
"code": 5
}
]
}
ただし、このパターンは、リソースに複数の問題がある場合には機能しません。たとえば、ESLint からの次の出力を想像してみてください。
test.js
1:0 error Missing "use strict" statement strict
1:9 error foo is defined but never used no-unused-vars
2:5 error x is defined but never used no-unused-vars
2:11 error Missing semicolon semi
3:1 error "bar" is not defined no-undef
4:1 error Newline required at end of file but not found eol-last
✖ 6 problems (6 errors, 0 warnings)
パターンの最初の正規表現は「test.js」に一致し、2番目の正規表現は「1:0 error ...」に一致します。次の行「1:9 error ...」は処理されますが、最初の正規表現には一致しないため、問題はキャプチャされません。
これを機能させるには、複数行パターンの最後の正規表現で loop
プロパティを指定できます。これを true に設定すると、タスクシステムは、正規表現が一致する限り、複数行マッチャーの最後のパターンを出力中の行に適用するように指示されます。
最初のパターンによってキャプチャされた情報 (この場合は test.js
に一致) は、loop
パターンに一致する後続の各行と組み合わされて、複数の問題が作成されます。この例では、6つの問題が作成されます。
以下は、ESLint stylish の問題を完全にキャプチャするための問題マッチャーです。
{
"owner": "javascript",
"fileLocation": ["relative", "${workspaceFolder}"],
"pattern": [
{
"regexp": "^([^\\s].*)$",
"file": 1
},
{
"regexp": "^\\s+(\\d+):(\\d+)\\s+(error|warning|info)\\s+(.*)\\s\\s+(.*)$",
"line": 1,
"column": 2,
"severity": 3,
"message": 4,
"code": 5,
"loop": true
}
]
}
注: 同じリソースでまったく同じ行と列に複数の問題が発生した場合、表示される問題は1つだけです。これは、複数行の問題マッチャーだけでなく、すべての問題マッチャーに適用されます。
既存の問題マッチャーの変更
既存の問題マッチャーがあなたのニーズに近い場合、tasks.json
タスクでそれを変更できます。たとえば、$tsc-watch
問題マッチャーは閉じられたドキュメントにのみ適用されます。すべてのドキュメントに適用したい場合は、それを変更できます。
{
"type": "npm",
"script": "watch",
"problemMatcher": {
"base": "$tsc-watch",
"applyTo": "allDocuments"
},
"isBackground": true
}
その他に変更可能な問題マッチャーのプロパティには、background
、fileLocation
、owner
、pattern
、severity
、source
があります。
バックグラウンド / ウォッチタスク
一部のツールは、ファイルシステムでの変更を監視しながらバックグラウンドで実行し、ディスク上のファイルが変更されたときにアクションをトリガーする機能をサポートしています。Gulp
では、このような機能は npm モジュール gulp-watch を介して提供されます。TypeScript コンパイラ tsc
は、--watch
コマンドラインオプションを介してこの機能を組み込みでサポートしています。
VS Code でバックグラウンドタスクがアクティブであり、問題結果を生成しているというフィードバックを提供するために、問題マッチャーは出力中のこれらの state
変更を検出するために追加情報を使用する必要があります。tsc
コンパイラを例にとってみましょう。コンパイラがウォッチモードで起動されると、次の追加情報がコンソールに出力されます。
> tsc --watch
12:30:36 PM - Compilation complete. Watching for file changes.
ディスク上のファイルに問題が含まれていて変更された場合、次の出力が表示されます。
12:32:35 PM - File change detected. Starting incremental compilation...
src/messages.ts(276,9): error TS2304: Cannot find name 'candidate'.
12:32:35 PM - Compilation complete. Watching for file changes.
出力を確認すると、次のパターンが表示されます。
File change detected. Starting incremental compilation...
がコンソールに出力されると、コンパイラが実行されます。Compilation complete. Watching for file changes.
がコンソールに出力されると、コンパイラが停止します。- これら2つの文字列の間に問題が報告されます。
- コンパイラは最初の起動時にも一度実行されます (
File change detected. Starting incremental compilation...
をコンソールに出力せずに)。
この情報をキャプチャするために、問題マッチャーは background
プロパティを提供できます。
tsc
コンパイラの場合、適切な background
プロパティは次のようになります。
"background": {
"activeOnStart": true,
"beginsPattern": "^\\s*\\d{1,2}:\\d{1,2}:\\d{1,2}(?: AM| PM)? - File change detected\\. Starting incremental compilation\\.\\.\\.",
"endsPattern": "^\\s*\\d{1,2}:\\d{1,2}:\\d{1,2}(?: AM| PM)? - Compilation complete\\. Watching for file changes\\."
}
問題マッチャーの background
プロパティに加えて、タスク自体もバックグラウンドで実行され続けるように isBackground
としてマークする必要があります。
ウォッチモードで実行される tsc
タスクの完全に手作業で作成された tasks.json
は次のようになります。
{
"version": "2.0.0",
"tasks": [
{
"label": "watch",
"command": "tsc",
"args": ["--watch"],
"isBackground": true,
"problemMatcher": {
"owner": "typescript",
"fileLocation": "relative",
"pattern": {
"regexp": "^([^\\s].*)\\((\\d+|\\d+,\\d+|\\d+,\\d+,\\d+,\\d+)\\):\\s+(error|warning|info)\\s+(TS\\d+)\\s*:\\s*(.*)$",
"file": 1,
"location": 2,
"severity": 3,
"code": 4,
"message": 5
},
"background": {
"activeOnStart": true,
"beginsPattern": "^\\s*\\d{1,2}:\\d{1,2}:\\d{1,2}(?: AM| PM)? - File change detected\\. Starting incremental compilation\\.\\.\\.",
"endsPattern": "^\\s*\\d{1,2}:\\d{1,2}:\\d{1,2}(?: AM| PM)? - Compilation complete\\. Watching for file changes\\."
}
}
}
]
}
次のステップ
以上がタスクでした - 続けていきましょう...
- tasks.json スキーマ - 完全な
tasks.json
スキーマと説明を確認できます。 - 基本的な編集 - 強力な VS Code エディターについて学習します。
- コード ナビゲーション - ソースコード内をすばやく移動します。
- 言語サポート - VS Code に付属している言語とコミュニティ拡張機能を通じてサポートされているプログラミング言語について学びます。
- デバッグ - VS Code エディターでソースコードを直接デバッグします。
よくある質問
タスクは、統合ターミナルに指定されたシェルとは異なるシェルを使用できますか?
はい。"terminal.integrated.automationProfile.*"
設定を使用して、タスクを含む VS Code のすべての自動化に使用されるシェルを設定できます。
"terminal.integrated.automationProfile.windows": {
"path": "cmd.exe"
}
または、options.shell
プロパティでタスクのシェルをオーバーライドできます。これは、タスクごと、グローバル、またはプラットフォームごとに設定できます。たとえば、Windows で cmd.exe を使用するには、tasks.json
に次を含めます。
{
"version": "2.0.0",
"windows": {
"options": {
"shell": {
"executable": "cmd.exe",
"args": [
"/d", "/c"
]
}
}
},
...
バックグラウンドタスクを launch.json の prelaunchTask
として使用できますか?
はい。バックグラウンドタスクは終了されるまで実行されるため、バックグラウンドタスク単独では「完了」したという信号がありません。バックグラウンドタスクを prelaunchTask
として使用するには、タスクシステムとデバッグシステムがタスクが「終了した」ことを知るための方法があるように、バックグラウンドタスクに適切なバックグラウンド problemMatcher
を追加する必要があります。
タスクは次のようになります。
{
"type": "npm",
"script": "watch",
"problemMatcher": "$tsc-watch",
"isBackground": true
}
注:
$tsc-watch
は、バックグラウンドタスクに必要な バックグラウンド 問題マッチャーです。
次に、launch.json
ファイルでタスクを prelaunchTask
として使用できます。
{
"name": "Launch Extension",
"type": "extensionHost",
"request": "launch",
"runtimeExecutable": "${execPath}",
"args": ["--extensionDevelopmentPath=${workspaceRoot}"],
"stopOnEntry": false,
"sourceMaps": true,
"outFiles": ["${workspaceRoot}/out/src/**/*.js"],
"preLaunchTask": "npm: watch"
}
バックグラウンドタスクの詳細については、バックグラウンド / ウォッチタスクを参照してください。
タスクを実行すると「コマンドが見つかりません」と表示されるのはなぜですか?
「コマンドが見つかりません」というメッセージは、実行しようとしているタスクコマンドがターミナルで実行可能なものとして認識されない場合に発生します。ほとんどの場合、これはコマンドがシェルの起動スクリプトの一部として設定されているために発生します。タスクは非ログインおよび非インタラクティブとして実行されるため、シェルの起動スクリプトは実行されません。特に nvm
は、その設定の一部として起動スクリプトを使用することが知られています。
この問題を解決するにはいくつかの方法があります。
- コマンドがパス上にあり、パスに追加するために起動スクリプトを必要としないことを確認してください。これは問題を解決する最も徹底的な方法であり、推奨される解決策です。
- タスクをログインまたはインタラクティブとして実行するための1回限りの修正を行うことができます。これは、他の結果を招く可能性があるため推奨されません。ただし、単一のタスクに対する迅速で簡単な修正となる場合もあります。以下は、シェルとして
bash
を使用してこれを行うタスクの例です。
{
"type": "npm",
"script": "watch",
"options": {
"shell": {
"args": ["-c", "-l"]
}
}
}
上記の npm
タスクは、デフォルトでタスクシステムが行うように、コマンド (-c
) を付けて bash
を実行します。ただし、このタスクは bash
をログインシェル (-l
) としても実行します。