Git 2.18 (Q2 2018) --preserve-mergeएक नया विकल्प जोड़कर विकल्प में काफी सुधार करेगा ।
" git rebase" सीखा " --rebase-merges" प्रतिबद्ध ग्राफ के पूरे टोपोलॉजी को कहीं और प्रत्यारोपण करने के लिए ।
(नोट: Git 2.22, Q2 2019, वास्तव में पदावनत --preserve-merge , और Git 2.25, Q1 2020, इसे " git rebase --help" आउटपुट में विज्ञापन देना बंद कर देता है )
देखें 25cff9f प्रतिबद्ध , 7543f6f प्रतिबद्ध , 1131ec9 प्रतिबद्ध , 7ccdf65 प्रतिबद्ध , 537e7d6 प्रतिबद्ध , a9be29c प्रतिबद्ध , 8f6aed7 प्रतिबद्ध , 1644c73 प्रतिबद्ध , d1e8b01 प्रतिबद्ध , 4c68e7d प्रतिबद्ध , 9055e40 प्रतिबद्ध , cb5206e प्रतिबद्ध , a01c2a5 प्रतिबद्ध , 2f6b1d1 प्रतिबद्ध , प्रतिबद्ध bf5c057 (25 अप्रैल 2018) द्वारा जोहानिस Schindelin ( dscho) । स्टीफन बेलर ( ) द्वारा प्रतिबद्ध f431d73 (25 अप्रैल 2018)
देखें ।stefanbeller
फिलिप वुड ( ) द्वारा 2429335 (25 अप्रैल 2018) प्रतिबद्ध
देखें । ( जूनियो सी हमानो द्वारा विलय - में - २ सी १ , ई ६ ए , २३ मई २०१io )phillipwood
gitster
pull: --rebase-mergesशाखा टोपोलॉजी को फिर से बनाने के लिए स्वीकार करते हैं
कमांड preserveके --preserve-merges
विकल्प को पास करने की विधा के समान, मोड बस विकल्प को पास करता
है।rebasemerges--rebase-merges
यह उपयोगकर्ताओं को आसानी से गैर-तुच्छ प्रतिबद्ध टोपोलॉजी को फिर से शुरू करने की अनुमति देगा, जब उन्हें बिना चपटा किए, नए कमिट्स को खींचना होगा।
git rebaseमैन पेज में अब एक पूर्ण खंड है जो मर्ज के साथ पुन: इतिहास को समर्पित है ।
निकालें:
कई कारण हैं कि एक डेवलपर मर्ज कमिट को फिर से बनाना चाहता है: एकाधिक, अंतर-संबंधित शाखाओं पर काम करते समय शाखा संरचना (या "प्रतिबद्ध टोपोलॉजी") रखने के लिए।
निम्नलिखित उदाहरण में, डेवलपर एक विषय शाखा पर काम करता है जो कि बटन को परिभाषित करने के तरीके को रिफ्लेक्टर करता है, और एक अन्य विषय शाखा पर जो "रिफंडिंग ए बग" बटन को लागू करने के लिए उस रिफैक्टरिंग का उपयोग करता है।
उत्पादन git log --graph --format=%s -5इस तरह दिख सकता है:
* Merge branch 'report-a-bug'
|\
| * Add the feedback button
* | Merge branch 'refactor-button'
|\ \
| |/
| * Use the Button class for all buttons
| * Extract a generic Button class from the DownloadButton one
हो सकता है कि डेवलपर master
शाखा टोपोलॉजी को रखते हुए एक नए सिरे से कमिट करना चाहता हो , उदाहरण के लिए जब पहली विषय शाखा को masterदूसरे से पहले बहुत एकीकृत करने की उम्मीद की जाती है , तो कहना है DownloadButtonकि क्लास में किए गए बदलावों के साथ मर्ज संघर्षों को हल करना।
में है master।
--rebase-mergesविकल्प का उपयोग करके यह रिबेस किया जा सकता है।
एक छोटे से उदाहरण के लिए 1644c73 प्रतिबद्ध देखें :
rebase-helper --make-script: मर्ज करने के लिए एक ध्वज का परिचय
सिक्वेंसर ने सिर्फ शाखा संरचना ( आत्मा के समान --preserve-merges, लेकिन काफी कम टूटी हुई डिजाइन के साथ ) को फिर से बनाने के इरादे से नए आदेशों को सीखा ।
आइए rebase--helper, नए --rebase-mergesविकल्प द्वारा ट्रिगर किए गए इन आदेशों का उपयोग करके टूडू सूचियों को उत्पन्न करने की अनुमति दें ।
इस तरह एक प्रतिबद्ध टोपोलॉजी के लिए (जहां HE C को इंगित करता है):
- A - B - C (HEAD)
\ /
D
उत्पन्न टूडू सूची इस तरह दिखाई देगी:
# branch D
pick 0123 A
label branch-point
pick 1234 D
label D
reset branch-point
pick 2345 B
merge -C 3456 D # C
क्या अंतर है --preserve-merge?
प्रतिबद्ध 8f6aed7 बताते हैं:
एक बार, यहाँ डेवलपर ने सोचा: यह अच्छा नहीं होगा यदि, कहो, Git for Windows 'पैच ऑफ द कोर के ऊपर Git को शाखाओं की एक मोटी रेखा के रूप में दर्शाया जा सकता है, और कोर Git के शीर्ष पर रीबेड किया जा सकता है पैच श्रृंखला का चेरी-पिक'एबल सेट बनाए रखें?
इस जवाब देने के लिए मूल प्रयास किया गया था: git rebase --preserve-merges।
हालांकि, उस प्रयोग को एक इंटरैक्टिव विकल्प के रूप में कभी नहीं किया गया था, और यह केवल गुल्लक-समर्थित था git rebase --interactiveक्योंकि उस आदेश का कार्यान्वयन पहले से ही बहुत, बहुत परिचित लग रहा था: यह उसी व्यक्ति द्वारा डिज़ाइन किया गया था जिसने डिजाइन किया था --preserve-merges: आपका वास्तव में।
और "तुम्हारा सही मायने में", लेखक खुद को संदर्भित करता है: जोहानस शिंडेलिन ( dscho) , जो मुख्य कारण है (कुछ अन्य नायकों के साथ - हेंस, स्टीफन, सेबस्टियन, ...) कि हमारे पास Git है विंडोज के लिए (भले ही दिन में वापस - 2009 - यह आसान नहीं था )।
वह सितंबर 2015 से Microsoft में काम कर रहे हैं , जो समझ में आता है कि Microsoft अब Git का भारी उपयोग करता है और उसे अपनी सेवाओं की आवश्यकता है।
यह प्रवृत्ति 2013 में वास्तव में TFS के साथ शुरू हुई थी । तब से, Microsoft ग्रह पर सबसे बड़ी गिट रिपॉजिटरी का प्रबंधन करता है ! और, अक्टूबर 2018 से, Microsoft ने GitHub का अधिग्रहण किया ।
अप्रैल 2018 में Git Merge 2018 के लिए आप जोहान्स को इस वीडियो में बोलते देख सकते हैं ।
कुछ समय बाद, कुछ अन्य डेवलपर (मैं आपको देख रहा हूं, एंड्रियास!; ;-)) ने फैसला किया कि यह एक अच्छा विचार होगा जिसे (कैविट्स के साथ) और गिट अनुरक्षक (अच्छी तरह से, अंतरिम गिट अनुचर) के साथ --preserve-mergesसंयोजित करने की अनुमति होगी। --interactiveजूनियो की अनुपस्थिति के दौरान, वह) सहमत है, और वह यह है कि --preserve-mergesडिजाइन का ग्लैमर जल्दी और असमान रूप से अलग होने लगा।
यहां जोनाथन सुसे से एंड्रियास श्वाब के बारे में बात कर रहे हैं ।
आप उनकी कुछ चर्चाओं को 2012 में देख सकते हैं ।
कारण? में --preserve-mergesमोड, किसी मर्ज के माता पिता (या उस बात के लिए की प्रतिबद्ध किसी भी प्रतिबद्ध) स्पष्ट रूप से कहा नहीं कर रहे थे, लेकिन थे
गर्भित प्रतिबद्ध नाम के लिए पारित द्वारा pickआदेश ।
यह असंभव बना दिया, उदाहरण के लिए, कमिट को फिर से चालू करने के लिए ।
विषय शाखाओं को दो में विभाजित करने के लिए, शाखाओं या देवता के बीच कमिट को स्थानांतरित करने का उल्लेख नहीं करना।
काश, इन कमियों ने उस मोड को भी रोक दिया (जिसका मूल उद्देश्य विंडोज की जरूरतों के लिए गिट की सेवा करना था, अतिरिक्त उम्मीद के साथ कि यह दूसरों के लिए भी उपयोगी हो सकता है) विंडोज की जरूरतों के लिए सेवा प्रदान करने से।
पांच साल बाद, जब यह वास्तव में एक अनिर्दिष्ट हो गया था, आंशिक रूप से संबंधित, बड़े रूप से संबंधित विंडोज में गिट के पैच-थ्रू पैच श्रृंखला, जो कि विंडोज के लिए समय-समय पर कोर गिट के टैग पर बगावत की गई थी (डेवलपर के अवांछनीय क्रोध अर्जित करना) git-remote-hgविंडोज के प्रतिस्पर्धात्मक दृष्टिकोण के लिए पहली बार गिट का पालन करने वाली बीमार
श्रृंखला, जिसे बाद में अनुचर के बिना छोड़ दिया गया था) वास्तव में अस्थिर था, " गिट गार्डन कैंची " का जन्म हुआ : एक स्क्रिप्ट, इंटरैक्टिव रीबेज के शीर्ष पर गुल्लक-बैकिंग, यह पहले पैच के शाखा टोपोलॉजी को फिर से निर्धारित करने के लिए निर्धारित करेगा, आगे के संपादन के लिए एक छद्म टूडू सूची बनाएं, परिणाम को एक वास्तविक टूडू सूची में बदल देगा (भारी उपयोग करना)exec लापता टूडू सूची आदेशों को "लागू" करने के लिए कमांड करें और अंत में नए बेस कमिट के शीर्ष पर पैच श्रृंखला को फिर से बनाएं।
( 9055e40 में इस पैच में गिट गार्डन कैंची लिपि को संदर्भित किया गया है )
यह 2013 में था।
और डिजाइन के साथ आने और इसे आउट-ऑफ-ट्री स्क्रिप्ट के रूप में लागू करने में लगभग तीन सप्ताह लग गए। कहने की जरूरत नहीं कि कार्यान्वयन को स्थिर करने के लिए काफी कुछ वर्षों की आवश्यकता थी, जबकि सभी डिजाइन खुद को ध्वनि साबित करते थे।
इस पैच के साथ, गीट गार्डन कैंची की अच्छाई git
rebase -iअपने आप आती है । विकल्प
पास करना --rebase-mergesएक टूडू सूची उत्पन्न करेगा जिसे आसानी से समझा जा सकता है, और जहां यह स्पष्ट है कि कैसे फिर से शुरू होता है । कमांड
डालकर labelऔर कॉल करके नई शाखाओं को पेश किया जा सकता है merge <label>।
और एक बार जब यह मोड स्थिर हो जाएगा और सार्वभौमिक रूप से स्वीकार कर लिया जाएगा, तो हम उस डिज़ाइन की गलती को हटा सकते हैं जो थी--preserve-merges ।
Git 2.19 (Q3 2018) के --rebase-mergesसाथ काम करके नए विकल्प में सुधार करता है --exec।
" --exec" विकल्प " git rebase --rebase-merges" ने निष्पादन कमांड को गलत स्थानों पर रखा, जिसे सही कर दिया गया है।
देखें 1ace63b प्रतिबद्ध (09 अगस्त 2018), और f0880f7 प्रतिबद्ध द्वारा (06 अगस्त 2018) जोहानिस Schindelin ( dscho) ।
(द्वारा विलय Junio सी Hamano - gitster- में प्रतिबद्ध 750eb11 , 20 अगस्त 2018)
rebase --exec: इसके साथ काम करो --rebase-merges
के विचार --execएक संलग्न करने के लिए है execप्रत्येक के बाद कॉल pick।
चूंकि fixup!/ एस शुरू होने के बाद quash!, इस विचार को "पिक, संभवतः एक फिक्सअप / स्क्वैश चेन" के लिए लागू करने के लिए बढ़ाया गया था, यानी एक निष्पादन को pickइसके और इसी fixupया squashलाइनों में से किसी के
बीच नहीं डाला जाएगा ।
वर्तमान कार्यान्वयन इसे प्राप्त करने के लिए एक गंदे चाल का उपयोग करता है: यह मानता है कि केवल पिक / फिक्सअप / स्क्वैश कमांड हैं, और फिर
किसी भी पहले लेकिन पहले लाइनों को सम्मिलित करता है और एक अंतिम जोड़ देता है।execpick
के द्वारा उत्पन्न टूडू सूचियों के साथ git rebase --rebase-merges, यह सरल कार्यान्वयन इसकी समस्याओं को दिखाता है: यह सटीक गलत चीज़ पैदा करता है जब वहाँ होते हैं label, resetऔर mergeआदेश।
: आइए परिवर्तन कार्यान्वयन वास्तव में ऐसा करने के लिए हम क्या चाहते हैं के लिए देखो
pickलाइनों, किसी भी फिक्स-अप / स्क्वैश जंजीरों को छोड़, और फिर सम्मिलित exec
लाइन । बल्कि, कुल्ला, दोहराएं।
नोट: हम जब भी संभव हो, टिप्पणी लाइनों से पहले सम्मिलित करने के लिए दर्द उठाते हैं, क्योंकि खाली कमेंट्स को टिप्पणी-आउट पिक लाइनों द्वारा दर्शाया जाता है (और हम इस तरह की रेखा से पहले एक पूर्ववर्ती पिक की निष्पादन रेखा सम्मिलित करना चाहते हैं , बाद में नहीं)।
हालांकि, यह भी आज्ञाओं के execबाद लाइनों को जोड़ते हैं merge, क्योंकि वे pickआज्ञाओं की भावना के समान हैं : वे नए आवागमन जोड़ते हैं।
Git 2.22 (Q2 2019), रिबेज मध्यवर्ती राज्यों को संग्रहीत करने के लिए Refs / rewritten / hierarchy के उपयोग को ठीक करता है, जो स्वाभाविक रूप से प्रति वर्कट्री प्रति पदानुक्रम बनाता है।
देखें b9317d5 प्रतिबद्ध , 90d31ff प्रतिबद्ध , 09e6564 प्रतिबद्ध (07 मार्च 2019) द्वारा गुयेन थाई Ngọc Duy ( pclouds) ।
(द्वारा विलय Junio सी Hamano - gitster- में प्रतिबद्ध 917f2cd , 09 अप्रैल 2019)
सुनिश्चित करें कि प्रति-कार्य / फिर से लिखा गया है
a9be29c (सीक्वेंसर: labelकमांड वर्कट्री-लोकल, 2018-04-25, Git 2.19) द्वारा जनरेट किया गया रिफ्स बनाते हैं refs/rewritten/।
दुर्भाग्य से (मेरा बुरा) कुछ स्थानों पर हैं जिन्हें यह सुनिश्चित करने के लिए अद्यतन की आवश्यकता है कि यह वास्तव में प्रति-कार्य-विषय है।
- add_per_worktree_entries_to_dir()यह सुनिश्चित करने के लिए अद्यतन किया जाता है कि refs/rewritten/प्रति-रेपो-प्रति के बजाय प्रति-कार्य-सूची को देखें ।
common_list[]अपडेट किया गया है ताकि git_path()सही स्थान लौटाया जा सके। इसमें " rev-parse --git-path" शामिल हैं ।
यह गंदगी मेरे द्वारा बनाई गई है।
मैंने इसे शुरू करने की कोशिश की, refs/worktree,जहां सभी रेफरी विशेष उपचार के बिना प्रति-वर्कट्री होंगे।
दुर्भाग्यपूर्ण refs / rewritten refs / worktree से पहले आया था इसलिए यह सब हम कर सकते हैं।
Git 2.24 (Q4 2019) के साथ, " git rebase --rebase-merges" विभिन्न मर्ज रणनीतियों को चलाना और उनके लिए रणनीति विशिष्ट विकल्प पास करना सीखा।
एलिजा न्यूरेन ( ) द्वारा प्रतिबद्ध 476998 डी (04 सितंबर 2019) देखें । प्रतिबद्ध e1fac53
देखें , a63f990 प्रतिबद्ध करेंnewren
, 5dcdd74 प्रतिबद्ध , e145d99 प्रतिबद्ध , 4e6023b प्रतिबद्ध , f67336d प्रतिबद्ध , a9c7107 प्रतिबद्ध , b8c6f24 प्रतिबद्ध , d51b771 प्रतिबद्ध , प्रतिबद्ध c248d32 , प्रतिबद्ध 8c1e240 , प्रतिबद्ध 5efed0e , प्रतिबद्ध 68b54f6 , 2e7bbac प्रतिबद्ध , प्रतिबद्ध 6180b20 , d5b581f प्रतिबद्ध 31 ( जुलाई 2019) द्वाराजोहान्स शिंडेलिन ( dscho) ।
(द्वारा विलय Junio सी Hamano - gitster- में प्रतिबद्ध 917a319 , 18 सितं, 2019)
Git 2.25 (Q1 2020) के साथ, लॉजिक वर्कट्री लोकल और रिपॉजिटरी ग्लोबल रीफ्स को अलग-अलग बताने के लिए इस्तेमाल किया जाता है, संरक्षित-मर्ज को सुविधाजनक बनाने के लिए।
देख प्रतिबद्ध f45f88b , प्रतिबद्ध c72fc40 , 8a64881 , 7cb8c92 के लिए प्रतिबद्ध , SZEDER गैबोर () द्वारा e536b1fszeder (21 अक्टूबर 2019 ) ।
(द्वारा विलय Junio सी Hamano - gitster- में db806d7 प्रतिबद्ध , 10 नवंबर 2019)
path.c: matchमान के बिना फ़ंक्शन को कॉल न करेंtrie_find()
साइन-ऑफ-बाय: SZEDER गैबर
'लॉग / रेफ्स' एक कार्यशील पेड़-विशिष्ट पथ नहीं है, लेकिन चूंकि प्रतिबद्ध b9317d55a3 (सुनिश्चित करें कि refs / rewritten / per-worktree है, 2019-03-07, v2.22.0-rc0) ' git rev-parse --git-path' एक फर्जी मार्ग लौटा रहा है यदि एक अनुगामी ' /' मौजूद है:
$ git -C WT/ rev-parse --git-path logs/refs --git-path logs/refs/
/home/szeder/src/git/.git/logs/refs
/home/szeder/src/git/.git/worktrees/WT/logs/refs/
हम एक trieडेटा संरचना का उपयोग कुशलतापूर्वक यह तय करने के लिए करते हैं कि कोई पथ सामान्य डायर का है या पेड़-विशिष्ट काम कर रहा है।
जैसा कि ऐसा होता है b9317d55a3 एक बग को ट्रिगर करता है जो trieकार्यान्वयन के रूप में पुराना है, 4e09cf2acf (" path: आम डायर चेकिंग का अनुकूलन करें " में जोड़ा गया , 2015-08-31, Git v2.7.0-rc0 - बैच # 2 में सूचीबद्ध मर्ज )।
वर्णन करने वाली टिप्पणी के अनुसार trie_find(), इसे केवल दिए गए मैच फंक्शन को 'fn' के लिए "/ -or- \ 0-कुंजी के लिए प्री-टर्मिनेटेड उपसर्ग के लिए कॉल करना चाहिए, जिसके लिए ट्राइ में एक मान होता है"।
यह सच नहीं है: तीन जगह हैं जहां trie_find () मैच फ़ंक्शन को कॉल करता है, लेकिन उनमें से एक मूल्य के अस्तित्व के लिए चेक को याद कर रहा है।
b9317d55a3 ने दो नई कुंजियाँ जोड़ींtrie :
- '
logs/refs/rewritten', और
- '
logs/refs/worktree', पहले से मौजूद ' logs/refs/bisect' के बगल में ।
इससे trieमार्ग ' logs/refs/' के साथ एक नोड उत्पन्न हुआ , जो पहले मौजूद नहीं था, और जिसका कोई मूल्य संलग्न नहीं है।
' logs/refs/' के लिए एक क्वेरी इस नोड को ढूंढती है और फिर उस matchफ़ंक्शन को कॉल करती है जो मान के अस्तित्व की जांच नहीं करता है, और इस प्रकार matchफ़ंक्शन NULLको मान के रूप में आमंत्रित करता है ।
जब matchफ़ंक्शन check_common()को एक NULLमान के साथ लागू किया जाता है , तो यह 0 देता है, जो इंगित करता है कि queried पथ सामान्य निर्देशिका से संबंधित नहीं है, जिसके परिणामस्वरूप अंततः ऊपर दिखाए गए बोगस पथ।
लापता स्थिति को जोड़ें trie_find()ताकि यह गैर-मौजूदा मूल्य के साथ मैच फ़ंक्शन को कभी भी आमंत्रित न करे।
check_common() उसके बाद यह जांचने के लिए नहीं होगा कि उसे एक गैर-पूर्ण मान मिला है, इसलिए उस शर्त को हटा दें।
मेरा मानना है कि ऐसे अन्य मार्ग नहीं हैं जो समान बोगस आउटपुट का कारण बन सकते हैं।
AFAICT केवल दूसरी कुंजी है जिसके परिणामस्वरूप मैच फ़ंक्शन को एक NULLमान के साथ बुलाया जा रहा है, ' co' (कुंजियों के कारण ' common' और ' config')।
हालांकि, जैसा कि वे एक निर्देशिका में नहीं हैं जो आम निर्देशिका से संबंधित है, जिसके परिणामस्वरूप कार्य-विशिष्ट पेड़-विशिष्ट पथ अपेक्षित है।
git --rebase-mergesअंततः पुराने को बदल देगाgit --preserve-merges। देखें नीचे मेरा उत्तर