Saya mencari pendapat tentang bagaimana menangani file biner besar yang menjadi sandaran kode sumber (aplikasi web) saya. Kami sedang mendiskusikan beberapa alternatif:
- Salin file biner dengan tangan.
- Pro: Tidak yakin.
- Kontra: Saya sangat menentang ini, karena meningkatkan kemungkinan kesalahan ketika membuat situs baru / memigrasikan yang lama. Membangun rintangan lain untuk diambil.
- Kelola semuanya dengan Git .
- Pro: Menghapus kemungkinan untuk 'lupa' untuk menyalin file penting
- Contra: Membengkak repositori dan mengurangi fleksibilitas untuk mengelola basis kode dan checkout, klon, dll. Akan memakan waktu cukup lama.
- Pisahkan repositori.
- Pro: Memeriksa / mengkloning kode sumber secepat mungkin, dan gambar diarsipkan dengan benar dalam repositori mereka sendiri.
- Contra: Menghapus kesederhanaan memiliki satu-satunya repositori Git pada proyek. Itu pasti memperkenalkan beberapa hal lain yang belum saya pikirkan.
Apa pengalaman / pemikiran Anda tentang ini?
Juga: Apakah ada yang punya pengalaman dengan beberapa repositori Git dan mengelolanya dalam satu proyek?
File adalah gambar untuk program yang menghasilkan PDF dengan file-file di dalamnya. File-file tidak akan sering berubah (seperti tahun-tahun sebelumnya), tetapi mereka sangat relevan dengan suatu program. Program tidak akan berfungsi tanpa file.
Jawaban:
Jika program tidak akan berfungsi tanpa file, sepertinya membaginya menjadi repo terpisah adalah ide yang buruk. Kami memiliki suite pengujian besar yang kami pecah menjadi repo yang terpisah tetapi itu benar-benar file "tambahan".
Namun, Anda mungkin dapat mengelola file dalam repo yang terpisah dan kemudian menggunakannya
git-submodule
untuk menarik mereka ke dalam proyek Anda dengan cara yang waras. Jadi, Anda masih memiliki riwayat lengkap dari semua sumber Anda, tetapi, seperti yang saya mengerti, Anda hanya akan memiliki satu revisi yang relevan dari submodule gambar Anda. Thegit-submodule
fasilitas akan membantu Anda menjaga versi yang benar dari kode sejalan dengan versi yang benar dari gambar.Inilah pengantar yang bagus untuk submodul dari Git Book.
sumber
Saya menemukan git-lampiran baru - baru ini yang menurut saya luar biasa. Itu dirancang untuk mengelola file besar secara efisien. Saya menggunakannya untuk koleksi foto / musik saya (dll.). Pengembangan git-annex sangat aktif. Konten file dapat dihapus dari repositori Git, hanya hierarki pohon dilacak oleh Git (melalui symlinks). Namun, untuk mendapatkan konten file, langkah kedua diperlukan setelah menarik / mendorong, misalnya:
Ada banyak perintah yang tersedia, dan ada dokumentasi yang bagus di situs web. Paket tersedia di Debian .
sumber
git annex
tersedia di Windows juga. Jika ada yang pernah mengujinya di Windows, saya ingin mendengar tentang pengalamannya!Solusi lain, sejak April 2015 adalah Git Large File Storage (LFS) (oleh GitHub).
Ia menggunakan git-lfs (lihat git-lfs.github.com ) dan diuji dengan server yang mendukungnya: lfs-test-server :
Anda dapat menyimpan metadata hanya di repo git, dan file besar di tempat lain.
sumber
lfs-test-server
dinyatakan tidak untuk penggunaan produksi. Sebenarnya, saya sedang mengerjakan server LFS produksi ( github.com/artemkin/git-lfs-server ). Ini sedang dalam proses, tetapi sudah bisa diperbaiki, dan kami sedang mengujinya sendiri.Lihat git bup yang merupakan ekstensi Git untuk secara cerdas menyimpan binari besar dalam repositori Git.
Anda ingin memilikinya sebagai submodule, tetapi Anda tidak perlu khawatir tentang repositori semakin sulit ditangani. Salah satu contoh kasus penggunaan mereka adalah menyimpan gambar VM di Git.
Saya belum benar-benar melihat tingkat kompresi yang lebih baik, tetapi repositori saya tidak memiliki binari yang sangat besar di dalamnya.
Jarak tempuh Anda mungkin beragam.
sumber
Anda juga bisa menggunakan git-fat . Saya suka itu hanya tergantung pada stok Python dan
rsync
. Ini juga mendukung alur kerja Git yang biasa, dengan perintah cukup jelas berikut ini:Selain itu, Anda perlu memeriksa file .gitfat ke dalam repositori Anda dan memodifikasi .gitattributes Anda untuk menentukan ekstensi file yang ingin Anda
git fat
kelola.Anda menambahkan biner menggunakan normal
git add
, yang pada gilirannya memanggilgit fat
berdasarkan aturan gitattributes Anda.Akhirnya, ini memiliki keuntungan bahwa lokasi penyimpanan biner Anda sebenarnya dapat dibagikan di seluruh repositori dan pengguna dan mendukung apa pun yang
rsync
dilakukan.UPDATE: Jangan gunakan git-fat jika Anda menggunakan jembatan Git-SVN. Ini akhirnya akan menghapus file biner dari repositori Subversion Anda. Namun, jika Anda menggunakan repositori Git murni, ini berfungsi dengan baik.
sumber
Saya akan menggunakan submodules (sebagai Pat Notz) atau dua repositori yang berbeda. Jika Anda memodifikasi file biner Anda terlalu sering, maka saya akan mencoba untuk meminimalkan dampak dari repositori besar yang membersihkan riwayat:
Saya memiliki masalah yang sangat mirip beberapa bulan yang lalu: ~ 21 GB file MP3, tidak diklasifikasikan (nama buruk, id3 buruk, tidak tahu apakah saya suka file MP3 itu atau tidak ...), dan direplikasi pada tiga komputer.
Saya menggunakan hard disk drive eksternal dengan repositori Git utama, dan saya mengkloningnya ke setiap komputer. Kemudian, saya mulai mengklasifikasikan mereka dengan cara biasa (mendorong, menarik, menggabungkan ... menghapus dan mengganti nama berkali-kali).
Pada akhirnya, saya hanya punya ~ 6 GB file MP3 dan ~ 83 GB di direktori .git. Saya menggunakan
git-write-tree
dangit-commit-tree
untuk membuat komit baru, tanpa komit leluhur, dan memulai cabang baru menunjuk komit itu. "Log git" untuk cabang itu hanya memperlihatkan satu komit.Kemudian, saya menghapus cabang lama, hanya menyimpan cabang baru, menghapus ref-log, dan menjalankan "git prune": setelah itu, folder .git saya hanya berbobot ~ 6 GB ...
Anda dapat "membersihkan" repositori besar dari waktu ke waktu dengan cara yang sama: "git clone" Anda akan lebih cepat.
sumber
Solusi yang ingin saya ajukan didasarkan pada cabang-cabang yatim dan sedikit penyalahgunaan mekanisme tag, untuk selanjutnya disebut sebagai * Orphan Tags Binary Storage (OTABS)
TL; DR 12-01-2017 Jika Anda dapat menggunakan LFS github atau pihak ketiga lainnya, tentu saja Anda harus melakukannya. Jika Anda tidak bisa, maka baca terus. Berhati-hatilah, solusi ini adalah peretasan dan harus diperlakukan seperti itu.
Properti yang diinginkan OTABS
git pull
dangit fetch
, termasukgit fetch --all
masih bandwidth efisien , yaitu tidak semua binari besar ditarik dari jarak jauh secara default.Properti OTABS yang tidak diinginkan
git clone
berpotensi tidak efisien (tetapi tidak harus, tergantung pada penggunaan Anda). Jika Anda menyebarkan solusi ini Anda mungkin harus nasihat rekan Anda untuk menggunakangit clone -b master --single-branch <url>
bukangit clone
. Ini karena git clone secara default benar-benar mengkloning seluruh repositori, termasuk hal-hal yang biasanya tidak ingin Anda buang bandwidthnya, seperti komitmen yang tidak direferensikan. Diambil dari SO 4811434 .git fetch <remote> --tags
bandwidth tidak efisien, tetapi tidak selalu penyimpanan tidak efisien. Anda selalu dapat menyarankan kolega Anda untuk tidak menggunakannya.git gc
trik untuk membersihkan repositori Anda dari file yang tidak Anda inginkan lagi.Menambahkan File Biner
Sebelum Anda mulai memastikan bahwa Anda telah melakukan semua perubahan, pohon kerja Anda mutakhir dan indeks Anda tidak mengandung perubahan yang tidak dikomit. Mungkin merupakan ide yang bagus untuk mendorong semua cabang lokal Anda ke remote Anda (github dll.) Seandainya terjadi bencana.
git checkout --orphan binaryStuff
akan melakukan trik. Ini menghasilkan cabang yang sepenuhnya terputus dari cabang lain, dan komit pertama yang Anda buat di cabang ini tidak memiliki induk, yang akan menjadikannya komit root.git rm --cached * .gitignore
.rm -fr * .gitignore
..git
Direktori internal akan tetap tidak tersentuh, karena*
wildcard tidak cocok dengan itu.git fetch
penyumbatan koneksi mereka. Anda dapat menghindari ini dengan mendorong tag bukannya cabang. Ini masih dapat memengaruhi bandwidth dan penyimpanan sistem file rekan Anda jika mereka memiliki kebiasaan mengetikgit fetch <remote> --tags
, tetapi baca terus untuk mencari solusinya. Silakan dangit tag 1.0.0bin
git push <remote> 1.0.0bin
.git branch -D binaryStuff
. Komit Anda tidak akan ditandai untuk pengumpulan sampah, karena tag anak yatim yang menunjuk padanya1.0.0bin
cukup untuk membuatnya tetap hidup.Memeriksa File Biner
git checkout 1.0.0bin -- VeryBigBinary.exe
.1.0.0bin
diunduh, dalam hal ini Anda harusgit fetch <remote> 1.0.0bin
terlebih dahulu.VeryBigBinary.exe
ke master Anda.gitignore
, sehingga tidak ada seorang pun di tim Anda yang akan mencemari sejarah utama proyek dengan biner secara tidak sengaja.Sepenuhnya Menghapus File Biner
Jika Anda memutuskan untuk sepenuhnya membersihkan VeryBigBinary.exe dari repositori lokal Anda, repositori jarak jauh dan repositori kolega Anda, Anda bisa:
git push <remote> :refs/tags/1.0.0bin
git tag -l | xargs git tag -d && git fetch --tags
. Diambil dari SO 1841341 dengan sedikit modifikasi.git -c gc.reflogExpire=0 -c gc.reflogExpireUnreachable=0 -c gc.rerereresolved=0 -c gc.rerereunresolved=0 -c gc.pruneExpire=now gc "$@"
. Ini juga akan menghapus semua komitmen yang tidak direferensikan lainnya. Diambil dari SO 1904860git clone -b master --single-branch <url>
melakukannyagit clone
.2.0.0bin
. Jika Anda khawatir tentang mengetik rekan kerja,git fetch <remote> --tags
Anda sebenarnya dapat memberi nama lagi1.0.0bin
. Ini akan memastikan bahwa lain kali mereka mengambil semua tag yang lama1.0.0bin
akan direferensikan dan ditandai untuk pengumpulan sampah berikutnya (menggunakan langkah 3). Ketika Anda mencoba untuk menimpa tag pada remote Anda harus menggunakan-f
seperti ini:git push -f <remote> <tagname>
Kata penutup
OTABS tidak menyentuh master Anda atau cabang kode sumber / pengembangan lainnya. Hash komit, semua sejarah, dan ukuran kecil dari cabang-cabang ini tidak terpengaruh. Jika Anda sudah membengkak riwayat kode sumber Anda dengan file biner Anda harus membersihkannya sebagai bagian dari pekerjaan. Skrip ini mungkin berguna.
Dikonfirmasi untuk bekerja di Windows dengan git-bash.
Ini adalah ide yang baik untuk menerapkan satu set tric standar untuk membuat penyimpanan file biner lebih efisien. Menjalankan yang sering dari
git gc
(tanpa argumen tambahan) membuat git mengoptimalkan penyimpanan yang mendasari file Anda dengan menggunakan delta biner. Namun, jika file Anda tidak mungkin tetap sama dengan komit, Anda dapat menonaktifkan delta biner sama sekali. Selain itu, karena tidak masuk akal untuk mengompres file yang sudah dikompresi atau dienkripsi, seperti .zip, .jpg atau .crypt, git memungkinkan Anda untuk mematikan kompresi penyimpanan yang mendasarinya. Sayangnya ini adalah pengaturan semua atau tidak sama sekali yang mempengaruhi kode sumber Anda juga.Anda mungkin ingin membuat skrip bagian-bagian dari OTABS untuk memungkinkan penggunaan yang lebih cepat. Secara khusus, langkah scripting 2-3 dari Completely Deleting Binary Files ke dalam
update
git hook dapat memberikan semantik yang menarik tapi mungkin berbahaya untuk git fetch ("ambil dan hapus semua yang sudah ketinggalan zaman").Anda mungkin ingin melewati langkah 4 dari File Biner yang Dihapus Sepenuhnya untuk menyimpan riwayat lengkap semua perubahan biner pada remote dengan biaya mengasapi repositori pusat. Repositori lokal akan tetap ramping dari waktu ke waktu.
Di dunia Java dimungkinkan untuk menggabungkan solusi ini dengan
maven --offline
membuat bangunan offline yang dapat direproduksi, yang disimpan sepenuhnya dalam kontrol versi Anda (lebih mudah dengan pakar daripada dengan gradle). Di dunia Golang, layak untuk membangun solusi ini untuk mengelola GOPATH Andago get
. Dalam dunia python adalah mungkin untuk menggabungkan ini dengan virtualenv untuk menghasilkan lingkungan pengembangan mandiri tanpa bergantung pada server Pypi untuk setiap build dari awal.Jika file biner Anda terlalu sering berubah, seperti membangun artefak, mungkin ide yang baik untuk naskah solusi yang menyimpan 5 versi terbaru dari artefak di tag yatim
monday_bin
,tuesday_bin
, ...,friday_bin
, dan juga tag yatim piatu untuk setiap rilis1.7.8bin
2.0.0bin
, dll. Anda dapat memutarweekday_bin
dan menghapus binari lama setiap hari. Dengan cara ini Anda mendapatkan yang terbaik dari dua dunia: Anda menyimpan seluruh sejarah kode sumber Anda tetapi hanya riwayat yang relevan dari dependensi biner Anda. Juga sangat mudah untuk mendapatkan file biner untuk tag yang diberikan tanpa mendapatkan seluruh kode sumber dengan semua riwayatnya:git init && git remote add <name> <url> && git fetch <name> <tag>
harus melakukannya untuk Anda.sumber
git gc
" - berhenti membaca di sana secara berkala . Mengapa ada orang yang melepaskan sabuk pengaman terakhir mereka demi melakukan peretasan?git gc
tidak aman untuk dijalankan. Semua komitmen Anda yang menggantung akan tetap tersimpangit push <remote> 1.0.0bin
-remote: error: GH001: Large files detected. You may want to try Git Large File Storage
. Sepertinya mungkin GitHub tidak lagi mendukung ini? Biner yang dimaksud berukuran 100MB.Menurut pendapat saya, jika Anda cenderung sering memodifikasi file-file besar itu, atau jika Anda berniat membuat banyak
git clone
ataugit checkout
, maka Anda harus secara serius mempertimbangkan untuk menggunakan repositori Git lain (atau mungkin cara lain untuk mengakses file-file itu).Tetapi jika Anda bekerja seperti kami, dan jika file biner Anda tidak sering dimodifikasi, maka klon / checkout pertama akan lama, tetapi setelah itu harus secepat yang Anda inginkan (mengingat pengguna Anda tetap menggunakan repositori hasil kloning pertama mereka punya).
sumber
SVN tampaknya menangani delta biner lebih efisien daripada Git.
Saya harus memutuskan sistem versi untuk dokumentasi (file JPEG, file PDF, dan file .odt). Saya baru saja menguji menambahkan file JPEG dan memutarnya 90 derajat empat kali (untuk memeriksa efektivitas delta biner). Repositori Git tumbuh 400%. Repositori SVN hanya tumbuh 11%.
Jadi sepertinya SVN jauh lebih efisien dengan file biner.
Jadi pilihan saya adalah Git untuk kode sumber dan SVN untuk file biner seperti dokumentasi.
sumber
git gc
total repositori git dikurangi menjadi 184KB. Kemudian saya mengubah satu pixel dari putih menjadi hitam dan melakukan perubahan ini, ukuran total repositori git meningkat menjadi 388KB, dan setelahgit gc
ukuran total repositori git dikurangi menjadi 184KB. Ini menunjukkan bahwa git cukup baik dalam mengompresi dan menemukan delta file biner.git clone --filter
dari Git 2.19 + klon dangkalOpsi baru ini pada akhirnya mungkin menjadi solusi terakhir untuk masalah file biner, jika Git dan GitHub devs dan membuatnya cukup ramah pengguna (yang mereka mungkin masih belum mencapai untuk submodul misalnya).
Hal ini memungkinkan untuk hanya mengambil file dan direktori yang Anda inginkan untuk server, dan diperkenalkan bersama dengan ekstensi protokol jarak jauh.
Dengan ini, pertama-tama kita bisa melakukan klon dangkal, dan kemudian mengotomatiskan gumpalan mana yang akan diambil dengan sistem build untuk setiap jenis build.
Bahkan sudah ada
--filter=blob:limit<size>
yang memungkinkan membatasi ukuran gumpalan maksimum untuk mengambil.Saya telah memberikan contoh detail minimal tentang bagaimana fitur di: Bagaimana cara mengkloning hanya subdirektori dari repositori Git?
sumber
Saya pribadi telah mengalami kegagalan sinkronisasi dengan Git dengan beberapa host cloud saya setelah data biner aplikasi web saya berlekuk di atas angka 3 GB . Saya menganggap BFT Repo Cleaner pada saat itu, tetapi rasanya seperti retasan. Sejak itu saya mulai menyimpan file di luar ruang lingkup Git, alih-alih memanfaatkan alat yang dibuat khusus seperti Amazon S3 untuk mengelola file, versi, dan cadangan.
Iya. Tema Hugo terutama dikelola dengan cara ini. Agak kudgy, tapi itu menyelesaikan pekerjaan.
Saran saya adalah memilih alat yang tepat untuk pekerjaan itu . Jika itu untuk sebuah perusahaan dan Anda sedang mengelola codeline Anda di GitHub, bayar uangnya dan gunakan Git-LFS. Jika tidak, Anda dapat menjelajahi lebih banyak opsi kreatif seperti desentralisasi, penyimpanan file terenkripsi menggunakan blockchain .
Opsi tambahan untuk dipertimbangkan termasuk Minio dan s3cmd .
sumber
Lihat di camlistore . Ini sebenarnya bukan berbasis Git, tapi saya merasa lebih tepat untuk apa yang harus Anda lakukan.
sumber