From afb0f07f14ec599ac7d75f7a8aafe8895d4dd390 Mon Sep 17 00:00:00 2001 From: hardness1020 Date: Fri, 29 May 2026 15:51:50 -0700 Subject: [PATCH] docs(s07_skill_loading): note SKILL.md can guide later resource access via file/bash tools --- s07_skill_loading/README.en.md | 10 +++++----- s07_skill_loading/README.ja.md | 12 ++++++------ s07_skill_loading/README.md | 10 +++++----- 3 files changed, 16 insertions(+), 16 deletions(-) diff --git a/s07_skill_loading/README.en.md b/s07_skill_loading/README.en.md index eb76756..35399dd 100644 --- a/s07_skill_loading/README.en.md +++ b/s07_skill_loading/README.en.md @@ -37,7 +37,7 @@ Two-level design: | Level | Location | Timing | Cost | |-------|----------|--------|------| | 1. Catalog | system prompt | Injected at startup (harness scans skills/) | ~100 tokens/skill, carried every turn | -| 2. Content | tool_result | When Agent calls load_skill | ~2000 tokens/skill, on demand | +| 2. Content | tool_result | When Agent calls load_skill; SKILL.md can guide later read_file/bash access to extra resources | ~2000 tokens/skill, on demand | The dispatch mechanism is unchanged, `load_skill` auto-dispatches via `TOOL_HANDLERS[block.name]`. @@ -90,7 +90,7 @@ def build_system() -> str: SYSTEM = build_system() ``` -**Level 2: load_skill**: the Agent decides "I need the SQL style guide" and calls `load_skill("sql-style")`. Lookup goes through the registry, not file paths, eliminating path traversal risk. The content is injected via `tool_result`: +**Level 2: load_skill**: the Agent decides "I need the SQL style guide" and calls `load_skill("sql-style")`. Lookup goes through the registry, not file paths, eliminating path traversal risk. The SKILL.md content is injected via `tool_result`, and can include later access to referenced `references/`, `scripts/`, or `assets/` through the existing file and bash tools. ```python def load_skill(name: str) -> str: @@ -109,7 +109,7 @@ The key distinction: skill content is not part of the system prompt. It enters t | Component | Before (s06) | After (s07) | |-----------|-------------|-------------| | Tool count | 7 (bash, read, write, edit, glob, todo_write, task) | 8 (+load_skill) | -| Knowledge loading | None | Two-level: startup catalog in SYSTEM + runtime load_skill | +| Knowledge loading | None | Two-level: startup catalog in SYSTEM + runtime load_skill; SKILL.md may guide later resource access | | SYSTEM prompt | Static string | Startup scan of skills/ injects catalog | | Skill registry | None | SKILL_REGISTRY (populated at startup, prevents path traversal) | | Loop | Unchanged | Unchanged (skill tool auto-dispatches) | @@ -168,7 +168,7 @@ The complete field list changes across versions; above are the core fields relev ### 3. Precise Implementation of Two-Level Loading 1. **Catalog (at startup)**: `getSkillDirCommands()` scans directory → registers as `Command` objects containing only metadata. `getSkillListingAttachments()` formats the skill list as attachments, budgeted at ~1% of the context window (cap 8000 characters). -2. **Load (on invocation)**: Model calls `Skill` tool (input fields are `skill` + optional `args`; teaching version uses `name`) → `getPromptForCommand()` expands full SKILL.md content → `SkillTool` returns a tool_result with display text `"Launching skill: {name}"`, while the actual skill content is injected via `newMessages`. The teaching version merges both into "injected via tool_result" as a simplification. +2. **Load (on invocation)**: Model calls `Skill` tool (input fields are `skill` + optional `args`; teaching version uses `name`) → `getPromptForCommand()` expands full SKILL.md content → `SkillTool` returns a tool_result with display text `"Launching skill: {name}"`, while the actual skill content is injected via `newMessages`. The teaching version merges both into "injected via tool_result" as a simplification; the loaded SKILL.md can still guide later access to referenced resources through existing file/bash tools. ### The Teaching Version's Simplification Is Intentional @@ -179,4 +179,4 @@ The complete field list changes across versions; above are the core fields relev - + diff --git a/s07_skill_loading/README.ja.md b/s07_skill_loading/README.ja.md index e38afaa..7e12baa 100644 --- a/s07_skill_loading/README.ja.md +++ b/s07_skill_loading/README.ja.md @@ -37,7 +37,7 @@ SYSTEM = ( | 層 | 場所 | タイミング | コスト | |---|------|-----------|--------| | 1. カタログ | system prompt | 起動時に注入(harness が skills/ をスキャン) | ~100 トークン/スキル、毎ターン携帯 | -| 2. 内容 | tool_result | Agent が load_skill を呼び出したとき | ~2000 トークン/スキル、オンデマンド | +| 2. 内容 | tool_result | Agent が load_skill を呼び出したとき。SKILL.md は、必要に応じて read_file/bash で追加リソースへアクセスするための手がかりになる | ~2000 トークン/スキル、オンデマンド | ディスパッチ機構は変わらず、`load_skill` は `TOOL_HANDLERS[block.name]` を通じて自動的にディスパッチされる。 @@ -90,7 +90,7 @@ def build_system() -> str: SYSTEM = build_system() ``` -**第 2 層:load_skill**:Agent が「SQL スタイルガイドが必要」と判断し、`load_skill("sql-style")` を呼び出す。レジストリを通じて検索し、ファイルパスを経由しないため、パストラバーサルのリスクがない。内容は `tool_result` を通じて注入される: +**第 2 層:load_skill**:Agent が「SQL スタイルガイドが必要」と判断し、`load_skill("sql-style")` を呼び出す。レジストリを通じて検索し、ファイルパスを経由しないため、パストラバーサルのリスクがない。SKILL.md の内容は `tool_result` を通じて注入され、既存の file および bash ツールを通じて、参照される `references/`、`scripts/`、`assets/` へのその後のアクセスも含められる。 ```python def load_skill(name: str) -> str: @@ -109,7 +109,7 @@ def load_skill(name: str) -> str: | コンポーネント | 変更前 (s06) | 変更後 (s07) | |---------------|-------------|-------------| | ツール数 | 7 (bash, read, write, edit, glob, todo_write, task) | 8 (+load_skill) | -| 知識読み込み | なし | 2 層:起動時カタログ注入 SYSTEM + 実行時 load_skill | +| 知識読み込み | なし | 2 層:起動時カタログ注入 SYSTEM + 実行時 load_skill。SKILL.md がその後のリソースアクセスを案内できる | | SYSTEM プロンプト | 静的文字列 | 起動時に skills/ をスキャンしてカタログ注入 | | スキルレジストリ | なし | SKILL_REGISTRY(起動時に充填、パストラバーサル防止) | | ループ | 変更なし | 変更なし(スキルツールは自動ディスパッチ) | @@ -168,15 +168,15 @@ CC の SKILL.md YAML frontmatter は `parseSkillFrontmatterFields()`(`loadSkil ### 三、2 層読み込みの正確な実装 1. **カタログ(起動時)**:`getSkillDirCommands()` がディレクトリをスキャン → メタデータのみを含む `Command` オブジェクトとして登録。`getSkillListingAttachments()` がスキルリストを添付ファイルとしてフォーマット、コンテキストウィンドウの ~1% を予算とする(上限 8000 文字)。 -2. **読み込み(呼び出し時)**:モデルが `Skill` ツールを呼び出す(入力フィールドは `skill` + オプションの `args`、教育版は `name` を使用)→ `getPromptForCommand()` が完全な SKILL.md 内容を展開 → `SkillTool` が返す tool_result の表示テキストは `"Launching skill: {name}"` のみ、実際のスキル内容は `newMessages` を通じて注入される。教育版では両者を「tool_result を通じて注入」として簡略化している。 +2. **読み込み(呼び出し時)**:モデルが `Skill` ツールを呼び出す(入力フィールドは `skill` + オプションの `args`、教育版は `name` を使用)→ `getPromptForCommand()` が完全な SKILL.md 内容を展開 → `SkillTool` が返す tool_result の表示テキストは `"Launching skill: {name}"` のみ、実際のスキル内容は `newMessages` を通じて注入される。教育版では両者を「tool_result を通じて注入」として簡略化している。読み込まれた SKILL.md は、モデルが後続で既存の file/bash ツールから関連リソースへアクセスする際の手がかりにもなる。 ### 教育版の単純化は意図的 - 複数ファイル・複数ソース → 1 つの `skills/` ディレクトリ:2 層読み込みの核心概念を示すのに十分 - 複数の frontmatter フィールド → name/description のみ解析:解析の複雑さを削減 -- forked skills(`context: 'fork'`)→ 省略:教学版では inline skill loading のみ展開する +- forked skills(`context: 'fork'`)→ 省略:教育版では inline skill loading のみ展開する - `Skill` ツールの入力 `skill`+`args` → 教育版は `name` を使用:追加の引数解析の複雑さを回避 - + diff --git a/s07_skill_loading/README.md b/s07_skill_loading/README.md index 86be90e..8b53c76 100644 --- a/s07_skill_loading/README.md +++ b/s07_skill_loading/README.md @@ -37,7 +37,7 @@ SYSTEM = ( | 层 | 位置 | 时机 | 代价 | |---|------|------|------| | 1. 目录 | system prompt | 启动时注入(harness 扫描 skills/) | ~100 tokens/skill,每轮都带 | -| 2. 内容 | tool_result | Agent 调用 load_skill 时 | ~2000 tokens/skill,按需 | +| 2. 内容 | tool_result | Agent 调用 load_skill 时;SKILL.md 可指引后续的 read_file/bash 调用,用于按需访问额外资源 | ~2000 tokens/skill,按需 | dispatch 机制不变,load_skill 通过 `TOOL_HANDLERS[block.name]` 分发。 @@ -90,7 +90,7 @@ def build_system() -> str: SYSTEM = build_system() ``` -**第二级:load_skill**:Agent 决定"我需要 SQL 风格指南",调用 `load_skill("sql-style")`。通过注册表查找,不走文件路径,没有路径遍历风险。内容通过 `tool_result` 注入: +**第二级:load_skill**:Agent 决定"我需要 SQL 风格指南",调用 `load_skill("sql-style")`。通过注册表查找,不走文件路径,没有路径遍历风险。SKILL.md 内容通过 `tool_result` 注入,并可通过现有的 file 和 bash 工具进一步访问引用的 `references/`、`scripts/` 或 `assets/`。 ```python def load_skill(name: str) -> str: @@ -109,7 +109,7 @@ def load_skill(name: str) -> str: | 组件 | 之前 (s06) | 之后 (s07) | |------|-----------|-----------| | 工具数量 | 7 (bash, read, write, edit, glob, todo_write, task) | 8 (+load_skill) | -| 知识加载 | 无 | 两级:启动时目录注入 SYSTEM + 运行时 load_skill | +| 知识加载 | 无 | 两级:启动时目录注入 SYSTEM + 运行时 load_skill;SKILL.md 可指引后续资源访问 | | SYSTEM 提示 | 静态字符串 | 启动时扫描 skills/ 注入目录 | | 技能注册表 | 无 | SKILL_REGISTRY(启动时填充,防路径遍历) | | 循环 | 不变 | 不变(skill 工具自动分发) | @@ -168,7 +168,7 @@ CC 的 SKILL.md YAML frontmatter 由 `parseSkillFrontmatterFields()` 解析(`l ### 三、两级加载的精确实现 1. **Catalog(启动时)**:`getSkillDirCommands()` 扫描目录 → 注册为 `Command` 对象,只包含元数据。`getSkillListingAttachments()` 把技能列表格式化为附件,预算为上下文窗口的 ~1%(上限 8000 字符)。 -2. **Load(调用时)**:模型调 `Skill` 工具(输入字段是 `skill` + 可选 `args`,教学版用 `name`)→ `getPromptForCommand()` 展开完整 SKILL.md 内容 → `SkillTool` 返回的 tool_result 展示文本只是 `"Launching skill: {name}"`,真正的技能内容通过 `newMessages` 注入对话。教学版把两者合并为"通过 tool_result 注入"是一种简化。 +2. **Load(调用时)**:模型调 `Skill` 工具(输入字段是 `skill` + 可选 `args`,教学版用 `name`)→ `getPromptForCommand()` 展开完整 SKILL.md 内容 → `SkillTool` 返回的 tool_result 展示文本只是 `"Launching skill: {name}"`,真正的技能内容通过 `newMessages` 注入对话。教学版把两者合并为"通过 tool_result 注入"是一种简化;加载后的 SKILL.md 仍可作为指引,帮助模型后续通过现有 file/bash 工具访问相关资源。 ### 教学版的简化是刻意的 @@ -179,4 +179,4 @@ CC 的 SKILL.md YAML frontmatter 由 `parseSkillFrontmatterFields()` 解析(`l - +