我有问题,请多多指教!我有一个现有的git repo,出于各种原因(我不会在这里讨论),我正在尝试创建一个ROOT提交
说这是我的git提交历史记录:
(ROOT) C1 <-C2 <-C3 <-C4 <-C5 <--branchname (HEAD)
我想在C1之前添加一个初始提交(CX,它不是空的)。所以它应该像这样结束:
(NEW ROOT) CX-C1 <-C2 <-C3 <-C4 <-C5 <--branchname (HEAD)
我在这里找到了类似的问题:Insert a commit before the root commit in Git?但这是为了在现有根之前附加一个EMPTY git commit。我还在这里尝试了答案中的步骤:https://stackoverflow.com/a/9736098/11491070进行了一次更改:我将git commit --allow-empty -m 'initial'
替换为git add .; git commit -m "initial laravel commit"; git push;
,然后执行了重新设置步骤:git rebase --onto newroot --root master
失败,并出现TON合并冲突:
First, rewinding head to replay your work on top of it...
Applying: add initial quickadminpanel, with admin intrface and APIs for tags. Also added (but not yet enabled) ajax datatables module
Using index info to reconstruct a base tree...
.git/rebase-apply/patch:4537: trailing whitespace.
*
.git/rebase-apply/patch:4539: trailing whitespace.
*
.git/rebase-apply/patch:4547: trailing whitespace.
*
warning: 3 lines add whitespace errors.
Falling back to patching base and 3-way merge...
CONFLICT (add/add): Merge conflict in webpack.mix.js
Auto-merging webpack.mix.js
CONFLICT (add/add): Merge conflict in routes/web.php
Auto-merging routes/web.php
CONFLICT (add/add): Merge conflict in routes/api.php
Auto-merging routes/api.php
CONFLICT (add/add): Merge conflict in resources/views/welcome.blade.php
Auto-merging resources/views/welcome.blade.php
CONFLICT (add/add): Merge conflict in resources/sass/app.scss
Auto-merging resources/sass/app.scss
CONFLICT (add/add): Merge conflict in resources/sass/_variables.scss
Auto-merging resources/sass/_variables.scss
CONFLICT (add/add): Merge conflict in resources/lang/en/validation.php
Auto-merging resources/lang/en/validation.php
CONFLICT (add/add): Merge conflict in resources/lang/en/passwords.php
Auto-merging resources/lang/en/passwords.php
CONFLICT (add/add): Merge conflict in resources/lang/en/pagination.php
Auto-merging resources/lang/en/pagination.php
CONFLICT (add/add): Merge conflict in resources/lang/en/auth.php
Auto-merging resources/lang/en/auth.php
CONFLICT (add/add): Merge conflict in resources/js/bootstrap.js
Auto-merging resources/js/bootstrap.js
CONFLICT (add/add): Merge conflict in resources/js/app.js
Auto-merging resources/js/app.js
CONFLICT (add/add): Merge conflict in package.json
Auto-merging package.json
CONFLICT (add/add): Merge conflict in database/seeds/DatabaseSeeder.php
Auto-merging database/seeds/DatabaseSeeder.php
CONFLICT (add/add): Merge conflict in database/migrations/2014_10_12_100000_create_password_resets_table.php
Auto-merging database/migrations/2014_10_12_100000_create_password_resets_table.php
CONFLICT (add/add): Merge conflict in database/factories/UserFactory.php
Auto-merging database/factories/UserFactory.php
CONFLICT (add/add): Merge conflict in database/.gitignore
Auto-merging database/.gitignore
CONFLICT (add/add): Merge conflict in config/services.php
Auto-merging config/services.php
CONFLICT (add/add): Merge conflict in config/logging.php
Auto-merging config/logging.php
CONFLICT (add/add): Merge conflict in config/database.php
Auto-merging config/database.php
CONFLICT (add/add): Merge conflict in config/cache.php
Auto-merging config/cache.php
CONFLICT (add/add): Merge conflict in config/broadcasting.php
Auto-merging config/broadcasting.php
如何解决此问题?请帮助!
[首先,请注意:您已将存储库向前拉。 Git会倒退它们。将根提交last(即左侧)和latest >>提交first(即右侧)放入]:>C1 <-C2 <-C3 <-C4 <-C5 <--branchname
分支名称始终包含最新
提交的哈希ID。这就是Git如何知道最新的一个。 Git使用C5
查找C4
,因为提交C5
本身具有唯一的哈希ID,contains就是提交C4
的唯一哈希ID。同时C4
保留C3
的哈希ID,依此类推; C2
拥有C1
的唯一哈希ID,C1
是根提交因为内部没有父哈希ID。第二,实际上不能更改任何提交。因此,您将在此处执行not
“ change commitC1
”-您和Git都无法执行此操作-而是进行一个新的提交,即C1'
或C21
或我们要调用的任何内容。在进行此新提交之前,我们需要另一个新提交CX
,它是一个根提交并包含所需的内容。您可以
使用Antony Hatchkins's answer中的方法,但是如今,这样做的方法是从git checkout --orphan
开始(而不是棘手的符号引用命令):git checkout --orphan newroot
git rm -rf --cached . # same as before
<arrange work tree as desired> # same as before
git add . # or git add each file, same as before
git commit # same as before
这是创建提交CX
的操作序列,因此我们具有:
C1--C2--C3--C4--C5 <-- master
CX <-- newroot
现在我们进入最有趣的部分。使用通过选择樱桃进行重新设置工作。这会将提交git rebase
是错误的方法。因为
C1
转换为对每个文件的[[add请求–提交C1
是根提交,将其与empty tree进行比较以查看发生了什么更改,并且如您所见,这导致您在C1
中已经添加的每个文件中的添加/添加冲突。您必须在这里回答的问题-我不能为您回答-是:您想要在新的CX
副本中想要什么[[0],类似于C1
,但它具有C1
作为其父项?最后,我们将拥有:CX
C1--C2--C3--C4--C5 [abandoned]
CX--C1'-C2'-C3'-C4-C5' <-- master
的哈希ID上运行git checkout
,是否应该像在C1'
的哈希ID上运行git checkout
一样看到相同内容?这两个提交将具有不同的哈希ID,但是作者和提交者,时间戳和日志消息相同,依此类推。如果它们也应该具有相同的tree(快照),则使用
C1
和git replace
可以轻松完成工作。这是基本的食谱:git filter-branch
((此时您可以运行git replace --graft <hash-of-C1> newroot
以确保它看起来正确)。然后运行:git log
(假设您只希望复制git filter-branch -- master
中的提交,并更新参考master
)。无操作筛选器分支(未指定筛选器)以正确的顺序(即,向前,即向Git的后退)复制每个可到达的提交,先复制master
,然后复制C1
,依此类推,但是—至关重要的是-遵守替换指令
。所以现在我们有了这个:
C2
如果这是理想的最终结果,我们现在只需要删除
C1--C2--C3--C4--C5 refs/original/refs/heads/master CX <-- refs/replace/<hash-of-C1> \ C1'-C2'-C3'-C4-C5' <-- master
名称和不再有用的refs/original/
名称:
refs/replace/<hash-of-C1>
您的历史记录现在已被重写。所有old
克隆都必须销毁(或者至少应该停止使用它们),因为它们中的哈希ID是original提交的哈希ID,而您不想重生使生活变得悲惨。更新后的克隆中废弃的C1至C5是无害的:它们可以以废弃状态留在那里,直到Git's GrimReaper
Collectorgit update-ref -d refs/original/refs/heads/master git update-ref -d refs/replace/<hash-of-C1>
到处乱扔垃圾为止。