Adds auto-import feature to complement bd-35's auto-export, completing the automatic sync workflow for git collaboration. **Implementation:** - Auto-import checks if JSONL is newer than DB on command startup - Silently imports JSONL when modification time is newer - Skips import command itself to avoid recursion - Can be disabled with --no-auto-import flag **Documentation updates:** - Updated README.md git workflow section - Updated CLAUDE.md workflow and pro tips - Updated bd quickstart with auto-sync section - Updated git hooks README to clarify they're now optional **Testing:** - Tested auto-import by touching JSONL and running commands - Tested auto-export with create/close operations - Complete workflow verified working Closes bd-33 🤖 Generated with [Claude Code](https://claude.com/claude-code) Co-Authored-By: Claude <noreply@anthropic.com>
4.8 KiB
4.8 KiB
Git Hooks for Beads
Optional git hooks for immediate export/import of beads issues.
NOTE: As of bd v0.9+, auto-sync is enabled by default! These hooks are optional and provide:
- Immediate export (no 5-second debounce wait)
- Guaranteed import after every git operation
- Extra safety for critical workflows
What These Hooks Do
- pre-commit: Exports SQLite → JSONL before every commit (immediate, no debounce)
- post-merge: Imports JSONL → SQLite after git pull/merge (guaranteed)
- post-checkout: Imports JSONL → SQLite after branch switching (guaranteed)
This keeps your .beads/issues.jsonl (committed to git) in sync with your local SQLite database (gitignored).
Do You Need These Hooks?
Most users don't need hooks anymore! bd automatically:
- Exports after CRUD operations (5-second debounce)
- Imports when JSONL is newer than DB
Install hooks if you:
- Want immediate export (no waiting 5 seconds)
- Want guaranteed import after every git operation
- Need extra certainty for team workflows
- Prefer explicit automation over automatic behavior
Installation
Quick Install
cd /path/to/your/project
./examples/git-hooks/install.sh
The installer will prompt before overwriting existing hooks.
Manual Install
# Copy hooks to .git/hooks/
cp examples/git-hooks/pre-commit .git/hooks/
cp examples/git-hooks/post-merge .git/hooks/
cp examples/git-hooks/post-checkout .git/hooks/
# Make them executable
chmod +x .git/hooks/pre-commit
chmod +x .git/hooks/post-merge
chmod +x .git/hooks/post-checkout
Usage
Once installed, the hooks run automatically:
# Creating/updating issues
bd create "New feature" -p 1
bd update bd-1 --status in_progress
# Committing changes - hook exports automatically
git add .
git commit -m "Update feature"
# 🔗 Exporting beads issues to JSONL...
# ✓ Beads issues exported and staged
# Pulling changes - hook imports automatically
git pull
# 🔗 Importing beads issues from JSONL...
# ✓ Beads issues imported successfully
# Switching branches - hook imports automatically
git checkout feature-branch
# 🔗 Importing beads issues from JSONL...
# ✓ Beads issues imported successfully
How It Works
The Workflow
- You work with bd commands (
create,update,close) - Changes are stored in SQLite (
.beads/*.db) - fast local queries - Before commit, hook exports to JSONL (
.beads/issues.jsonl) - git-friendly - JSONL is committed to git (source of truth)
- After pull/merge/checkout, hook imports JSONL back to SQLite
- Your local SQLite cache is now in sync with git
Why This Design?
SQLite for speed:
- Fast queries (dependency trees, ready work)
- Rich SQL capabilities
- Sub-100ms response times
JSONL for git:
- Clean diffs (one issue per line)
- Mergeable (independent lines)
- Human-readable
- AI-resolvable conflicts
Best of both worlds!
Troubleshooting
Hook not running
# Check if hook is executable
ls -l .git/hooks/pre-commit
# Should show -rwxr-xr-x
# Make it executable if needed
chmod +x .git/hooks/pre-commit
Export/import fails
# Check if bd is in PATH
which bd
# Check if you're in a beads-initialized directory
bd list
Merge conflicts in issues.jsonl
If you get merge conflicts in .beads/issues.jsonl:
- Most conflicts are safe to resolve by keeping both sides
- Each line is an independent issue
- Look for
<<<<<<< HEADmarkers - Keep all lines that don't conflict
- For actual conflicts on the same issue, choose the newest
Example conflict:
<<<<<<< HEAD
{"id":"bd-3","title":"Updated title","status":"closed","updated_at":"2025-10-12T10:00:00Z"}
=======
{"id":"bd-3","title":"Updated title","status":"in_progress","updated_at":"2025-10-12T09:00:00Z"}
>>>>>>> feature-branch
Resolution: Keep the HEAD version (newer timestamp).
After resolving:
git add .beads/issues.jsonl
git commit
bd import -i .beads/issues.jsonl # Sync to SQLite
Uninstalling
rm .git/hooks/pre-commit
rm .git/hooks/post-merge
rm .git/hooks/post-checkout
Customization
Skip hook for one commit
git commit --no-verify -m "Skip hooks"
Add to existing hooks
If you already have git hooks, you can append to them:
# Append to existing pre-commit
cat examples/git-hooks/pre-commit >> .git/hooks/pre-commit
Filter exports
Export only specific issues:
# Edit pre-commit hook, change:
bd export --format=jsonl -o .beads/issues.jsonl
# To:
bd export --format=jsonl --status=open -o .beads/issues.jsonl
See Also
- Git hooks documentation
- ../../TEXT_FORMATS.md - JSONL merge strategies
- ../../GIT_WORKFLOW.md - Design rationale