3

I am on branchX. I make some changes in my working directory. They all get reflected in "Changes not staged for commit". Now I do git checkout branchY. Sometimes I get the changes getting moved into "Changes not staged for commit" of the branchY like :

M <some file1 path>
M <some file2 path>

and sometimes git gives me this message - Please commit your changes or stash them before you switch branches.

How does git decide it when to reflect the changes and when to abort ? Should not git never move "Changes not staged for commit" changes of one branch into other if I checkout without committing them ?

Number945
  • 4,631
  • 8
  • 45
  • 83
  • 1
    Although there's already an accepted answer, I thought I should link this to the other question... – torek Oct 12 '18 at 15:12

2 Answers2

2

The second message you're quoting (Please commit your changes or stash them before you switch branches.) occurs when moving your pending changes would create conflicts on the to-be-checked-out branch.

When no conflicts are detected, the working tree is first updated regarding the commit HEAD is now pointing to, then your pending changes are replayed above and you're ready to add more changes or commit right away.

And as a sidenote, it's widely considered a good practice to always return to a clean state before checking another branch out. Committing on the branch* or stashing changes are probably the most common ways to achieve this.

(* since this commit is only local for now, you'll have the opportunity to amend it or drop it entirely when you'll return to this branch.)

Romain Valeri
  • 19,645
  • 3
  • 36
  • 61
2

The relevant documentation man git-checkout says:

git checkout <branch>

To prepare for working on <branch>, switch to it by updating the index and the files in the working tree, and by pointing HEAD at the branch. Local modifications to the files in the working tree are kept, so that they can be committed to the <branch>.

However, if the changes you made in the working directory overlap with changes introduced in the <branch>, you have a conflict. This is similar to merge conflicts, and thus the checkout is aborted.

You can use the -m (or --merge) flag to proceed with the checkout anyways, but you have to resolve the conflicts, as you would do while merging.

alfunx
  • 3,080
  • 1
  • 12
  • 23