Nhận thay đổi từ chủ thành chi nhánh trong Git


689

Trong kho lưu trữ của tôi, tôi có một chi nhánh được gọi là aq tôi đang làm việc.

Sau đó tôi đã cam kết công việc mới và lỗi trong master.

Cách tốt nhất để có được những cam kết vào aqchi nhánh là gì? Tạo một chi nhánh mới khác mastervà hợp nhất nó với aq?


3
Trong tương lai, bạn cũng có thể bắt đầu nhánh bugfix của mình từ một tổ tiên chung của master và các nhánh khác sẽ cần sửa chữa, để bạn có thể hợp nhất nó vào tất cả các nhánh đó, mà không cần chọn bất cứ thứ gì khác.
Cascabel

2
@Jefromi nhưng điều đó nằm ngoài tầm kiểm soát của anh ấy nếu anh ấy không phải là người duy nhất làm việc trong dự án. người khác cập nhật chủ. chết tiệt, bản thân bạn có thể cập nhật chủ từ nhánh thứ ba, và tình huống sẽ không thể tránh khỏi, và cần một giải pháp chung.
ahnbizcad

@ahnbizcad Tôi khá chắc chắn rằng anh ta kiểm soát nơi anh ta bắt đầu chi nhánh của mình. Nếu chi nhánh của anh ta là tổ tiên chung của những người anh ta muốn hợp nhất và mọi người sau đó thêm vào các chi nhánh đó, thì đó vẫn sẽ là một tổ tiên chung.
Cascabel

Các bạn thắc mắc, lệnh này có làm được không,git pull origin my_branch_name
Basheer AL-MOMani

Câu trả lời:


794

Kiểm tra aqchi nhánh, và rebase từ master.

git checkout aq
git rebase master

rebase có thể đến từ bất kỳ chi nhánh khác? I E. git rebase otherbranch? Có vẻ như tôi hơi lạc lõng trong câu hỏi của mình, tôi đã phân nhánh từ một chi nhánh sau đó thực hiện các thay đổi cho chi nhánh ban đầu.
Ngủ

2
Nếu tôi đúng, rebase theo yêu cầu kéo, nó sẽ hiển thị tất cả các cam kết chính. nếu bạn sử dụng merge / origin master, tất cả các xác nhận chính sẽ được hiển thị dưới dạng 1 cam kết, điều này giúp cho việc xem lại mã dễ dàng hơn.
Người dùng Foo Bar

4
Đôi khi, git mergesẽ tốt hơn. Nếu cả hai nhánh phát triển theo thời gian, bạn nên xem xét cái nào là tốt nhất cho bạn.
erick2red

70
Đi dự tiệc muộn, nhưng đây là một tổng quan tuyệt vời về thời điểm rebase vs merge: atlassian.com/git/tutorials/merging-vs-rebasing/
Lỗi

7
Nếu các cam kết trước đó của bạn trên nhánh aq là công khai thì đừng thực hiện rebase. atlassian.com/git/tutorials/rewriting-history/git-rebase
Hanmant

301

Bạn sẽ có thể chỉ git merge origin/masterkhi bạn ở chi nhánh aq của bạn.

git checkout aq
git merge origin/master

55
Nếu rebase là tốt hơn thì tốt hơn hoàn toàn phụ thuộc vào tình hình cụ thể.
Bombe

13
tại sao bạn không gọi "git merge master" thay vì "git merge origin / master"?
Michael Küller

145
Sử dụng rebasenếu chi nhánh của bạn là địa phương và chưa được đẩy đến origin. Sử dụng mergenếu chi nhánh của bạn đã được đẩy. rebasesẽ viết lại lịch sử.
garbagecollector

17
@Toskan bạn có thể gặp phải các vấn đề trong đó chủ địa phương của bạn không cập nhật với điều khiển từ xa. Bằng cách này, nó đảm bảo rằng bạn đang hợp nhất trong bản sao từ xa của mã.
Chris Kooken

8
@garbagecollector Tôi chống lại rebase (tôi có thể, nhưng sẽ không rebase) Tôi thấy không có lý do gì để đánh bạc với rebase. Nó chỉ làm cho mọi thứ phức tạp không cần thiết. Bạn luôn có câu hỏi "Tôi đã đẩy cái này ra xa chưa?" để suy ngẫm và đó là một nỗi đau để giải thích cho người mới. Một số người nói rằng nó tránh hợp nhất cam kết. Nhưng tôi muốn có cam kết hợp nhất. Họ không lộn xộn, họ tài liệu khi các chi nhánh được hợp nhất. Vì vậy, lần cuối cùng, cuối cùng chúng ta có thể ngừng hành động như tất cả chúng ta đang cam kết làm chủ không? Nếu bạn không thích hợp nhất cam kết trong nhật ký rất nhiều, chỉ cần lọc chúng với - không hợp nhất.
Nurettin

