Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to prevent git stash dropping changes to files with the "assume unchanged" bit?

I have used git update-index --assume-unchanged on some files to keep my changes to them from being committed.

When using git stash in the repository, those changes are stashed along with any other outstanding changes. This is expected behaviour, however git stash pop doesn't bring them back, so the changes are just lost.

Anyone know how to either prevent the files with the assume unchanged bit from having their changes stashed? Alternatively perhaps you know how to make sure that any changes that are stashed against those files are at least brought back?

like image 405
Stephen Emslie Avatar asked May 11 '11 10:05

Stephen Emslie


People also ask

How do I fix please commit your changes or stash them before merge abortion?

The “commit your changes or stash them before you can merge” error is raised when you try to pull code from a remote repository that conflicts with a local change you have made to a repository. To solve this error, either commit your change to the repository, discard your change, or stash your change for later.

Does git stash remove staged changes?

NO, no changes have been lost. Acc. to the documentation: Git re-modifies the files you uncommitted when you saved the stash.

What happens if you git stash multiple times?

If you want to git stash pop twice because you want both stashes in the same commit but you encounter "error: Your local changes to the following files would be overwritten by merge:" on your 2nd git stash pop , then you can: 1) git stash pop , 2) git add . , and 3) git stash pop .


1 Answers

assume-unchanged is a performance hack, and represents a promise from you that the file has not changed. If you actually change the file all bets are off. You should either rearchitect your repo so that you don't commit these files (perhaps commit filename.sample and .gitignore filename) or play tricks with branches so that the files you do not want shared with the rest of the world are off on another branch or otherwise hidden.

I have seen/thought of four suggestions on how to hide these changes.

1: Use a smudge/clean filter to change the file to what you want on checkout and clean it on checkin. Ugly.

2: Create a local configuration branch as described in http://thomasrast.ch/git/local-config.html The critical thing to remember here is that you develop on the primary branch and merge onto the config branch for testing. Back out to the primary branch to change, push, etc.

3: Create a private development branch, make the change you never want shared, and then make a fake merge (git merge -s ours privatebranch). You can then develop and test on your private branch and the change you do not want shared should not be when you merge back, as long as the change is far away from your normal work. However, when you get new changes from upstream, you need to pull them directly from upstream into the private branch. You then merge from private back into master and push upstream from master. You must never merge from master back into private. Likewise, you must never rebase (well, possibly rebase -p would work, but no guarantees). These merge/rebase and where each must occur makes this less attractive.

4: Create a private development branch, make the change you never want shared, and then create a merge driver (see man gitattributes) which will refuse to merge the file in question from master to private or from private to master (probably by comparing the SHA of the file on the private branch to the various branch's SHAs and copying the previous value if it matches).

like image 196
Seth Robertson Avatar answered Sep 18 '22 23:09

Seth Robertson