mirror of
https://github.com/adobe/skills.git
synced 2026-09-19 08:06:09 +08:00
c2a1c0a606
Helper (bin/aem-agentkit-helper):
- op_walk now re-checks resolved-realpath segments against the deny-list,
closing the in-workspace symlink bypass (e.g. safe-name -> .git/).
- op_write_atomic enforces the SKILL.md allow-list AND a per-segment
deny-list; helper is now the trust anchor for "no writes outside the
allow-list" instead of trusting the orchestrating LLM. Adds case-
insensitive FS collision detection and validate-before-makedirs
ancestor checks so a workspace symlink cannot redirect mkdir.
- op_open: fail-closed when the TOCTOU re-check is unavailable (returns
toctouVerified flag); opens the resolved realpath so legitimate
intra-workspace symlinks (pnpm, yarn workspaces) are no longer
rejected; bounded buffer read with actual-size diagnostic.
- op_lock: PID-0/negative-PID rejected as stale; PID-reuse defense via
start-time token; empty/corrupt lock files recovered; stale-lock
recovery is race-safe.
- op_cleanup_tmp: recovers orphan .tmp left by a crashed write-atomic
when the .tmp sits at an allow-listed path. Uses bounded walk with
realpath validation per entry.
- op_sha256_canonical: NFC-normalizes JSON string leaves so HFS+ (NFD)
and ext4/APFS (NFC) hash identically; accepts leading blank lines
before the Markdown marker so IDE auto-prettiers don't reclassify
generated files as human-curated.
- New ops/flags: protocol-version (skill version decoupled from wire
protocol), --self-test, stderr traceback on internal errors.
- Hardening: explicit POSIX allow-list, Python 3.10+ guard, /private/var/run
rejected on macOS, compiled deny-list regex, per-invocation op cap.
- _fd_realpath now uses stdlib fcntl.F_GETPATH on macOS (the prior
ctypes path failed on real macOS, silently disabling the TOCTOU check).
Tests (tests/test_helper.py, 27 -> 67 tests):
- Allow-list + deny-list enforcement on write-atomic (.git/hooks/, .env,
node_modules/, escape via intermediate symlink, opt-out flag).
- Lock empty/corrupt/PID-0/negative; two-live-invocation blocking
(AC 18 now actually exercised, not just manually verified).
- op_walk: symlink-deny-bypass regression (.git via in-workspace
symlink), per-subtree cap doesn't drop other roots, global cap,
depth cap, glob dialect.
- NFC/NFD stability, nested-marker preservation, marker-spoof recompute.
- TOCTOU toctouVerified, maxBytes with actual-size, intra-workspace
symlink open, match-deny ENOENT fallback (allowed + denied), orphan-
tmp recovery + post-recovery write.
- Generous subprocess timeouts with actionable assertion messages.
CI (.github/workflows/validate.yml):
- New test-aem-agentkit-helper job runs the helper unit suite on every
PR across Ubuntu + macOS / Python 3.10, 3.11, 3.12. Previously the
27 tests were documentation only; this makes them a real gate.
Test runner (tests/run-tests.sh):
- Guarded chmod (no working-tree mutation); prints both --version and
--protocol-version.
Docs:
- SKILL.md: all 13 generation steps numbered; self-validation failures
categorized (evidence-resolution, module-mismatch, marker-checksum,
url-scoping, strip-list-survivor, manifest-drift,
missing-subproject-context); new Threat Model section with in-scope
and explicitly out-of-scope (prompt-injection via raw bytes, supply-
chain helper tampering, Windows); allow-list documented as helper-
enforced; semantic-equivalence wording for role projections.
- 24 templates: replaced 1.0.0-beta literal with {{SKILL_VERSION}}
token so future version bumps don't require coordinated find/replace.
- AGENTS.module.core, AGENTS.module.ui.apps, AGENTS.subproject got a
"## After making changes" block instructing the agent to run
/regen-context. AGENTS.md is read at session start by every spec-
compliant agent, so the cross-skill index-mutation contract is
wired where it's actually consumed (rather than touching sibling
skill SKILL.md files).
- helpers.md: glob dialect explicit (fnmatch, not git-style **);
protocol-version vs skill-version separation; new write-atomic
behavior; cleanup-tmp orphan recovery.
- upgrade-and-migration.md: SHA-256 pin table with advisory->hard
graduation path; templates use {{SKILL_VERSION}}.
- privacy-and-sanitization.md § 2.2: raw bytes via op_open are NOT
sanitized; orchestrator's responsibility.
- collision-rules.md: dropped 1024-byte _disable_agentkit threshold;
added case-insensitive FS collision row.
- per-tool-artifacts.md § 7: semantic equivalence (not byte-identical)
across IDE projections.
- manifest.md: files[].mtime field for v2 incremental drift detection.
- codified-context.md: enterprise-scale cost disclosure.
- README.md: IDE detection signal table synced with SKILL.md.
All 67 tests pass on Python 3.14 (macOS Darwin 24.3).
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>