Cách hợp nhất nhánh hiện tại vào nhánh khác


182

Tôi có hai nhánh, chủ và dev. Tôi luôn làm việc trên dev và chỉ kiểm tra mã vào nhánh chính sau khi nó được chấp thuận cho sử dụng sản xuất. Khi tôi làm như vậy, tôi phải làm như sau:

git checkout master
git merge dev
git checkout dev

Điều đó rất dài dòng và vì tôi thường xuyên làm điều đó, tôi muốn giảm thiểu nó. Có một lệnh git nào tôi có thể sử dụng để hợp nhất từ ​​nhánh nhánh hiện tại của tôi với nhánh nhánh khác mà không phải kiểm tra nhánh chính trước không? Một cái gì đó có thể như:

git merge dev to master

sẽ là tuyệt vời Tôi đã xem qua tài liệu git và không thấy gì cả.


1
Bạn đã thử sử dụng git đẩy cho việc này?
Jay Sullivan

11
Những gợi ý của đẩy là gì? Đó là để cập nhật điều khiển từ xa , không hợp nhất trong kho lưu trữ của chính mình.
Cascabel

4
Jefromi là đúng, đẩy không hữu ích ở đây. Tôi đang nói về một chi nhánh địa phương khác, không phải là một chi nhánh từ xa.
Chris

2
Thậm chí tệ hơn là khi bạn có thay đổi địa phương không bị giam: git stash, git checkout master, git merge dev, git checkout dev, git stash pop.
Mu Tâm

2
Câu hỏi hay. Tôi cũng muốn điều này vì tôi muốn kéo vào một chi nhánh không hiện tại. Tôi muốn tránh chuyển đổi các nhánh vì tôi có một quy trình khởi động bản dựng nếu bất kỳ tệp nào trong cây làm việc thay đổi.
Kelvin

Câu trả lời:


94

1. Thêm một bí danh từ xa cho kho lưu trữ cục bộ của bạn, ví dụ:

git remote add self file:///path/to/your/repository

(Hoặc trên cửa sổ git remote add self C:\path\to\your\repository)

2. Đẩy vào điều khiển từ xa, ví dụ:

git push self dev:master

2
Submodules! Điều này không chỉ giải quyết vấn đề của câu hỏi mà còn giải quyết vấn đề chuyển nhánh khi chỉ có một mô hình con. Mẹo tuyệt vời!
eddiemoya

2
+1 Đây là sáng tạo và hoàn toàn không chạm vào cây làm việc. Chỉ cần làm rõ: /path/to/your/repositoryđường dẫn đến cây làm việc của bạn, tức là không bao gồm .gitthư mục. Ngoài ra, điều này sẽ đi mà không nói: điều khiển từ xa sẽ phải được cập nhật nếu bạn di chuyển repo.
Kelvin

Tôi không có bất kỳ may mắn nào để làm việc này trong windows ... git remote add self file:///c/projectschỉ cần quay lại với các ghi chú sử dụng
Maslow

2
@ JosephK.Strauss Trước tiên, bạn có thể hợp nhất chủ vào nhánh hiện tại ( dev) và sau đó đẩy cam kết hợp nhất bằng cách sử dụng git push self dev:master.
Leonid Shvechikov

4
Tại sao bí danh từ xa? .làm việc tốt cho tôi : git push . head:master.
geon

60

Câu trả lời được bình chọn cao nhất hiện tại của @zerome là một câu trả lời hay, nhưng hơi dài dòng một cách không cần thiết.

Trong cơ sở của repo git của bạn, bạn có thể làm điều này: git push . dev:master

Một giải pháp tổng quát hơn sẽ hoạt động ở bất cứ đâu trên cây sẽ là:

git push $(git rev-parse --show-toplevel) dev:master

3
git push . dev:masterđơn giản hóa cuộc sống của tôi rất nhiều! Câu trả lời hay nhất cho đến nay, cảm ơn bạn
Jeremy Belolo

bạn có định đẩy chủ đã hợp nhất vào một kho lưu trữ từ xa như github không? tiết kiệm một bước bằng cách thực hiệngit push origin dev:master
Alex R

1
Có thể tái tạo merge --no-ffhành vi với điều này?
shoutuma

1
Tôi nhận được tên từ xa không hợp lệ "." trong Windows. Tôi vẫn cần phải làm gì git remote add self file:///myRepo?
kiewic

