Skip to content

Comment on Resistance Against Git Merge Hell (2015)

Comments

The more I work with git, the more I wish there was a rebase (including squash/fixup) which kept the original commits, but hides them. I’m not sure how that would work in practice, but there is value in keeping all change history, and there is also value in having a readable commit history, but git does not let you do both.

That's effectively what merge does. If you want to think of your branch as one linear history, then git merge creates a single commit in your branch which represents a collection of commits from some other space (and there's no rule that you need to use the default merge commit message). Then you use `git log --first-parent` to view your branch's simple linear history.

Not really, for two reasons.

First, merge only ever allows you to arrive at a single commit, so it's strictly less powerful than rebase. With rebase, you could start with a sequence of three commits, "A", "B", and "squash! A", and turn that into two commits, "A'" and "B'". Merge doesn't let you do that.

Second, sometimes a merge commit really is semantically useful and you want it to be shown as a merge with two parents. There is no canonical way to distinguish this kind of merge from the kind of merge you seem to be thinking of.

Personally, I think the way to resolve this would be to have optional "squash/cherry-pick parent" metadata on a commit, so that commits that result from a cherry-pick or a rebase can point back to the original commit(s) in a more structured way (remember that a rebase is really just a sequence of cherry-picks). This metadata could also be used to preserve `git commit --amend` version history. Augment it with a "reverse diff" bit and it can be used to track reverts as well.

Work with it a bit more, discover reflog, and you'll find that's exactly what happens (until gc) ;)

It could be a bit more visible somehow though, I get the sentiment. Maybe it's more of an add-on to git's role though, at least without plenty else also becoming more visible/GUI-like too.

If it’s only saved until gc then it isn’t something you can rely on

It's saved while it's in the reflog, and then saved until gc. How long things stay in the reflog is configurable.

The bigger deal is that things are never shared simply for being in the reflog - which is probably correct for its intended use but doesn't really fit what's asked for up thread.

I wish there was a rebase (including squash/fixup) which kept the original commits, but hides them

That's exactly what rebase does.

(OJFord said that too, but buried the lede slightly, so I thought it worth saying in a single sentence.)

AboutSource Built by g1lg1l

Hackerly is an independent reader for Hacker News, built on the public HN API. Not affiliated with Y Combinator.