Skip to content

feat(cli): conflict-aware plan preview for init (enhance --dry-run) #62

Description

@Lillevang

Status: needs technical refinement. This is a design sketch focused on the UX. Acceptance criteria are provisional and the open questions at the bottom must be settled before implementation.

Problem

--dry-run exists, but it does not give the user a true picture of what will happen. It classifies existing files as skip correctly when --force is absent, but with --force every path — including files it would destructively overwrite — prints a plain write. There is no distinction between creating a new file and overwriting one the user already has, and no summary of the net effect.

Observed today (init --dry-run --force --agents-only go-cli into a dir whose .agent/AGENTS.md already contains the user's own notes):

  write  .agent/AGENTS.md (dry-run)      <- silently destroys existing user content; looks identical to a new file
  write  README.agent.md (dry-run)       <- same

So the one moment a preview matters most — "am I about to overwrite something I care about?" — is exactly where today's output is silent. The user can't tell a safe run from a destructive one at a glance, and there's no tally to confirm the net result.

Goal

Turn the preview into a real plan: evaluated against the target directory's actual contents, classify every action and summarize it, so the user knows precisely what will change before committing. Keep it seamless — same flag, richer truth. No new dependencies (raw output, consistent with #58).

Proposed UX (illustrative — exact wording is a refinement item)

agent-init: plan for go-cli in ./myapp   (--agents-only, --force)

  create    .agent/CODEBASE.md
  create    .devcontainer/Dockerfile
  overwrite .agent/AGENTS.md        (existing file will be replaced)   <- highlighted (red/bold)
  skip      README.agent.md         (exists; use --force to overwrite)  (only when --force absent)
  link      AGENTS.md -> .agent/AGENTS.md
  git       would initialize a git repo (omit with --no-git)

Plan: 12 create, 1 overwrite, 0 skip, 3 link. Run without --dry-run to apply.

Key changes vs today:

Provisional acceptance criteria (pending refinement)

  • Plan output classifies each path as create / overwrite / skip based on the target's actual contents, not a blanket write.
  • overwrite actions (only reachable with --force) are visually distinct and clearly flagged as destructive.
  • A summary tally line states the net effect.
  • git-init intent is shown (suppressed with --no-git).
  • Plan mode writes nothing and has no side effects (already true; preserve).
  • Composes correctly with --agents-only and the visibility modes once those exist.

Open questions (need technical refinement)

  1. Keep the flag as --dry-run, or add --plan as a clearer alias / discoverable verb? (agent-init plan ...?)
  2. How to represent the visibility-feature writes (.gitignore / .git/info/exclude / global excludes) in the plan once feat(cli): support local visibility — ignore the agent-init scaffold in the committed .gitignore #51/feat(cli): support global-default visibility — ignore the agent-init scaffold in all repos via core.excludesfile #52/feat(cli): support hidden visibility — fully hide the scaffold in one repo via .git/info/exclude (no committed trace) #53 land.
  3. For overwrite, is a one-line note enough, or should the plan offer a diff of what changes? (Likely out of scope / bloat — confirm.)
  4. Grouping vs interleaving (group by action type, or keep file order)?

Related

  • init output: fix symlink paths, add clarity + color #58 — output clarity + color; the tally and color treatment land there and this plan builds on them.
  • Companion feature: undo / uninstall a scaffold (separate issue) — shares this preview machinery (--dry-run should preview removals too).
  • Honors the 2026-05-24 "stay small and simple" decision: no new dependencies, no interactive wizard.

Metadata

Metadata

Assignees

No one assigned

    Labels

    area:bootstrapInit/bootstrap flow and onboarding UXarea:cliCLI surface, flags, help outputenhancementNew feature or requestneeds-refinementDesign/feature needs further technical refinement before implementation

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions