エージェントスキルを使うと、タスクに必要な指示と補助ファイルをまとめてエージェントに提供し、繰り返し利用できます。スキルは Responses API のシェルツールで使用することも、Agents API のサンドボックスに配置して利用することもできます。
以下のアップロード、アタッチ、バージョン管理の手順は、Responses API のシェルツールを対象としています。Agents API のセッションでは、サンドボックス内のディレクトリからスキルを検出します。
Responses API は、スキルのローカル実行とホスト型コンテナでの実行に対応しています。手元のマシンでコードを実行するには、シェルツールのローカル実行モードを使用します。
スキルは、SKILL.md マニフェスト(フロントマターと指示)と関連ファイルをまとめたディレクトリです。社内のスタイルガイドから複数のステップを含むワークフローまで、手順や規約をスキル単位で明文化できます。アップロードしたスキルは、バージョン付きのバンドルとして管理されます。
スキルは、オープンな Agent Skills 標準と互換性があります。
1
2
3
4
5
6---
name: basic-math
description: Add or multiply numbers.
---
Use this skill when you need a quick sum or product of numbers.
スキルを検出した段階で、モデルに提示されるのはスキルの名前と説明です。説明には、スキルで何ができるか、どのようなときに使うかの両方を記載してください。たとえば、「取引先との契約書をレビューし、代替条項を使って修正案を示す」と書くと、「法務を支援する」よりも、モデルが用途を判断しやすくなります。
主な指示は SKILL.md に記載し、必要に応じて補助ファイルへのリンクを追加します。
review-pr/
├── SKILL.md
├── references/
│ └── review-guidelines.md
├── scripts/
│ └── check-changes.sh
└── assets/
└── review-template.md
references/ には参考資料を、scripts/ には繰り返し実行する処理のスクリプトを、assets/ には再利用するテンプレートを配置します。
ディレクトリをマルチパートフォームデータとしてアップロードするか、最上位フォルダーを 1 つだけ含む .zip ファイルをアップロードできます。
複数の files[] パートをアップロードします。各パートには、共通の最上位フォルダー内でのファイルのパスを含めます。
1
2
3
4curl -X POST 'https://api.openai.com/v1/skills' \
-H "Authorization: Bearer $OPENAI_API_KEY" \
-F 'files[]=@./basic_math/SKILL.md;filename=basic_math/SKILL.md;type=text/markdown' \
-F 'files[]=@./basic_math/calculate.py;filename=basic_math/calculate.py;type=text/plain'
最上位フォルダーを zip 形式で圧縮し、作成した zip ファイルをアップロードします。
1
2
3curl -X POST 'https://api.openai.com/v1/skills' \
-H "Authorization: Bearer $OPENAI_API_KEY" \
-F 'files=@./basic_math.zip;type=application/zip'
新しいバージョンをアップロードしてから利用可能になるまでの短い間、そのバージョンへのリクエストが 404 を返すことがあります。コンテナまたは Live セッションにアタッチする前に、GET /v1/skills/{skill_id}/versions/{version} で取得してください。アップロードの成功直後に取得リクエストが 404 を返した場合は、タイムアウトを設定し、短い待機時間を挟んで再試行します。取得に成功したら、返されたバージョン文字列をスキル参照に指定します。
ホスト型シェル環境にスキルをマウントするには、シェルツールを呼び出す際に tools[].environment.skills でスキルをアタッチします。
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19curl -L 'https://api.openai.com/v1/responses' \
-H "Content-Type: application/json" \
-H "Authorization: Bearer $OPENAI_API_KEY" \
-d '{
"model": "gpt-6-astra",
"tools": [
{
"type": "shell",
"environment": {
"type": "container_auto",
"skills": [
{ "type": "skill_reference", "skill_id": "<skill_id>" },
{ "type": "skill_reference", "skill_id": "<skill_id>", "version": "2" }
]
}
}
],
"input": "Use the skills to add 144 and 377, then compute triangle area with base 9 height 13."
}'
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23import OpenAI from "openai";
const client = new OpenAI();
const response = await client.responses.create({
model: "gpt-6-astra",
tools: [
{
type: "shell",
environment: {
type: "container_auto",
skills: [
{ type: "skill_reference", skill_id: "<skill_id>" },
{ type: "skill_reference", skill_id: "<skill_id>", version: "2" },
],
},
},
],
input:
"Use the skills to add 144 and 377, then compute triangle area with base 9 height 13.",
});
console.log(response.output_text);
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22response = client.responses.create(
model="gpt-6-astra",
tools=[
{
"type": "shell",
"environment": {
"type": "container_auto",
"skills": [
{"type": "skill_reference", "skill_id": "<skill_id>"},
{
"type": "skill_reference",
"skill_id": "<skill_id>",
"version": "2",
},
],
},
}
],
input="Use the skills to add 144 and 377, then compute triangle area with base 9 height 13.",
)
print(response.output_text)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30package main
import (
"context"
"fmt"
"github.com/openai/openai-go/v3"
"github.com/openai/openai-go/v3/responses"
)
func main() {
client := openai.NewClient()
tool := responses.ToolUnionParam{OfShell: &responses.FunctionShellToolParam{
Environment: responses.FunctionShellToolEnvironmentUnionParam{OfContainerAuto: &responses.ContainerAutoParam{
Skills: []responses.ContainerAutoSkillUnionParam{
{OfSkillReference: &responses.SkillReferenceParam{SkillID: "<skill_id>"}},
{OfSkillReference: &responses.SkillReferenceParam{SkillID: "<skill_id>", Version: openai.String("2")}},
},
}},
}}
response, err := client.Responses.New(context.Background(), responses.ResponseNewParams{
Model: "gpt-6-astra",
Tools: []responses.ToolUnionParam{tool},
Input: responses.ResponseNewParamsInputUnion{OfString: openai.String("Use the skills to add 144 and 377, then compute triangle area with base 9 height 13.")},
})
if err != nil {
panic(err)
}
fmt.Println(response.OutputText())
}
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39import com.openai.client.OpenAIClient;
import com.openai.client.okhttp.OpenAIOkHttpClient;
import com.openai.core.JsonValue;
import com.openai.models.responses.ResponseCreateParams;
import java.util.List;
import java.util.Map;
String skillId = "<skill_id>";
ResponseCreateParams params =
ResponseCreateParams.builder()
.model("gpt-6-astra")
.input(
"Use the skills to add 144 and 377, then compute a triangle area with base 9 and height 13.")
.putAdditionalBodyProperty(
"tools",
JsonValue.from(
List.of(
Map.of(
"type",
"shell",
"environment",
Map.of(
"type",
"container_auto",
"skills",
List.of(
Map.of("type", "skill_reference", "skill_id", skillId),
Map.of(
"type", "skill_reference",
"skill_id", skillId,
"version", "2")))))))
.build();
client.responses().create(params).output().stream()
.flatMap(item -> item.message().stream())
.flatMap(message -> message.content().stream())
.flatMap(content -> content.outputText().stream())
.forEach(text -> System.out.println(text.text()));
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28require "openai"
client = OpenAI::Client.new
response = client.responses.create(
model: "gpt-6-astra",
input: "Use the skills to add 144 and 377, then compute a triangle area with base 9 and height 13.",
tools: [
{
type: :shell,
environment: {
type: :container_auto,
skills: [
{
type: :skill_reference,
skill_id: "<skill_id>"
},
{
type: :skill_reference,
skill_id: "<skill_id>",
version: "2"
}
]
}
}
]
)
puts(response.output_text)
スキルをマウントすると、モデルはいつ使うかを自ら判断できます。スキルを使うタイミングをより確実に制御したい場合は、必要な場面で「<skill name> スキルを使ってください」とモデルに明示的に指示します。
スキルはローカルシェルモードでも利用できます。ただし、ローカルシェルとホスト型シェルでは、対応するスキルのアタッチ形式が異なります。
- ホスト型シェルでは、アップロード済みのスキルを
skill_reference でアタッチできます。厳選スキルの参照やバージョンの明示的な指定にも対応しています。
- ローカルシェルは
skill_reference によるアタッチに対応していません。自身で管理するランタイム内のローカルファイルパスを使って、スキルのファイルを提供してください。
ローカルシェルでの実行について詳しくは、シェルガイドを参照してください。
JavaScript のサンプルを実行するには、Node.js と起動済みの Docker デーモンが必要です。相対パスでインポートできるように、Docker アダプターを support/local-skill-sandbox.mjs に、サンプルを tools/skills/local-shell.mjs に保存します。OPENAI_API_KEY を設定したら、support と tools があるディレクトリで次のコマンドを実行し、SDK のインストール、アダプターでバージョンを固定したイメージの取得、サンプルの実行を順に行います。
123npm install openai
docker pull "$(node --input-type=module -e 'import { sandboxImage } from "./support/local-skill-sandbox.mjs"; console.log(sandboxImage)')"
node tools/skills/local-shell.mjs
アダプターの各ヘルパーが担う処理は次のとおりです。
| ヘルパー |
アプリケーション側で行う処理 |
withLocalSkillSandbox(name, workflow) |
/workspace/skills/csv-insights/SKILL.md と /workspace/reports.csv を含む隔離された Python 環境を作成します。workflow を呼び出す際に AbortSignal を渡し、ワークフローが終了したら環境を削除します。 |
executeShellCall(name, call, signal) |
その環境内で要求されたコマンドを実行し、shell_call_output を返します。これには元の call_id、標準出力、標準エラー出力、およびコマンドの終了結果またはタイムアウトの情報を含めます。 |
readSkillReport(name, signal) |
環境内に生成された /workspace/report.md を、読み取りサイズに上限を設けて読み込みます。 |
アダプターでは、実行時間と出力量の上限を必ず適用してください。このサンプルでは、生成されたコマンドは隔離されたランタイム内でのみ実行されます。
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22curl -L 'https://api.openai.com/v1/responses' \
-H "Content-Type: application/json" \
-H "Authorization: Bearer $OPENAI_API_KEY" \
-d '{
"model": "gpt-6-astra",
"tools": [
{
"type": "shell",
"environment": {
"type": "local",
"skills": [
{
"name": "csv-insights",
"description": "Summarize CSV files and produce a markdown report.",
"path": "<path-to-skill-folder>"
}
]
}
}
],
"input": "Use the csv-insights skill and run locally to summarize today\'s CSV reports in this repo."
}'
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56import { randomUUID } from "node:crypto";
import OpenAI from "openai";
import {
withLocalSkillSandbox,
executeShellCall,
readSkillReport,
} from "../../support/local-skill-sandbox.mjs";
// Requires Docker. The application-owned helper prepares a disposable Python
// sandbox with the skill and CSV files; generated commands run only inside it.
const name = "node-skill-" + randomUUID();
await withLocalSkillSandbox(name, async (signal) => {
const client = new OpenAI();
/** @type {OpenAI.Responses.ResponseCreateParamsNonStreaming} */
const params = {
model: "gpt-6-astra",
tools: [
{
type: "shell",
environment: {
type: "local",
skills: [
{
name: "csv-insights",
description: "Summarize CSV files and produce a markdown report.",
path: "/workspace/skills/csv-insights",
},
],
},
},
],
input:
"Use the csv-insights skill and run locally to summarize /workspace/reports.csv. Read the skill instructions, write /workspace/report.md, and include the total in your final answer.",
};
for (let turn = 0; turn <= 8; turn++) {
const response = await client.responses.create(params, { signal });
if (response.status !== "completed")
throw new Error(`Response ended with status ${response.status}`);
const results = [];
for (const item of response.output) {
if (item.type !== "shell_call") continue;
if (turn === 8)
throw new Error("Shell workflow exceeded eight tool turns");
results.push(await executeShellCall(name, item, signal));
}
if (results.length === 0) {
console.log(response.output_text);
console.log("Report:\n" + (await readSkillReport(name, signal)));
return;
}
params.previous_response_id = response.id;
params.input = results;
}
throw new Error("Shell workflow exceeded eight turns");
});
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22response = client.responses.create(
model="gpt-6-astra",
tools=[
{
"type": "shell",
"environment": {
"type": "local",
"skills": [
{
"name": "csv-insights",
"description": "Summarize CSV files and produce a markdown report.",
"path": "<path-to-skill-folder>",
}
],
},
}
],
input="Use the csv-insights skill and run locally to summarize today's CSV reports in this repo.",
)
# Execute returned shell calls locally and submit their shell_call_output to continue.
print(response.output)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55// The surrounding program prepares an isolated sandbox with the skill files.
client := openai.NewClient()
tool := responses.ToolUnionParam{OfShell: &responses.FunctionShellToolParam{
Environment: responses.FunctionShellToolEnvironmentUnionParam{
OfLocal: &responses.LocalEnvironmentParam{
Skills: []responses.LocalSkillParam{{
Name: "csv-insights",
Description: "Summarize CSV files and produce a markdown report.",
Path: "/workspace/skills/csv-insights",
}},
},
},
}}
params := responses.ResponseNewParams{
Model: "gpt-6-astra",
Tools: []responses.ToolUnionParam{tool},
Input: responses.ResponseNewParamsInputUnion{OfString: openai.String(
"Use the csv-insights skill and run locally to summarize /workspace/reports.csv. Read the skill instructions, write /workspace/report.md, and include the total in your final answer.")},
}
for turn := 0; turn <= 8; turn++ {
response, err := client.Responses.New(ctx, params)
if err != nil {
return err
}
if response.Status != responses.ResponseStatusCompleted {
return fmt.Errorf("response ended with status %s", response.Status)
}
results := responses.ResponseInputParam{}
for _, item := range response.Output {
if item.Type != "shell_call" {
continue
}
if turn == 8 {
return fmt.Errorf("shell workflow exceeded eight tool turns")
}
result, err := executeShellCall(ctx, name, item.AsShellCall())
if err != nil {
return err
}
results = append(results, result)
}
if len(results) == 0 {
fmt.Println(response.OutputText())
// Read the artifact without executing generated code outside the container.
report, err := readReport(ctx, name)
if err != nil {
return fmt.Errorf("read generated report: %w", err)
}
fmt.Printf("Report:\n%s\n", report)
return nil
}
params.PreviousResponseID = openai.String(response.ID)
params.Input = responses.ResponseNewParamsInputUnion{OfInputItemList: results}
}
return fmt.Errorf("shell workflow exceeded eight turns")
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38import com.openai.client.OpenAIClient;
import com.openai.client.okhttp.OpenAIOkHttpClient;
import com.openai.core.JsonValue;
import com.openai.models.responses.ResponseCreateParams;
import java.util.List;
import java.util.Map;
String skillPath = "<path-to-skill-folder>";
ResponseCreateParams params =
ResponseCreateParams.builder()
.model("gpt-6-astra")
.input("Use the csv-insights skill to summarize today's CSV reports.")
.putAdditionalBodyProperty(
"tools",
JsonValue.from(
List.of(
Map.of(
"type",
"shell",
"environment",
Map.of(
"type",
"local",
"skills",
List.of(
Map.of(
"name", "csv-insights",
"description",
"Summarize CSV files and produce a Markdown report.",
"path", skillPath)))))))
.build();
client.responses().create(params).output().stream()
.flatMap(item -> item.message().stream())
.flatMap(message -> message.content().stream())
.flatMap(content -> content.outputText().stream())
.forEach(text -> System.out.println(text.text()));
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52require "openai"
require "open3"
require "securerandom"
# LocalSkillSandbox is the application-owned Docker executor defined in this
# complete example. It prepares the skill files, bounds execution, and cleans up.
def run_local_skill(name)
sandbox = LocalSkillSandbox.new(name)
begin
# Reserve teardown before creation, even if Docker creation is interrupted.
sandbox.prepare
client = OpenAI::Client.new(max_retries: 0)
params = {
model: "gpt-6-astra",
input: "Use the csv-insights skill and run locally to summarize /workspace/reports.csv. Read the skill instructions, write /workspace/report.md, and include the total in your final answer.",
tools: [
{
type: :shell,
environment: {
type: :local,
skills: [
{
name: "csv-insights",
description: "Summarize CSV files and produce a Markdown report.",
path: "/workspace/skills/csv-insights"
}
]
}
}
]
}
9.times do |turn|
response = client.responses.create(**params, request_options: { timeout: sandbox.remaining })
raise "Response did not complete" unless response.status == OpenAI::Responses::ResponseStatus::COMPLETED
calls = response.output.grep(OpenAI::Models::Responses::ResponseFunctionShellToolCall)
if calls.empty?
puts(response.output_text)
puts("Report:\n#{sandbox.report}")
return response
end
raise "Shell workflow exceeded eight tool turns" if turn == 8
params[:input] = calls.map { |call| sandbox.execute(call) }
params[:previous_response_id] = response.id
end
ensure
sandbox.close
end
end
run_local_skill("ruby-skill-#{SecureRandom.hex(8)}")
Agents API でスキルを使うには、サンドボックス内にスキルのディレクトリを配置し、セッションの作成時にその親ディレクトリを environment.capability_directories に登録します。登録した親ディレクトリを機能ディレクトリと呼びます。ハーネスはこれらのディレクトリからスキルを検出します。この構成では、ホスト型シェルの skill_reference アタッチ形式は使用しません。
たとえば、契約書のレビュー用スキルと Pull Request のレビュー用スキルを、サンドボックス内に次のように配置します。
/workspace/capabilities/
├── legal/
│ └── contract-redline/
│ ├── SKILL.md
│ └── references/
│ └── fallback-clauses.md
└── engineering/
└── review-pr/
├── SKILL.md
└── references/
└── review-guidelines.md
セッション作成リクエストでは、次の環境設定を指定します。
12345678910{
"environment": {
"type": "self_hosted",
"workspace_directory": "/workspace",
"capability_directories": [
"/workspace/capabilities/legal",
"/workspace/capabilities/engineering"
]
}
}
機能ディレクトリには次の要件があります。
- パスはサンドボックス内のディレクトリを指している必要があります。
- 各パスは一意の絶対パスである必要があり、パスの構成要素に
. や .. は使用できません。
- 1 つのセッションに登録できる機能ディレクトリは最大 32 個です。
- ディレクトリはあらかじめ環境内に作成しておく必要があります。
サンドボックスが利用可能になると、ハーネスはこれらのディレクトリ内で SKILL.md ファイルを検索し、検出した各スキルの名前と説明をコンテキストに追加します。モデルはタスクに合うスキルを選び、指示の全文と補助ファイルを読み込むことができます。
セッションの設定についてはエージェントの設定を、実行環境についてはサンドボックスの接続を参照してください。スキルをエージェントに提供する前に、スキルとその補助ファイルの内容を確認し、サンドボックスのセキュリティガイドに従ってください。
Responses API のシェルツールでは、モデルが利用可能なスキルを把握できるよう、プラットフォームが各スキルの name、description、path をユーザープロンプトのコンテキストに追加します。
モデルはこのメタデータを基にスキルを呼び出すかどうかを判断します。スキルを呼び出す場合は、path を使って SKILL.md から Markdown 形式の指示をすべて読み込みます。
スキルの指示は、システムプロンプトではなくユーザープロンプトの入力として扱われるため、ユーザーが指定する他の指示と同じ優先順位になります。使用するスキルを明示的に指定するには、モデルに「<skill name> スキルを使ってください」と指示できます。
SKILL.md のファイル名の照合では、大文字と小文字を区別しません。
- 各スキルバンドルには、
skill.md/SKILL.md ファイルを必ず 1 つだけ含めてください。
- スキルのフロントマターは、Agent Skills の仕様に従って検証されます。
- アップロードできる zip ファイルのサイズは最大
50 MB です。
- スキルの各バージョンに含められるファイルは最大
500 個です。
- 圧縮前の各ファイルのサイズは最大
25 MB です。
Responses API で使用するスキルはすべて、事前に内容を確認してください。スキルには、プロンプトインジェクションによるデータの不正な持ち出しなどのセキュリティリスクがあります。このツールを使う前に、後述のリスクと安全対策をよく確認してください。
- バージョンを指定しない場合は
default_version が使われます。
latest_version は、最後にアップロードしたバージョンを指します。
skill_reference.version には、"2" や "latest" などのバージョン文字列を指定できます。
default_version を更新する際も、値は文字列で指定する必要があります。
1
2
3curl -X POST 'https://api.openai.com/v1/skills/<skill_id>/versions' \
-H "Authorization: Bearer $OPENAI_API_KEY" \
-F 'files=@./geometry.zip;type=application/zip'
1
2
3
4curl -X POST 'https://api.openai.com/v1/skills/<skill_id>' \
-H "Content-Type: application/json" \
-H "Authorization: Bearer $OPENAI_API_KEY" \
-d '{"default_version": "2"}'
- デフォルトバージョンは削除できません。先に別のバージョンをデフォルトに設定してください。
- 最後に残ったバージョンを削除すると、スキル自体も削除されます。
- スキルを削除すると、そのすべてのバージョンも削除されます。
OpenAI は、ID(例:openai-spreadsheets)で参照できる自社製スキルを管理しています。
{ "type": "skill_reference", "skill_id": "openai-spreadsheets", "version": "latest" }
ホスト型スキルを作成せずに利用する場合は、環境の skills 配列に base64 でエンコードした zip バンドルを直接埋め込むことができます。
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20INLINE_ZIP=$(base64 -i ./basic_math.zip)
curl -L 'https://api.openai.com/v1/containers' \
-H "Content-Type: application/json" \
-H "Authorization: Bearer $OPENAI_API_KEY" \
-d '{
"name": "inline-skill-container",
"skills": [
{
"type": "inline",
"name": "basic_math",
"description": "Add or multiply numbers.",
"source": {
"type": "base64",
"media_type": "application/zip",
"data": "'"$INLINE_ZIP"'"
}
}
]
}'
Responses API で使用するスキルはすべて、事前に内容を確認することが重要です。スキルには、プロンプトインジェクションによるデータの不正な持ち出しなどのセキュリティリスクがあります。
スキルをネットワークアクセスと組み合わせて使う場合は、ネットワーク利用時のリスクと安全対策をよく確認してください。
スキルの内容は、モデルの計画、ツールの使用、コマンドの実行に影響する可能性があります。開発者が検証するまでは、どのスキルも信頼できるとは限らない入力として扱い、内容を確認してください。
一般のエンドユーザーが公開カタログを自由に閲覧し、任意のスキルを選択したりアタッチしたりできる製品設計は避けてください。このような設計では、次のリスクが大幅に高まります。
- 悪意のある SKILL.md の指示によるプロンプトインジェクションやポリシーの回避
- 未検証の自動処理によるデータの不正な持ち出しや破壊的な操作
開発者がスキルを確認して製品に組み込み、エンドユーザーには用途を限定した製品機能を通じてのみ提供してください。具体的には、次の対策を取ります。
- スキルを製品の特定のワークフローやユースケースに対応付けます。
- エンドユーザーが任意のスキルを自由に選択できないようにします。
- 書き込み操作や影響の大きい操作は、明示的な承認を得てポリシーチェックを通過した場合にのみ実行できるようにします。
書き込み操作や影響の大きい操作を行えるワークフローでは、実行前に明示的な承認を必須としてください。
Responses API は、スキルのローカル実行とホスト型コンテナでの実行に対応しています。ホスト型スキルのライフサイクルは、ホスト型シェルのコンテナと同じです。マウントしたスキルとコンテナ内のファイルは、コンテナがアクティブな間は利用でき、有効期限が切れるかコンテナが削除されると破棄されます。すべての処理を自身で管理するインフラ上で実行したい場合は、ローカルシェルモードを使用してください。Agents API のサンドボックスについては、サンドボックスのライフサイクルを参照してください。OpenAI のデータ管理についてもご覧ください。