<div dir="ltr"><div>By the magic of "Markdown Here", here's the same properly formatted from the original comment written in Markdown (and with typos fixed by the magic of google mail ;-):<br></div><div></div><div class="markdown-here-wrapper" style=""><blockquote style="margin:1.2em 0px;border-left:4px solid rgb(221,221,221);padding:0px 1em;color:rgb(119,119,119);quotes:none">
<p style="margin:0px 0px 1.2em!important">At some point I’d like you to show me how to do this.</p>
</blockquote>
<p style="margin:0px 0px 1.2em!important">Well, it’s not that hard, <code style="font-size:0.85em;font-family:Consolas,Inconsolata,Courier,monospace;margin:0px 0.15em;padding:0px 0.3em;white-space:pre-wrap;border:1px solid rgb(234,234,234);background-color:rgb(248,248,248);border-radius:3px;display:inline">git rebase A</code> just replays your commits on the currently checked out branch (say, <code style="font-size:0.85em;font-family:Consolas,Inconsolata,Courier,monospace;margin:0px 0.15em;padding:0px 0.3em;white-space:pre-wrap;border:1px solid rgb(234,234,234);background-color:rgb(248,248,248);border-radius:3px;display:inline">B</code>) on top of <code style="font-size:0.85em;font-family:Consolas,Inconsolata,Courier,monospace;margin:0px 0.15em;padding:0px 0.3em;white-space:pre-wrap;border:1px solid rgb(234,234,234);background-color:rgb(248,248,248);border-radius:3px;display:inline">A</code>, starting from the point where <code style="font-size:0.85em;font-family:Consolas,Inconsolata,Courier,monospace;margin:0px 0.15em;padding:0px 0.3em;white-space:pre-wrap;border:1px solid rgb(234,234,234);background-color:rgb(248,248,248);border-radius:3px;display:inline">A</code> and <code style="font-size:0.85em;font-family:Consolas,Inconsolata,Courier,monospace;margin:0px 0.15em;padding:0px 0.3em;white-space:pre-wrap;border:1px solid rgb(234,234,234);background-color:rgb(248,248,248);border-radius:3px;display:inline">B</code> diverge. The end result is the same as with <code style="font-size:0.85em;font-family:Consolas,Inconsolata,Courier,monospace;margin:0px 0.15em;padding:0px 0.3em;white-space:pre-wrap;border:1px solid rgb(234,234,234);background-color:rgb(248,248,248);border-radius:3px;display:inline">git merge A</code> (and you’ll have to fix pretty much the same conflicts if both branches modify the same file in different ways), only that you now have all the commits of <code style="font-size:0.85em;font-family:Consolas,Inconsolata,Courier,monospace;margin:0px 0.15em;padding:0px 0.3em;white-space:pre-wrap;border:1px solid rgb(234,234,234);background-color:rgb(248,248,248);border-radius:3px;display:inline">B</code> positioned neatly <em>after</em> the commits of <code style="font-size:0.85em;font-family:Consolas,Inconsolata,Courier,monospace;margin:0px 0.15em;padding:0px 0.3em;white-space:pre-wrap;border:1px solid rgb(234,234,234);background-color:rgb(248,248,248);border-radius:3px;display:inline">A</code>, instead of being a jumbled mess. The price you pay is that you’re rewriting history on <code style="font-size:0.85em;font-family:Consolas,Inconsolata,Courier,monospace;margin:0px 0.15em;padding:0px 0.3em;white-space:pre-wrap;border:1px solid rgb(234,234,234);background-color:rgb(248,248,248);border-radius:3px;display:inline">B</code>, so you’ll have to use <code style="font-size:0.85em;font-family:Consolas,Inconsolata,Courier,monospace;margin:0px 0.15em;padding:0px 0.3em;white-space:pre-wrap;border:1px solid rgb(234,234,234);background-color:rgb(248,248,248);border-radius:3px;display:inline">git push -f</code> (force push) to get your branch updated on the remote. At which point other people having checked out your <code style="font-size:0.85em;font-family:Consolas,Inconsolata,Courier,monospace;margin:0px 0.15em;padding:0px 0.3em;white-space:pre-wrap;border:1px solid rgb(234,234,234);background-color:rgb(248,248,248);border-radius:3px;display:inline">B</code> branch and working on it may get angry at you. ;-) But that’s expected with the kind of temporary branches you create for doing merge requests, where you usually rebase just once directly before your branch is merged. If it’s a bigger, more permanent branch with many people working on it, however, then it’s probably better to use <code style="font-size:0.85em;font-family:Consolas,Inconsolata,Courier,monospace;margin:0px 0.15em;padding:0px 0.3em;white-space:pre-wrap;border:1px solid rgb(234,234,234);background-color:rgb(248,248,248);border-radius:3px;display:inline">git merge</code> like on the master branch, and you can actually protect a branch to enforce that policy (at least I can do that on Github and Bitbucket, I think that it’s possible on Gitlab as well).</p>
<p style="margin:0px 0px 1.2em!important">In practice this means that, instead of, say, running <code style="font-size:0.85em;font-family:Consolas,Inconsolata,Courier,monospace;margin:0px 0.15em;padding:0px 0.3em;white-space:pre-wrap;border:1px solid rgb(234,234,234);background-color:rgb(248,248,248);border-radius:3px;display:inline">git merge master</code> on your feature branch, you’d be running <code style="font-size:0.85em;font-family:Consolas,Inconsolata,Courier,monospace;margin:0px 0.15em;padding:0px 0.3em;white-space:pre-wrap;border:1px solid rgb(234,234,234);background-color:rgb(248,248,248);border-radius:3px;display:inline">git rebase master</code> instead, and fixing any conflicts. At which point your feature branch should neatly merge into the master branch, basically it’s just a fast-forward now. So you either directly merge into master yourself (if you’re Jonathan and can push to master), or force-push your feature branch (<code style="font-size:0.85em;font-family:Consolas,Inconsolata,Courier,monospace;margin:0px 0.15em;padding:0px 0.3em;white-space:pre-wrap;border:1px solid rgb(234,234,234);background-color:rgb(248,248,248);border-radius:3px;display:inline">git push -f</code>) to your remote branch, prepare a merge request for it, and wait for Jonathan to come along. If your feature branch has to wait a wee bit longer than expected, and other stuff goes into master in the meantime, then you just redo the rebase and force-push once again, to have the branch and merge request updated accordingly.</p>
<p style="margin:0px 0px 1.2em!important">The web interface has an option for this too, I believe. But I strongly prefer to do all this kind of stuff in my local clone where I can quickly and easily create backup branches, test things out and inspect the results, and just redo everything from scratch if things go awry.</p>
<blockquote style="margin:1.2em 0px;border-left:4px solid rgb(221,221,221);padding:0px 1em;color:rgb(119,119,119);quotes:none">
<p style="margin:0px 0px 1.2em!important">I got stuck in a weird rebase state that consequently caused me to lose some data in the working directory of a completely different branch.</p>
</blockquote>
<p style="margin:0px 0px 1.2em!important">Yeah, if you completely mess up and suspect that your branches are in an inconsistent state, then it’s often easier to check out a completely fresh clone and just start over. It’s been a while that I had to do this, though, so either git, or I, or we both got better. ;-)</p>
<div title="MDH:PGRpdj4mZ3Q7IEF0IHNvbWUgcG9pbnQgSSdkIGxpa2UgeW91IHRvIHNob3cgbWUgaG93IHRvIGRv
IHRoaXMuPC9kaXY+PGJyPldlbGwsIGl0J3Mgbm90IHRoYXQgaGFyZCwgYGdpdCByZWJhc2UgQWAg
anVzdCByZXBsYXlzIHlvdXIgY29tbWl0cyBvbiB0aGUgY3VycmVudGx5IGNoZWNrZWQgb3V0IGJy
YW5jaCAoc2F5LCBgQmApIG9uIHRvcCBvZiBgQWAsIHN0YXJ0aW5nIGZyb20gdGhlIHBvaW50IHdo
ZXJlIGBBYCBhbmQgYEJgIGRpdmVyZ2UuIFRoZSBlbmQgcmVzdWx0IGlzIHRoZSBzYW1lIGFzIHdp
dGggYGdpdCBtZXJnZSBBYCAoYW5kIHlvdSdsbCBoYXZlIHRvIGZpeCBwcmV0dHkgbXVjaCB0aGUg
c2FtZSBjb25mbGljdHMgaWYgYm90aCBicmFuY2hlcyBtb2RpZnkgdGhlIHNhbWUgZmlsZSBpbiBk
aWZmZXJlbnQgd2F5cyksIG9ubHkgdGhhdCB5b3Ugbm93IGhhdmUgYWxsIHRoZSBjb21taXRzIG9m
IGBCYCBwb3NpdGlvbmVkIG5lYXRseSAqYWZ0ZXIqIHRoZSBjb21taXRzIG9mIGBBYCwgaW5zdGVh
ZCBvZiBiZWluZyBhIGp1bWJsZWQgbWVzcy4gVGhlIHByaWNlIHlvdSBwYXkgaXMgdGhhdCB5b3Un
cmUgcmV3cml0aW5nIGhpc3Rvcnkgb24gYEJgLCBzbyB5b3UnbGwgaGF2ZSB0byB1c2UgYGdpdCBw
dXNoIC1mYCAoZm9yY2UgcHVzaCkgdG8gZ2V0IHlvdXIgYnJhbmNoIHVwZGF0ZWQgb24gdGhlIHJl
bW90ZS4gQXQgd2hpY2ggcG9pbnQgb3RoZXIgcGVvcGxlIGhhdmluZyBjaGVja2VkIG91dCB5b3Vy
IGBCYCBicmFuY2ggYW5kIHdvcmtpbmcgb24gaXQgbWF5IGdldCBhbmdyeSBhdCB5b3UuIDstKSBC
dXQgdGhhdCdzIGV4cGVjdGVkIHdpdGggdGhlIGtpbmQgb2YgdGVtcG9yYXJ5IGJyYW5jaGVzIHlv
dSBjcmVhdGUgZm9yIGRvaW5nIG1lcmdlIHJlcXVlc3RzLCB3aGVyZSB5b3UgdXN1YWxseSByZWJh
c2UganVzdCBvbmNlIGRpcmVjdGx5IGJlZm9yZSB5b3VyIGJyYW5jaCA8c3BhbiB6ZXVtNGM1PSJQ
Ul81XzAiIGRhdGEtZGRud2FiPSJQUl81XzAiIGFyaWEtaW52YWxpZD0iZ3JhbW1hciIgY2xhc3M9
IkxtIG5nIj5nZXRzPC9zcGFuPiBtZXJnZWQuIElmIGl0J3MgYSBiaWdnZXIsIG1vcmUgcGVybWFu
ZW50IGJyYW5jaCB3aXRoIG1hbnkgcGVvcGxlIHdvcmtpbmcgb24gaXQsIGhvd2V2ZXIsIHRoZW4g
aXQncyBwcm9iYWJseSBiZXR0ZXIgdG8gdXNlIGBnaXQgbWVyZ2VgIGxpa2Ugb24gdGhlIG1hc3Rl
ciBicmFuY2gsIGFuZCB5b3UgY2FuIGFjdHVhbGx5IHByb3RlY3QgYSBicmFuY2ggdG8gZW5mb3Jj
ZSB0aGF0IHBvbGljeSAoYXQgbGVhc3QgSSBjYW4gZG8gdGhhdCBvbiBHaXRodWIgYW5kIEJpdGJ1
Y2tldCwgSSB0aGluayB0aGF0IGl0J3MgcG9zc2libGUgb24gR2l0bGFiIGFzIHdlbGwpLjxicj48
YnI+SW4gcHJhY3RpY2UgdGhpcyBtZWFucyB0aGF0LCBpbnN0ZWFkIG9mLCBzYXksIHJ1bm5pbmcg
YGdpdCBtZXJnZSBtYXN0ZXJgIG9uIHlvdXIgZmVhdHVyZSBicmFuY2gsIHlvdSdkIGJlIHJ1bm5p
bmcgYGdpdCByZWJhc2UgbWFzdGVyYCBpbnN0ZWFkLCBhbmQgPHNwYW4gemV1bTRjNT0iUFJfNl8w
IiBkYXRhLWRkbndhYj0iUFJfNl8wIiBhcmlhLWludmFsaWQ9ImdyYW1tYXIiIGNsYXNzPSJMbSBu
ZyI+Zml4PC9zcGFuPiBhbnkgY29uZmxpY3RzLiBBdCB3aGljaCBwb2ludCB5b3VyIGZlYXR1cmUg
YnJhbmNoIHNob3VsZCBuZWF0bHkgbWVyZ2UgaW50byB0aGUgbWFzdGVyIGJyYW5jaCwgYmFzaWNh
bGx5IGl0J3MganVzdCBhIGZhc3QtZm9yd2FyZCBub3cuIFNvIHlvdSBlaXRoZXIgZGlyZWN0bHkg
bWVyZ2UgaW50byBtYXN0ZXIgeW91cnNlbGYgKGlmIHlvdSdyZSBKb25hdGhhbiBhbmQgY2FuIHB1
c2ggdG8gbWFzdGVyKSwgb3IgZm9yY2UtcHVzaCB5b3VyIGZlYXR1cmUgYnJhbmNoIChgZ2l0IHB1
c2ggLWZgKSB0byB5b3VyIHJlbW90ZSBicmFuY2gsIHByZXBhcmUgYSBtZXJnZSByZXF1ZXN0IGZv
ciBpdCwgYW5kIHdhaXQgZm9yIEpvbmF0aGFuIHRvIGNvbWUgYWxvbmcuIElmIHlvdXIgZmVhdHVy
ZSBicmFuY2ggaGFzIHRvIHdhaXQgYSB3ZWUgYml0IGxvbmdlciB0aGFuIGV4cGVjdGVkLCBhbmQg
b3RoZXIgc3R1ZmYgZ29lcyBpbnRvIG1hc3RlciBpbiB0aGUgbWVhbnRpbWUsIHRoZW4geW91IGp1
c3QgcmVkbyB0aGUgcmViYXNlIGFuZCBmb3JjZS1wdXNoIG9uY2UgYWdhaW4sIHRvIGhhdmUgdGhl
IGJyYW5jaCBhbmQgbWVyZ2UgcmVxdWVzdCB1cGRhdGVkIGFjY29yZGluZ2x5Ljxicj48YnI+VGhl
IHdlYiBpbnRlcmZhY2UgaGFzIGFuIG9wdGlvbiBmb3IgdGhpcyB0b28sIEkgYmVsaWV2ZS4gQnV0
IEkgc3Ryb25nbHkgcHJlZmVyIHRvIGRvIGFsbCB0aGlzIGtpbmQgb2Ygc3R1ZmYgaW4gbXkgbG9j
YWwgY2xvbmUgd2hlcmUgSSBjYW4gcXVpY2tseSBhbmQgZWFzaWx5IGNyZWF0ZSBiYWNrdXAgYnJh
bmNoZXMsIHRlc3QgdGhpbmdzIG91dCBhbmQgaW5zcGVjdCB0aGUgcmVzdWx0cywgYW5kIGp1c3Qg
cmVkbyBldmVyeXRoaW5nIGZyb20gc2NyYXRjaCBpZiB0aGluZ3MgZ28gYXdyeS48YnI+PGJyPiZn
dDsgSSBnb3Qgc3R1Y2sgaW4gYSB3ZWlyZCByZWJhc2Ugc3RhdGUgdGhhdCBjb25zZXF1ZW50bHkg
Y2F1c2VkIG1lIHRvIGxvc2Ugc29tZSBkYXRhIGluIHRoZSB3b3JraW5nIGRpcmVjdG9yeSBvZiBh
IGNvbXBsZXRlbHkgZGlmZmVyZW50IGJyYW5jaC48YnI+PGJyPlllYWgsIGlmIHlvdSBjb21wbGV0
ZWx5IG1lc3MgdXAgYW5kIHN1c3BlY3QgdGhhdCB5b3VyIGJyYW5jaGVzIGFyZSBpbiBhbiBpbmNv
bnNpc3RlbnQgc3RhdGUsIHRoZW4gaXQncyBvZnRlbiBlYXNpZXIgdG8gY2hlY2sgb3V0IGEgY29t
cGxldGVseSBmcmVzaCBjbG9uZSBhbmQganVzdCBzdGFydCBvdmVyLiBJdCdzIGJlZW4gYSB3aGls
ZSB0aGF0IEkgaGFkIHRvIGRvIHRoaXMsIHRob3VnaCwgc28gZWl0aGVyIGdpdCwgb3IgSSwgb3Ig
d2UgYm90aCBnb3QgYmV0dGVyLiA7LSk=" style="height:0;width:0;max-height:0;max-width:0;overflow:hidden;font-size:0em;padding:0;margin:0"></div></div></div><br><div class="gmail_quote"><div dir="ltr" class="gmail_attr">On Tue, Jul 7, 2020 at 9:26 PM Jonathan Wilkes <<a href="mailto:jon.w.wilkes@gmail.com">jon.w.wilkes@gmail.com</a>> wrote:<br></div><blockquote class="gmail_quote" style="margin:0px 0px 0px 0.8ex;border-left:1px solid rgb(204,204,204);padding-left:1ex">Moving Albert's response to my question about git rebase here on the list:<br>
<br>
Albert wrote:<br>
> Thanks!<br>
<br>
>> At some point I'd like you to show me how to do this.<br>
<br>
> Well, it's not that hard, git rebase A just replays your commits on the currently checked out branch (say, B) on top of A, starting from the point where A and B diverge. The end result is the same as with git merge A (and you'll have to fix pretty much the same conflicts if both branches modify the same file in different ways), only that you now have all the commits of B positioned neatly after the commits of A, instead of being a jumbled mess. The price you pay is that you're rewriting history on B, so you'll have to use git push -f (force push) to get your branch updated on the remote. At which point other people having checked out your B branch and working on it may get angry at you. ;-) But that's expected with the kind of temporary branches you create for doing merge requests, where you usually rebase just once directly before your branch gets merged. If it's a bigger, more permanent branch with many people working on it, however, then it's probably better to use git merge like on the master branch, and you can actually protect a branch to enforce that policy (at least I can do that on Github and Bitbucket, I think that it's possible on Gitlab as well).<br>
<br>
> In practice this means that, instead of, say, running git merge master on your feature branch, you'd be running git rebase master instead, and fix any conflicts. At which point your feature branch should neatly merge into the master branch, basically it's just a fast-forward now. So you either directly merge into master yourself (if you're Jonathan and can push to master), or force-push your feature branch (git push -f) to your remote branch, prepare a merge request for it, and wait for Jonathan to come along. If your feature branch has to wait a wee bit longer than expected, and other stuff goes into master in the meantime, then you just redo the rebase and force-push once again, to have the branch and merge request updated accordingly.<br>
<br>
> The web interface has an option for this too, I believe. But I strongly prefer to do all this kind of stuff in my local clone where I can quickly and easily create backup branches, test things out and inspect the results, and just redo everything from scratch if things go awry.<br>
<br>
>> I got stuck in a weird rebase state that consequently caused me to lose some data in the working directory of a completely different branch.<br>
<br>
> Yeah, if you completely mess up and suspect that your branches are in an inconsistent state, then it's often easier to check out a completely fresh clone and just start over. It's been a while that I had to do this, though, so either git, or I, or we both got better. ;-)<br>
<br>
The problem I ran into is that an error about a botched rebase on a<br>
throwaway branch followed me around when I checked out a completely<br>
unrelated branch. Since I had already made some changes to files on<br>
the new branch before staging them, apparently the only "right"<br>
solution after that was to copy all my changed files to a directory<br>
outside of the repo, abort the rebase from the other branch, then<br>
paste everything back. Then I'd be doing ad hoc version-control to<br>
avoid losing data in a version-control system, which should never have<br>
to happen.<br>
<br>
-Jonathan<br>
_______________________________________________<br>
L2Ork-dev mailing list<br>
<a href="mailto:L2Ork-dev@disis.music.vt.edu" target="_blank">L2Ork-dev@disis.music.vt.edu</a><br>
<a href="https://disis.music.vt.edu/listinfo/l2ork-dev" rel="noreferrer" target="_blank">https://disis.music.vt.edu/listinfo/l2ork-dev</a></blockquote></div><br clear="all"><br>-- <br><div dir="ltr" class="gmail_signature"><div dir="ltr"><div><div dir="ltr"><div><div dir="ltr">Dr. Albert Gr"af<br>Computer Music Research Group, JGU Mainz, Germany<br>Email: <a href="mailto:aggraef@gmail.com" target="_blank">aggraef@gmail.com</a>, web: <a href="https://agraef.github.io/" target="_blank">https://agraef.github.io/</a></div></div></div></div></div></div>