Làm thế nào tôi có thể sử dụng git bisect để tìm cam kết TỐT đầu tiên?


90

Tôi có vấn đề sau:

  • phiên bản masterhoạt động tốt
  • phiên bản của thẻ cuối cùng trước master(giả sử last) có lỗi
  • một đồng nghiệp cần một bản vá để lastsửa đổi cho một lỗi nhất định

Được chứ. Hãy hỏi bạn bè của chúng tôi git bisectvề bản sửa đổi đã sửa lỗi:

git bisect start
git bisect bad last
git bisect good master

Nhưng điều đó sẽ không hiệu quả:

Một số vòng quay tốt không phải là tổ tiên của vòng quay xấu.
git bisect không thể hoạt động bình thường trong trường hợp này.
Có thể bạn nhầm lẫn vòng quay tốt và xấu?

Bất kỳ gợi ý để vượt qua điều này? Tôi đã bỏ lỡ điều gì đó trong tài liệu?


1
Tôi đang chạy git bisect run ...để tự động phân chia. Vì vậy, tôi không có cơ hội chỉ để hoán đổi các từ goodbad(điều đó đã quá rõ ràng). Làm thế nào để sử dụng runđể tìm bản sửa đổi tốt đầu tiên?
Daniel Böhmer

@ DanielBöhmer: bạn phải hoán đổi các điều khoản bên trong script của bạn đang chạy, phải không?
eckes

Tập lệnh được chạy bởi git bisect runtrả về tốt hoặc xấu dưới dạng mã thoát, không phải dưới dạng chuỗi. Xem câu trả lời của tôi mà tôi vừa đăng dưới đây.
Daniel Böhmer

@ DanielBöhmer: tốt, trong trường hợp đó, bạn sẽ phải đảo ngược mã trả lại, phải không?
eckes

Đúng, đó là những gì được mô tả trong câu trả lời của tôi.
Daniel Böhmer

Câu trả lời:


98

Kể từ git 2.7, bạn có thể sử dụng các đối số --term-old và --term-new.

Ví dụ: bạn có thể xác định một cam kết khắc phục sự cố do đó:

git bisect start --term-new=fixed --term-old=unfixed
git bisect fixed master
git bisect unfixed $some-old-sha1

Khi bạn kiểm tra, hãy nói git bisect fixedhoặc git bisect unfixedkhi thích hợp.

Câu trả lời cũ, dành cho các phiên bản git trước 2.7

Thay vì tạm thời đào tạo bản thân để nghĩ rằng xấu có nghĩa là tốt và tốt có nghĩa là xấu, tại sao không tạo một số bí danh?

Trong ~/.gitconfigthêm những điều sau đây:

[alias]
        bisect-fixed = bisect bad
        bisect-unfixed = bisect good

Bạn có thể bắt đầu xác định một cam kết khắc phục sự cố do đó:

$ git bisect start
$ git bisect-fixed master
$ git bisect-unfixed $some-old-sha1

Khi bạn kiểm tra, hãy nói git bisect-fixedhoặc git bisect-unfixedkhi thích hợp.


5
Ngoài ra, git không cho phép bạn tạo bí danh cho các lệnh phụ. Do đó các dấu gạch ngang. Nếu nó thực sự là (hoặc được thực hiện), hy vọng ai đó sẽ cập nhật câu trả lời.
Michael Wolf

3
Ngay cả khi bạn sử dụng bí danh, đầu ra từ git sẽ không, vì vậy nó vẫn sẽ báo foo is the first bad commit, vì vậy có vẻ như đào tạo tạm thời vẫn cần thiết, phải không?
ThomasW

2
Điểm công bằng. (Đã ủng hộ nhận xét của bạn.) Mặc dù vậy, hy vọng rằng nó ít nhất là ít hơn một chút tải nhận thức bổ sung để đối phó và với tư cách là các lập trình viên, chúng tôi đã có rất nhiều.
Michael Wolf,

1
Tôi khuyên bạn nên sử dụng bí danh 'before' và 'after'. Bằng cách đó, bạn không cần phải làm ngược lại ý thức "khi tôi nhìn thấy lỗi, tôi nên viết 'tốt'"; thay vào đó, bạn chỉ có — có khả năng nhỏ hơn — chi phí nhớ rằng bạn đang tìm kiếm sự xuất hiện / biến mất của một lỗi (tức là nhớ loại thay đổi bạn đang tìm kiếm— “trước khi cái gì?”).
Jonas Kölker

1
@ JonasKölker, đó là một ý tưởng tuyệt vời. Tôi đã sử dụng bí danh được đề xuất trong câu trả lời, cũng như bisect-after = bisect badbisect-before = bisect goodtheo đề xuất của bạn. Bây giờ tôi có thể sử dụng một trong hai bộ bí danh. Chúng ta sẽ thấy cái mà tôi thích hơn sau một vài lần sử dụng.
Gabriel Staples

