Overview
セッションでstreaming: trueが設定されると、SDK は、一時的なイベント (デルタ、進行状況の更新) をリアルタイムで、永続的なイベント (完全なメッセージ、ツールの結果) と共に出力します。 すべてのイベントは共通のエンベロープを共有し、その形状がイベント dataに依存するtypeペイロードを運びます。

| 概念 | Description |
|---|---|
| エフェメラル イベント | 過渡;はリアルタイムでストリーミングされますが、セッション ログには保持 されません 。 セッションの再開時に再生されません。 |
| 永続化されたイベント | ディスク上のセッション イベント ログに保存されます。 セッションの再開時に再生されます。 |
| Delta イベント | 一時的なストリーミングデータチャンク(テキストまたは推論) 差分を蓄積して完全なコンテンツを構築します。 |
parentId チェーン | 各イベントの parentId は前のイベントを指し示し、ウォーク可能なリンクリストを形成します。 |
イベント エンベロープ
種類に関係なく、すべてのセッション イベントには次のフィールドが含まれます。
| フィールド | タイプ | Description |
|---|---|---|
id | ||
string (UUID v4) | 一意のイベント識別子 | |
timestamp | ||
string (ISO 8601) | イベントが作成されたとき | |
parentId | string | null | チェーン内の前のイベントの ID。最初のイベントのnull |
agentId | string? | サブエージェントから発生したイベントのサブエージェント インスタンス ID。ルート/メイン エージェントとセッション レベルのイベントには存在しません |
ephemeral | boolean? | 一時的なイベントの場合true。永続化されたイベントの場合は不在またはfalse |
type | string | イベント型識別子 (以下の表を参照) |
data | object | イベント固有のペイロード |
イベントに登録する
コード言語 navigation
// All events
session.on((event) => {
console.log(event.type, event.data);
});
// Specific event type — data is narrowed automatically
session.on("assistant.message_delta", (event) => {
process.stdout.write(event.data.deltaContent);
});
from copilot.session_events import SessionEventType
def handle(event):
if event.type == SessionEventType.ASSISTANT_MESSAGE_DELTA:
print(event.data.delta_content, end="", flush=True)
session.on(handle)
session.On(func(event copilot.SessionEvent) {
if d, ok := event.Data.(*copilot.AssistantMessageDeltaData); ok {
fmt.Print(d.DeltaContent)
}
})
session.On<SessionEvent>(evt =>
{
if (evt is AssistantMessageDeltaEvent delta)
{
Console.Write(delta.Data.DeltaContent);
}
});
// All events
session.on(event -> System.out.println(event.getType()));
// Specific event type — data is narrowed to the matching class
session.on(AssistantMessageDeltaEvent.class, event ->
System.out.print(event.getData().deltaContent())
);
ヒント
(Python/Go) これらの SDK では、個別のイベントごとのデータ型 (たとえば、AssistantMessageDeltaData) が使用されるため、各種類に関連するフィールドのみが存在します。
(.NET) .NET SDK では、イベントごとに個別の厳密に型指定されたデータ クラス (AssistantMessageDeltaData など) が使用されるため、各型に関連するフィールドのみが存在します。
(TypeScript) TypeScript SDK では判別共用体が使用されます。 event.typeで一致すると、 data ペイロードは自動的に正しい図形に絞り込まれます。
セッション開始前の購読
セッションは、作成または再開の呼び出しが返される前にイベントを生成できます。 エージェントは既に動作している可能性があります (特に、 continuePendingWorkを使用した再開時)、 session.idle などの一時的なイベントはセッション ログに書き込まれないため、 getMessages 後で復旧することはできません。 セッション ハンドルが存在した後にインストールされたサブスクリプションは、そのスタートアップ ウィンドウを見落とします。
ヒント
(Rust)Client::prepare_session``Client::prepare_resume_sessionは、プロトコル アクティビティが発生する前にセッションのイベント チャネルを所有するPreparedSessionを返します。 最初にサブスクライブしてから、 start()を呼び出します。
use github_copilot_sdk::{Client, SessionConfig};
async fn create_without_missing_startup_events(
client: &Client,
) -> Result<(), github_copilot_sdk::Error> {
let prepared = client.prepare_session(
SessionConfig::default().with_event_buffer_capacity(2048),
)?;
// Installed before any wire activity: nothing is dropped for lack of a receiver.
let mut events = prepared.subscribe();
tokio::spawn(async move {
while let Ok(event) = events.recv().await {
println!("{}", event.event_type);
}
});
let session = prepared.start().await?;
let _ = session;
Ok(())
}
prepare_* は同期的で不活性です。バッファー容量を検証し、ローカル チャネルを割り当て、それ以外は何もしません。 セッションは登録されておらず、 start() が最初にポーリングされるまで CLI には何も到達しません。 一度も開始されなかった準備済みセッションを破棄しても、状態を一切残さず、そのサブスクリプションは閉じられます。start() フューチャーを破棄すると、進行中の起動処理が取り消され、セッションの登録が解除されるため、同じセッション ID を使用した再試行は成功します。 クリーンアップの対象は、中断された起動処理が所有していた当該登録に厳密に限定されているため、すでに同じセッション ID を引き継いでいる再試行を排除することはできません。
スタートアップ バッファリングは、次の場合に計画する価値があります。
- イベント バッファーは有限であり、
event_buffer_capacityがオーバーライドしない限り 512 イベントです。0の容量は、クリップされるのではなく、無効な設定エラーとして拒否されます。 - 低速サブスクライバーは、スキップされたイベントの数を報告する
Laggedエラーを確認します。 セッションのイベント ループにバックプレッシャを適用することはありません。 - 大規模なスタートアップ バーストの無損失ビューを必要とするコンシューマーは、それをカバーする容量を構成するか、
start()と同時にサブスクリプションをドレインする必要があります。
メモ
サーバーがセッション ID を割り当てるクラウド セッションの場合、SDK は作成応答が到着し、ID がわかるまで通知をルーティングできません。 そのポイントの前に生成されたイベントは、どのセッションにもルーティングできません。 保証の範囲はより限定的です。ルーティングされたイベントは、インストール済みのレシーバーが存在しないことを理由に破棄されることはありません。 構成に session_id をピン留めして、最初のバイトからルーティングと完全な応答前カバレッジを取得します。
親エージェントの応答のみをレンダリングする
サブエージェント イベントは親セッション ストリームを共有し、エンベロープ レベルの agentIdを含めます。 ルート/メイン エージェント イベントとセッション レベルのイベントでは agentIdが省略されるため、メイン チャット レンダラーは、 agentId が設定されているアシスタント イベントを無視し、代わりにそれらのイベントをトレースまたは進行状況 UI にルーティングできます。
import type { CopilotSession } from "@github/copilot-sdk";
export function subscribeParentResponse(session: CopilotSession): void {
session.on("assistant.message_delta", (event) => {
if (!event.agentId) {
process.stdout.write(event.data.deltaContent);
}
});
}
from copilot import CopilotSession, SessionEvent, SessionEventType
from copilot.session_events import AssistantMessageDeltaData
def subscribe_parent_response(session: CopilotSession) -> None:
def handle(event: SessionEvent) -> None:
if event.type == SessionEventType.ASSISTANT_MESSAGE_DELTA and event.agent_id is None:
data = event.data
if isinstance(data, AssistantMessageDeltaData):
print(data.delta_content, end="", flush=True)
session.on(handle)
package example
import (
"fmt"
copilot "github.com/github/copilot-sdk/go"
)
func subscribeParentResponse(session *copilot.Session) {
session.On(func(event copilot.SessionEvent) {
if event.AgentID != nil {
return
}
if d, ok := event.Data.(*copilot.AssistantMessageDeltaData); ok {
fmt.Print(d.DeltaContent)
}
})
}
using System;
using GitHub.Copilot;
static class ParentAgentResponseExample
{
public static void SubscribeParentResponse(CopilotSession session)
{
session.On<AssistantMessageDeltaEvent>(evt =>
{
if (evt.AgentId is null)
{
Console.Write(evt.Data.DeltaContent);
}
});
}
}
import com.github.copilot.CopilotSession;
import com.github.copilot.generated.AssistantMessageDeltaEvent;
final class ParentAgentResponseExample {
static void subscribeParentResponse(CopilotSession session) {
session.on(AssistantMessageDeltaEvent.class, event -> {
if (event.getAgentId() == null) {
System.out.print(event.getData().deltaContent());
}
});
}
}
use github_copilot_sdk::session::Session;
async fn subscribe_parent_response(session: &Session) {
let mut events = session.subscribe();
while let Ok(event) = events.recv().await {
if event.event_type == "assistant.message_delta" && event.agent_id.is_none() {
if let Some(delta) = event.data.get("deltaContent").and_then(|v| v.as_str()) {
print!("{delta}");
}
}
}
}
アシスタント イベント
これらのイベントは、ターン スタートからストリーミング チャンク、最後のメッセージまで、エージェントの応答ライフサイクルを追跡します。
assistant.turn_start
エージェントがターンの処理を開始したときに出力されます。
| データ フィールド | タイプ | 必須 | Description |
|---|---|---|---|
turnId | string | ✅ | ターン識別子 (通常は、文字列化されたターン番号) |
interactionId | string | テレメトリ相関用の CAPI インタラクション ID |
assistant.intent
儚い。 エージェントが現在行っていることの簡単な説明。動作に応じて更新されます。
| データ フィールド | タイプ | 必須 | Description |
|---|---|---|---|
intent | string | ✅ | 人間が判読できる意図 (例: "コードベースの探索") |
assistant.reasoning
モデルから拡張思考ブロックを完成させます。 推論が完了した後に出力されます。
| データ フィールド | タイプ | 必須 | Description |
|---|---|---|---|
reasoningId | string | ✅ | この推論ブロックの一意識別子 |
content | string | ✅ | 完全な拡張思考テキスト |
assistant.reasoning_delta
儚い。 リアルタイムでストリーミングされる、モデルの拡張思考の増分チャンク。
| データ フィールド | タイプ | 必須 | Description |
|---|---|---|---|
reasoningId | string | ✅ | 対応する assistant.reasoning イベントと一致します |
deltaContent | string | ✅ | 推論コンテンツに追加するテキストの一部 |
assistant.message
この LLM 呼び出しに対するアシスタントの完全な応答。 ツール呼び出し要求を含めることができます。
| データ フィールド | タイプ | 必須 | Description |
|---|---|---|---|
messageId | string | ✅ | このメッセージのユニーク識別子 |
content | string | ✅ | アシスタントのテキスト応答 |
toolRequests | ToolRequest[] | アシスタントが行いたいと思うツール呼び出し (下記参照) | |
reasoningOpaque | string | 暗号化された拡張思考(アントロピックモデル)、セッションにバインドされた | |
reasoningText | string | 拡張思考から読み取り可能な推論テキスト | |
encryptedContent | string | 暗号化された推論コンテンツ (OpenAI モデル);session-bound | |
phase | string | 生成フェーズ (例: "thinking" と "response") | |
outputTokens | number | API 応答からの実際の出力トークン数 | |
interactionId | string | テレメトリ用の CAPI インタラクション ID | |
parentToolCallId | string | Deprecated. サブエージェントの属性にエンベロープ レベルの agentId を使用する |
**
ToolRequest フィールド:**
| フィールド | タイプ | 必須 | Description |
|---|---|---|---|
toolCallId | string | ✅ | このツール呼び出しの一意の ID |
name | string | ✅ | ツール名 (例: "bash"、 "edit"、 "grep") |
arguments | object | ツールの解析された引数 | |
type | "function" | "custom" | 呼び出しの種類。存在しない場合は"function"が既定値となります。 |
assistant.message_delta
儚い。 リアルタイムでストリーミングされる、アシスタントのテキスト応答の増分チャンク。
| データ フィールド | タイプ | 必須 | Description |
|---|---|---|---|
messageId | string | ✅ | 対応する assistant.message イベントと一致します |
deltaContent | string | ✅ | メッセージに追加するテキスト チャンク |
parentToolCallId | string | Deprecated. サブエージェントの属性にエンベロープ レベルの agentId を使用する |
assistant.turn_end
エージェントがターンを完了したときに生成されます (すべてのツールの実行が完了し、最終的な応答が配信されます)。
| データ フィールド | タイプ | 必須 | Description |
|---|---|---|---|
turnId | string | ✅ | 対応する assistant.turn_start イベントと一致します |
assistant.usage
儚い。 個々の API 呼び出しのトークンの使用状況とコストに関する情報。
| データ フィールド | タイプ | 必須 | Description |
|---|---|---|---|
model | string | ✅ | モデル識別子 (例: "gpt-5.4") |
inputTokens | number | 使用された入力トークン | |
outputTokens | number | 生成された出力トークン | |
reasoningTokens | number | 推論/考え方のチェーンに使用される出力トークン ( outputTokensのサブセット) | |
cacheReadTokens | number | プロンプト キャッシュから読み取られたトークン | |
cacheWriteTokens | number | プロンプト キャッシュに書き込まれたトークン | |
cacheExpiresAt | string | このモデル呼び出しのプロンプトキャッシュが期限切れとなる日時の ISO 8601 タイムスタンプ | |
content | boolean | 応答がブロックされたか、コンテンツ フィルターによって切り捨てられたか (finish_reason === 'content_filter') | |
finishReason | string | モデルの終了理由 (例: "stop"、 "length"、 "tool_calls"、 "content_filter") | |
cost | number | 請求のためのモデル乗算コスト | |
duration | number | API 呼び出し時間 (ミリ秒単位) | |
time | number | 要求ディスパッチから最初に受信したトークンまでの時間 (ストリーミング待機時間) | |
inter | number | 連続するトークン間の平均待機時間 (ストリーミング スループット) | |
reasoningEffort | string | この呼び出しに使用される推論作業レベル (例: "low"、 "medium"、 "high") | |
initiator | string | この呼び出しをトリガーした内容 (例: "sub-agent")、ユーザーが開始した場合は存在しない | |
apiCallId | string | プロバイダーからの完了 ID (例: chatcmpl-abc123) | |
serviceRequestId | string | CAPI ログの関連付け用の Copilot サービス リクエスト ID (x-copilot-service-request-id) | |
apiEndpoint | "/ | ||
| モデル呼び出しに使用される API エンドポイント。は、可観測性とコストの属性に役立ちます。 | |||
ws:/responses は、応答 API の Websocket バリアントです | |||
providerCallId | string | GitHub要求トレース ID (x-github-request-id) | |
parentToolCallId | string | Deprecated. サブエージェントの属性にエンベロープ レベルの agentId を使用する | |
quotaSnapshots | Record<string, QuotaSnapshot> | クォータ識別子でキー付けされたクォータごとのリソース使用量 | |
copilotUsage | CopilotUsage | API からの明細化されたトークン コストの内訳 |
assistant.streaming_delta
儚い。 低レベルのネットワーク進行状況インジケーター - ストリーミング API 応答から受信した合計バイト数。
| データ フィールド | タイプ | 必須 | Description |
|---|---|---|---|
total | number | ✅ | これまでに受信した累積バイト数 |
ツールの実行イベント
これらのイベントは、ツール呼び出しを要求するモデルから実行から完了までの、各ツール呼び出しの完全なライフサイクルを追跡します。
tool.execution_start
ツールの実行が開始されたときに出力されます。
| データ フィールド | タイプ | 必須 | Description |
|---|---|---|---|
toolCallId | string | ✅ | この呼び出しツールの一意の識別子 |
toolName | string | ✅ | ツールの名前 (例: "bash"、 "edit"、 "grep") |
arguments | object | ツールに渡される解析された引数 | |
mcpServerName | string | MCP サーバー名 (ツールが MCP サーバーによって提供される場合) | |
mcpToolName | string | MCP サーバー上の元のツール名 | |
parentToolCallId | string | Deprecated. サブエージェントの属性にエンベロープ レベルの agentId を使用する |
tool.execution_partial_result
Deprecated. ライブターミナル出力には tool.shell_output を使用します。 このエフェメラル イベントは、移行中は置換先と並行して引き続き発行されます。同じ出力を 2 回表示しないように、1 つの表現のみをサブスクライブします。
| データ フィールド | タイプ | 必須 | Description |
|---|---|---|---|
toolCallId | string | ✅ | 対応するtool.execution_startに一致します |
partialOutput | string | ✅ | stdout と stderr がマージされた有界累積置換スナップショット。追加専用チャンクではない |
tool.shell_output
儚い。 接続されたターミナル コマンドまたはユーザーが要求したターミナル コマンドからの追記専用の出力。 各イベントには、モデルの最終的なツール結果の書式設定に使用される区切り記号やマーカーを使用せずに、新しく観察されたシークレット フィルター処理されたテキストが含まれます。
| データ フィールド | タイプ | 必須 | Description |
|---|---|---|---|
toolCallId | string | ✅ | 元のツール呼び出しを識別します。 |
text | string | ✅ | 置換スナップショットではなく、追加する新しいテキスト |
stream | "stdout" | "stderr" | "terminal" | ||
出力ソース。省略とは "stdout" を意味します。 | |||
"terminal" は、本質的にマージされた PTY 出力を識別します。その stdout/stderr の出力元は特定できません | |||
sequence | number | ✅ | 0 から始まり、このツール呼び出しのすべてのストリームで、実際に観測された公開順に従って増加します |
streamとtextごとにtoolCallIdを個別に蓄積するか、統合表示用にチャンクを順番どおりに結合します。 シーケンス番号は、重複と欠落したチャンクを識別します。独立したオペレーティング システムの書き込み間の正確な順序は示しません。 後から購読したサブスクライバーは、0 より大きい最初のシーケンスを受信できます。
これらのイベントはライブ専用です。再開しても永続化または再生されません。 最終的な tool.execution_complete 結果、モデルに対する書式設定、分離されたコマンドのキャプチャは変更されません。 テキストにはターミナル コントロール シーケンスを含めることができます。レンダラーは、通常のターミナル テキスト処理を適用する必要があります。
接続されたターミナル コマンドは、非同期で実行される場合や initial_wait を過ぎても続行する場合、tool.execution_complete の後も実行を続けることができます。 続行中に受信した出力は、元の toolCallId を使用し、ゼロから再開するのではなく、同じ sequence を続行します。 アクティブな呼び出しのみを表示するコンシューマーは、完了した呼び出し状態を再作成するのではなく、完了後に受信したチャンクを無視する必要があります。
シークレットのフィルタリングは、デコードされた各チャンクに対して適用されます。 ランタイムは人為的に行を分割しませんが、オペレーティング システムの読み取りにより、行またはシークレットが複数のチャンクにまたがって分割されることがあります。クロスチャンク シークレット再構築は提供されていません。
tool.execution_progress
儚い。 実行中のツール (MCP サーバーの進行状況通知など) から人間が判読できる進行状況の状態。
| データ フィールド | タイプ | 必須 | Description |
|---|---|---|---|
toolCallId | string | ✅ | 対応するtool.execution_startに一致します |
progressMessage | string | ✅ | 進捗状況メッセージ |
tool.execution_complete
ツールの実行が正常に終了したとき、またはエラーが発生したときに生成されます。
| データ フィールド | タイプ | 必須 | Description |
|---|---|---|---|
toolCallId | string | ✅ | 対応するtool.execution_startに一致します |
success | boolean | ✅ | 実行が成功したかどうか |
model | string | このツール呼び出しを生成したモデル | |
interactionId | string | CAPI インタラクション ID | |
isUserRequested | boolean | ||
true ユーザーがこのツール呼び出しを明示的に要求したとき | |||
result | Result | 成功時と、失敗時にツールがエラーとともにコンテンツを返した場合に表示されます (以下を参照) | |
error | { message, code? } | エラー発生時に含まれる | |
toolTelemetry | object | ツール固有のテレメトリ (CodeQL チェック数など) | |
parentToolCallId | string | Deprecated. サブエージェントの属性にエンベロープ レベルの agentId を使用する |
**
Result フィールド:**
| フィールド | タイプ | 必須 | Description |
|---|---|---|---|
content | string | ✅ | LLM に送信される簡潔な結果 (トークン効率のために切り捨てられる可能性があります) |
detailedContent | string | 表示用の完全な結果。差分などの完全なコンテンツを保持する | |
contents | ContentBlock[] | 構造化コンテンツ ブロック (テキスト、ターミナル、イメージ、オーディオ、リソース) |
tool.user_requested
ユーザーが明示的にツールの呼び出しを要求したときに生成されます (呼び出しを選択したモデルではなく)。
| データ フィールド | タイプ | 必須 | Description |
|---|---|---|---|
toolCallId | string | ✅ | この呼び出しツールの一意の識別子 |
toolName | string | ✅ | ユーザーが呼び出すツールの名前 |
arguments | object | 呼び出しの引数 |
セッション ライフサイクル イベント
session.idle
儚い。 エージェントはすべての処理を完了し、次のメッセージの準備が整いました。 これはターンが完全に完了したことを示すシグナルです。
| データ フィールド | タイプ | 必須 | Description |
|---|---|---|---|
aborted | boolean | 前のターンが中止シグナルによって取り消された場合は True |
session.error
セッション処理中にエラーが発生しました。
| データ フィールド | タイプ | 必須 | Description |
|---|---|---|---|
errorType | string | ✅ | エラー カテゴリ (例: "authentication"、 "quota"、 "rate_limit") |
message | string | ✅ | 人間が読みやすいエラーメッセージ |
stack | string | エラースタックトレース | |
statusCode | number | アップストリーム要求からの HTTP 状態コード | |
providerCallId | string | サーバー側ログの関連付け用 GitHub リクエスト追跡 ID |
session.compaction_start
コンテキスト ウィンドウの圧縮が開始されました。
データ ペイロードが空 ({}) です。
session.compaction_complete
コンテキスト ウィンドウの圧縮が完了しました。
| データ フィールド | タイプ | 必須 | Description |
|---|---|---|---|
success | boolean | ✅ | 圧縮に成功したかどうか |
error | string | 圧縮に失敗した場合のエラー メッセージ | |
pre | number | 圧縮前のトークン | |
post | number | 圧縮後のトークン | |
pre | number | 圧縮前のメッセージ数 | |
messagesRemoved | number | 削除されたメッセージ | |
tokensRemoved | number | トークンが削除されました | |
summaryContent | string | LLM によって生成されたコンパクトな履歴の概要 | |
checkpointNumber | number | 復旧用に作成されたチェックポイント スナップショット番号 | |
checkpointPath | string | チェックポイントが格納されたファイル パス | |
compaction | { input, output, cachedInput } | 圧縮 LLM 呼び出しのトークンの使用 | |
requestId | string | GitHub のコンパクション呼び出し用リクエストトレーシング ID |
session.title_changed
儚い。 セッションの自動生成されたタイトルが更新されました。
| データ フィールド | タイプ | 必須 | Description |
|---|---|---|---|
title | string | ✅ | 新しいセッション タイトル |
session.context_changed
セッションの作業ディレクトリまたはリポジトリ コンテキストが変更されました。
| データ フィールド | タイプ | 必須 | Description |
|---|---|---|---|
cwd | string | ✅ | 現在の作業ディレクトリ |
gitRoot | string | Git リポジトリのルート | |
repository | string | ||
"owner/name"形式のリポジトリ | |||
branch | string | 現在の Git ブランチ |
session.usage_info
儚い。 コンテキスト ウィンドウ使用率スナップショット。
| データ フィールド | タイプ | 必須 | Description |
|---|---|---|---|
tokenLimit | number | ✅ | モデルのコンテキスト ウィンドウの最大トークン数 |
currentTokens | number | ✅ | コンテキスト ウィンドウ内の現在のトークン |
messagesLength | number | ✅ | 会話の現在のメッセージ数 |
session.session_limits_changed
現在の会計期間のセッション制限が変更されました。
null
sessionLimits値は、制限がアクティブでないことを意味します。
| データ フィールド | タイプ | 必須 | Description |
|---|---|---|---|
sessionLimits | Session | ✅ | 現在のセッションの制限、または制限が有効でない場合は null |
session | number | セッションの現在の会計期間で許可される AI クレジットの最大数 |
session.usage_checkpoint
セッションの再開時にアカウンティングを再構築するために使用される永続集計使用チェックポイント。
| データ フィールド | タイプ | 必須 | Description |
|---|---|---|---|
totalNanoAiu | number | ✅ | チェックポイント時点におけるセッション全体の nano-AI ユニットの累積コスト |
total | number | チェックポイント時に使用された Premium API 要求の合計数 |
session.task_complete
エージェントは、割り当てられたタスクを完了しました。
| データ フィールド | タイプ | 必須 | Description |
|---|---|---|---|
summary | string | 完了したタスクの概要 |
session.shutdown
セッションが終了しました。
| データ フィールド | タイプ | 必須 | Description |
|---|---|---|---|
shutdownType | "routine" | "error" | ✅ | 通常のシャットダウンまたはクラッシュ |
errorReason | string | ||
shutdownType が "error" である場合のエラー説明 | |||
total | number | ✅ | 使用された Premium API 要求の合計数 |
total | number | ✅ | API 呼び出しの累積時間 (ミリ秒単位) |
sessionStartTime | number | ✅ | セッションの開始時の Unix タイムスタンプ (ミリ秒) |
codeChanges | { linesAdded, linesRemoved, filesModified } | ✅ | コード変更メトリックの集計 |
modelMetrics | Record<string, ModelMetric> | ✅ | モデルごとの使用状況の内訳 |
currentModel | string | シャットダウン時に選択されたモデル |
アクセス許可とユーザー入力イベント
これらのイベントは、エージェントが続行する前にユーザーからの承認または入力を必要とする場合に生成されます。
permission.requested
エージェントには、アクション (コマンドの実行、ファイルの書き込みなど) を実行するためのアクセス許可が必要です。
| データ フィールド | タイプ | 必須 | Description |
|---|---|---|---|
requestId | string | ✅ | これを使用して、次の方法で応答します。 session.respond |
permissionRequest | PermissionRequest | ✅ | 要求されているアクセス許可の詳細 |
permissionRequestは、kindの判別共用体です。
kind | キー フィールド | Description |
|---|---|---|
"shell" | ||
fullCommandText、intention、commands[]、possiblePaths[] | シェル コマンドを実行する | |
"write" | ||
fileName、diff、intention、newFileContents?、fileEdits? | ファイルの書き込み/変更 | |
"read" | ||
path、intention | ファイルまたはディレクトリの読み取り | |
"mcp" | ||
serverName、toolName、toolTitle、args?、readOnly | MCP ツールを呼び出す | |
"url" | ||
url、intention | URL を取得する | |
"memory" | ||
subject、fact、citations | メモリを格納する | |
"custom-tool" | ||
toolName、toolDescription、args? | カスタム ツールを呼び出す |
すべての kind バリアントには、要求をトリガーしたツール呼び出しにリンクバックするオプションの toolCallId も含まれています。
書き込み要求は、promptRequest と fileEdits の両方に permissionRequest を含めることもできます。 各エントリにはオプションの before と after スナップショットが含まれており、それぞれにセッション ファイルシステム名前空間内の絶対pathと完全なUTF-8 contentがあります。
before がないことは作成を意味し、after がないことは削除を意味します。 空の content 文字列は、使用できないプレビューではなく、空のファイルを表します。 移動は、その両側に異なるパスを持つことができます。 移動によって既存の宛先が上書きされると、別のエントリでソースの削除と宛先の置換が記述されます。
これらのスナップショットは、後でライブ ファイルシステムを読み取るのではなく、計画された操作を記述します。 サンドボックスで保護されたファイルを読み取る前に行われた要求、UTF-8 以外のコンテンツ、名前付きパイプなどの読み取り不可能または通常ファイルではない移動先など、完全なテキスト プレビューを提供できない場合、ランタイムは fileEdits を省略します。 空の legacy newFileContents 値を削除と見なさないでください。 プレビューを使用しないコンシューマーは、既存のフィールドと承認の選択肢を引き続き使用できます。
permission.completed
アクセス許可要求が解決されました。
| データ フィールド | タイプ | 必須 | Description |
|---|---|---|---|
requestId | string | ✅ | 対応するpermission.requestedに一致します |
result.kind | string | ✅ | 次のいずれか: "approved"、 "denied-by-rules"、 "denied-interactively-by-user"、 "denied-no-approval-rule-and-could-not-request-from-user"、 "denied-by-content-exclusion-policy" |
user_input.requested
儚い。 エージェントがユーザーに質問しています。
| データ フィールド | タイプ | 必須 | Description |
|---|---|---|---|
requestId | string | ✅ | これを使用して、次の方法で応答します。 session.respond |
question | string | ✅ | ユーザーに提示する質問 |
choices | string[] | ユーザーの定義済みの選択肢 | |
allowFreeform | boolean | 自由形式のテキスト入力が許可されるかどうか |
user_input.completed
儚い。 ユーザー入力要求が解決されました。
| データ フィールド | タイプ | 必須 | Description |
|---|---|---|---|
requestId | string | ✅ | 対応するuser_input.requestedに一致します |
elicitation.requested
儚い。 エージェントには、ユーザーからの構造化されたフォーム入力 (MCP 引き出しプロトコル) が必要です。
| データ フィールド | タイプ | 必須 | Description |
|---|---|---|---|
requestId | string | ✅ | これを使用して、次の方法で応答します。 session.respond |
message | string | ✅ | 必要な情報の説明 |
mode | "form" | 現在、引き出しモードは"form"のみです。 | |
requestedSchema | { type: "object", properties, required? } | ✅ | フォーム フィールドを記述する JSON スキーマ |
elicitation.completed
儚い。 引き出し要請が解決されました。
| データ フィールド | タイプ | 必須 | Description |
|---|---|---|---|
requestId | string | ✅ | 対応するelicitation.requestedに一致します |
サブエージェントとスキル イベント
subagent.started
カスタム エージェントがサブエージェントとして呼び出されました。
| データ フィールド | タイプ | 必須 | Description |
|---|---|---|---|
toolCallId | string | ✅ | このサブエージェントを生成した親ツール呼び出し |
agentName | string | ✅ | サブエージェントの内部名 |
agentDisplayName | string | ✅ | 人間が判読できる表示名 |
agentDescription | string | ✅ | サブエージェントの機能の説明 |
model | string | 開始時に判明している場合に、サブエージェントが使用するモデル |
subagent.completed
サブエージェントが正常に完了しました。
| データ フィールド | タイプ | 必須 | Description |
|---|---|---|---|
toolCallId | string | ✅ | 対応するsubagent.startedに一致します |
agentName | string | ✅ | 内部名 |
agentDisplayName | string | ✅ | 表示名 |
model | string | サブエージェントで使用されるモデル | |
durationMs | number | ウォール クロックの実行時間 (ミリ秒) | |
totalTokens | number | 使用された入力トークンと出力トークンの合計 | |
totalToolCalls | number | 作成されたツール呼び出しの合計数 |
subagent.failed
サブエージェントでエラーが発生しました。
| データ フィールド | タイプ | 必須 | Description |
|---|---|---|---|
toolCallId | string | ✅ | 対応するsubagent.startedに一致します |
agentName | string | ✅ | 内部名 |
agentDisplayName | string | ✅ | 表示名 |
error | string | ✅ | エラー メッセージ |
model | string | サブエージェントに対して選択されたモデル (既知の場合) | |
durationMs | number | ウォール クロックの実行時間 (ミリ秒) | |
totalTokens | number | 失敗前に使用された入力トークンと出力トークンの合計 | |
totalToolCalls | number | 失敗前に行われたツール呼び出しの合計数 |
subagent.selected
現在の要求を処理するために、カスタム エージェントが選択 (推論) されました。
| データ フィールド | タイプ | 必須 | Description |
|---|---|---|---|
agentName | string | ✅ | 選択したエージェントの内部名 |
agentDisplayName | string | ✅ | 表示名 |
tools | string[] | null | ✅ | このエージェントで使用可能なツール名。すべてのツールにはnull |
subagent.deselected
カスタム エージェントの選択が解除され、既定のエージェントに戻りました。
データ ペイロードが空 ({}) です。
skill.invoked
現在の会話に対してスキルがアクティブ化されました。
| データ フィールド | タイプ | 必須 | Description |
|---|---|---|---|
name | string | ✅ | スキル名 |
path | string | ✅ | SKILL.md 定義へのファイル パス |
content | string | ✅ | 会話にすべてのスキルコンテンツが挿入されました。 |
allowedTools | string[] | スキルの allowed-tools frontmatter にリストされているツール。 SDK によって自動的に承認されることはありません。アクセス許可ハンドラーが引き続き決定します。 Copilot CLI は、スキルがアクティブな間、それらを自動的に承認します。 | |
pluginName | string | スキルの元のプラグイン | |
pluginVersion | string | プラグインのバージョン |
その他のイベント
abort
現在のターンは中止されました。
| データ フィールド | タイプ | 必須 | Description |
|---|---|---|---|
reason | string | ✅ | ターンが中止された理由 (例: "user initiated") |
user.message
ユーザーがメッセージを送信しました。 セッション タイムライン用に記録されます。
| データ フィールド | タイプ | 必須 | Description |
|---|---|---|---|
content | string | ✅ | ユーザーのメッセージ テキスト |
transformed | string | 前処理後に変換されたバージョン | |
attachments | Attachment[] | ファイル、ディレクトリ、選択項目、blob、または GitHub 参照の添付ファイル | |
source | string | メッセージ ソース識別子 | |
agentMode | string | エージェント モード: "interactive"、 "plan"、 "autopilot"、または "shell" | |
interactionId | string | CAPI インタラクション ID |
system.message
システムまたは開発者のプロンプトが会話に挿入されました。
| データ フィールド | タイプ | 必須 | Description |
|---|---|---|---|
content | string | ✅ | プロンプトの内容 |
role | "system" | "developer" | ✅ | メッセージ 役割 |
name | string | ソース識別子 | |
metadata | { promptVersion?, variables? } | プロンプト テンプレートのメタデータ |
external_tool.requested
エージェントは、外部ツール (SDK コンシューマーによって提供されるツール) を呼び出したいと考えています。
| データ フィールド | タイプ | 必須 | Description |
|---|---|---|---|
requestId | string | ✅ | これを使用して、次の方法で応答します。 session.respond |
sessionId | string | ✅ | この要求が属するセッション |
toolCallId | string | ✅ | この呼び出しのツール呼び出し ID |
toolName | string | ✅ | 外部ツールの名前 |
arguments | object | ツールの引数 |
external_tool.completed
外部ツール要求が解決されました。
| データ フィールド | タイプ | 必須 | Description |
|---|---|---|---|
requestId | string | ✅ | 対応するexternal_tool.requestedに一致します |
exit_plan_mode.requested
儚い。 エージェントによってプランが作成され、プラン モードを終了する必要があります。
| データ フィールド | タイプ | 必須 | Description |
|---|---|---|---|
requestId | string | ✅ | これを使用して、次の方法で応答します。 session.respond |
summary | string | ✅ | プランの概要 |
planContent | string | ✅ | プランファイルの全内容 |
actions | string[] | ✅ | 使用可能なユーザー アクション (承認、編集、拒否など) |
recommendedAction | string | ✅ | 推奨されるアクション |
exit_plan_mode.completed
儚い。 終了プラン モード要求が解決されました。
| データ フィールド | タイプ | 必須 | Description |
|---|---|---|---|
requestId | string | ✅ | 対応するexit_plan_mode.requestedに一致します |
command.queued
儚い。 スラッシュ コマンドがキューに登録され、実行されました。
| データ フィールド | タイプ | 必須 | Description |
|---|---|---|---|
requestId | string | ✅ | これを使用して、次の方法で応答します。 session.respond |
command | string | ✅ | スラッシュ コマンド テキスト (例: /help、 /clear) |
command.completed
儚い。 キューに登録されたコマンドが解決されました。
| データ フィールド | タイプ | 必須 | Description |
|---|---|---|---|
requestId | string | ✅ | 対応するcommand.queuedに一致します |
session_limits_exhausted.requested
儚い。 現在のセッション予算が使い果たされ、ランタイムは続行する前にユーザーの決定を必要とします。
| データ フィールド | タイプ | 必須 | Description |
|---|---|---|---|
requestId | string | ✅ | 保留中の上限を超える要求に応答するときにこの ID を使用します |
maxAiCredits | number | ✅ | 現在のアカウンティング ウィンドウ用に構成された最大 AI クレジット数 |
usedAiCredits | number | ✅ | 現在の会計ウィンドウで既に使用されている AI クレジット |
session_limits_exhausted.completed
儚い。 保留中の上限超過リクエストが解消されました。
| データ フィールド | タイプ | 必須 | Description |
|---|---|---|---|
requestId | string | ✅ | 対応する session_limits_ イベントと一致します |
response.action | "add" | "set" | "unset" | "cancel" | ✅ | 上限到達時のリクエストに対して選択されたアクション |
response.additional | number | ||
response.action が "add" の場合に現在の最大値に加算するAIクレジット | |||
response.max | number | ||
response.action が "set" の場合の AI クレジットの新しい絶対最大値 |
クイックリファレンス: エージェンティックターンフロー
一般的なエージェント ターンでは、次の順序でイベントが出力されます。
assistant.turn_start → Turn begins
├── assistant.intent → What the agent plans to do (ephemeral)
├── assistant.reasoning_delta → Streaming thinking chunks (ephemeral, repeated)
├── assistant.reasoning → Complete thinking block
├── assistant.message_delta → Streaming response chunks (ephemeral, repeated)
├── assistant.message → Complete response (may include toolRequests)
├── assistant.usage → Token usage for this API call (ephemeral)
│
├── [If tools were requested:]
│ ├── permission.requested → Needs user approval
│ ├── permission.completed → Approval result
│ ├── tool.execution_start → Tool begins
│ ├── tool.shell_output → Stream-tagged terminal output (ephemeral, repeated)
│ ├── tool.execution_progress → Progress updates (ephemeral, repeated)
│ ├── tool.execution_complete → Tool finished
│ │
│ └── [Agent loops: more reasoning → message → tool calls...]
│
assistant.turn_end → Turn complete
session.idle → Ready for next message (ephemeral)
すべてのイベントの種類の概要
この表に、主要な data ペイロード フィールドを示します。 共通のエンベロープ フィールドについては、上記で説明しています。
| イベントの種類 | エフェメラル | Category | キー データ フィールド |
|---|---|---|---|
assistant.turn_start | |||
| 助手 | |||
turnId、interactionId? | |||
assistant.intent | ✅ | 助手 | intent |
assistant.reasoning | |||
| 助手 | |||
reasoningId、content | |||
assistant.reasoning_delta | ✅ | 助手 | |
reasoningId、deltaContent | |||
assistant.streaming_delta | ✅ | 助手 | total |
assistant.message | |||
| 助手 | |||
messageId、content、toolRequests?、outputTokens?、phase? | |||
assistant.message_delta | ✅ | 助手 | |
messageId、deltaContent | |||
assistant.turn_end | 助手 | turnId | |
assistant.usage | ✅ | 助手 | |
model、 apiEndpoint?、 inputTokens?、 outputTokens?、 cost?、 duration? | |||
tool.user_requested | |||
| ツール | |||
toolCallId、toolName、arguments? | |||
tool.execution_start | |||
| ツール | |||
toolCallId、toolName、arguments?、mcpServerName? | |||
tool.execution_partial_ | ✅ | ツール | |
toolCallId、partialOutput | |||
tool.shell_output | ✅ | ツール | |
toolCallId、text、stream?、sequence | |||
tool.execution_progress | ✅ | ツール | |
toolCallId、progressMessage | |||
tool.execution_complete | |||
| ツール | |||
toolCallId、success、result?、error? | |||
session.idle | ✅ | Session | aborted? |
session.error | |||
| Session | |||
errorType、message、statusCode? | |||
session.compaction_start | |||
| Session | |||
| (空) | |||
session.compaction_complete | |||
| Session | |||
success、pre、summaryContent? | |||
session.title_changed | ✅ | Session | title |
session.context_changed | |||
| Session | |||
cwd、gitRoot?、repository?、branch? | |||
session.usage_info | ✅ | Session | |
tokenLimit、currentTokens、messagesLength | |||
session.session_limits_ | Session | sessionLimits | |
session.usage_checkpoint | |||
| Session | |||
totalNanoAiu、total | |||
session.task_complete | Session | summary? | |
session.shutdown | |||
| Session | |||
shutdownType、codeChanges、modelMetrics | |||
permission.requested | |||
| 許可 | |||
requestId、permissionRequest | |||
permission.completed | |||
| 許可 | |||
requestId、result.kind | |||
user_input.requested | ✅ | ユーザー入力 | |
requestId、question、choices? | |||
user_input.completed | ✅ | ユーザー入力 | requestId |
elicitation.requested | ✅ | ユーザー入力 | |
requestId、message、requestedSchema | |||
elicitation.completed | ✅ | ユーザー入力 | requestId |
subagent.started | |||
| サブエージェント | |||
toolCallId、agentName、agentDisplayName、model? | |||
subagent.completed | |||
| サブエージェント | |||
toolCallId、agentName、agentDisplayName、model?、durationMs?、totalTokens?、totalToolCalls? | |||
subagent.failed | |||
| サブエージェント | |||
toolCallId、agentName、error、model?、durationMs?、totalTokens?、totalToolCalls? | |||
subagent.selected | |||
| サブエージェント | |||
agentName、agentDisplayName、tools | |||
subagent.deselected | |||
| サブエージェント | |||
| (空) | |||
skill.invoked | |||
| Skill | |||
name、path、content、allowedTools? | |||
abort | コントロール | reason | |
user.message | |||
| ユーザー | |||
content、attachments?、agentMode? | |||
system.message | |||
| System | |||
content、role | |||
external_tool.requested | |||
| 外部ツール | |||
requestId、toolName、arguments? | |||
external_tool.completed | 外部ツール | requestId | |
command.queued | ✅ | 命令 | |
requestId、command | |||
command.completed | ✅ | 命令 | requestId |
session_limits_ | ✅ | Session | |
requestId、maxAiCredits、usedAiCredits | |||
session_limits_ | ✅ | Session | |
requestId、response.action | |||
exit_plan_mode.requested | ✅ | プラン モード | |
requestId、summary、planContent、actions | |||
exit_plan_mode.completed | ✅ | プラン モード | requestId |