views:

344

answers:

2

I'm new to git and I'm trying to understand the difference between a squash and a rebase. As I understand it you perform a squash when doing a rebase.

+1  A: 

Merge squash merges a tree (a sequence of commits) into a single commit. That is, it squashes all changes made in n commits into a single commit.

Rebasing is re-basing, that is, choosing a new base (parent commit) for a tree. Maybe the mercurial term for this is more clear: they call it transplant because it's just that: picking a new ground (parent commit, root) for a tree.

When doing an interactive rebase, you're given the option to either squash, pick, edit or skip the commits you are going to rebase.

Hope that was clear!

Mauricio Scheffer
+4  A: 

Both git merge --squashed and git rebase --interactive can produce on "squashed" commit.
But they serve different purpose.

it will produced a squashed commit on e the destination branch, without marking any merge relationship.
This is useful if you want to throw away completely the source branch, going from (schema taken from SO question):

      X                   stable
     /                   
a---b---c---d---e---f---g tmp

to:

      X-------------------G stable
     /                   
a---b---c---d---e---f---g tmp

and then deleting tmp branch.

it replays some or all of your commits on a new base, allowing you to squash (or more recently "fix up", see this SO question), going directly to:

      stable
      X-------------------G tmp
     /                     
a---b

if you choose to squash all commits of tmp (but, contrary to merge --squashed, you can choose to replay some, and squashing others).

So the difference:

  • one do not touch your source branch (tmp here) and create a single commit where you want.
  • the other allows you to go on on the same source branch with:
    • a new base
    • a cleaner history
VonC
`G` is `c--d--e--f--g` squashed together?
Wayne Conrad
@Wayne: yes, G in those examples represent the `tmp` commits squashed together.
VonC