git rất chậm khi theo dõi các tệp nhị phân lớn


83

Dự án của tôi đã được sáu tháng và git rất chậm. Chúng tôi theo dõi khoảng 30 tệp có kích thước từ 5 MB đến 50 MB. Đó là các tệp nhị phân và chúng tôi giữ chúng trong git. Tôi tin rằng những tệp đó đang làm chậm git.

Có cách nào để loại bỏ tất cả các tệp có kích thước> 5MB từ kho lưu trữ. Tôi biết tôi sẽ mất tất cả các tệp này và điều đó không sao với tôi.

Lý tưởng nhất là tôi muốn một lệnh liệt kê tất cả các tệp lớn (> 5MB). Tôi có thể thấy danh sách và sau đó tôi nói không sao, hãy tiếp tục và xóa những tệp đó và làm cho git nhanh hơn.

Tôi nên đề cập rằng git không chỉ chậm trên máy của tôi mà việc triển khai ứng dụng trên môi trường dàn dựng hiện mất khoảng 3 giờ.

Vì vậy, bản sửa lỗi phải là một cái gì đó sẽ ảnh hưởng đến máy chủ và không chỉ người dùng của kho lưu trữ.


4
Bạn có thể thử sử dụng git từ git-bigfilesdự án
Jakub Narębski

1
bạn có thể muốn thử sử dụng một cái gì đó như git-annex để quản lý các tệp nhị phân. git-annex.branchable.com
Jed Schneider

Trong trường hợp nó hữu ích cho bất kỳ ai, hãy để tôi nói thêm rằng phiên bản git Cygwin của tôi đang bị giảm giá. Khi tôi sử dụng Git-Bash, cùng một kho lưu trữ không có vấn đề gì.
Sridhar Sarnobat

Không biết có còn như vậy không. Tôi hy vọng họ tắt tính năng nén cho mọi thứ mà hiệu ứng nén dưới 50% (hoặc bất kỳ X% có thể chọn một lần nào khác). Ở một số điểm, tốc độ rõ ràng vượt trội không gian phần cứng!
Trilarion

Câu trả lời:


125

Bạn có thu gom rác không?

git gc

Điều này tạo ra sự khác biệt đáng kể về tốc độ, ngay cả đối với các repos nhỏ.


8
Điều này được thực hiện tự động khi có quá nhiều thứ lộn xộn. Tôi nghi ngờ nó thực sự sẽ giúp OP.
Cascabel

@Jefromi, có phải là mới không? Tôi vừa nâng cấp lên 1.7.1 ngày hôm qua, nhưng trước đó phiên bản tôi đang sử dụng chắc chắn không tự động chạy gc.
kubi

@kubi: Chà, nó đã không tồn tại mãi mãi, nhưng nó không hoàn toàn mới - nó được gọi từ commit, merge, am và rebase kể từ caf9de2 (14/09/2007) hoặc trong phiên bản ổn định v1.5.4 (1/02/2008 ).
Cascabel

1
Suy nghĩ thứ hai, git gckhông thể được gọi commitmerge, nếu không git fsck --unreachablesẽ không bao giờ trả lại bất cứ điều gì.
kubi

4
Tìm thấy rồi. Số lượng vật thể rời mặc định trước khi tự động gcchạy là 6700, điều này giải thích tại sao tôi chưa bao giờ thấy nó chạy.
kubi

79

Giải trình

Git thực sự giỏi trong lịch sử khổng lồ của các tệp văn bản nhỏ vì nó có thể lưu trữ chúng và các thay đổi của chúng một cách hiệu quả. Đồng thời, git rất tệ với các tệp nhị phân và sẽ lưu trữ các bản sao riêng biệt của tệp một cách ngây thơ ( ít nhất là theo mặc định ). Kho lưu trữ trở nên rất lớn, và sau đó nó sẽ chậm dần, như bạn đã quan sát.

