diff --git a/.beads/issues.jsonl b/.beads/issues.jsonl index 46aaeda0..453c0e12 100644 --- a/.beads/issues.jsonl +++ b/.beads/issues.jsonl @@ -63,7 +63,7 @@ {"id":"bd-tne","title":"Add Claude setup tip with dynamic priority","description":"Add a predefined tip that suggests running `bd setup claude` when Claude Code is detected but not configured. This tip should have higher priority (shown more frequently) until the setup is complete.","status":"closed","priority":2,"issue_type":"task","created_at":"2025-11-11T23:29:29.871324-08:00","updated_at":"2025-11-25T17:52:35.044989-08:00","closed_at":"2025-11-25T17:52:35.044989-08:00","dependencies":[{"issue_id":"bd-tne","depends_on_id":"bd-d4i","type":"blocks","created_at":"2025-11-11T23:29:29.872081-08:00","created_by":"daemon"}]} {"id":"bd-tqo","title":"deletions.jsonl gets corrupted with full issue objects instead of deletion records","description":"## Bug Description\n\nThe deletions.jsonl file was found to contain full issue objects (like issues.jsonl) instead of deletion records.\n\n### Expected Format (DeletionRecord)\n```json\n{\"id\":\"bd-xxx\",\"timestamp\":\"2025-...\",\"actor\":\"user\",\"reason\":\"deleted\"}\n```\n\n### Actual Content Found\n```json\n{\"id\":\"bd-03r\",\"title\":\"Document deletions manifest...\",\"description\":\"...\",\"status\":\"closed\",...}\n```\n\n## Impact\n- bd sync sanitization step reads deletions.jsonl and removes any matching IDs from issues.jsonl\n- With 60 full issue objects in deletions.jsonl, ALL 60 issues were incorrectly removed during sync\n- This caused complete data loss of the issue database\n\n## Root Cause (suspected)\nSomething wrote issues.jsonl content to deletions.jsonl. Possible causes:\n- Export writing to wrong file\n- File path confusion during sync\n- Race condition between export and deletion tracking\n\n## Related Issues\n- bd-0b2: --no-git-history flag (just fixed)\n- bd-4pv: export outputs only 1 issue after corruption \n- bd-4t7: auto-import runs during --no-auto-import\n\n## Reproduction\nUnknown - discovered during bd sync session on 2025-11-26\n\n## Fix\nNeed to investigate what code path could write issue objects to deletions.jsonl","status":"closed","priority":1,"issue_type":"bug","created_at":"2025-11-26T23:17:01.938931-08:00","updated_at":"2025-11-26T23:25:21.445143-08:00","closed_at":"2025-11-26T23:25:02.209911-08:00"} {"id":"bd-tru","title":"Update documentation for bd prime and Claude integration","description":"Update AGENTS.md, README.md, and QUICKSTART.md to document the new `bd prime` command, `bd setup claude` command, and tip system.","status":"closed","priority":2,"issue_type":"task","created_at":"2025-11-11T23:30:22.77349-08:00","updated_at":"2025-11-25T17:47:30.807069-08:00","closed_at":"2025-11-25T17:47:30.807069-08:00"} -{"id":"bd-tt0","title":"Sync validation false positive: legitimate deletions trigger 'data loss detected'","description":"## Problem\n`bd sync` fails with false positive data loss detection when legitimate deletions occur:\n```\nPost-import validation failed: import reduced issue count: 26 → 25 (data loss detected!)\n```\n\n## Root Cause\nThe validation in `sync.go:329-340` counts DB issues BEFORE import, but `purgeDeletedIssues()` in `importer.go:159` legitimately removes issues DURING import. The validation doesn't account for expected deletions.\n\n**The Flow:**\n```\nsync.go:293 → beforeCount = countDBIssues() = 26\nsync.go:310-319 → sanitizeJSONL removes deleted issues from JSONL (RemovedCount=N)\nsync.go:323 → importFromJSONL() runs subprocess\n └→ importer.go:159 purgeDeletedIssues() removes issues from DB\nsync.go:331 → afterCount = countDBIssues() = 25\nsync.go:335 → validatePostImport(26, 25) → ERROR\n```\n\n## Fix\nPass `sanitizeResult.RemovedCount` to validation and account for expected deletions:\n\n```go\n// sync.go around line 335\nexpectedDecrease := 0\nif sanitizeResult != nil {\n expectedDecrease = sanitizeResult.RemovedCount\n}\nif err := validatePostImportWithDeletions(beforeCount, afterCount, expectedDecrease); err != nil {\n // ...\n}\n```\n\n```go\n// integrity.go - new or modified function\nfunc validatePostImportWithDeletions(before, after, expectedDeletions int) error {\n if after \u003c before - expectedDeletions {\n return fmt.Errorf(\"unexpected data loss: %d → %d (expected max decrease: %d)\", \n before, after, expectedDeletions)\n }\n // ...\n}\n```\n\n## Files\n- cmd/bd/sync.go:329-340\n- cmd/bd/integrity.go:289-301","status":"in_progress","priority":1,"issue_type":"bug","created_at":"2025-11-28T17:06:15.515768-08:00","updated_at":"2025-11-28T18:36:39.679422-08:00"} +{"id":"bd-tt0","title":"Sync validation false positive: legitimate deletions trigger 'data loss detected'","description":"## Problem\n`bd sync` fails with false positive data loss detection when legitimate deletions occur:\n```\nPost-import validation failed: import reduced issue count: 26 → 25 (data loss detected!)\n```\n\n## Root Cause\nThe validation in `sync.go:329-340` counts DB issues BEFORE import, but `purgeDeletedIssues()` in `importer.go:159` legitimately removes issues DURING import. The validation doesn't account for expected deletions.\n\n**The Flow:**\n```\nsync.go:293 → beforeCount = countDBIssues() = 26\nsync.go:310-319 → sanitizeJSONL removes deleted issues from JSONL (RemovedCount=N)\nsync.go:323 → importFromJSONL() runs subprocess\n └→ importer.go:159 purgeDeletedIssues() removes issues from DB\nsync.go:331 → afterCount = countDBIssues() = 25\nsync.go:335 → validatePostImport(26, 25) → ERROR\n```\n\n## Fix\nPass `sanitizeResult.RemovedCount` to validation and account for expected deletions:\n\n```go\n// sync.go around line 335\nexpectedDecrease := 0\nif sanitizeResult != nil {\n expectedDecrease = sanitizeResult.RemovedCount\n}\nif err := validatePostImportWithDeletions(beforeCount, afterCount, expectedDecrease); err != nil {\n // ...\n}\n```\n\n```go\n// integrity.go - new or modified function\nfunc validatePostImportWithDeletions(before, after, expectedDeletions int) error {\n if after \u003c before - expectedDeletions {\n return fmt.Errorf(\"unexpected data loss: %d → %d (expected max decrease: %d)\", \n before, after, expectedDeletions)\n }\n // ...\n}\n```\n\n## Files\n- cmd/bd/sync.go:329-340\n- cmd/bd/integrity.go:289-301","status":"closed","priority":1,"issue_type":"bug","created_at":"2025-11-28T17:06:15.515768-08:00","updated_at":"2025-11-28T18:46:19.722924-08:00","closed_at":"2025-11-28T18:46:19.722924-08:00"} {"id":"bd-tys","title":"Git history fallback has incorrect logic for detecting deletions","description":"## Problem\n\nThe `wasInGitHistory` function in `internal/importer/importer.go:891` returns true if the ID is found **anywhere** in git history. But finding an ID in history doesn't necessarily mean it was deleted - it could mean:\n\n1. The issue was added (appears in a commit adding it)\n2. The issue was modified (appears in commits updating it)\n3. The issue was deleted (appears in a commit removing it)\n\nThe current logic incorrectly treats all three cases as 'deleted'.\n\n## Correct Logic\n\n`git log -S` with `--oneline` shows commits where the string was added OR removed. To detect deletion specifically:\n\n1. ID appears in git history (was once in JSONL)\n2. ID is NOT currently in JSONL\n\nThe second condition is already checked by the caller (`purgeDeletedIssues`), so technically the logic is correct in context. But the function name and doc comment are misleading.\n\n## Fix Options\n\n1. **Rename function** to `wasEverInJSONL` and update doc comment to clarify\n2. **Add explicit check** for current JSONL state in the function itself\n\nOption 1 is simpler and correct since caller already filters.","status":"closed","priority":3,"issue_type":"bug","created_at":"2025-11-25T12:46:16.073661-08:00","updated_at":"2025-11-25T15:11:54.426093-08:00","closed_at":"2025-11-25T15:11:54.426093-08:00"} {"id":"bd-upd","title":"Sync should cleanup snapshot files after completion","description":"After sync completion, orphan .base.jsonl and .left.jsonl snapshot files remain in .beads/ directory. These should be cleaned up on successful sync.","status":"closed","priority":2,"issue_type":"bug","created_at":"2025-11-28T17:27:36.727246-08:00","updated_at":"2025-11-28T18:22:16.904307-08:00","closed_at":"2025-11-28T17:42:14.57165-08:00"} {"id":"bd-v0x","title":"Auto-detect issue prefix from existing JSONL in 'bd init'","description":"When running `bd init` in a fresh clone with existing JSONL, it should auto-detect the issue prefix from the JSONL file instead of requiring `--prefix`.\n\nCurrently you must specify `--prefix ef` manually. But the JSONL file already contains issues like `ef-1it`, `ef-1jp` etc., so the prefix is known.\n\n**Ideal UX**:\n```\n$ bd init\nDetected issue prefix 'ef' from existing JSONL (38 issues).\n✓ Database initialized...\n```\n\nThis would make fresh clone hydration a single command: `bd init` with no flags.","status":"open","priority":2,"issue_type":"feature","created_at":"2025-11-27T20:21:21.049215-08:00","updated_at":"2025-11-27T20:21:21.049215-08:00"}