Chezmoi Lock File Troubleshooting Guide
Understanding the Error
The error “timeout obtaining persistent state lock, is another instance of chezmoi running?” occurs when:
- Another chezmoi process is already running
- A previous chezmoi process crashed and left a lock file behind
- File system permissions prevent lock file operations
- The chezmoi data directory is corrupted
Step-by-Step Resolution
Step 1: Check for Running Processes
Linux/macOS:
# Check for running chezmoi processes
ps aux | grep chezmoi
pgrep -f chezmoi
# If processes are found, kill them
pkill -f chezmoi
# Or more forcefully:
pkill -9 -f chezmoiWindows:
# Check for running processes
tasklist | findstr chezmoi
# Kill any found processes
taskkill /F /IM chezmoi.exeStep 2: Locate and Remove Lock Files
Find your chezmoi data directory:
# Show chezmoi data directory location
chezmoi dataCommon lock file locations:
- Linux:
~/.local/share/chezmoi/.chezmoi.lock - macOS:
~/Library/Application Support/chezmoi/.chezmoi.lock - Windows:
%LOCALAPPDATA%\chezmoi\.chezmoi.lock
Remove the lock file:
# Linux/macOS
rm ~/.local/share/chezmoi/.chezmoi.lock
# Windows (PowerShell)
Remove-Item "$env:LOCALAPPDATA\chezmoi\.chezmoi.lock"
# Windows (CMD)
del "%LOCALAPPDATA%\chezmoi\.chezmoi.lock"Step 3: Clear Chezmoi State (If Accessible)
If chezmoi commands still work, try clearing the state:
# Clear specific state buckets
chezmoi state delete-bucket --bucket=entryState
chezmoi state delete-bucket --bucket=scriptState
# Or reset all state
chezmoi state reset
# Verify state is cleared
chezmoi state dumpStep 4: Handle Script Failures
If you’re getting script errors (like 30_setup-pre-commit.sh: exit status 1):
Option 1: Skip scripts temporarily
chezmoi apply --exclude=scriptsOption 2: Debug the specific script
# Run with verbose output
chezmoi apply --verbose
# Check the script manually
cat ~/.local/share/chezmoi/.chezmoiscripts/linux/30_setup-pre-commit.sh
# Test script independently
bash ~/.local/share/chezmoi/.chezmoiscripts/linux/30_setup-pre-commit.shOption 3: Temporarily disable the script
# Rename to disable
mv ~/.local/share/chezmoi/.chezmoiscripts/linux/30_setup-pre-commit.sh \
~/.local/share/chezmoi/.chezmoiscripts/linux/30_setup-pre-commit.sh.disabledStep 5: Force Apply if Necessary
# Force apply all changes
chezmoi apply --force
# Apply with debugging
chezmoi apply --debug --verbose
# Dry run to see what would happen
chezmoi apply --dry-runPrevention Strategies
1. Proper Shutdown
Always let chezmoi commands complete naturally rather than interrupting them.
2. Regular State Maintenance
# Periodically check state
chezmoi doctor
# Clean up state
chezmoi state reset3. Script Best Practices
- Make scripts idempotent (safe to run multiple times)
- Add proper error handling
- Use exit codes appropriately
4. Backup Configuration
# Backup your chezmoi configuration
chezmoi archive --output=chezmoi-backup.tar.gz
# Export to a git repository
chezmoi cd
git add .
git commit -m "Backup configuration"
git pushAdvanced Troubleshooting
Complete Reset
If all else fails, you can completely reset chezmoi:
# Backup first!
chezmoi archive --output=backup-$(date +%Y%m%d).tar.gz
# Remove all chezmoi data
rm -rf ~/.local/share/chezmoi
rm -rf ~/.config/chezmoi
# Reinitialize
chezmoi init <your-dotfiles-repo>Check File Permissions
# Check permissions on chezmoi directory
ls -la ~/.local/share/chezmoi/
# Fix permissions if needed
chmod 755 ~/.local/share/chezmoi/
chmod 644 ~/.local/share/chezmoi/*Debugging with Strace (Linux)
# See what files chezmoi is trying to access
strace -f -e trace=openat,unlink chezmoi apply 2>&1 | grep lockWhen to Seek Further Help
Contact chezmoi support or community if:
- Lock files keep reappearing after removal
- Scripts consistently fail with unclear errors
- Chezmoi commands hang indefinitely
- State corruption persists after reset
Useful Commands Reference
# Diagnostic commands
chezmoi doctor # Check for common issues
chezmoi data # Show data directory
chezmoi state dump # Show current state
chezmoi diff # Show pending changes
# Recovery commands
chezmoi apply --dry-run # Preview changes
chezmoi apply --force # Force apply all changes
chezmoi apply --exclude=scripts # Skip script execution
chezmoi re-add # Re-add all managed files