git-troubleshooting について
コミットやブランチの復旧、マージやリベースの問題、リポジトリ破損、一般的なエラーの診断と復旧手順を案内するスキルです。Git の問題に対処するための手順や診断コマンドを必要とする開発者向けです。
主な機能
- 01reflog によるコミットやブランチの復旧
- 02detached HEAD 状態への対処
- 03マージとリベースの問題解決
- 04リポジトリ破損の確認と修復
- 05認証、サブモジュール、性能の問題診断
- 06一般的なエラーへの対処方法
活用シーン
- 01誤った reset 後のコミット復旧
- 02マージ競合や失敗したリベースの解決
- 03リポジトリ破損や Git 認証問題の調査
インストール
コマンドをコピーしてターミナルで実行します。
$
npx skills add https:/ / github.com/ geoffjay/ claude-plugins --skill git-troubleshootingインストール後、Claude Code で/git-troubleshootingを入力して読み込まれたか確認します。
詳細
Git トラブルシューティングスキル
このスキルでは、Git の問題の診断と解決、ミスからの復旧、リポジトリの破損の修復、一般的なエラーへの対処に関する包括的なガイダンスを提供します。
使用するタイミング
次の場合にこのスキルを有効にします。
- Git のエラーメッセージが表示されたとき
- 失われたコミットやブランチを復旧するとき
- 破損したリポジトリを修復するとき
- detached HEAD の状態を解決するとき
- 失敗したマージやリベースに対処するとき
- リポジトリの問題を診断するとき
- 強制プッシュから復旧するとき
- 認証の問題を修復するとき
失われたコミットの復旧
Reflog の使用
# View reflog (local history of HEAD)
git reflog
# View reflog for specific branch
git reflog show branch-name
# Output example:
# abc123 HEAD@{0}: commit: feat: add authentication
# def456 HEAD@{1}: commit: fix: resolve bug
# ghi789 HEAD@{2}: reset: moving to HEAD~1
# Recover lost commit
git cherry-pick abc123
# Or create branch from lost commit
git branch recovered-branch abc123
# Or reset to lost commit
git reset --hard abc123
Dangling コミットの検索
# Find all unreachable objects
git fsck --lost-found
# Output:
# dangling commit abc123
# dangling blob def456
# View dangling commit
git show abc123
# Recover dangling commit
git branch recovered abc123
# Or merge it
git merge abc123
削除したブランチの復旧
# Find branch commit in reflog
git reflog
# Look for branch deletion:
# abc123 HEAD@{5}: checkout: moving from feature-branch to main
# Recreate branch
git branch feature-branch abc123
# Or if branch was merged before deletion
git log --all --oneline | grep "feature"
git branch feature-branch def456
リセット後の復旧
# After accidental reset --hard
git reflog
# Find commit before reset:
# abc123 HEAD@{0}: reset: moving to HEAD~5
# def456 HEAD@{1}: commit: last good commit
# Restore to previous state
git reset --hard def456
# Or create recovery branch
git branch recovery def456
Detached HEAD の解決
Detached HEAD の理解
# Detached HEAD state occurs when:
git checkout abc123
git checkout v1.0.0
git checkout origin/main
# HEAD is not attached to any branch
Detached HEAD からの復旧
# Check current state
git status
# HEAD detached at abc123
# Option 1: Create new branch
git checkout -b new-branch-name
# Option 2: Return to previous branch
git checkout main
# Option 3: Reattach HEAD to branch
git checkout -b temp-branch
git checkout main
git merge temp-branch
# If you made commits in detached HEAD:
git reflog
# Find the commits
git branch recovery-branch abc123
Detached HEAD の防止
# Instead of checking out tag directly
git checkout -b release-v1.0 v1.0.0
# Instead of checking out remote branch
git checkout -b local-feature origin/feature-branch
# Check if HEAD is detached
git symbolic-ref -q HEAD && echo "attached" || echo "detached"
マージコンフリクトの修正
コンフリクトマーカーの理解
<<<<<<< HEAD (Current Change)
int result = add(a, b);
||||||| merged common ancestors (Base)
int result = sum(a, b);
=======
int sum = calculate(a, b);
>>>>>>> feature-branch (Incoming Change)
基本的なコンフリクト解決
# When merge conflict occurs
git status
# both modified: file.go
# View conflict
cat file.go
# Option 1: Keep ours (current branch)
git checkout --ours file.go
git add file.go
# Option 2: Keep theirs (incoming branch)
git checkout --theirs file.go
git add file.go
# Option 3: Manual resolution
# Edit file.go to resolve conflicts
git add file.go
# Complete merge
git commit
操作の中止
# Abort merge
git merge --abort
# Abort rebase
git rebase --abort
# Abort cherry-pick
git cherry-pick --abort
# Abort revert
git revert --abort
# Abort am (apply mailbox)
git am --abort
複雑なコンフリクトの解決
# Use merge tool
git mergetool
# View three-way diff
git diff --ours
git diff --theirs
git diff --base
# Show conflicts with context
git diff --check
# List conflicted files
git diff --name-only --diff-filter=U
# After resolving all conflicts
git add .
git commit
失敗したリベースの修正
失敗したリベースからの復旧
# Abort current rebase
git rebase --abort
# Find state before rebase
git reflog
# abc123 HEAD@{1}: rebase: checkout main
# Return to pre-rebase state
git reset --hard HEAD@{1}
# Alternative: use ORIG_HEAD
git reset --hard ORIG_HEAD
リベースのコンフリクト
# During rebase conflict
git status
# both modified: file.go
# Resolve conflicts
# Edit file.go
git add file.go
git rebase --continue
# Skip problematic commit
git rebase --skip
# Edit commit during rebase
git commit --amend
git rebase --continue
間違ったブランチへのリベース
# Find original branch point
git reflog
# Reset to before rebase
git reset --hard HEAD@{5}
# Rebase onto correct branch
git rebase correct-branch
リポジトリの破損
破損の検出
# Check repository integrity
git fsck --full
# Check connectivity
git fsck --connectivity-only
# Verify pack files
git verify-pack -v .git/objects/pack/*.idx
破損したオブジェクトの修復
# Remove corrupted object
rm .git/objects/ab/cd1234...
# Try to recover from remote
git fetch origin
# Rebuild object database
git gc --prune=now
# Aggressive cleanup
git gc --aggressive --prune=now
インデックスの破損の修復
# Remove corrupted index
rm .git/index
# Rebuild index
git reset
# Or reset to HEAD
git reset --hard HEAD
破損したパックファイルからの復旧
# Unpack corrupted pack
git unpack-objects < .git/objects/pack/pack-*.pack
# Remove corrupted pack
rm .git/objects/pack/pack-*
# Repack repository
git repack -a -d
# Verify integrity
git fsck --full
参照の修正
破損したブランチ参照
# View all references
git show-ref
# Manual reference fix
echo "abc123def456" > .git/refs/heads/branch-name
# Or use update-ref
git update-ref refs/heads/branch-name abc123
# Delete corrupted reference
git update-ref -d refs/heads/bad-branch
HEAD 参照の修正
# HEAD is corrupted or missing
echo "ref: refs/heads/main" > .git/HEAD
# Or point to specific commit
echo "abc123def456" > .git/HEAD
# Verify HEAD
git symbolic-ref HEAD
古い参照のプルーニング
# Remove stale remote references
git remote prune origin
# Remove all stale references
git fetch --prune
# Remove all remote branches that no longer exist
git branch -vv | grep ': gone]' | awk '{print $1}' | xargs git branch -D
変更の取り消し
直前のコミットを取り消す(変更は保持)
# Soft reset (changes staged)
git reset --soft HEAD~1
# Mixed reset (changes unstaged)
git reset HEAD~1
直前のコミットを取り消す(変更を破棄)
# Hard reset
git reset --hard HEAD~1
# Can still recover via reflog
git reflog
git reset --hard HEAD@{1}
複数のコミットを取り消す
# Reset to specific commit
git reset --hard abc123
# Revert multiple commits (creates new commits)
git revert HEAD~3..HEAD
# Interactive rebase to remove commits
git rebase -i HEAD~5
# Mark commits with 'drop' or delete lines
ファイルへの変更を取り消す
# Discard uncommitted changes
git checkout -- file.go
# Or in Git 2.23+
git restore file.go
# Discard staged changes
git reset HEAD file.go
git restore file.go
# Or in Git 2.23+
git restore --staged file.go
git restore file.go
# Restore file from specific commit
git checkout abc123 -- file.go
公開済みのコミットを取り消す
# Never use reset on public commits
# Use revert instead
git revert HEAD
git revert abc123
git revert abc123..def456
# Revert merge commit
git revert -m 1 merge-commit-hash
強制プッシュの問題への対処
強制プッシュ後の復旧
# If you were force pushed over
git reflog
# abc123 HEAD@{1}: pull: Fast-forward
# Recover your commits
git reset --hard HEAD@{1}
# Create backup branch
git branch backup-branch
# Merge with force-pushed branch
git pull origin main
git merge backup-branch
強制プッシュによる損害の防止
# Always fetch before force push
git fetch origin
# View what would be lost
git log origin/main..HEAD
# Force push with lease (safer)
git push --force-with-lease origin main
# Configure push protection
git config --global push.default simple
大容量ファイルの問題
大容量ファイルの検索
# Find large files in history
git rev-list --objects --all | \
git cat-file --batch-check='%(objecttype) %(objectname) %(objectsize) %(rest)' | \
awk '/^blob/ {print substr($0,6)}' | \
sort --numeric-sort --key=2 | \
tail -10
# Verify current large files
git ls-files | xargs ls -lh | sort -k 5 -h -r | head -20
大容量ファイルの削除
# Using git-filter-repo (recommended)
git filter-repo --path large-file.bin --invert-paths
# Using BFG
bfg --strip-blobs-bigger-than 100M
# After removal
git reflog expire --expire=now --all
git gc --prune=now --aggressive
git push --force origin main
大容量ファイルの防止
# Configure pre-commit hook
cat > .git/hooks/pre-commit << 'EOF'
#!/bin/bash
if git diff --cached --name-only | xargs du -h | awk '$1 ~ /M$|G$/' | grep .; then
echo "Error: Large file detected"
exit 1
fi
EOF
chmod +x .git/hooks/pre-commit
認証の問題
SSH キーの問題
# Test SSH connection
ssh -T [email protected]
# Check SSH key
ls -la ~/.ssh
# Generate new SSH key
ssh-keygen -t ed25519 -C "[email protected]"
# Add key to ssh-agent
eval "$(ssh-agent -s)"
ssh-add ~/.ssh/id_ed25519
# Configure SSH
cat > ~/.ssh/config << EOF
Host github.com
HostName github.com
User git
IdentityFile ~/.ssh/id_ed25519
EOF
HTTPS 認証
# Cache credentials
git config --global credential.helper cache
git config --global credential.helper 'cache --timeout=3600'
# Or use store (less secure)
git config --global credential.helper store
# Update remote URL
git remote set-url origin https://github.com/user/repo.git
# Use personal access token
git clone https://[email protected]/user/repo.git
権限拒否
# Check remote URL
git remote -v
# Change to SSH
git remote set-url origin [email protected]:user/repo.git
# Change to HTTPS
git remote set-url origin https://github.com/user/repo.git
# Verify permissions
ls -la .git/
chmod -R u+rw .git/
サブモジュールの問題
サブモジュールが初期化されていない
# Initialize submodules
git submodule init
git submodule update
# Or in one command
git submodule update --init --recursive
サブモジュール内の Detached HEAD
# Enter submodule
cd submodule-dir
# Create branch
git checkout -b main
# Or attach to existing branch
git checkout main
git pull origin main
# Update parent repo
cd ..
git add submodule-dir
git commit -m "chore: update submodule"
サブモジュールのコンフリクト
# Check submodule status
git submodule status
# Reset submodule
git submodule update --init --force
# Remove and re-add submodule
git submodule deinit -f path/to/submodule
git rm -f path/to/submodule
git submodule add <url> path/to/submodule
パフォーマンスの問題
操作が遅い
# Optimize repository
git gc --aggressive
# Repack efficiently
git repack -a -d --depth=250 --window=250
# Prune old objects
git prune --expire now
# Clean up unnecessary files
git clean -fdx
大規模なリポジトリ
# Shallow clone
git clone --depth 1 <url>
# Fetch only one branch
git clone --single-branch --branch main <url>
# Partial clone
git clone --filter=blob:none <url>
# Sparse checkout
git sparse-checkout init --cone
git sparse-checkout set folder1 folder2
メモリの問題
# Increase memory limits
git config --global pack.windowMemory "100m"
git config --global pack.packSizeLimit "100m"
git config --global pack.threads "1"
# Disable delta compression temporarily
git config --global pack.compression 0
一般的なエラーメッセージ
「fatal: refusing to merge unrelated histories」
# Allow merging unrelated histories
git pull origin main --allow-unrelated-histories
「fatal: not a git repository」
# Reinitialize repository
git init
# Or check if .git directory exists
ls -la .git
# Restore from backup if corrupted
「error: Your local changes would be overwritten」
# Stash changes
git stash
git pull
git stash pop
# Or discard changes
git reset --hard HEAD
git pull
「error: failed to push some refs」
# Fetch and merge first
git pull origin main
# Or rebase
git pull --rebase origin main
# Force push (dangerous)
git push --force origin main
# Safer force push
git push --force-with-lease origin main
「fatal: unable to access: SSL certificate problem」
# Disable SSL verification (not recommended)
git config --global http.sslVerify false
# Or update SSL certificates
git config --global http.sslCAInfo /path/to/cacert.pem
診断コマンド
リポジトリの健全性チェック
# Full integrity check
git fsck --full --strict
# Check connectivity
git fsck --connectivity-only
# Verify objects
git verify-pack -v .git/objects/pack/*.idx
# Check reflog
git reflog expire --dry-run --all
# Analyze repository
git count-objects -vH
デバッグ情報
# Enable verbose logging
GIT_TRACE=1 git status
GIT_TRACE=1 git pull
# Debug specific operations
GIT_TRACE_PACKET=1 git fetch
GIT_TRACE_PERFORMANCE=1 git diff
GIT_CURL_VERBOSE=1 git push
# Configuration debugging
git config --list --show-origin
git config --list --show-scope
予防策
- 定期的なバックアップ: リスクの高い操作の前にバックアップブランチを作成します
- Reflog の使用: Reflog は安全網です。適切な状態に保ちます
- Rerere の有効化: 記録済みのコンフリクト解決を再利用します
- ブランチの保護: ブランチ保護ルールを使用します
- コミット前フック: コミットが作成される前に検証します
- 定期的なメンテナンス: 定期的に
git gcを実行します - 強制プッシュ前のテスト: 必ず
--dry-runで確認します - コミュニケーション: 影響の大きい操作についてチームに知らせます
- Git 内部の仕組みを学ぶ: Git の動作を理解することで問題を防げます
- Git を最新の状態に保つ: 最新の安定版を使用します
リソース
追加のトラブルシューティングガイドは assets/ ディレクトリにあります。
troubleshooting/- 段階的な復旧手順scripts/- 診断および復旧スクリプトchecklists/- 問題診断のワークフロー
references/ ディレクトリには次の資料があります。
- Git のエラーメッセージデータベース
- 復旧手順のドキュメント
- Git の内部構造ガイド
- よくある落とし穴のドキュメント
コメント
Markdown 対応