Stashing unsaved work
dirty working tree
The working tree is dirty when it has modified files. They may represent unsaved work. Untracked files live outside of Git, but may also represent unsaved work.
the modified files that we added to the index became staged files. They also represent unsaved work.
There are a few scenario where Git has to clear up both the working tree and the index, to replace them with the content from another commit. This may occur when switching to a branch that points to another commit, or when merging some remote branch into our current one. (this does not occur when creating a branch because it keeps pointing to the current commit, keeping the current changes relevant)
The straightforward solution is to save the pending work into a new commit to make the working directory and index clean, and then perform the operation mentioned above.
stashing and popping
In the case where we don't want to create a commit, but we want to preserve the work that lives in the working tree and the index, we may ask Git to stash -u the changes. Under the hood, Git creates a hidden commit for the working tree and one for the index.
Later, we may reverse the operation, bringing back the unsaved work to the working tree and the index, with pop --index.
git stash
git stash -u # include the untracked files
Restore the working directory and staging area, assuming we are back on the correct branch. the --index flag restores the staging area as well.
git stash pop --index # if it worked without conflict
git stash pop --index
git stash drop # if conflict happened and has been sovled
git stash apply --index # apply never drops the stash
git stash drop
conflict resolution on pop
When popping the unsaved files back to the working tree, there may be a conflict. The conflict resolution is the same as the one for merge conflicts. If it cannot solve the conflict itself, it will expose the incompatible changes in the files with visible marks to let the developer pick one. Similar for merge conflicts, the developer edits the file and signals it as resolved by performing a git add on the file.
As Git is conservative, it does not clear the stash if a conflict was detected. After we have resolved the conflict, we may have to clear the stash manually.
advanced: If we attempt to pop back a file from the index into an index that has a distinct version that also received work, it will fail completely, since the manual resolution is not possible for files that are in the index.