92

Đầu tiên hãy kiểm tra để làm chủ:

git checkout master

Thực hiện tất cả các thay đổi, hotfix và cam kết và đẩy chủ của bạn.

Quay trở lại chi nhánh của bạn, 'aq' và hợp nhất chủ trong đó:

git checkout aq
git merge master

Chi nhánh của bạn sẽ được cập nhật với chủ. Một ví dụ hay và cơ bản về hợp nhất là Phân nhánh 3,2 Git - Phân nhánh và hợp nhất cơ bản .


25

Không có gì đảm bảo rằng các bản sửa lỗi chính không nằm trong số các cam kết khác, do đó bạn không thể hợp nhất. Làm

git checkout aq
git cherry-pick commit1
git cherry-pick commit2
git cherry-pick commit3
...

giả sử những cam kết đó đại diện cho các sửa lỗi.

Từ giờ trở đi, hãy sửa lỗi trong một nhánh riêng. Bạn sẽ có thể chỉ

git merge hotfixes

khi bạn muốn cuộn tất cả chúng vào nhánh dev thông thường.


17

Hoặc cherry-pickcác cam kết liên quan vào chi nhánh aqhoặc hợp nhất chi nhánh masterthành chi nhánh aq.


5
@Slee bạn đã tự trả lời ... đó không phải là giải pháp cho tình huống này
mtet88

13

Hợp nhất nó với aq

git checkout master
git pull
git checkout aq
git merge --no-ff master
git push

8

Cách dễ dàng

# 1. Create a new remote branch A base on last master
# 2. Checkout A
# 3. Merge aq to A

7

Đối với tôi, tôi đã có những thay đổi và tôi muốn có những thay đổi mới nhất từ ​​chi nhánh cơ sở. Tôi đã không thể làm được rebase, và cherry-picksẽ mất mãi mãi, vì vậy tôi đã làm như sau:

git fetch origin <base branch name>  
git merge FETCH_HEAD

vì vậy trong trường hợp này:

git fetch origin master  
git merge FETCH_HEAD

7

Điều này ( từ đây ) làm việc cho tôi:

git checkout aq
git pull origin master
...
git push

Trích dẫn:

git pull origin mastertìm nạp và hợp nhất nội dung của nhánh chính với nhánh của bạn và tạo một cam kết hợp nhất. Nếu có bất kỳ xung đột hợp nhất nào, bạn sẽ được thông báo ở giai đoạn này và bạn phải giải quyết các cam kết hợp nhất trước khi tiếp tục . Khi bạn đã sẵn sàng để đẩy các cam kết cục bộ của mình, bao gồm cả cam kết hợp nhất mới của bạn, đến máy chủ từ xa, hãy chạy git push.


Điều quan trọng cần lưu ý rằng giải pháp này là hoàn hảo nếu một sự hợp nhất được yêu cầu cụ thể, nghĩa là, nếu nhánh chính không thể bị từ chối vì một số lý do.
cudacoder

3

Bạn có một vài lựa chọn. git rebase master aqtrên nhánh sẽ giữ tên cam kết, nhưng KHÔNG TÁI LẠI nếu đây là một nhánh từ xa. Bạn có thể git merge master aqnếu bạn không quan tâm đến việc giữ tên cam kết. Nếu bạn muốn giữ tên cam kết và đó là một nhánh từ xa, git cherry-pick <commit hash>các cam kết trên nhánh của bạn.


0

Bạn cũng có thể làm điều này bằng cách chạy một dòng duy nhất.
git merge aq master

Điều này tương đương với

git checkout aq
git merge master

