這篇要討論的是如果我們對於已經提交的資訊感到後悔,例如帳號密碼,那麼我們有幾種處理方式,
但在處理之前,最安全的就是先把實際的帳密改掉,這樣被看到了也無所謂。
刪除 git
這是很爛的方法但他是個有效的方式,整個 .git 資料夾都刪了就沒紀錄了。
然後看看現行是要把帳密的檔案刪除或搬走。
不過之前的那些修改紀錄與版本就都沒了。
重新提交
去修改或刪除帳密檔案,然後提交,不過有個缺點,
就是可以利用 git 回到之前有帳密的版本。
像是 reset 等這些退版指令。
忽略提交
可以利用之前學過的 .gitignore 讓 git 忽略該帳密檔,
如果是已經被追蹤的檔案記得要下 git rm filename --cached
取消追蹤才行。
修改紀錄
查出是哪個提交有帳密檔,使用之前所學的 rebase -i 然後把 commit 拆下來,
看是要刪檔案還是修改內容等再重新提交上去。
filter-branch
其實 git 提供一個 filter-branch
指令可以來處理這件事,
$ git filter-branch --tree-filter "rm -f mypassword.txt"
Rewrite db3bbec63301d1c638e828c9a38a29314c8a0c44 (9/10) (1 seconds passed, remaining 0 predicted)
Ref 'refs/heads/master' was rewritten
這個指令的好處有:
- 你不需要知道是從哪個提交開始上傳了這個密碼檔,他會找到最早有他的地方將他刪除並把後面的 commit 全部重做
- 因為
--tree-filter
所以當你 checkout 到分支執行這個指令就會幫我們自動搞定有這個檔的 commit
因為後面相關 commit 都會重做,所以如果是很早之前就有的,那就會看到一堆 rewrite 且會跑一陣子。
這個指令是針對這個 branch 所以如果每個 branch 都要刪這個檔案,那就要自己 checkout 到分支去執行這個指令。
如果後悔了就下指令退版回去:
$ git reset refs/original/refs/heads/master --hard
這是因為我們在執行 filter-branch
時 git 會先幫我們紀錄還沒執行的版本。
不然就是找出想回去的 sha1 出來退版回去也行。
刪乾淨
因為剛剛還可以回得去就表示其實並沒有真的刪乾淨,如果真的想完全從 git 把這個檔案刪乾淨,
就要加上 -f 參數
$ git filter-branch -f --tree-filter "rm -f mypassword.txt"
事情還沒完喔,因為可以用 reset 回去,所以也要處理一下 refs/original/refs/heads/master
$ rm .git/refs/original/refs/heads/master
還有之前提到的 reflog
他會記錄 30 天內的提交資訊,所以我們要讓他利刻過期:
$ git reflog expire --all --expire=now
檢查一下會看到很多 unreachable
物件:
$ git fsck --unreachable
那就啟動 git 回收機制把這些垃圾清掉:
$ git gc --prune=now
應該沒有垃圾了:
$ git fsck
Checking object directories: 100% (256/256), done.
Checking objects: 100% (14/14), done.
好了,這下真的回不去了,要徹底刪除一個檔案還真不容易,因為這一切都是 git 為我們著想的保護機制。