許可画面の判定表 — 見るだけ・注意・危険
Claude Code が打った Git のコマンド延べ約14,000回のうち、約8,200回は status・diff・log・show の見るだけのコマンドでした。残りの中に、ごくたまに、許可すると取り戻せないものが混ざります。この回では、第1部〜第3部のコマンドを安全(見るだけ)・注意・危険の3段に分けた判定表にまとめ、危険の段のコマンドで何が消えるのかを1コマンドずつ確かめます。最後に、迷ったときに許可の前に打つ安全策を見ます。
- 上のターミナルは、実際に打ったときと同じ出力です(Git は英語で答えます)
- 下の中で起きていることは、Git の中の何が変わったかを図にしたものです。丸がコミット、黒い札がブランチ、ピンクの札が HEAD です
- 図の下に並ぶ3つの箱は作業ツリー・ステージ・HEAD のコミット(1-1 3つの場所)、その下は退避(stash)の棚です
- 右の説明をスクロールして読み進めると、左のターミナルでコマンドが1つずつ打たれます。
→キーでも1つずつ進みます(←で1つ戻ります。スマホでは「次へ」ボタン)。最後まで進んでから→を押すと次の区間へ移ります。黄色く光っているのが、そのコマンドで変わった場所です
1. 3段の決め方 — 何が消えうるか、取り戻せるか
許可するかどうかは、何が消えうるかと消えたら取り戻せるかの2つで決めます。
- 安全 見るだけ。手元のブランチ・ファイル・GitHub のどれも変えない。そのまま許可してよい
- 注意 手元や GitHub が変わる。消えうるのはコミット済みのものだけ。何が変わるかを読んでから許可する
- 危険 コミットしていない変更か、GitHub の歴史が消える。消えるものを逃がしてから許可する
分かれ目は、消えるものがコミットになっていたかどうかです。3-4 reflogで見たとおり、reflog(HEAD が通った場所の記録)はコミットを覚えているので、付箋から外れたコミットも reflog が残る間は辿り直せます。ステージや作業ツリーにだけあった変更、一度も add していないファイルは、どこにも記録されません。GitHub にだけあったコミットも、手元の reflog には出てきません。
これまでの回の表で「消えうるもの」がなしだった git add や git switch も、手元を変えるので、この回では注意の一番軽いところに置きます。git fetch は手元の写しの origin/main を動かすだけなので、見るだけの仲間です(2-3)。
2. 判定表
コマンドの欄は git の後ろの部分です。同じ段の中では、上ほど軽いものです。
| 判定 | コマンド | 何が起きるか | 消えうるもの | 取り戻せるか |
|---|---|---|---|---|
| 安全 | status diff log show branch(名前なし)reflog stash list worktree list clean -n | 見るだけ | なし | — |
fetch / fetch -q | 手元の写し(origin/main)だけを動かす | なし | — | |
| 注意 | add commit revert merge pull --ff-only stash stash pop push | 記録を足す・付箋を進める(push は GitHub 側)・書きかけを棚へ出し入れする | なし | — |
switch / checkout ブランチ / branch -d | 乗り換える・取り込み済みの付箋を剥がす。危ないときは止まる | なし | — | |
restore --staged ファイル / reset -q HEAD ファイル | add を取り消す | add の後に書き換えていたら、add した時点の版 | ふつうは作業ツリーに新しい版が残る | |
merge --abort / rebase --abort | 始める前に戻す | コンフリクトを直しかけた中身 | 戻らない | |
worktree add / worktree remove | 作業ツリーを増やす・片付ける。書きかけがあれば remove は止まる | detached HEAD の作業ツリーで作り、付箋を貼っていないコミット | 手元の reflog に残らない(4-3) | |
checkout コミットID / reset --soft HEAD~1 / reset HEAD~1 / commit --amend / rebase / pull --rebase | 付箋を動かす・コミットを作り直す | 付箋から外れたコミット | reflog で戻せる | |
push --force-with-lease | 手元の写しが GitHub の今と同じときだけ付け替える | 直前に fetch していると、GitHub にだけあるコミット | 手元にはない(3-3) | |
branch -D | 確かめずに付箋を剥がす | そのブランチにしか無いコミットへの道筋 | reflog が残る間は戻せる | |
stash drop | 退避を1つ、戻さずに捨てる | まだ戻していない、その書きかけ | 出力に出る ID を控えていれば git stash apply ID で戻せる(1-7 stash) | |
| 危険 | reset --hard(行き先なし・HEAD~1・origin/main なども) | ステージと作業ツリーを行き先の中身で上書き | 未コミットの変更すべて | 戻らない(外れたコミットは reflog) |
checkout -- ファイル / checkout ファイル / restore ファイル | そのファイルの作業ツリーをステージの中身で上書き | そのファイルの未 add の変更 | 戻らない | |
checkout HEAD -- ファイル / checkout -f ブランチ / switch -f ブランチ | ステージと作業ツリーを HEAD や乗り換え先の中身で上書き | そのファイル(-f はすべて)の未コミットの変更 | 戻らない | |
clean -f / clean -fd | 追跡していないファイル(-d はフォルダも)を消す | 一度も add していないファイル | 戻らない | |
stash clear | 退避の棚を空にする | 棚にある、まだ戻していない書きかけすべて | ほぼ戻らない | |
worktree remove --force | 作業ツリーのフォルダを書きかけごと消す | その作業ツリーの未コミットの変更と追跡していないファイル | 戻らない(4-3) | |
push --force / push -f | 確かめずに GitHub 側の付箋を付け替える | GitHub にだけあるコミット | 手元にはない(3-3) | |
reflog expire --expire=now --all / gc --prune=now | reflog と、辿れないコミットを今すぐ片付ける | 付箋から外れたコミットすべて | 戻らない |
危険の段の大半は、作業ツリーやステージを上書きするコマンドです。付箋やコミットを動かすだけのものは、reflog が後ろで支えるので注意の段に収まります。ここから、危険の段の代表を動かしてみます。
3. git reset --hard — 書きかけがまとめて消える
1-5 resetで見たとおり、--hard はステージと作業ツリーを行き先の中身で上書きします。「いったんきれいにしてやり直します」や、2台で作業していて「GitHub に合わせます」(git reset --hard origin/main)と言うときに出てくる形です。
git reset --hard — 書きかけがまとめて消える
許可画面に
git reset --hardが出たら、許可する前にまずgit statusを見ます。modified: todo.txtが書きかけ、Untracked filesのdraft.txtは一度も add していないファイルです。$ git status On branch main Changes not staged for commit: (use "git add <file>..." to update what will be committed) (use "git restore <file>..." to discard changes in working directory) modified: todo.txt Untracked files: (use "git add <file>..." to include in what will be committed) draft.txt no changes added to commit (use "git add" and/or "git commit -a")git diffで、書きかけの中身を確かめます。+バターを買うの1行が、これから消えうるものです。$ git diff diff --git a/todo.txt b/todo.txt --- a/todo.txt +++ b/todo.txt +バターを買う書きかけを add して、ステージに載せておきます。コミットはしていません。
$ git add todo.txt行き先を書かない
git reset --hardは、付箋を動かさずに、ステージと作業ツリーを HEAD の中身で上書きします。HEAD is now at e5c0a62 パンを追加は「HEAD のコミットの中身に戻した」という意味です。$ git reset --hard HEAD is now at e5c0a62 パンを追加「バターを買う」が消えました。add してステージに載せていても、
--hardはステージごと上書きします。$ cat todo.txt 牛乳を買う 卵を買う パンを買う一度も add していない
draft.txtは残っています。reset --hardは、Git が追跡していないファイルには手を出しません。$ git status On branch main Untracked files: (use "git add <file>..." to include in what will be committed) draft.txt nothing added to commit but untracked files present (use "git add" to track)増えたのは
reset: moving to HEADの1行で、指しているのは元と同じe5c0a62です。reflog はコミットの記録なので、コミットしていない「バターを買う」はどの行にもありません。これが「危険」の段に入る理由です。$ git reflog -2 e5c0a62 (HEAD -> main) HEAD@{0}: reset: moving to HEAD e5c0a62 HEAD@{1}: commit: パンを追加
守られるのはコミットになったものだけで、add は守りになりません。一度も add していないファイルは対象外で、それを消すのは 5 節の git clean です。
4. checkout -- ファイル と restore — 1ファイルの書きかけが消える
Claude Code が打った git checkout 56回のうち、44回が git checkout -- ファイル でした。1-4 checkoutで見たとおり、ファイル名が付いた checkout はファイルを戻す仕事をします。git restore ファイル も同じ仕事です。
checkout -- ファイル と restore — 1ファイルの書きかけが消える
notes.txtとtodo.txtの2つに、書きかけがあります。$ git status On branch main Changes not staged for commit: (use "git add <file>..." to update what will be committed) (use "git restore <file>..." to discard changes in working directory) modified: notes.txt modified: todo.txt no changes added to commit (use "git add" and/or "git commit -a")notes.txtの「卵は10個入り」まで add して、ステージに載せます。$ git add notes.txtadd したあとで、
notes.txtにもう1行書き足します。この「牛乳は低脂肪」は、まだ作業ツリーにしかありません。$ echo "牛乳は低脂肪" >> notes.txtgit checkout -- ファイルは、そのファイルの作業ツリーを ステージの中身 で上書きします。Updated 1 path from the indexのthe indexがステージのことです。$ git checkout -- notes.txt Updated 1 path from the indexadd した「卵は10個入り」は残り、add していない「牛乳は低脂肪」だけが消えました。消えるのは そのファイルの未 add の変更 です。
$ cat notes.txt 特売は水曜 卵は10個入りgit restore ファイルも同じ動きで、何も出力しません。todo.txtの「バターを買う」は一度も add していないので、丸ごと消えました。$ git restore todo.txt残っているのは、ステージに載せた
notes.txtの変更だけです。$ git status On branch main Changes to be committed: (use "git restore --staged <file>..." to unstage) modified: notes.txtHEADを挟むと、ステージと作業ツリーの両方を HEAD のコミットの中身 で上書きします。出力のfrom e5c0a62が、HEAD のコミットです。$ git checkout HEAD -- notes.txt Updated 1 path from e5c0a62add した「卵は10個入り」も消え、
working tree cleanになりました。どのコマンドも HEAD を動かさないので、reflog にも何も残りません。$ git status On branch main nothing to commit, working tree clean
何も挟まなければステージの中身で、HEAD を挟むと HEAD の中身で上書きします。-- は省けるので、checkout の後ろにファイル名があれば危険の側と覚えておきます。
5. git clean — 追跡していないファイルが消える
git clean は、追跡していないファイル(git status の Untracked files に並ぶもの)を消します。試しに作ったファイルの片付けに使いますが、自分が作ったばかりのファイルも同じく消えます。
git clean — 追跡していないファイルが消える
Untracked filesに、一度も add していないrecipe.txtとscratch.txtがあります。todo.txtには書きかけがあります。$ git status On branch main Changes not staged for commit: (use "git add <file>..." to update what will be committed) (use "git restore <file>..." to discard changes in working directory) modified: todo.txt Untracked files: (use "git add <file>..." to include in what will be committed) recipe.txt scratch.txt no changes added to commit (use "git add" and/or "git commit -a")git cleanは、追跡していないファイルを消すコマンドです。-fが無いとrefusing to clean(消すのを断ります)と止まり、何も消しません。$ git clean fatal: clean.requireForce is true and -f not given: refusing to clean-nは、消すものを見せるだけです。Would removeの行が、-fを付けたら消えるファイルです。$ git clean -n Would remove recipe.txt Would remove scratch.txtrecipe.txtは残したいので、add して追跡に入れます。$ git add recipe.txtもう一度見ると、
Would removeはscratch.txtだけになりました。$ git clean -n Would remove scratch.txt-fで本当に消します。Removing scratch.txtと出て、作業ツリーから無くなりました。$ git clean -f Removing scratch.txtadd した
recipe.txtと、追跡しているtodo.txtの書きかけは残っています。消えたscratch.txtは一度も add していないので、Git のどこにも中身が残っていません。$ git status On branch main Changes to be committed: (use "git restore --staged <file>..." to unstage) new file: recipe.txt Changes not staged for commit: (use "git add <file>..." to update what will be committed) (use "git restore <file>..." to discard changes in working directory) modified: todo.txt
reset や checkout で消えた書きかけは、少なくとも前の版がコミットに残っています。追跡していないファイルは、Git が一度も中身を受け取っていません。だから Git も -f が無いと動きません。clean -f を見たら、先に git clean -n を頼んでください。git stash は追跡していないファイルを退避しないので、clean の前の守りになりません(1-7)。
6. git branch -D — 付箋は剥がれても、コミットは戻せる
git branch -D は確かめずにブランチを消すので、危険に見えます。この表では注意の段の一番重いところに置きました。消すのは付箋で、コミットではないからです。
git branch -D — 付箋は剥がれても、コミットは戻せる
献立を試しに書くブランチ
menuを作って乗ります。$ git switch -c menu Switched to a new branch 'menu'新しいファイル
menu.txtを作ります。$ echo "月曜はカレー" > menu.txtステージに載せます。
$ git add menu.txtmenuだけが1つ先へ進みました。「献立を書く」は、menuの付箋からしか辿れません。$ git commit -m "献立を書く" [menu d24492c] 献立を書く 1 file changed, 1 insertion(+) create mode 100644 menu.txtmainに戻ります。$ git switch main Switched to branch 'main'小文字の
-dは、mainに取り込まれていないコミットがあるとnot fully mergedで止まります。hint は「本当に消すなら-Dで」と言っています。$ git branch -d menu error: the branch 'menu' is not fully merged hint: If you are sure you want to delete it, run 'git branch -D menu'大文字の
-Dは、確かめずに付箋を剥がします。「献立を書く」は薄くなりました。(was d24492c)が、剥がす前に指していたコミットです。$ git branch -D menu Deleted branch menu (was d24492c).HEAD の reflog には、
menuにいたときのcommit: 献立を書くがHEAD@{1}として残っています。コミットしたものは、reflog が残っている間は辿れます。$ git reflog -3 e5c0a62 (HEAD -> main) HEAD@{0}: checkout: moving from menu to main d24492c HEAD@{1}: commit: 献立を書く e5c0a62 HEAD@{2}: checkout: moving from main to menuそこに同じ名前の付箋を貼り直します。今いる
mainには触りません。$ git branch menu HEAD@{1}「献立を書く」が戻りました。だから
-Dは、書きかけを消すコマンドとは分けて「注意」の段に置きます。$ git log --oneline --all d24492c (menu) 献立を書く e5c0a62 (HEAD -> main) パンを追加 8b41d07 卵を追加 3f2a9c1 牛乳を追加
剥がした付箋のコミットはコミット済みなので、HEAD の reflog が残る間は辿り直せます(3-4)。ただし reflog は時間がたつと片付けられるので、許可する前に git log --oneline ブランチ名 -3 で中身を見ておくと確実です。
7. GitHub の歴史が消える — push --force
もう1種類の危険が、GitHub 側の歴史が消えるものです。git push --force は GitHub 側の付箋を手元の位置へ付け替えるので、もう1台の PC が push したコミットが外れます。GitHub にだけあったコミットは、手元のどの reflog にも出てきません。Windows と Mac の2台で使っていると、Mac の push を Windows からの force push で消すことが起こりえます(3-3)。main への --force は許可せず、作業ブランチなら --force-with-lease に変えてもらいます。
並行セッションで使う git worktree remove --force(実測25回)も危険の段です。作業ツリーを書きかけごと消します。仕組みは次の回で見ます。
8. 迷ったときの安全策 — 先に逃がしてから許可する
危険の段のコマンドでも、Claude Code が打とうとする理由はたいてい正しいものです。困るのは、そのついでに自分の書きかけまで消えることです。許可する前に、書きかけを逃がしておきます。
危険なコマンドの前に、書きかけを退避する
Claude Code が、直前のコミット
バターを追加を取り消すためにgit reset --hard HEAD~1の許可を求めてきた場面です。まず、取り消すコミットが一番上にあるのを確かめます。$ git log --oneline -3 71d9b3e (HEAD -> main) バターを追加 e5c0a62 パンを追加 8b41d07 卵を追加notes.txtに自分の書きかけがあります。このまま--hardを許可すると、これも消えます。$ git status On branch main Changes not staged for commit: (use "git add <file>..." to update what will be committed) (use "git restore <file>..." to discard changes in working directory) modified: notes.txt no changes added to commit (use "git add" and/or "git commit -a")許可する前に、書きかけを 退避の棚 にしまいます。
$ git stash Saved working directory and index state WIP on main: 71d9b3e バターを追加working tree cleanになりました。これで--hardが上書きしても、消える書きかけはありません。$ git status On branch main nothing to commit, working tree cleanここで許可します。
mainの付箋がパンを追加に戻り、作業ツリーもその中身になりました。$ git reset --hard HEAD~1 HEAD is now at e5c0a62 パンを追加退避した書きかけを戻します。
Dropped refs/stash@{0}は、戻したので棚から外した、という意味です。$ git stash pop On branch main Changes not staged for commit: (use "git add <file>..." to update what will be committed) (use "git restore <file>..." to discard changes in working directory) modified: notes.txt no changes added to commit (use "git add" and/or "git commit -a") Dropped refs/stash@{0} (7cfbe44288cbee281ae388b9dddf5da565048dae)「卵は10個入り」が戻ってきました。
$ cat notes.txt 特売は水曜 卵は10個入り取り消した
バターを追加は、HEAD@{1}の71d9b3eとして残っています。コミットしたものは reflog から、書きかけは棚から、どちらも戻せる状態で危険なコマンドを通せました。$ git reflog -2 e5c0a62 (HEAD -> main) HEAD@{0}: reset: moving to HEAD~1 71d9b3e HEAD@{1}: commit: バターを追加
stash の代わりに、仮のコミットで逃がしてもかまいません。コミットになっていれば、付箋から外れても reflog から拾えます。clean の前は git clean -n、branch -D の前は git log、force push の前は git fetch と git status で、消えるものを先に見ます。
9. Claude Code の許可画面で見かけたら
許可画面では、コマンドの名前より先に付いている印を見ます。
| 見る場所 | 例 | 判定と、何のしるしか |
|---|---|---|
--hard | reset --hard | 危険 ステージと作業ツリーを上書きする |
--force / -f | push --force / clean -f / worktree remove --force | 危険 止まるはずの安全装置を外す |
-- や後ろのファイル名 | checkout -- todo.txt / restore todo.txt | 危険 そのファイルの書きかけを捨てる |
drop / clear / --prune | stash clear / gc --prune=now | 危険 取り戻すための控えを捨てる |
大文字の -D | branch -D | 注意 確かめずに付箋を剥がす |
印が無く、status・diff・log・show・fetch で始まるものは見るだけです。確認を省く設定にしてよいのは、この安全の段だけです。危険の段は、許可する前に git status を自分の目で見ると決めておけば、取り戻せないものを消す場面はまず起きません。
まとめ
- 許可の判断は「何が消えうるか」と「消えたら取り戻せるか」で決める。reflog が覚えているのはコミットだけ
- 安全は見るだけ(fetch を含む)。注意は変わるが、消えうるのはコミット済みのものだけ。危険は未コミットの変更か、GitHub の歴史が消える
- 危険の代表は
reset --hard・checkout -- ファイル・restore ファイル・clean -f・stash clear・worktree remove --force・push --force。branch -Dは付箋だけなので注意 - 迷ったら
git status→ stash か仮のコミット → 許可。clean は-nで先に見る
次の回では、Claude Code が並行してセッションを走らせるときに使う git worktree を扱います。1つのリポジトリに作業ツリーと HEAD をいくつも持たせる仕組みをコミットグラフで見て、この表で危険の段に置いた git worktree remove --force で何が消えるのかを確かめます。