Đây là một vấn đề phổ biến giữa các DVCS, trầm trọng hơn do bạn tải xuống mọi phiên bản của mọi tệp ("toàn bộ kho lưu trữ") mỗi khi bạn sao chép. Các nhân viên tại Kiln đang làm việc trên một plugin để xử lý các tệp lớn này giống như Subversion, chỉ tải xuống các phiên bản lịch sử theo yêu cầu.

Giải pháp

Lệnh này sẽ liệt kê tất cả các tệp trong thư mục hiện tại có kích thước> = 5MB.

find . -size +5000000c 2>/dev/null -exec ls -l {} \;

Nếu bạn muốn xóa các tệp khỏi toàn bộ lịch sử của kho lưu trữ, bạn có thể sử dụng ý tưởng này git filter-branchđể xem lịch sử và loại bỏ tất cả dấu vết của các tệp lớn. Sau khi làm điều này, tất cả các bản sao mới của kho lưu trữ sẽ gọn gàng hơn. Nếu bạn muốn nâng cấp kho lưu trữ mà không cần sao chép, bạn sẽ tìm thấy hướng dẫn trên trang người dùng (xem "Danh sách kiểm tra để thu hẹp kho lưu trữ").

git filter-branch --index-filter \
    'find . -size +5000000c 2>/dev/null -exec git rm --cached --ignore-unmatch {} \;'

Một lời cảnh báo : điều này sẽ làm cho kho lưu trữ của bạn không tương thích với các bản sao khác, vì các cây và chỉ mục có các tệp khác nhau được kiểm tra; bạn sẽ không thể đẩy hoặc kéo khỏi chúng nữa.


4
Lưu ý: đó là phiên bản find.exe của Unix / Linux, không phải find.exe của Windows.
Craig Trader

1
+1. Có thể muốn gửi đầu ra của findmột tệp trước, hãy kiểm tra danh sách, sau đó sử dụng git rm, đề phòng trường hợp có bất kỳ lần truy cập sai nào. Ngoài ra, hãy kiểm tra git statussau khi xóa các tệp lớn và sử dụng git checkout HEAD <file>để lấy lại mọi tệp bị xóa nhầm.
Cascabel

2
Tôi nghĩ rằng nhận xét của bạn rằng git "lưu trữ các bản sao riêng biệt theo mặc định" là ngược. Theo chuỗi email bạn đã liên kết đến ( thread.gmane.org/gmane.comp.version-control.git/146957/… ) theo mặc định, git cố gắng khác biệt các tệp nhị phân - và đó là nguyên nhân gây ra sự cố; không phải là nơi lưu trữ.
Alexander Bird

16

Đây là một bản sửa đổi được kiểm duyệt nhằm mục đích ít tiêu cực và gây viêm nhiễm hơn:

Git có một điểm yếu nổi tiếng khi nói đến các tệp không phải là tệp văn bản từng dòng. Hiện tại không có giải pháp nào và không có kế hoạch nào được nhóm git cốt lõi công bố để giải quyết vấn đề này. Có những giải pháp thay thế nếu dự án của bạn nhỏ, chẳng hạn như 100 MB hoặc lâu hơn. Có tồn tại các nhánh của dự án git để giải quyết vấn đề khả năng mở rộng này, nhưng các nhánh này chưa trưởng thành tại thời điểm này. Một số hệ thống kiểm soát sửa đổi khác không có vấn đề cụ thể này. Bạn nên coi vấn đề này chỉ là một trong nhiều yếu tố khi quyết định có chọn git làm hệ thống kiểm soát sửa đổi của mình hay không.


8
"Git có một điểm yếu nổi tiếng ..." - cần dẫn nguồn
Nav

6
Tôi biết điều đó. ai cần trích dẫn khi kiến ​​thức phổ biến thực tế của nó. chỉ cần không sử dụng git cho nhị phân. sử dụng lực lượng lao động hoặc quản lý tài sản chuyên biệt.
v.oddou