47

Tôi sẽ chỉ "ăn gian" git và hoán đổi ý nghĩa của tốt <=> xấu.

Nói cách khác, hãy coi "xấu" là thứ không thể hiện vấn đề, vì vậy đây không phải là phiên bản "tốt" để bạn làm căn cứ cho bản vá.

Tốt và xấu dù sao cũng là những khái niệm khá chủ quan, phải không? :)

git bisect start
git bisect good last
git bisect bad master

2
Vâng, nếu bạn nghĩ về nó thì không có ý nghĩa chung chung là tốt hay xấu (có lẽ thậm chí không phải trong tôn giáo) .. nó chỉ phụ thuộc vào mục đích của bạn. Bằng cách này nó không thực sự lừa dối - nhưng có lẽ Git's Sin (để ở lại chủ đề tôn giáo: D là chọn một thuật ngữ gây tranh cãi như vậy hơn là một "mục tiêu" / "nguồn gốc" trung lập hơn ... Nhưng vâng, triết học có thể là tâm trí- boggling ;-)
inger

Đây hẳn là lần đầu tiên tôi nghe nói rằng bọ có thể "tốt".
MarcH

1
Đó là những gì tôi đã làm trước khi tôi tìm thấy câu hỏi này. Tôi sẽ không làm điều đó nữa. Hãy nhớ rằng, chỉ cần một câu trả lời sai trước khi toàn bộ phần chia nhỏ bị hỏng. Đừng xoay chuyển tâm trí của bạn.
proski

20

Nếu bạn đang sử dụng git bisect runnhư tôi đã làm với provelệnh của Perl (chạy các bài kiểm tra tự động), bạn không có cơ hội chỉ để hoán đổi goodbad. Sự thành công của các thử nghiệm sẽ được báo cáo dưới dạng mã thoát.

Tôi đã tìm thấy một cú pháp Bash hợp lệ để phủ định mã thoát của chương trình do git bisect run:

git bisect start
git bisect bad HEAD                 # last revision known to PASS the tests
git bisect good $LAST_FAIL_REVISION # last revision known to FAIL the tests
git bisect run bash -c "! prove"

Điều này đã cho tôi bản sửa đổi đầu tiên để vượt qua các bài kiểm tra prove.


Tôi đồng ý, tôi không muốn sửa đổi trường hợp thử nghiệm của mình để điều này là hoàn hảo.
seanlinsley

8

Git bây giờ cho phép bạn sử dụng oldnewkhông đầu tiên định nghĩa chúng. Bạn phải gọi git bisect startmà không có cam kết như các đối số khác, sau đó bắt đầu phân chia đúng cách bằng cách gọi

git bisect old <rev>
git bisect new <rev>

https://git-scm.com/docs/git-bisect#_alternate_terms

Về cơ bản, đây là những gì @MarcH đã đề xuất nên được thực hiện.


1
Đây là câu trả lời phù hợp nhất (đối với git hiện đại). Và lệnh bắt đầu phải là (theo liên kết bạn đã chia sẻ):git bisect start --term-new fixed --term-old broken
Sam Protsenko

Thật. Khi nào các tùy chọn này được giới thiệu? Tôi muốn cập nhật câu trả lời của mình.
Michael Wolf

@MichaelWolf Chúng đã xuất hiện trong phiên bản 2.7.0 .
GKFX

6

Bí danh Git là một ý tưởng hay, tuy nhiên các điều khoản fixedunfixedcó cùng một vấn đề hơn là goodbad: bạn không thể có chúng tương thích với cả hồi quy và tiến trình. Thật dễ dàng để tìm thấy các từ hoạt động theo một trong hai cách: chỉ cần chọn chúng từ thuật ngữ tìm kiếm nhị phân ban đầu có bản chất trung lập không có định kiến ​​về điều gì là tốt hay xấu. Ví dụ:

git config --global alias.bisect-high 'bisect bad'
git config --global alias.bisect-low  'bisect good'

Với các thuật ngữ trung lập như thế này, bạn luôn có thể nhập: git bisect-high(hoặc git bisect-upper, hoặc git-bisect max, ... sự lựa chọn của bạn!) Cho dù bạn đang tìm kiếm hồi quy hay sửa chữa .

Thật tệ là các nhà phát triển git bisect không thể đơn giản sử dụng lại bất kỳ thuật ngữ nào hiện có. Nói chung, giao diện người dùng không phải là mối quan tâm của git: http://stevebennett.me/2012/02/24/10-things-i-hate-about-git/


Từ: git.github.io/rev_news/2015/07/08/edition-5 "Một số loạt bản vá đang được đánh bóng để cho phép git bisect sử dụng một cặp thuật ngữ tùy ý thay vì tốt và xấu, ..."
MarcH
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.