- Add nolint:unparam for readOnly param in sqlite_open.go
- Handle cmd.Help() error in wisp.go
- Handle rows.Close() error in migration 028
- Handle targetStore.Close() error in create.go
- Update Nix vendorHash for current dependencies
Cherry-picked from PR #769
Implements the 'bd orphans' command to identify issues referenced in commits
but still open in the database, and refactors to eliminate code duplication.
- Creates cmd/bd/orphans.go with Cobra command structure
- Identifies orphaned issues (referenced in git commits but still open/in_progress)
- Supports multiple output formats (human, JSON, detailed)
- Auto-close with --fix flag
DRY refactoring:
- Extracted FindOrphanedIssues() to cmd/bd/doctor/git.go as shared core logic
- Moved OrphanIssue type to cmd/bd/doctor/types.go
- Refactored CheckOrphanedIssues() to use FindOrphanedIssues()
Cherry-picked from PR #767
Co-authored-by: Amp <amp@ampcode.com>
Move cleanup, compact, and reset commands under `bd admin` namespace.
Creates hidden aliases for backwards compatibility that show deprecation
notice when used.
- Create cmd/bd/admin.go with parent command
- Create cmd/bd/admin_aliases.go for hidden backwards-compat aliases
- Update cleanup.go, compact.go, reset.go to remove rootCmd.AddCommand
- Update all documentation to use `bd admin <cmd>` syntax
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
- Add --check flag to doctor for specific check modes
- Add --check=pollution to run detailed pollution detection
- Add --clean flag to delete detected test issues
- Mark detect-pollution command as hidden (deprecated)
- Update fix messages to point to new doctor --check=pollution
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
- Add --thanks flag to bd info command
- Make bd thanks a hidden command (deprecated but still works)
- Part of CLI consolidation effort (bd-9115)
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
Analysis found these commands are dead code:
- gt never calls `bd pin` - uses `bd update --status=pinned` instead
- Beads.Pin() wrapper exists but is never called
- bd hook functionality duplicated by gt mol status
- Code comment says "pinned field is cosmetic for bd hook visibility"
Removed:
- cmd/bd/pin.go
- cmd/bd/unpin.go
- cmd/bd/hook.go
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
- Add TestSpawnMoleculeEphemeralFlag: verifies DB-based spawn
- Add TestSpawnMoleculeFromFormulaEphemeral: verifies formula-based spawn
- Both tests confirm Ephemeral flag is set correctly
- Tests also verify ephemeral issues excluded from ready work
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
- Delete mol_catalog.go (duplicate functionality)
- Update mol.go help text to point to bd formula list
- Update CLI_REFERENCE.md and MOLECULES.md docs
- Update deprecated template.go references
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
Adds --prefix as a forgiving alias to --rig flag. Accepts:
- Exact prefix: bd-, gt-
- Prefix without hyphen: bd, gt
- Rig name: beads, gastown
All resolve to the correct rig via routes.jsonl lookup.
This matches agents' mental model of prefix-based routing.
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
Adds --rig flag to bd create that allows creating issues in a different
rig without having to cd to that directory.
Example: bd create --rig beads --title='Bug report'
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
When `bd dep add` fails to resolve the dependency ID locally, it now
checks routes.jsonl for a matching prefix and auto-converts to an
external reference format (external:<project>:<id>).
This allows simpler syntax like:
bd dep add gt-xyz bd-abc
Instead of the verbose:
bd dep add gt-xyz external:beads:bd-abc
New functions in routing package:
- ExtractProjectFromPath: Gets project name from route path
- ResolveToExternalRef: Converts foreign ID to external ref using routes
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
The verb 'wisp' fits the chemistry metaphor (pour, bond, burn, squash)
while 'ephemeral' is an adjective. The internal API field remains
'Ephemeral' but the CLI command is now 'bd mol wisp'.
Commands:
bd mol wisp <proto> - create ephemeral wisp
bd mol wisp list - list wisps
bd mol wisp gc - garbage collect old wisps
For consistency, all molecule operations are now under bd mol:
- bd mol pour <proto> - create persistent mol
- bd mol ephemeral <proto> - create ephemeral mol
- bd mol ephemeral list - list ephemeral issues
- bd mol ephemeral gc - garbage collect old ephemeral issues
This aligns with existing mol subcommands: bond, squash, burn, etc.
The `bd comment --no-db` command was failing because
initializeNoDbMode() set the global `store` but never set
`storeActive = true`. When comments.go called ensureStoreActive(),
the guard check failed and it tried to find a SQLite database,
returning an ironic error telling the user to use --no-db.
Why only `comment` was affected:
- Commands like `create`, `update`, `close` use `store` directly
- The `comment` command calls `ensureStoreActive()` first as a safety check
- That function guards on `storeActive && store != nil`
- Since `storeActive` was never set, the guard failed and it looked for SQLite
The fix aligns no-db mode with what ensureStoreActive() expects.
The --resolution flag was accidentally removed by a bd sync commit.
This restores the hidden alias for --reason, following Jira CLI convention.
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
Writes activity.json to ~/gt/daemon/ when bd runs inside a Gas Town
workspace. This enables the daemon to detect bd usage and adjust its
polling frequency with exponential backoff.
Best-effort: silently skips if not in Gas Town or on any error.
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
created_by was recently added in c3ef1c3f38 but was missing support for passing in the CreatedBy through the RPC path so a create that was using the daemon was never having the created_by field set.
Modern git (2.28+) uses 'main' as default branch, not 'master'.
Tests were failing because they assumed 'master' branch exists.
Changes:
- Use 'git init --initial-branch=main' instead of bare 'git init'
- Change 'git checkout master' to 'git checkout main'
- Add git.ResetCaches() after os.Chdir() to clear cached git state
- Ensures test isolation when changing directories
Adds automatic database recovery when bd doctor --fix detects corruption:
- Detects SQLite corruption (malformed database, SQLITE_CORRUPT errors)
- Backs up corrupted database before recovery attempt
- Rebuilds from JSONL if available (issues.jsonl, deletions.jsonl)
- Falls back to fresh database if JSONL unavailable
- Reports recovery results (issues imported, success/failure)
Recovery is triggered automatically by --fix when corruption is detected.
No manual intervention required.
The defer-in-loop pattern was causing all routed storage connections
to accumulate until function exit. This could lead to resource leaks
when showing multiple routed issues. Now explicitly close each
connection after processing each issue.
(bd-uu8p)
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
When an ID needs routing to a different beads directory, the daemon
cannot resolve it. Now we check needsRouting() before daemon resolution
and handle routed IDs via direct mode with routing.
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
Enables cross-repo issue lookups via routes.jsonl configuration.
Running `bd show gt-xyz` from ~/gt now routes to the correct beads
directory based on the issue ID prefix.
- Add internal/routing/routes.go with routing logic
- Add cmd/bd/routed.go with routed storage helpers
- Update show command to use routed resolution in direct mode
- Support redirect files for canonical database locations
- Debug output available via BD_DEBUG_ROUTING=1
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
Add a created_by field to track who created each issue, similar to how
comments have an author field.
- Add CreatedBy string field to Issue struct
- Add migration 029 to add created_by column to issues table
- Update all SELECT/INSERT/Scan statements across storage layer
- Populate created_by in bd create from actor chain
- Display created_by in bd show output
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
The CheckChildParentDependencies detection and ChildParentDependencies fix
were flagging ALL child→parent dependencies, including legitimate
'parent-child' type structural hierarchy relationships.
Now only blocking types (blocks, conditional-blocks, waits-for) are
detected as anti-patterns. The 'parent-child' type is a legitimate
hierarchy marker used for:
- Tracking parent-child relationships
- Transitive block propagation (if parent blocked, children blocked)
- Hierarchy visualization in external tools
Changes:
- Add type filter to SELECT queries (only blocking types)
- Add type filter to DELETE statement (preserve parent-child)
- Add regression test TestChildParentDependencies_PreservesParentChildType
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
Mail gates check for messages matching the pattern (await_id):
- Case-insensitive substring match on message subjects
- If waiters specified, only matches messages to those recipients
- Closes gate when matching message found
Note: Full testing blocked by bd-70c4 (await fields being cleared).
The code is correct but gate fields get corrupted by auto-import.
Also adds context and storage imports for mail gate function.
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
Human gates now have proper workflow:
- Create with: bd gate create --await human:approve-deploy
- Approve with: bd gate approve <gate-id> [--comment "reason"]
- bd gate eval now reports human gates as "awaiting approval"
- Rejects non-human gates with clear error message
Also added mail gate placeholder in eval (awaiting mail: ...).
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
The merged field does not exist in gh pr view output. The actual
fields are:
- state: OPEN, CLOSED, or MERGED
- mergedAt: timestamp string (empty if not merged)
Also simplified the switch statement since state already distinguishes
merged vs closed-without-merge PRs.
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
Implements evaluation for GitHub-related gate types:
- gh:run: Checks if a GitHub Actions run has completed using
`gh run view <id> --json status,conclusion`
- gh:pr: Checks if a PR has been merged/closed using
`gh pr view <id> --json state,merged`
Both gate types require the gh CLI to be installed and authenticated.
If gh fails (not installed, network issues, invalid IDs), the gate is
skipped rather than erroneously closed.
Refactors the eval loop to use a switch statement for cleaner
gate type dispatch.
(gt-twjr5.3)
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>