1
@ v.oddou Chà, có sự khác biệt giữa "tôi biết nó" và "kiến thức chung thực tế của nó". Điều này không phải ai cũng biết và có lẽ nó không hoàn toàn đúng. Vì vậy, bất kỳ loại trích dẫn nào cũng cải thiện câu trả lời này. Nó ổn nhưng chắc chắn không nổi bật và được sao lưu.
Trilarion

2
Chà, không phải đổ thêm dầu vào lửa, nhưng nếu bạn thực hiện tìm kiếm trên google về "git và tệp nhị phân chậm", có rất nhiều liên kết được tìm thấy báo cáo rằng người dùng gặp sự cố khi quản lý tệp nhị phân trong git. Ngoài ra, các nhà phát triển sử dụng SCM này hay SCM khác biết điểm mạnh và điểm yếu của mỗi hệ thống ... vì vậy, git đã phát triển danh tiếng là trở nên thực sự chậm chạp khi các tệp nhị phân được đưa vào một kho lưu trữ.
AhiyaHiya

nó trong tất cả các tài nguyên giới thiệu mà tôi đã sử dụng rằng git không tốt với các tệp nhị phân. git-annex tồn tại để sửa lỗi này. git là tuyệt vời, nhưng không phải cho dữ liệu nhị phân. Sẽ rất tốt nếu liên kết tới các nhánh bổ sung các tính năng nhị phân, để mọi người có thể hỗ trợ công việc.
mờTew

15

Không có gì cụ thể về tệp nhị phân và cách git xử lý chúng. Khi bạn thêm tệp vào kho lưu trữ git, tiêu đề sẽ được thêm vào và tệp được nén bằng zlib và được đổi tên sau hàm băm SHA1. Điều này hoàn toàn giống nhau bất kể loại tệp nào. Không có gì trong nén zlib khiến nó có vấn đề với các tệp nhị phân.

Nhưng tại một số điểm (push, gc) Git bắt đầu xem xét khả năng nén nội dung delta. Nếu git tìm thấy các tệp giống nhau (tên tệp, v.v.), nó sẽ đưa chúng vào RAM và bắt đầu nén chúng lại với nhau. Nếu bạn có 100 tệp và mỗi tệp có dung lượng 50Mb, nó sẽ cố gắng đưa 5GB vào bộ nhớ cùng một lúc. Để làm được điều này, bạn phải thêm một số thứ nữa để làm cho mọi thứ hoạt động. Máy tính của bạn có thể không có dung lượng RAM này và nó bắt đầu hoán đổi. Quá trình này cần có thời gian.

Bạn có thể giới hạn độ sâu của nén delta để quá trình không sử dụng nhiều bộ nhớ nhưng kết quả là nén kém hiệu quả hơn. (core.bigFileThreshold, thuộc tính delta, pack.window, pack.depth, pack.windowMemory, v.v.)

Vì vậy, có rất nhiều suy nghĩ bạn có thể làm để làm cho git hoạt động rất tốt với các tệp lớn.


4
Xem ở đây để biết giải thích về cách vô hiệu hóa các nỗ lực "delta" đó xảy ra.
Alexander Bird

6

Một cách để đẩy nhanh tiến độ là sử dụng --depth 1cờ. Xem trang người đàn ông để biết chi tiết. Tôi không phải là một guru giỏi về git nhưng tôi tin rằng điều này nói làm tương đương với a p4 gethoặc an svn get, tức là nó chỉ cung cấp cho bạn các tệp mới nhất thay vì "đưa cho tôi tất cả các bản sửa đổi của tất cả các tệp trong suốt thời gian" đó là làm gì git clone.


1
Điều này không cho phép bạn đẩy từ kho lưu trữ, vì vậy nó có giới hạn hữu ích.
Martin C. Martin

4

bạn đã nói với git những tệp đó là tệp nhị phân chưa?