1
Nhưng điều này không thực sự hợp nhất ... Nó sẽ hoạt động nếu dev đi trước chủ, nhưng nếu không thì sao?
Thomas Levesque

44

Đặt cược tốt nhất của bạn sẽ là chỉ sử dụng một bí danh, được đặt trong gitconfig ( ~/.gitconfig) toàn cầu của bạn :

[alias]
    merge-to = "!f() { git checkout $1 && git merge $2 && git checkout -; }; f"

để bạn có thể gọi nó từ bất kỳ kho lưu trữ nào

git merge-to master dev

3
Điều gì sẽ xảy ra nếu hợp nhất không tự động, nhưng yêu cầu độ phân giải hợp nhất? (Trong trường hợp này, tôi cho rằng không có công việc nào được thực hiện trên chủ, vì vậy nó sẽ không xảy ra, nhưng vẫn vậy) ...
Stein G. Strindhaug

@Stein: Vì tôi đã sử dụng &&, không ;, nó sẽ thất bại trong việc hợp nhất và không cố gắng chuyển trở lại. Hy vọng rằng người dùng đủ thông minh để xem thông báo "hợp nhất thất bại" và xử lý nó.
Cascabel

6
Tôi thích merge-to = "!f() { export tmp_branch=chi nhánh git này | grep '*' | tr -d '*' ; git checkout $1 && echo git merge $tmp_branch && echo git checkout $tmp_branch; unset $tmp_branch; }; f", nó cho phép của tôi không cần phải gõ vào chi nhánh Tôi hiện đang trên, vì vậy nếu tôi muốn hợp nhất devvào mastervà tôi đang trên devngay bây giờ tôi chỉ cần gõgit merge-to master
Steve

2
Phiên bản tốt hơn với backticks chính xác và không có tiếng vang:merge-to = "!f() { export tmp_branch=`git branch | grep '* ' | tr -d '* '`; git checkout $1 && git merge $tmp_branch && git checkout $tmp_branch; unset $tmp_branch; }; f"
Simon Epskamp

2
lệnh unset không đúng. cố định là: merge-to = "! f () {xuất khẩu tmp_branch = git branch | grep '* ' | tr -d '* '; git checkout $ 1 && git merge --no-ff $ tmp_branch && $ git checkout tmp_branch; tmp_branch unset;}; f"
sassman

38

Một sửa đổi nhỏ từ bí danh Jefromi không yêu cầu bạn nhập vào nhánh hiện tại.

Vì vậy, bạn sử dụng nó như : git merge-to dev.

Điều này sẽ chuyển sang devchi nhánh, hợp nhất nó với HIỆN TẠI và sau đó sẽ chuyển trở lại.

Ví dụ, giả sử bạn đang ở masternhánh, nó sẽ hợp nhất master thành dev và bạn vẫn sẽ ở trên master.

Nó chắc chắn đi đến dotfiles của tôi :)

[alias]
  merge-to = "!gitmergeto() { export tmp_branch=`git branch | grep '* ' | tr -d '* '` && git checkout $1 && git merge $tmp_branch && git checkout $tmp_branch; unset tmp_branch; }; gitmergeto"

6

Cái này cũ rồi, nhưng ...

Kết hợp các giải pháp từ @ kevin-lyda và @ dmytrii-nagirniak ở trên. bí danh này hợp nhất nhánh hiện tại vào nhánh được chỉ định. Nó sử dụng phương thức điều khiển từ xa với và sử dụng các lệnh git để lấy bối cảnh.

[alias]
    merge-to = "!gitmergeto() { git push \"`git rev-parse --show-toplevel`\" `git rev-parse --abbrev-ref HEAD`:$1; } && gitmergeto"

Được sử dụng như:

git merge-to other-branch-name

4

Để hợp nhất nhánh hiện tại vào nhánh khác mà không cần kiểm tra nhánh khác:

Hợp nhất chuyển tiếp nhanh

Điều này thực sự dễ dàng. Theo định nghĩa, hợp nhất chuyển tiếp nhanh chỉ đơn giản là con trỏ nhánh được di chuyển về phía trước trong cây cam kết. Vì vậy, tất cả những gì bạn cần làm chỉ là mô phỏng rằng:

git branch -f master dev

