2012-02-12 93 views
1

我的存儲庫設置出現問題:我初始化了我的存儲庫在錯誤的目錄中並開始使用它。我已經創建了一些分支並再次合併它們。我想保留這段歷史。過濾器分支移動根目錄後重復提交

現在它是如何:

wrongRootProjectDir/ 
| 
+-.git 
| 
+-realProjectDir 
    | 
    +-<Project files> 

究竟應該如何樣子:

realProjectDir 
| 
+-.git 
| 
+-<Project files> 

所以基本上我想一切都轉向一個目錄了。 wrongRootProjectDir也只包含.git文件和realProjectDir目錄。

我在SO How can I move a directory in a Git repo for all commits?找到了一些提示,說明可能有辦法。我運行一個git clone oldrepo newrepo得到一個備份回購和新回購跑

git filter-branch --subdirectory-filter realProjectDir -- --all 

。它似乎工作,但是我從舊的存儲庫中丟失了我的合併和分支結構。過濾回購有正確的路徑,但缺乏合併提交。另外老提交仍然在周圍,使回購看起來是這樣的:

(Commit A) 
| 
(Commit B) 
| 
(Commit C) 
| 
(Commit A') 
| 
(Commit B') 
| 
(Commit C') 

其中A」是新的提交。我的多個分支有問題,並且使用filter-branches?所以現在我每次都提交兩次,一次用錯誤的舊路徑,一次用新路徑。

摘要

有向上移動一個完整的目錄樹中的一個層,並保持各分公司的方式,而不會產生雙提交合並?

更新 我仍然無法設法保留我的合併提交和正確的分支佈局。一切都變成了一連串的承諾。

更新

添加了歷史樹前:

Commit history before filter-branch

,並使用gitk運行過濾器分支後:

Commit history after filter-branch

工作目錄是乾淨的時我ru這個命令。爲了測試我使用簡單的cp -r將整個目錄樹複製到另一個目錄並在那裏進行測試。 filter-branch命令在這種意義上起作用,即它移動子目錄,但它仍然使歷史變平坦。據我所知,我沒有做太複雜的事情,只是正常的分支和合並的東西。

更新

我發現了以前的狀態了錯誤的圖片。我試圖轉換一個非重寫的存儲庫。

+0

filter-branch不是什麼扁平化的東西,它不會創建重複的提交。你的問題是別的。我已經寫了一個關於什麼是*實際*發生的最佳猜測的答案;如果這還不夠,你可以清楚地解釋如何重現這個問題(例如原始歷史記錄,確切的命令運行,最終歷史記錄 - 包括你如何查看歷史記錄),我可能會提供幫助。 – Cascabel 2012-02-12 18:24:35

+0

你的歷史之前有過濾器分支的備份參考。它已被重寫。這些提交也在你的實際分支上,你將要重寫嗎?或者在其他地方的實際分支,已經平坦的歷史? (使用'gitk --branches'來查看實際的分支。)你的屏幕截圖實際上並沒有證明這些是正在被重寫爲平面的提交。考慮到這些參考文獻的存在,您必須將'-f'傳遞給filter-branch才能使其正常工作。你也沒有提到。 – Cascabel 2012-02-12 21:17:10

+0

@Jefromi我展示了錯誤的圖片。我剛剛從已經重寫過的回購中複製出來。正如你所說的那樣,提交是備份的。我現在用我的回購之前的真實狀態替換了圖片。 – GorillaPatch 2012-02-12 22:20:26

回答

1

filter-branch也正是這樣做的工具。這是它的全部目的。如果您遇到問題,那是因爲您做錯了,而您沒有告訴我們。 filter-branch不平坦的歷史。您可能會看到gitk --all,並且看到重寫的歷史記錄和舊的歷史記錄(將會標記爲original/refs/heads/...) - 在這種情況下,請注意兩個歷史記錄之間沒有關聯。也有可能你在之前做了一些事情,把搞亂了。當你再次嘗試時,你是從一個新的克隆中開始,從你想要的確切的原始歷史開始?

下面是關於一個最簡單的例子證明了這工作正是因爲它應該:

git init 
mkdir subdir 
touch x subdir/a subdir/b subdir/c 
git add subdir/a 
git commit -m 'a' 
git add subdir/b 
git commit -m 'b' 
git checkout -b foo HEAD^ 
git add subdir/c 
git commit -m 'c' 
git checkout master 
git merge foo 
git add x 
git commit -m 'x' 
git filter-branch --subdirectory-filter subdir -- --all 
# now inspect e.g. with gitk --all 

原裁判在裁判/原廠/裁判身邊不停地/ ...所以,如果你搞砸了,你可以回到他們身邊。如果你檢查結果,並確定一切都很好,那麼你可以刪除它們。在手冊頁對於給出的方法是這樣的:

git for-each-ref --format="%(refname)" refs/original/ | xargs -n 1 git update-ref -d 

但實際上你也可以只是做rm -rf .git/refs/original

+0

在這方面你是對的,我看到了舊的歷史和新的變化。但是所有的合併都是平坦的。雖然你的例子工作正常。我發佈了一些完全按照您指定的方式運行filter-branch命令之前和之後的gitk屏幕截圖。 – GorillaPatch 2012-02-12 19:58:55

0

這應該爲你做它(其他城市realProjectDir到任何該文件夾命名):用一個子目錄過濾

git filter-branch --prune-empty --subdirectory-filter realProjectDir master 

Reference

+0

沒有,沒有做任何事情。沒有雙重提交,但.git目錄也沒有移動到正確的位置。 – GorillaPatch 2012-02-12 17:03:22

相關問題