Skip to content

Keep the agent skill fresh across upgrades and script-drive Homebrew updates#57

Merged
faustodavid merged 4 commits into
mainfrom
feature/secure-homebrew-tap-ci
Jun 10, 2026
Merged

Keep the agent skill fresh across upgrades and script-drive Homebrew updates#57
faustodavid merged 4 commits into
mainfrom
feature/secure-homebrew-tap-ci

Conversation

@faustodavid

@faustodavid faustodavid commented Jun 10, 2026

Copy link
Copy Markdown
Owner

Summary

Skill freshness (auto-update on brew upgrade):

  • Copy-mode skill syncs write a .smith-skill-meta.json marker (source path + smith version) so smith-managed copies are distinguishable from hand-rolled directories.
  • New ensure_skill_fresh() runs on CLI startup, throttled to once/24h (SMITH_SKILL_CHECK=0 kill switch). It silently re-syncs stale marker-bearing copies and repairs broken symlinks, printing one stderr line. Unmanaged directories only get a hint — smith never deletes content it didn't write. Working symlinks are never touched (they already track upgrades via Homebrew's opt path, and devs deliberately link repo checkouts).
  • sync_skill now swaps via a staged copy: a mid-copy failure restores the previous install instead of leaving a partial one.
  • scripts/install.py delegates to smith skill sync (locating fresh installs via uv tool dir --bin), so all install paths share one sync implementation.

Homebrew release plumbing:

  • update_homebrew_formula.py owns the canonical bootstrap build-backend list (--print-extra-packages, --sync-bootstrap-resources with resource-stanza validation) and pins GitHub release tarballs via --sha256, parsing both the old git pin and new tarball pin forms.
  • The release validation workflow dispatches the tap's Update Smith Formula workflow with HOMEBREW_TAP_DISPATCH_TOKEN (fine-grained PAT, Actions r/w on the tap only — no contents write), falling back to the manual-handoff message when the secret is absent.
  • Version bumped to 0.1.3: the tap workflow runs this script from the release tag, so the new flags activate at this release (pairs with faustodavid/homebrew-tap branch workflow-script-driven-update).

Test plan

  • make check passes (lint, format, mypy, 790+ unit/contract tests with coverage gates, skill validation).
  • End-to-end simulation: stale copy auto-refreshed once with a single stderr line, throttled silence on the next run, kill switch honored, unmanaged directory left untouched.
  • New script modes round-tripped against the real tap formula (ruby -c clean).

faustodavid and others added 2 commits June 7, 2026 21:29
…pdates

Skill freshness:
- Copy-mode skill syncs write a .smith-skill-meta.json marker recording the
  source and smith version, so smith-managed copies are distinguishable from
  hand-rolled directories.
- ensure_skill_fresh() runs on CLI startup (throttled to once per day,
  SMITH_SKILL_CHECK=0 kill switch) and silently re-syncs stale marker-bearing
  copies and broken symlinks. Unmanaged directories only get a stderr hint;
  working symlinks are never touched.
- sync_skill swaps in the new skill via a staged copy so a mid-copy failure
  restores the previous install instead of leaving a partial one.
- scripts/install.py delegates to smith skill sync (locating fresh installs
  via uv tool dir --bin), keeping its copy logic only as a PATH fallback.

Homebrew release plumbing:
- update_homebrew_formula.py owns the canonical bootstrap build-backend list
  (--print-extra-packages, --sync-bootstrap-resources with resource-stanza
  validation) and can pin GitHub release tarballs via --sha256, parsing both
  the old git pin and the new tarball pin.
- The release validation workflow now dispatches the tap's Update Smith
  Formula workflow with HOMEBREW_TAP_DISPATCH_TOKEN, falling back to the
  manual handoff message when the secret is absent.

Bump version to 0.1.3 to carry the script flags the tap workflow needs.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>

@chatgpt-codex-connector chatgpt-codex-connector Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Codex Review

smith/src/smith/skill.py

Lines 205 to 207 in e094dc0

if skill_target_points_to_source(target, source):
mode = "symlink" if target.is_symlink() else "directory"
return SkillSyncResult(

P2 Badge Stamp current copied installs before returning

When the target is an unmarked copied directory whose contents already match the source (for example a copy produced by an older installer or the fallback path), this early current return skips writing .smith-skill-meta.json. On a later upgrade, ensure_skill_fresh sees the now-stale directory but refuses to refresh it because marker is None, so even a user who ran smith skill sync while it was current will only get the manual hint instead of automatic refresh. For directory-mode current targets, backfill the marker before returning.

ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".

Comment thread scripts/install.py
Comment on lines +34 to +36
found = shutil.which("smith")
if found:
return found

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2 Badge Prefer the freshly installed uv tool over PATH

When a user already has an older smith earlier on PATH (for example from Homebrew or a prior uv/pipx install), this returns that stale executable instead of the uv tool install result. The subsequent smith skill sync can therefore run the old sync implementation; in particular pre-marker versions sync successfully but do not write .smith-skill-meta.json, so the installer's copy is not recognized as smith-managed and will not auto-refresh on later upgrades. Since the script has just installed the intended CLI, it should locate/use uv's tool bin before falling back to PATH.

Useful? React with 👍 / 👎.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
@faustodavid faustodavid merged commit 0ee9d68 into main Jun 10, 2026
8 checks passed
@faustodavid faustodavid deleted the feature/secure-homebrew-tap-ci branch June 10, 2026 14:28
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant