0

I have a GitHub fork of an open source library. In my local copy of that fork I have modified many of the CMakeLists.txt included (and other files) so that it does not compile the whole library (since there are plenty of things I do not need). Therefore, in order to smoothly integrate my changes I do

git update-index --assume-unchanged <files>

So that allows me to use git as if I did not change any of those files. However, whenever the remote has changes and I try to pull them (or whenever I want to create a new branch), I get the following error:

error: Your local changes to the following files would be overwritten by merge:
    CMakeLists.txt
    demos/CMakeLists.txt
    <other files>
Please, commit your changes or stash them before you can merge.
Aborting

So I have to undo all the changes manually, and git update-index --no-assume-unchanged <files>, pull and then redo again changes and update-index. This is painful, since I have to do it almost daily.

What I want here is to update my locally-modified files if they have any change (actually, they are not likely to be changed, so the probability for conflicts is low) but to keep the changes I did and keep git assuming that they have not been changing.

Is there a better way of doing this?

EDIT: sorry if this has been asked already. I was looking for it but I was unable to find a response for my specific case. Thank you!

Javi
  • 3,440
  • 5
  • 29
  • 43

3 Answers3

1

There is this really obscure command you need to use - git commit ;)

Seriously, just commit your work and let pull + rebase/merge take care of things.

Imagine you have 2 commits ahead of your upstream like this

Upstream <- Work you want to push <- Changes to CMakeLists.txt

git reset HEAD~1 - will "uncommit" your most recent commit, so that you can push just your first commit.

Alternately

git push HEAD~1:UPSTREAM - will accomplish the same but leave your work committed.

Or you could say git branch PUSH_ME HEAD~1 and then git push PUSH_ME:UPSTREAM

There are no end of options here. The only thing you have to do is have your changes commits while you are working so that you can pull/merge things properly.

Andrew C
  • 13,845
  • 6
  • 50
  • 57
  • I think you don't understand my question. Those files in the error are under --assume-unchanged so I do not want to commit them. – Javi Sep 28 '14 at 00:35
  • Right, you would "git add" them normally and commit them. You never want to store changes in your working directory only, that defeats the whole purpose of Git. – Andrew C Sep 28 '14 at 00:41
  • You mean to commit them normally and forget about update-index and that stuff? Then what about if I want to do a pull request? I would have to remove all those changes. – Javi Sep 28 '14 at 00:46
  • git gives you a number of options to do that. You could keep the changes as your most recent commit and then `git push HEAD~1`, or you can back out the commits with `git reset HEAD~1` and then `git push` normally, or you could apply a branch to the point you want to share and push that. – Andrew C Sep 28 '14 at 00:49
  • I still think that or I am not understanding you or you are not understanding me. It is not a commit that I want to reset or something. I locally clone the fork, I work on it, but since I do not want all the library to compile, I modify some files (for instance, not to compile all the demos). Then I push the changes to my fork and then a pull request. I want this just of the important changes. Those changes I did just for development I do not want them to be commited and pushed but I want to keep them locally so whenever I continue with my work I do not have to redo those changes. – Javi Sep 28 '14 at 00:56
  • Trust me I get it - you can commit your changes and *not* push them. Committing them is a good thing. Try the commands I mentioned above. You can either "uncommit" them when it's convenient too, or you can selectively push only the commits you want. – Andrew C Sep 28 '14 at 02:57
  • But them let's see if I understand it because I do not see how it will work. I fork the upstream. I do these initial changes I always do but do not want to push, but I commit them. So now I am in state Head+1, then I implement my contribution, commit it, state Head+2. Now I want to push only the changes in Head+2, so you mean to just push this last commit? How? because I see http://stackoverflow.com/questions/1789017/git-push-a-single-commit at it does not seem that obvious. Sorry for being that slow with this :) – Javi Sep 28 '14 at 04:30
  • sorry I haven't seen the update. I think that will not work for my case, since I will have: `Upstream <- Changes to CMakeLists.txt <- Work you want to push` – Javi Oct 02 '14 at 23:49
  • You can use `git rebase -i` to reorder your commits when you are ready to push. – Andrew C Oct 02 '14 at 23:56
  • I will do some tests before accepting your answer to be sure I got it :) Thank you for the help! – Javi Oct 03 '14 at 01:10
0

If the files are not included in the repository you should include them in the .gitignore instead of apply the --assume-unchanged. Is that the case?

esteve_jm
  • 16
  • 4
  • It is that not the case. The point is that I have a CMakeLists.txt which compiles for example 5 demos, and I just want to compile one of them since the others are not relevant. Then I comment those lines in the CMakeLists.txt, assume unchanged, do the work, commit, push, pull request. That is smooth, the changes in the CMakeLists.txt are not commited because of the assume-unchanged. But now, I want to keep those changes while updating the local copy from the remote (as those files I modify are usually not modified). – Javi Sep 28 '14 at 01:03
0

I am responding myself to this question since it will be clearer.

First, I did all the changes I did not want to push and commited them, let's say this commit is SHA1. And then did the rest of the changes and commited them with SHA2.

Now, my repo looks like this: master <- SHA1 <- SHA2 I need to push SHA2 without pushing SHA1. If I do `git push origin SHA2:master, SHA1 will be commited as well as SHA2 depends on it.

However, doing git rebase -i shows the following:

pick SHA1 comment1 pick SHA2 comment2

So I changed the order of those commits:

pick SHA2 comment2 pick SHA1 comment1

And now SHA2 no longer depends on SHA1. Doing git push origin SHA2:master pushes only the changes of SHA2.

Finally, if some changes happen in the upstream, doing git pull will work smoothly.

Javi
  • 3,440
  • 5
  • 29
  • 43