Inspector
ソースコード: lib/inspector.js
node:inspector
モジュールは、V8 インスペクターとやり取りするための API を提供します。
以下を使用してアクセスできます:
import * as inspector from 'node:inspector/promises'
const inspector = require('node:inspector/promises')
または
import * as inspector from 'node:inspector'
const inspector = require('node:inspector')
Promises API
追加: v19.0.0
クラス: inspector.Session
- 拡張: <EventEmitter>
inspector.Session
は、V8 インスペクターバックエンドにメッセージをディスパッチし、メッセージの応答と通知を受信するために使用されます。
new inspector.Session()
追加: v8.0.0
inspector.Session
クラスの新しいインスタンスを作成します。インスペクターセッションは、メッセージをインスペクターバックエンドにディスパッチする前に、session.connect()
を通じて接続する必要があります。
Session
を使用する場合、コンソール API によって出力されたオブジェクトは、手動でRuntime.DiscardConsoleEntries
コマンドを実行しない限り、解放されません。
イベント: 'inspectorNotification'
追加: v8.0.0
- <Object> 通知メッセージオブジェクト
V8 インスペクターからの通知を受信したときに発生します。
session.on('inspectorNotification', message => console.log(message.method))
// Debugger.paused
// Debugger.resumed
特定のメソッドを持つ通知のみをサブスクライブすることもできます。
イベント: <inspector-protocol-method>
; {#event-<inspector-protocol-method>;}
追加: v8.0.0
- <Object> 通知メッセージオブジェクト
メソッドフィールドが <inspector-protocol-method>
値に設定されたインスペクター通知を受信したときに発生します。
次のスニペットは、'Debugger.paused'
イベントにリスナーをインストールし、プログラムの実行が中断されるたびに(ブレークポイントなどによって)プログラムの一時停止の理由を出力します。
session.on('Debugger.paused', ({ params }) => {
console.log(params.hitBreakpoints)
})
// [ '/the/file/that/has/the/breakpoint.js:11:0' ]
session.connect()
追加: v8.0.0
インスペクターバックエンドにセッションを接続します。
session.connectToMainThread()
追加: v12.11.0
メインスレッドのインスペクターバックエンドにセッションを接続します。この API がワーカー スレッドで呼び出されなかった場合、例外がスローされます。
session.disconnect()
追加: v8.0.0
セッションを即座に閉じます。保留中のすべてのメッセージコールバックはエラーで呼び出されます。メッセージを再度送信できるようにするには、session.connect()
を呼び出す必要があります。再接続されたセッションは、有効化されたエージェントや設定されたブレークポイントなど、すべてのインスペクターの状態を失います。
session.post(method[, params])
追加: v19.0.0
インスペクターバックエンドにメッセージをポストします。
import { Session } from 'node:inspector/promises'
try {
const session = new Session()
session.connect()
const result = await session.post('Runtime.evaluate', { expression: '2 + 2' })
console.log(result)
} catch (error) {
console.error(error)
}
// 出力: { result: { type: 'number', value: 4, description: '4' } }
V8 インスペクタープロトコルの最新バージョンは、Chrome DevTools Protocol Viewerで公開されています。
Node.js インスペクターは、V8 によって宣言されたすべての Chrome DevTools Protocol ドメインをサポートしています。Chrome DevTools Protocol ドメインは、アプリケーションの状態を検査し、実行時イベントをリッスンするために使用されるランタイムエージェントの 1 つと対話するためのインターフェースを提供します。
例としての使用法
デバッガー以外にも、さまざまな V8 プロファイラーが DevTools プロトコルを通じて利用できます。
CPU プロファイラー
CPU プロファイラーの使用例を以下に示します。
import { Session } from 'node:inspector/promises'
import fs from 'node:fs'
const session = new Session()
session.connect()
await session.post('Profiler.enable')
await session.post('Profiler.start')
// ここで測定対象のビジネスロジックを呼び出します...
// しばらくして...
const { profile } = await session.post('Profiler.stop')
// プロファイルをディスクに書き込んだり、アップロードしたりします。
fs.writeFileSync('./profile.cpuprofile', JSON.stringify(profile))
ヒーププロファイラー
ヒーププロファイラーの使用例を以下に示します。
import { Session } from 'node:inspector/promises'
import fs from 'node:fs'
const session = new Session()
const fd = fs.openSync('profile.heapsnapshot', 'w')
session.connect()
session.on('HeapProfiler.addHeapSnapshotChunk', m => {
fs.writeSync(fd, m.params.chunk)
})
const result = await session.post('HeapProfiler.takeHeapSnapshot', null)
console.log('HeapProfiler.takeHeapSnapshot done:', result)
session.disconnect()
fs.closeSync(fd)
コールバック API
クラス: inspector.Session
- 拡張: <EventEmitter>
inspector.Session
は、V8 インスペクターバックエンドにメッセージをディスパッチし、メッセージの応答と通知を受信するために使用されます。
new inspector.Session()
追加: v8.0.0
inspector.Session
クラスの新しいインスタンスを作成します。インスペクターセッションは、メッセージをインスペクターバックエンドにディスパッチする前に、session.connect()
を介して接続する必要があります。
Session
を使用する場合、console API によって出力されたオブジェクトは、Runtime.DiscardConsoleEntries
コマンドを手動で実行しない限り、解放されません。
イベント: 'inspectorNotification'
追加: v8.0.0
- <Object> 通知メッセージオブジェクト
V8 Inspector からの通知を受信したときに発生します。
session.on('inspectorNotification', message => console.log(message.method))
// Debugger.paused
// Debugger.resumed
特定の方法を持つ通知のみをサブスクライブすることも可能です:
イベント: <inspector-protocol-method>
; {#event-<inspector-protocol-method>;_1}
追加: v8.0.0
- <Object> 通知メッセージオブジェクト
method フィールドが\<inspector-protocol-method\>
値に設定されているインスペクター通知を受信したときに発生します。
以下のスニペットは、'Debugger.paused'
イベントにリスナーをインストールし、プログラムの実行が中断されるたび(例えば、ブレークポイントを介して)プログラムの中断理由を出力します。
session.on('Debugger.paused', ({ params }) => {
console.log(params.hitBreakpoints)
})
// [ '/the/file/that/has/the/breakpoint.js:11:0' ]
session.connect()
追加: v8.0.0
インスペクターバックエンドにセッションを接続します。
session.connectToMainThread()
追加: v12.11.0
メインスレッドのインスペクターバックエンドにセッションを接続します。この API が Worker スレッドで呼び出されなかった場合、例外がスローされます。
session.disconnect()
追加: v8.0.0
セッションを直ちに閉じます。保留中のメッセージコールバックはすべてエラーとともに呼び出されます。再度メッセージを送信できるようにするには、session.connect()
を呼び出す必要があります。再接続されたセッションは、有効なエージェントや構成済みのブレークポイントなど、すべてのインスペクター状態を失います。
session.post(method[, params][, callback])
[履歴]
バージョン | 変更点 |
---|---|
v18.0.0 | callback 引数に無効なコールバックを渡すと、ERR_INVALID_CALLBACK の代わりにERR_INVALID_ARG_TYPE がスローされるようになりました。 |
v8.0.0 | 追加: v8.0.0 |
method
<string>params
<Object>callback
<Function>
インスペクターバックエンドにメッセージを投稿します。応答を受信するとcallback
に通知されます。callback
は、エラーとメッセージ固有の結果の 2 つのオプションの引数を受け取る関数です。
session.post('Runtime.evaluate', { expression: '2 + 2' }, (error, { result }) => console.log(result))
// 出力: { type: 'number', value: 4, description: '4' }
V8 インスペクタープロトコルの最新バージョンは、Chrome DevTools プロトコルビューアーで公開されています。
Node.js インスペクターは、V8 によって宣言されたすべての Chrome DevTools プロトコルドメインをサポートしています。Chrome DevTools プロトコルドメインは、アプリケーションの状態を検査し、実行時イベントをリッスンするために使用されるランタイムエージェントの 1 つと対話するためのインターフェースを提供します。
HeapProfiler.takeHeapSnapshot
またはHeapProfiler.stopTrackingHeapObjects
コマンドを V8 に送信するときにreportProgress
をtrue
に設定することはできません。
例
デバッガーの他に、DevTools プロトコルを介してさまざまな V8 プロファイラーを利用できます。
CPU プロファイラー
以下は、CPU プロファイラー の使用方法を示す例です。
const inspector = require('node:inspector')
const fs = require('node:fs')
const session = new inspector.Session()
session.connect()
session.post('Profiler.enable', () => {
session.post('Profiler.start', () => {
// ここで測定対象のビジネスロジックを呼び出す...
// しばらくして...
session.post('Profiler.stop', (err, { profile }) => {
// プロファイルをディスクに書き込んだり、アップロードしたりする
if (!err) {
fs.writeFileSync('./profile.cpuprofile', JSON.stringify(profile))
}
})
})
})
ヒーププロファイラー
以下は、ヒーププロファイラー の使用方法を示す例です。
const inspector = require('node:inspector')
const fs = require('node:fs')
const session = new inspector.Session()
const fd = fs.openSync('profile.heapsnapshot', 'w')
session.connect()
session.on('HeapProfiler.addHeapSnapshotChunk', m => {
fs.writeSync(fd, m.params.chunk)
})
session.post('HeapProfiler.takeHeapSnapshot', null, (err, r) => {
console.log('HeapProfiler.takeHeapSnapshot done:', err, r)
session.disconnect()
fs.closeSync(fd)
})
共通オブジェクト
inspector.close()
[履歴]
バージョン | 変更 |
---|---|
v18.10.0 | API はワーカー スレッドで公開されます。 |
v9.0.0 | v9.0.0 で追加 |
残りのすべての接続を閉じようとします。すべてが閉じられるまでイベントループをブロックします。すべての接続が閉じられると、インスペクターを非アクティブ化します。
inspector.console
- <Object> リモートインスペクターコンソールにメッセージを送信するためのオブジェクト。
require('node:inspector').console.log('a message')
インスペクターコンソールには、Node.js コンソールとの API のパリティはありません。
inspector.open([port[, host[, wait]]])
[履歴]
バージョン | 変更点 |
---|---|
v20.6.0 | inspector.open() が Disposable オブジェクトを返すようになりました。 |
port
<number> インスペクター接続をリッスンするポート。オプション。デフォルト: CLI で指定されたもの。host
<string> インスペクター接続をリッスンするホスト。オプション。デフォルト: CLI で指定されたもの。wait
<boolean> クライアントが接続するまでブロックします。オプション。デフォルト:false
。- 戻り値: <Disposable>
inspector.close()
を呼び出す Disposable。
ホストとポートでインスペクターをアクティブにします。node --inspect=[[host:]port]
と同等ですが、node の起動後にプログラムで実行できます。
wait が true
の場合、クライアントがインスペクトポートに接続し、フロー制御がデバッガークライアントに渡されるまでブロックされます。
host
パラメータの使用に関する セキュリティ警告 を参照してください。
inspector.url()
- 戻り値: <string> | <undefined>
アクティブなインスペクターの URL を返すか、ない場合は undefined
を返します。
$ node --inspect -p 'inspector.url()'
Debugger listening on ws://127.0.0.1:9229/166e272e-7a30-4d09-97ce-f1c012b43c34
For help, see: https://nodejs.org/en/docs/inspector
ws://127.0.0.1:9229/166e272e-7a30-4d09-97ce-f1c012b43c34
$ node --inspect=localhost:3000 -p 'inspector.url()'
Debugger listening on ws://localhost:3000/51cf8d0e-3c36-4c59-8efd-54519839e56a
For help, see: https://nodejs.org/en/docs/inspector
ws://localhost:3000/51cf8d0e-3c36-4c59-8efd-54519839e56a
$ node -p 'inspector.url()'
undefined
inspector.waitForDebugger()
追加: v12.7.0
クライアント(既存または後で接続されたもの)が Runtime.runIfWaitingForDebugger
コマンドを送信するまでブロックします。
アクティブなインスペクターがない場合は例外がスローされます。
DevTools との統合
node:inspector
モジュールは、Chrome DevTools Protocol をサポートする devtools と統合するための API を提供します。実行中の Node.js インスタンスに接続された DevTools フロントエンドは、インスタンスから放出されるプロトコルイベントをキャプチャし、デバッグを容易にするためにそれらを適切に表示できます。以下のメソッドは、接続されたすべてのフロントエンドにプロトコルイベントをブロードキャストします。メソッドに渡されるparams
は、プロトコルに応じてオプションになる場合があります。
// `Network.requestWillBeSent`イベントが発火します。
inspector.Network.requestWillBeSent({
requestId: 'request-id-1',
timestamp: Date.now() / 1000,
wallTime: Date.now(),
request: {
url: 'https://nodejs.org/en',
method: 'GET',
},
})
inspector.Network.requestWillBeSent([params])
追加: v22.6.0, v20.18.0
params
<Object>
この機能は、--experimental-network-inspection
フラグが有効になっている場合にのみ利用可能です。
接続されたフロントエンドにNetwork.requestWillBeSent
イベントをブロードキャストします。このイベントは、アプリケーションが HTTP リクエストを送信しようとしていることを示します。
inspector.Network.responseReceived([params])
追加: v22.6.0, v20.18.0
params
<Object>
この機能は、--experimental-network-inspection
フラグが有効になっている場合にのみ利用可能です。
接続されたフロントエンドにNetwork.responseReceived
イベントをブロードキャストします。このイベントは、HTTP レスポンスが利用可能になったことを示します。
inspector.Network.loadingFinished([params])
追加: v22.6.0, v20.18.0
params
<Object>
この機能は、--experimental-network-inspection
フラグが有効になっている場合にのみ利用可能です。
接続されたフロントエンドに Network.loadingFinished
イベントをブロードキャストします。このイベントは、HTTP リクエストのロードが完了したことを示します。
inspector.Network.loadingFailed([params])
追加: v22.7.0, v20.18.0
params
<Object>
この機能は、--experimental-network-inspection
フラグが有効になっている場合にのみ利用可能です。
接続されたフロントエンドに Network.loadingFailed
イベントをブロードキャストします。このイベントは、HTTP リクエストのロードに失敗したことを示します。
ブレークポイントのサポート
Chrome DevTools Protocol の Debugger
ドメイン では、inspector.Session
がプログラムにアタッチし、ブレークポイントを設定してコードをステップ実行できます。
しかし、session.connect()
で接続された同一スレッドの inspector.Session
でブレークポイントを設定することは避けるべきです。アタッチおよび一時停止されるプログラムはまさにデバッガー自身であるためです。代わりに、session.connectToMainThread()
でメインスレッドに接続し、ワーカー スレッドにブレークポイントを設定するか、WebSocket 接続を介して Debugger プログラムで接続してみてください。