Hãy cẩn thận: Điều này giả định rằng masterchỉ ra một cam kết cũng thuộc devnhánh hoặc một số nhánh khác. Nếu không, bạn có nguy cơ mất việc! Không giống như git mergesẽ tạo ra một cam kết hợp nhất (hoặc khiếu nại) khi không thể chuyển tiếp nhanh, phương thức này âm thầm buộc con trỏ nhánh trỏ đến một cam kết khác.

Điều này cũng giả sử bạn là người duy nhất làm việc trên repo và / hoặc bạn biết bạn đang làm gì.

Mẹo: Nếu bạn đã thực hiện git fetchvà bạn có các cam kết mới origin/master, bạn có thể di chuyển masterchi nhánh mà không cần kiểm tra bằng cách sử dụng:

git branch -f master origin/master

Hợp nhất thông qua cam kết hợp nhất

Không phải lúc nào cũng khả thi. Để tạo một cam kết hợp nhất, bạn phải thực hiện một thao tác hợp nhất. Và để thực hiện thao tác hợp nhất, bạn nên có các xác nhận trong nhánh khác không thuộc nhánh hiện tại.

Nếu bạn có các cam kết trong masterchi nhánh không thuộc devchi nhánh, bạn có thể:

Tuyên bố miễn trừ trách nhiệm: Đây chỉ là một bằng chứng về khái niệm, chỉ để cho thấy đôi khi có thể thực hiện hợp nhất với chi nhánh khác mà không cần kiểm tra. Nếu bạn muốn sử dụng nó hàng ngày, có lẽ bạn muốn tạo bí danh cho nó bằng cách sử dụng chuyển hướng shell hoặc tạo một kịch bản shell cho nó. Sau đó, một lần nữa, bạn cũng có thể tạo một kịch bản shell cho quá trình ngắn hơn được hiển thị trong câu hỏi.

git checkout -b temp
git merge --no-ff -e master
git branch -f master temp
git checkout dev
git branch -D temp

Giải trình:

  1. Kiểm tra một nhánh tạm thời trỏ đến cùng một cam kết như nhánh hiện tại.
  2. Hợp nhất mastervào nhánh tạm thời và khởi chạy trình soạn thảo thông báo cam kết. Nếu bạn muốn cam kết hợp nhất trông giống như bạn đã hợp nhất devchi nhánh vào master, hãy chỉnh sửa nó từ đây:

    Merge branch 'master' into temp
    

    đến đây:

    Merge branch 'dev'
    

    Mẹo: Bạn có thể sử dụng -m "Merge branch 'dev'"thay vì -eđể nhanh hơn.

  3. Cập nhật master con trỏ nhánh để trỏ đến cam kết hợp nhất.
  4. Kiểm tra devchi nhánh.
  5. Buộc xóa chi nhánh tạm thời.

Điều này vẫn chạm vào cây làm việc của bạn, nhưng tối thiểu là như vậy. Nó không quay ngược lại cây cho đến trạng thái ban đầu masterchỉ để mang lại sự thay đổi phát triển một lần nữa. Một số có thể không quan tâm, nhưng đối với những người khác nó có thể quan trọng.


1

Rất nhiều lần bạn đến từ chi nhánh mà bạn muốn hợp nhất chi nhánh hiện tại. Trong trường hợp đó bạn có thể làm:

git co - && git merge @{-1}

ví dụ:

git checkout somebranch      // (while on master)

// add some commits

git co - && git merge @{-1}  // will merge somebranch into master

1

Giải pháp của tôi tương tự như các câu trả lời khác, với những khác biệt sau:

  • chức năng được chia thành nhiều dòng để dễ đọc
  • chức năng gọi set -ex để mỗi lệnh được in và nếu lệnh bị lỗi, hàm sẽ thoát ngay lập tức
  • bí danh chuyển các đối số của nó ngoại trừ đầu tiên (nhánh đích) đến git merge
  • hàm này bao gồm lệnh null : git merge, đảm bảo hoàn thành tab hoạt động với một số thiết lập shell (ví dụ: gitfasttừ oh-my-zsh)
[alias]
  merge-to = "!f() { : git merge ; \
      set -ex ; \
      local this=$(git rev-parse --abbrev-ref HEAD) ; \
      local target=$1 ; \
      shift ; \
      git checkout $target ; \
      git merge $this \"$@\" ; \
      git checkout $this ; \
    } ; f"
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.