Skip to content

Automate Claude global config sync into chezmoi (greenlight + /chezmoi-sync) #49

Description

@nickvigilante

Summary

Make all Claude global configuration live in and stay synced with chezmoi,
with a low-friction, greenlit capture of the changes Claude Code (and
plugins/RTK) write to their own settings — rather than one PR per change.

Design agreed in a planning session; implementation deferred until the
in-flight Claude↔chezmoi work (generated settings.json / permissions) lands,
to avoid collisions. Related: #37, #36, #32.

Decisions

  • Greenlight, batched per branch. Each sync = one descriptively-named
    branch → PR → merge to main, so all machines converge via chezmoi update.
    (Per-change PRs are overkill; a session's batch per branch is the unit.)
  • SessionStart drift-detection hook. Scoped chezmoi diff over the
    tracked ~/.claude set; if drift exists, surface a reminder so Claude
    proactively offers to sync at session start.
  • /chezmoi-sync command — broad and bidirectional. Not Claude-specific:
    • live newer than source → offer chezmoi add (capture up)
    • source newer than live → offer chezmoi apply (push down)
    • per-element: list each drifted path, show its diff, choose
      capture / apply / skip
    • must degrade gracefully around template-render failureschezmoi status currently aborts on the Bitwarden-templated ~/.kube/homelab.yaml;
      the command should fall back to per-path diffing rather than fail the scan.

Track-allowlist (everything else under ~/.claude ignored)

  • settings.json (see caveat below), CLAUDE.md, RTK.md, agents/,
    commands/, skills/, hooks/*.py.
  • Never tracked: ~/.claude.json (≈84 KB, ~200 secret-ish keys — already
    in .chezmoiignore, keep it there), settings.local.json (machine-local),
    *cache*.json, daemon.status.json, mcp-needs-auth-cache.json,
    hooks/__pycache__/ (a .pyc is currently tracked — drop it).

Caveat — settings.json is a GENERATED target

Per the new permissions convention, settings.json's Bash allowlist is
generated from .chezmoidata/permissions.toml + a template. So the sync must
not chezmoi add settings.json (that would clobber the template with
rendered output). Reconcile its drift instead by:

This is the main point to align with the in-flight work before implementing.

CLAUDE.md templating — pattern, not a task

Do not template CLAUDE.md wholesale (it's the most-loaded instruction
file; a template error has a huge blast radius). When a real per-machine
difference appears (YAGNI until then), isolate it into an @-imported fragment:

  • templated fragmentdot_claude/CLAUDE.machine.md.tmpl on
    {{ .chezmoi.hostname }} / OS, imported via @CLAUDE.machine.md; or
  • host-gated fragments — plain per-host files applied via a templated
    .chezmoiignore (the existing per-host pattern).

chezmoi skill updates needed

  • Add a "Claude config sync" section (allowlist + the greenlight//chezmoi-sync
    workflow).
  • Fix the stale guidance: commit bodies use Assisted-by: AI, never
    Co-Authored-By.

Safety

Public repo: secrets never tracked; betterleaks pre-commit + CI is the backstop.

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions