`git pull` กินการบ้านของฉันอย่างไร


53

ฉันรู้สึกเหมือนเด็กในสำนักงานใหญ่อธิบายว่าสุนัขกินการบ้านของฉันในคืนก่อนที่จะถึงกำหนด แต่ฉันกำลังดูข้อผิดพลาดการสูญเสียข้อมูลบางอย่างที่บ้าในหน้าและฉันไม่สามารถเข้าใจได้ว่ามันเกิดขึ้นได้อย่างไร ฉันอยากรู้ว่าคอมไพล์กินพื้นที่เก็บข้อมูลของฉันได้อย่างไร! ฉันใส่คอมไพล์ผ่านนักเขียนหลาย ๆ ครั้งและมันก็ไม่เคยกระพริบ ฉันเคยใช้มันเพื่อแบ่ง repo 20 Gig Subversion ออกเป็น 27 repos git และกรองตัว foo ออกจากพวกมันเพื่อแก้ปัญหายุ่งเหยิงและมันก็ไม่เคยสูญเสียไบต์บนฉัน reflog อยู่ที่นั่นเสมอเพื่อถอยกลับ คราวนี้พรมหมดแล้ว!

จากมุมมองของฉันสิ่งที่ฉันทำก็คือการเรียกใช้git pullและมันทำให้พื้นที่เก็บข้อมูลในเครื่องของฉันหมด ฉันไม่ได้หมายความว่า "ทำให้สับสนรุ่นที่เช็คเอาต์" หรือ "สาขาที่ฉันไป" หรืออะไรทำนองนั้น ผมหมายถึงสิ่งทั้งหมดจะหายไป

นี่คือภาพหน้าจอของเทอร์มินัลของฉันในเหตุการณ์:

ภาพหน้าจอของเหตุการณ์ที่เกิดขึ้น

ให้ฉันแนะนำคุณผ่านสิ่งนั้น พรอมต์คำสั่งของฉันมีข้อมูลเกี่ยวกับ repo git ปัจจุบัน (โดยใช้การนำ vcs_info ของ prezto) เพื่อให้คุณสามารถดูว่า git repo หายไปเมื่อใด คำสั่งแรกนั้นปกติพอ:

  » caleb » jaguar » ~/p/w/incil.info » ◼  zend ★ »
❯❯❯ git co master
Switched to branch 'master'
Your branch is up-to-date with 'origin/master'.

คุณจะเห็นว่าฉันอยู่ที่สาขา 'zend' และเช็คเอาท์อาจารย์ จนถึงตอนนี้ดีมาก คุณจะเห็นในพรอมต์ก่อนคำสั่งถัดไปของฉันที่จะเปลี่ยนสาขาได้สำเร็จ:

  » caleb » jaguar » ~/p/w/incil.info » ◼  master ★ »
❯❯❯ git pull
remote: Counting objects: 37, done.
remote: Compressing objects: 100% (37/37), done.
remote: Total 37 (delta 25), reused 0 (delta 0)
Unpacking objects: 100% (37/37), done.
From gitlab.alerque.com:ipk/incil.info
 + 7412a21...eca4d26 master     -> origin/master  (forced update)
   f03fa5d..c8ea00b  devel      -> origin/devel
 + 2af282c...009b8ec verse-spinner -> origin/verse-spinner  (forced update)
First, rewinding head to replay your work on top of it...
>>> elapsed time 11s

และเช่นเดียวกับที่มันหายไป ตัวทำเครื่องหมายเวลาที่ผ่านไปจะแสดงผลออกมาก่อนการแจ้งเตือนครั้งถัดไปหากผ่านไปนานกว่า 10 วินาที Git ไม่ได้ให้ผลลัพธ์ใด ๆ นอกเหนือจากการแจ้งว่ามีการกรอกซ้ำเพื่อเล่นซ้ำ ไม่มีข้อบ่งชี้ว่าเสร็จแล้ว

พรอมต์ถัดไปจะไม่มีข้อมูลเกี่ยวกับสาขาที่เราเปิดหรือสถานะของคอมไพล์

การไม่สังเกตเห็นว่ามันล้มเหลวฉันพยายามเรียกใช้คำสั่ง git อื่นเพียงเพื่อบอกว่าฉันไม่ได้อยู่ใน repo git โปรดทราบว่า PWD ไม่ได้เปลี่ยนแปลง:

  » caleb » jaguar » ~/p/w/incil.info »
❯❯❯ git fetch --all
fatal: Not a git repository (or any parent up to mount point /home)
Stopping at filesystem boundary (GIT_DISCOVERY_ACROSS_FILESYSTEM not set).

หลังจากนี้ดูรอบ ๆ แสดงให้เห็นว่าฉันอยู่ในไดเรกทอรีว่างเปล่าอย่างสมบูรณ์ ไม่มีอะไร ไม่มีไดเรกทอรี '.git' ไม่มีอะไรเลย ว่างเปล่า

คอมไพล์ท้องถิ่นของฉันเป็นเวอร์ชัน 2.0.2 ต่อไปนี้เป็นเกร็ดความรู้สองสามข้อจากการตั้งค่า git ของฉันที่อาจเกี่ยวข้องกับการทำสิ่งที่เกิดขึ้น:

[branch]
        autosetuprebase = always
        rebase = preserve
[pull]
        rebase = true
[rebase]
        autosquash = true
        autostash = true
[alias]
        co = checkout

ตัวอย่างเช่นฉันได้git pullตั้งค่าให้ทำการ rebase แทนการผสานเสมอดังนั้นส่วนของเอาต์พุตด้านบนจึงเป็นเรื่องปกติ

ฉันสามารถกู้คืนข้อมูล ฉันไม่คิดว่ามีคอมไพล์ใด ๆ วัตถุอื่นที่ไม่ใช่ stashes สำคัญบางอย่างที่ไม่ได้รับการผลักดันให้ Repos อื่น ๆ แต่ผมอยากจะรู้ว่าสิ่งที่เกิดขึ้น

ฉันได้ตรวจสอบ:

  • ข้อความใน dmesg หรือ systemd journal ไม่มีอะไรที่เกี่ยวข้องกับระยะไกล
  • ไม่มีข้อบ่งชี้ว่าไดร์ฟหรือระบบไฟล์ล้มเหลว (LVM + LUKS + EXT4 ทั้งหมดดูเป็นปกติ) ไม่มีอะไรหายไป + พบ
  • ฉันไม่ได้ทำอะไรเลย ไม่มีอะไรในประวัติศาสตร์ที่ฉันไม่ได้แสดงไว้ข้างต้นและไม่มีขั้วอื่นใดถูกใช้ในช่วงเวลานี้ ไม่มีrmคำสั่งลอยอยู่รอบ ๆ ที่อาจมีการดำเนินการใน CWD ผิด ฯลฯ
  • poking ที่ repo git อื่นในไดเรกทอรีอื่นไม่แสดงความผิดปกติที่กำลังดำเนินการgit pulls

ฉันควรมองหาอะไรที่นี่?


4
@ แพทริกตามที่ฉันอธิบายในคำถามแล้วไม่มีไม่มี.gitอยู่ ไม่มีสิ่งใด - สิ่งที่เคยเป็นไดเรกทอรีราก git ไม่มีอะไรในนั้น
Caleb

2
@Alexander การดำเนินการดึงเป็นเรื่องปกติ (อื่น ๆ ที่เป็น rebase มากกว่าการรวม) การแจ้งเตือนเกี่ยวกับการอัปเดตที่บังคับแสดงว่า repo ที่ฉันดึงออกมานั้นมีแรงผลักที่รีเซ็ตมันจากตำแหน่งที่แตกต่างจาก repo ในพื้นที่ที่เห็นล่าสุด นี่เป็นเรื่องปกติเพราะฉันกำลังซิงค์วัสดุที่พัฒนาขึ้นอย่างแข็งขันและบ่อยครั้งที่มีการ rebased ระหว่างคอมพิวเตอร์ของฉันเองไม่ใช่สาขาสาธารณะที่นักพัฒนาคนอื่นจะเห็น
คาเลบ

3
@Caleb พร้อมต์เชลล์ของคุณมีการระบุสาขา git ซึ่งหมายถึงการสร้าง PS1 รวมถึงคำสั่ง git ที่ไม่ได้แสดงในบันทึกของคุณ พวกเขาสามารถเปลี่ยนรูปภาพเป็นหลักและสามารถเป็นแหล่งที่มาของปัญหา คุณควรอัปเดตคำถามที่อธิบายวิธีการสร้างเชลล์พรอมต์ของคุณอย่างแม่นยำคำสั่งใดบ้างที่เรียกใช้เพื่อรับสาขาปัจจุบันและพิจารณาวิธีที่พวกเขาอาจทำลาย repo ของคุณ
Netch

2
@Caleb คุณควรถามรายชื่อผู้รับจดหมายข่าวการพัฒนา git; คุณสามารถเขียนมันเป็นรายงานข้อผิดพลาดหรือเพียงแค่ถามอย่างไม่เป็นทางการ - มันเหมือนกันอยู่แล้ว มีนักพัฒนาบางคนที่รู้คอมไพล์อย่างน่าประทับใจ - พวกเขาอาจบอกได้โดยสัญชาตญาณว่าเกิดอะไรขึ้น (ถ้าไม่พวกเขาจะติดตามการสนทนาอย่างเงียบ ๆ ) และพวกเขารู้ว่ามันเคยเกิดขึ้นมาก่อนหรือไม่ (การรายงานว่ามีวิธี "เป็นทางการ" เพื่อรายงานข้อบกพร่องสำหรับคอมไพล์)
Volker Siegel

7
@ Wildcard จริงๆแล้วฉันมีความหมายที่จะรวบรวมคำตอบนี้ไว้เพราะฉันคิดออกว่าเกิดอะไรขึ้น ระบบเพิ่งมาจากโหมดสลีปและเครือข่ายออกมาหลายวันก่อนที่จะเข้าสู่โหมดสลีป อยู่ที่ไหนสักแห่งในกระบวนการนั้นฉันได้ทิ้งกระบวนการ pacman ที่กำลังพยายามอัพเกรดบางอย่างในระบบ เพื่อทำให้เรื่องสั้นสั้นกลายเป็นว่า glibc ได้รับการปรับปรุงและไบนารี git ก็ถูกเขียนทับ เนื่องจากวิธีการที่แยกตัวเองหนึ่งตัวอย่างจบลงด้วยความแตกต่างจากที่อื่นและพวกเขากินอาหารกลางวันของกันและกัน ไดเรกทอรีว่างเปล่าจริง ๆ (ไม่ชัดเจน
Caleb

คำตอบ:


6

ใช่gitกินการบ้านของฉัน ทั้งหมดของมัน.

ฉันทำddอิมเมจของแผ่นดิสก์นี้หลังจากเหตุการณ์เกิดขึ้นและยุ่งไปกับมันในภายหลัง การสร้างชุดเหตุการณ์ขึ้นใหม่จากบันทึกของระบบฉันอนุมานสิ่งที่เกิดขึ้นเป็นอย่างนี้:

  1. pacman -Syuมีการออกคำสั่งการอัปเดตระบบ ( ) เป็นเวลาหลายวันก่อนเหตุการณ์นี้
  2. การหยุดทำงานของเครือข่ายแบบขยายหมายความว่ามีการพยายามดาวน์โหลดแพ็คเกจใหม่อีกครั้ง ผิดหวังที่ไม่มีอินเทอร์เน็ตฉันจะทำให้ระบบเข้าสู่โหมดสลีและเข้านอน
  3. อีกหลายวันต่อมาระบบก็ตื่นขึ้นมาและมันก็เริ่มค้นหาและดาวน์โหลดแพ็คเกจอีกครั้ง
  4. การดาวน์โหลดแพ็กเกจเสร็จสิ้นบางครั้งก่อนที่ฉันจะเกิดความวุ่นวายกับที่เก็บนี้
  5. ระบบglibcติดตั้งได้อัปเดตหลังและก่อนที่จะgit checkoutgit pull
  6. gitไบนารีได้แทนที่หลังจากที่git pullเริ่มต้นและก่อนที่จะดำเนินการเสร็จสิ้น
  7. และในวันที่เจ็ดgitพักจากการทำงานทั้งหมดของมัน และลบโลกดังนั้นทุกคนก็ต้องพักผ่อนด้วย

ฉันไม่ทราบแน่ชัดว่าเกิดสภาวะการแข่งขันแบบใดที่ทำให้เกิดเหตุการณ์นี้ขึ้น แต่การสลับไบนารีในระหว่างการดำเนินการนั้นไม่ดีอย่างแน่นอนหรือสภาพที่สามารถทดสอบ / ทำซ้ำได้ โดยปกติแล้วสำเนาของไบนารีที่ทำงานอยู่จะถูกเก็บไว้ในหน่วยความจำ แต่gitมันแปลกและบางอย่างเกี่ยวกับวิธีที่มันวางไข่เวอร์ชั่นของตัวเองอีกครั้งฉันมั่นใจว่าจะนำไปสู่ความยุ่งเหยิงนี้ เห็นได้ชัดว่ามันควรจะตายแทนที่จะทำลายทุกอย่าง แต่นั่นคือสิ่งที่เกิดขึ้น


1
git อาจล้มเหลวเนื่องจาก git ใช้คำสั่ง differend แทนไบนารีเดียว ดึง Git ง่ายรันgit-fetch, git-rebaseหรือgit-mergeและgit gc
Ferrybig

2

อาจเป็นไปได้โดยความล้มเหลวในการกำหนดเส้นทางของไฟล์ที่จะถูกลบ

กรณีของคุณทำให้ฉันนึกถึงวันที่สวยงามว่าเมื่อremove(path)วิธีโฮมเมดของฉันพยายามลบโฟลเดอร์รูทเพราะพารามิเตอร์ที่กำหนดเป็นสตริงว่างเปล่าซึ่งระบบปฏิบัติการแก้ไข (!) เป็นโฟลเดอร์รูท

นี่อาจเป็นข้อผิดพลาดคอมไพล์ที่คล้ายกัน ดังนั้น:

  1. คำสั่ง Rebase ต้องการลบไฟล์เช่นremove(project_folder + file_path)(รหัสเทียม)
  2. อย่างใดที่file_pathว่างเปล่าในเวลา
  3. คำสั่งประเมินว่าเป็นสิ่งที่ชอบ remove(project_folder)

1

ด้วยโชคคุณสามารถแก้ไขได้ด้วยคำสั่งต่อไปนี้:

git reset --hard ORIG_HEAD  

เมื่อการเปลี่ยนแปลงที่อาจเป็นอันตรายเริ่มขึ้น git จะหยุดสถานะปัจจุบันของคุณใน ORIG_HEAD ด้วยคุณสามารถยกเลิกการรวมหรือการคืนค่า

คู่มือ Git: การยกเลิกการผสาน


4
ฉันไม่คิดว่าคุณจะอ่านคำถามทั้งหมด การเรียงลำดับของการแก้ไขนี้จะสมบูรณ์ออกจากคำถามเพราะไม่มีคอมไพล์ข้อมูลเมตา การรีเซ็ตเช่นนี้จำเป็นต้องมีไดเรกทอรี. git และวัตถุบางอย่างที่อยู่ภายในเพื่อให้สามารถใช้งานได้ ฉันไม่มีอะไร. มันไม่ได้เป็นเพียงแค่ไดเร็คทอรี่สำหรับใช้ทำงานที่ยุ่งเหยิง แต่มันไม่มีที่เก็บข้อมูลอีกต่อไป
คาเลบ

อ่าขอโทษด้วย นั่นเป็นเรื่องที่แปลกมาก ถ้า git repo หายไปฉันคิดว่าจะไม่มีวิธีการกู้คืนเว้นแต่ว่าคุณเป็นไฟล์แชโดว์ใน linux และมีการสำรองข้อมูลไฟล์ fs ฉันจะลบคำตอบของฉันเนื่องจากไม่เกี่ยวข้อง
Routhinator

ใช่ฉันรู้ว่ามันเป็นปัญหาที่ผิดปกติ (และฉันมีการสำรองข้อมูล) คำถามของฉันคือว่ามันผิดอย่างไร ... จะหาข้อผิดพลาดใน git หรือไดรเวอร์ระบบไฟล์ของฉันได้หรืออะไรก็ตามที่อาจจะบอร์กกินไดเรกทอรีในระหว่างการดำเนินการเช่นนี้
คาเลบ

ฉันยังอยากรู้อยากเห็นมาก จะเกลียดสิ่งนี้จะเกิดขึ้นกับ repos ของฉัน
Routhinator

-1

ดูเหมือนว่ามีใครบางคนวิ่งgit push --forceบน repo นี้และคุณดึงการเปลี่ยนแปลงเหล่านั้นลง ลองคัดลอก repo ที่สดใหม่ซึ่งจะทำให้คุณกลับสู่สถานะการทำงานที่สะอาดอีกครั้ง


1
การกดปุ่มบังคับนั้นจะทำการ reboot ครั้งสุดท้าย นั่นไม่ใช่สิ่งที่ฉันดึงลงมา (ไดเรกทอรีการทำงานไม่ใช่ไดเรกทอรีการทำงานอีกต่อไป!) และแม้ว่ามันจะถูกโคลนอีกครั้งก็ไม่มีเหตุผลใด ๆ
คาเลบ

4
ฉันไม่คิดว่าคุณสามารถลบ.gitไดเรกทอรีsomeones ด้วยการกดบังคับ
Grzegorz
โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.