このディレクトリ構造を含むリポジトリがあるとしましょう:
repo/
blog/
_posts/
some-post.html
another-file.txt
_posts
をリポジトリの最上位に移動したいので、構造は次のようになります。
repo/
_posts/
some-post.html
another-file.txt
これはgit mv
で十分簡単ですが、履歴を_posts
alwaysがレポのルートに存在するように見せたいし、取得できるようにしたいです。 some-post.html
経由のgit log -- _posts/some-post.html
の全履歴。 git filter-branch
でいくつかの魔法を使ってこれを達成できると思いますが、その方法を正確に理解していません。何か案は?
これを実現するには、サブディレクトリフィルターを使用できます。
$ git filter-branch --subdirectory-filter blog/ -- --all
編集1:_posts
を効果的にルートにしたくない場合は、代わりにツリーフィルターを使用します。
$ git filter-branch --tree-filter 'mv blog/_posts .' HEAD
編集2:一部のコミットにblog/_posts
が存在しなかった場合、上記は失敗します。代わりにこれを使用してください:
$ git filter-branch --tree-filter 'test -d blog/_posts && mv blog/_posts . || echo "Nothing to do"' HEAD
Ramkumarの回答は非常に有用で価値がありますが、多くの状況では機能しません。たとえば、ディレクトリを他のサブディレクトリとともに新しい場所に移動する場合。
このため、manページには完璧なコマンドが含まれています。
git filter-branch --index-filter \
'git ls-files -s | sed "s-\t\"*-&NEWSUBDIR/-" |
GIT_INDEX_FILE=$GIT_INDEX_FILE.new \
git update-index --index-info &&
mv "$GIT_INDEX_FILE.new" "$GIT_INDEX_FILE"' HEAD
NEWSUBDIRを目的の新しいディレクトリに置き換えるだけです。 dir1/dir2/dir3 /-などのネストされたディレクトリを使用することもできます