ví dụ: được thêm vào *.ext binarykho lưu trữ của bạn.gitattributes


Tôi giả định rằng nói với git rằng các tệp là tệp nhị phân tăng tốc độ.
Nick Vanderbilt

nó có thể xảy ra nếu heuristics của git không thể tự động cho biết tệp là tệp nhị phân.
sml


2

Tôi đã chạy Git từ năm 2008 trên cả windows và GNU / linux và hầu hết các tệp tôi theo dõi đều là tệp nhị phân. Một số repo của tôi có dung lượng vài GB và chứa Jpeg và các phương tiện khác. Tôi có nhiều máy tính cả ở nhà và nơi làm việc chạy Git.

Tôi chưa bao giờ có các triệu chứng được mô tả bởi bài viết gốc. Nhưng chỉ một vài tuần trước, tôi đã cài đặt MsysGit trên một máy tính xách tay Win-XP cũ và hầu như bất cứ điều gì tôi đã làm, nó đều dừng lại. Ngay cả khi kiểm tra chỉ với hai hoặc ba tệp văn bản nhỏ cũng chậm một cách đáng kinh ngạc. Chúng ta đang nói về 10 phút để thêm một tệp nhỏ hơn 1k ... có vẻ như các quy trình git vẫn tồn tại mãi mãi. Mọi thứ khác hoạt động như mong đợi trên máy tính này.
Tôi đã hạ cấp từ phiên bản mới nhất xuống 1.6 gì đó và các vấn đề đã biến mất ...
Tôi có Máy tính xách tay khác cùng nhãn hiệu, cũng được cài đặt Win-XP của cùng một bộ phận CNTT có cùng hình ảnh, trong đó Git hoạt động tốt bất kể phiên bản. .. Vì vậy, phải có một cái gì đó kỳ lạ với máy tính cụ thể đó.

Tôi cũng đã thực hiện một số thử nghiệm với các tệp nhị phân và nén. Nếu bạn có ảnh BMP và bạn thực hiện các thay đổi nhỏ đối với nó và cam kết chúng, git gc sẽ nén rất tốt. Vì vậy, kết luận của tôi là việc nén không phụ thuộc vào việc các tệp có phải là tệp nhị phân hay không.


-2

Chỉ cần thiết lập các tệp để được bỏ qua. Xem liên kết bên dưới:

http://help.github.com/git-ignore/


@Jefromi thực sự nếu bạn nhìn vào liên kết tôi đã đăng, bạn sẽ thấy rằng có hướng dẫn trong đoạn thứ hai cho anh ta biết chính xác những gì cần làm trong trường hợp đó.
joshlrogers

14
Thật. Nhưng nội dung trực tiếp của câu trả lời của bạn là "bỏ qua các tệp", không phải "xóa tệp khỏi theo dõi rồi bỏ qua chúng". Nói chung tốt hơn là viết nó ở đây hơn là liên kết đến một trang web khác.
Cascabel

-24

Đó là bởi vì git không thể mở rộng.

Đây là một hạn chế nghiêm trọng trong git bị át bởi sự ủng hộ của git. Tìm kiếm trong danh sách gửi thư git và bạn sẽ thấy hàng trăm người dùng thắc mắc tại sao chỉ 100 MB hình ảnh ít ỏi (ví dụ, cho một trang web hoặc ứng dụng) lại khiến git phải bó tay. Vấn đề dường như là gần như tất cả git đều dựa vào một cách tối ưu hóa mà chúng gọi là "đóng gói". Thật không may, việc đóng gói không hiệu quả đối với tất cả trừ các tệp văn bản nhỏ nhất (tức là mã nguồn). Tệ hơn nữa, nó ngày càng kém hiệu quả hơn khi lịch sử tăng lên.