Đây không phải là làm những gì bạn nghĩ nó đang làm. git merge a bsáp nhập các chi nhánh abvào chi nhánh hiện tại. Nhưng git merge akhi bạn ở chi nhánh asẽ không làm gì cả (đó là lý do tại sao điều này trông hơi giống như nó đang làm những gì bạn nghĩ nó đang làm). (Xem git-scm.com/docs/git-merge#Documentation/ trên .)
MikeBeaton

0

BIÊN TẬP:

Câu trả lời của tôi dưới đây các tài liệu một cách để hợp nhất masterthành aq, nơi mà nếu bạn xem chi tiết của việc hợp nhất nó sẽ liệt kê những thay đổi được thực hiện trên aqtrước khi hợp nhất, không những thay đổi được thực hiện trênmaster . Tôi đã nhận ra rằng đó có thể không phải là những gì bạn muốn, ngay cả khi bạn nghĩ đó là!

Chỉ:

git checkout aq
git merge master

Ổn.

Vâng, sự hợp nhất đơn giản này sẽ cho thấy rằng những thay đổi masterđược thực hiện aqtại thời điểm đó, chứ không phải theo cách khác; nhưng không sao - vì đó là điều đã xảy ra! Sau này, khi cuối cùng bạn hợp nhất chi nhánh của mình vào master, đó là khi hợp nhất cuối cùng sẽ hiển thị tất cả các thay đổi của bạn như được thực hiện master(đó chính xác là những gì bạn muốn và là cam kết nơi mọi người sẽ mong đợi tìm thấy thông tin đó bằng mọi cách).

Tôi đã kiểm tra và cách tiếp cận bên dưới cũng cho thấy chính xác các thay đổi tương tự (tất cả các thay đổi được thực hiện aqkể từ khi phân tách ban đầu giữa aqmaster) như cách tiếp cận thông thường ở trên, khi cuối cùng bạn hợp nhất mọi thứ lại master. Vì vậy, tôi nghĩ rằng nhược điểm thực sự duy nhất của nó (ngoài việc quá phức tạp và không chuẩn ...: - /) là nếu bạn quay trở lại với những thay đổi gần đây git reset --hard HEAD~<n>và điều này vượt qua sự hợp nhất, thì phiên bản bên dưới sẽ quay trở lại Chi nhánh 'sai' mà bạn phải sửa bằng tay (ví dụ: với git reflog& git reset --hard [sha]).


[Vì vậy, những gì tôi nghĩ trước đây là:]

Có một vấn đề với:

git checkout aq
git merge master

bởi vì những thay đổi được hiển thị trong cam kết hợp nhất (ví dụ: nếu bạn nhìn bây giờ hoặc sau này trong Github, Bitbucket hoặc trình xem lịch sử git địa phương yêu thích của bạn) là những thay đổi được thực hiện trên bản gốc, có thể không phải là điều bạn muốn.

Mặt khác

git checkout master
git merge aq

hiển thị các thay đổi được thực hiện trong aq, có thể những gì bạn muốn. (Hoặc, ít nhất, đó thường là những gì tôi muốn!) Nhưng hợp nhất hiển thị các thay đổi đúng là ở nhánh sai!

Làm thế nào để đối phó?!

Toàn bộ quá trình, kết thúc bằng một cam kết hợp nhất hiển thị các thay đổi được thực hiện trên aq (theo hợp nhất thứ hai ở trên), nhưng với việc hợp nhất ảnh hưởng đến nhánh aq, là:

git checkout master
git merge aq
git checkout aq
git merge master
git checkout master
git reset --hard HEAD~1
git checkout aq

Điều này: hợp nhất aq với chủ, chuyển tiếp nhanh đó cùng hợp nhất với aq, hoàn tác nó trên chủ và đưa bạn trở lại aq một lần nữa!

Tôi cảm thấy như mình đang thiếu thứ gì đó - đây dường như là thứ bạn rõ ràng muốn và là thứ khó thực hiện.

Ngoài ra, rebase KHÔNG tương đương. Nó mất dấu thời gian và danh tính của các cam kết được thực hiện trên aq, đó cũng không phải là điều tôi muốn.


0

Kịch bản:

  • Tôi đã tạo một nhánh từ master nói nhánh-1 và kéo nó đến địa phương của tôi.
  • My Friend đã tạo một nhánh từ master nói nhánh-2.
  • Ông cam kết một số thay đổi mã để làm chủ.
  • Bây giờ tôi muốn thực hiện những thay đổi đó từ chi nhánh chính sang chi nhánh địa phương của tôi.

Giải pháp

git stash // to save all existing changes in local branch
git checkout master // Switch to master branch from branch-1
git pull // take changes from the master
git checkout branch-1 // switchback to your own branch
git rebase master // merge all the changes and move you git head  forward
git stash apply // reapply all you saved changes 

Bạn có thể tìm thấy xung đột trên tệp của mình sau khi thực hiện "git stash áp dụng". Bạn cần sửa nó bằng tay và bây giờ bạn đã sẵn sàng để đẩy.

Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.