I have a project with a messy history which gets messier the further back into the past you look. What I am trying to do is to preserve everything up to a specific commit, and squash everything from that commit onward. So in the following scheme, I would like to keep everything between and including A and B as is, and squash everything between B and C:
A-...-B-...-C
Unfortunately, when doing an interactive rebase I seem to end up flattening the entire history along the way, which is not ideal. I would like to still see the branches and merges between A and B. Is there any straightforward way to do that? Am I missing something really simple?
You should write
where N is the number of commits between B and C.
You should squash each of the other commits into C. On the branch you've rebased in, you will have all the commits between A and B preserved.
Also see this tutorial: http://pcottle.github.io/learnGitBranching/.