gastownhall/beads · error
failed to untrack last-touched file: %w
Error message
failed to untrack last-touched file: %w
What it means
FixLastTouchedTracking untracks the machine-local .beads/last-touched file with `git rm --cached <lastTouchedPath>` so it is no longer committed while keeping the local copy. This error wraps a non-zero exit of that git command. Like the redirect fix, the root cause lies in git's index/repository state.
Source
Thrown at cmd/bd/doctor/gitignore.go:707
func FixLastTouchedTracking(repoPath string) error {
lastTouchedPath := filepath.Join(repoPath, ".beads", "last-touched")
// Check if file is actually tracked first
cmd := exec.Command("git", "ls-files", lastTouchedPath) // #nosec G204 - args are hardcoded paths
output, err := cmd.Output()
if err != nil {
return nil // Not a git repo, nothing to do
}
trackedPath := strings.TrimSpace(string(output))
if trackedPath == "" {
return nil // Not tracked, nothing to do
}
// Untrack the file (keeps the local copy)
cmd = exec.Command("git", "rm", "--cached", lastTouchedPath) // #nosec G204 - args are hardcoded paths
if err := cmd.Run(); err != nil {
return fmt.Errorf("failed to untrack last-touched file: %w", err)
}
return nil
}
// CheckProjectGitignore checks if the project-root .gitignore contains patterns
// to prevent accidentally committing Dolt database files and credential keys.
// repoPath is the project root directory.
func CheckProjectGitignore(repoPath string) DoctorCheck {
gitignorePath := filepath.Join(repoPath, ".gitignore")
content, err := os.ReadFile(gitignorePath) // #nosec G304 -- path is hardcoded
if err != nil {
if os.IsNotExist(err) {
return DoctorCheck{
Name: "Project Gitignore",
Status: StatusWarning,
Message: "No project .gitignore found — Dolt/credential files may be committed accidentally",View on GitHub (pinned to 71377f2769)
Solutions
- Run `git rm --cached .beads/last-touched` manually to see git's real error
- Finish or abort any in-progress merge/rebase (`git status`) and retry
- Verify tracking state: `git ls-files .beads/last-touched`; if empty, the file is already untracked and no fix is needed
- Run bd from within the repository containing .beads/ so git resolves the correct index
Example fix
// before: file tracked, untrack fails during rebase $ bd doctor --fix failed to untrack last-touched file: exit status 1 // after $ git rebase --abort $ bd doctor --fix # untracks .beads/last-touched, keeps local copy
Defensive patterns
Strategy: validation
Validate before calling
const tracked = execSync('git ls-files -- .beads/last-touched', { encoding: 'utf8' }).trim();
const midOp = execSync('git status --porcelain', { encoding: 'utf8' }).split('\n').some(l => /^(UU|AA|DD|REBASE|MERGE)/.test(l));
if (midOp) throw new Error('finish or abort merge/rebase before bd doctor --fix');
if (!tracked) console.log('.beads/last-touched already untracked'); Try / catch
try {
execSync('bd doctor --fix', { stdio: 'inherit' });
} catch (err) {
if (String(err.stderr).includes('failed to untrack last-touched file')) {
console.error('git state:', execSync('git status --short', { encoding: 'utf8' }));
}
throw err;
} Prevention
- Ensure .beads/.gitignore contains the last-touched pattern from day one
- Treat .beads/last-touched as machine-local: never `git add -f` it
- Keep git operations (merge/rebase) out of the same session as doctor --fix in scripts
- Run `bd doctor` (no --fix) first to preview what will be untracked
When it happens
Trigger: FixLastTouchedTracking detects last-touched is tracked and runs `git rm --cached lastTouchedPath`; git exits non-zero because the file is not in the index, a merge/rebase is in progress, the path differs from the index entry, or the directory is not a git repository.
Common situations: last-touched was committed before the ignore rule existed; stale index entries after moving .beads/; running bd outside the repo; CI environments with detached/incomplete checkouts; git hooks failing on index operations.
Related errors
- failed to untrack redirect file: %w
- not a git repository
- failed to install hooks: %w
- git config --unset core.hooksPath failed: %w (output: %s)
- reading git log: %w
AI-assisted analysis of gastownhall/beads@71377f2769 (2026-08-30).
Data as JSON: /api/errors/d7c66f5047342669.
Report an issue: GitHub.