Đó thực sự là một lỗ hổng đáng xấu hổ trong git, vốn được quảng cáo là "nhanh" (mặc dù thiếu bằng chứng), và các nhà phát triển git đều nhận thức được điều đó. Tại sao họ vẫn chưa sửa nó? Bạn sẽ tìm thấy câu trả lời trong danh sách gửi thư git từ các nhà phát triển git, những người sẽ không nhận ra sự cố vì họ tài liệu Photoshop (* .psd) là định dạng độc quyền. Vâng, nó thực sự rất tệ.

Đây là kết quả:

Sử dụng git cho các dự án nhỏ, chỉ dành cho mã nguồn mà bạn không muốn thiết lập một kho lưu trữ riêng. Hoặc đối với các dự án chỉ dành cho mã nguồn nhỏ mà bạn muốn tận dụng mô hình sao chép toàn bộ-repo của git để phát triển phi tập trung. Hoặc khi bạn chỉ đơn giản là muốn tìm hiểu một công cụ mới. Tất cả những điều này đều là những lý do chính đáng để sử dụng git và việc học các công cụ mới luôn thú vị.

Không sử dụng git nếu bạn có cơ sở mã lớn, tệp nhị phân, lịch sử khổng lồ, v.v. Chỉ một trong các kho lưu trữ của chúng tôi là TB. Git không thể xử lý nó. VSS, CVS và SVN xử lý tốt. (Mặc dù vậy, SVN phình to.)

Ngoài ra, hãy cho git thời gian để trưởng thành. Nó vẫn chưa trưởng thành, nhưng nó đã có rất nhiều động lực. Theo thời gian, tôi nghĩ bản chất thực tế của Linus sẽ vượt qua những người theo chủ nghĩa OSS, và git cuối cùng sẽ có thể sử dụng được trong lĩnh vực lớn hơn.


15
Câu trả lời này thực sự quá tiêu cực và gây viêm nhiễm. Có, git có vấn đề về khả năng mở rộng với các tệp nhị phân . Nó khá có thể mở rộng và nhanh chóng cho mã. Có rất nhiều bằng chứng về tốc độ (mặc dù bạn khẳng định ngược lại), thậm chí bỏ qua thực tế là CVS / SVN yêu cầu truy cập mạng thay vì truy cập đĩa cho nhiều hoạt động. Có rất nhiều dự án lớn với lịch sử khổng lồ khá hài lòng khi sử dụng git.
Cascabel

8
Và ... của bạn trên Photoshop? Tôi sẽ không lãng phí thời gian của mình để viết một câu trả lời chi tiết, nhưng nếu đọc toàn bộ chuỗi thread.gmane.org/gmane.comp.version-control.git/146957/… (có thể bạn khó chịu vì John trong chủ đề là bạn?), tôi thấy rất nhiều phản hồi hợp lý về cách tốt nhất để xử lý vấn đề này với git hiện tại, cách nó có thể được giải quyết trong tương lai và tại sao nó không phải là ưu tiên hàng đầu của họ.
Cascabel

14
Vâng, tôi không nghĩ bạn đúng, ở đây. Git làm việc cách quá tốt cho hạt nhân Linux để xứng đáng một thô bạo, "không phải là khả năng mở rộng."
Andres Jaan Tack

1
Nhận xét này sẽ đáng tin hơn nếu nó có liên kết hoặc dữ liệu để sao lưu nó. BTW, bạn nghĩ gì về sự lanh lợi?
vy32

3
Có thể anh ấy không bày tỏ quan điểm phổ biến, nhưng tôi nghĩ anh ấy bỏ phiếu từ chối là quá mức vì nó 'tiêu cực' hơn Câu trả lời của OP. Chúng ta nên khuyến khích sự bất đồng quan điểm, không nên dồn dập chỉ vì ai đó không thích hương vị kiểm soát phiên bản của năm. GIT thực sự không phù hợp để theo dõi các tệp nhị phân. Nhưng nó hoạt động tốt cho mã nguồn, đó là mục đích chính, đó là lý do tại sao nó hoạt động tuyệt vời ở nhân linux.
dyasta
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.