git merge: apply changes to code that moved to a different file
git
Solution
I had a similar issue, and I resolved it by rebasing my work to match the target file organization. This works because git keep tracks of files content, so by rebasing on top of a rename, the changes are applied as necessary.
More precisely, let's say that you modified `original.txt` on your branch (the `local` branch), but on the master branch, `original.txt` has been copied to another one, say `copy.txt`. This copy has been done in a commit that we name commit `CP`.
You want to apply all your local changes, commits `A` and `B` below, that were made on `original.txt`, to the new file `copy.txt`.
---- X -----CP------ (master)
\
`--A---B--- (local)
Create a throwaway branch `move` at the starting point of your changes with `git branch move X`. That is to say, put the `move` branch at commit `X`, the one before the commits you want to merge; most likely, this is the commit from which you branched out to implement your changes. As user @digory doo wrote below, you can do `git merge-base master local` to find `X`.
---- X (move)-----CP----- (master)
\
`--A---B--- (local)
On this branch, issue the following renaming command:
git mv original.txt copy.txt
This renames the file. Note that `copy.txt` did not yet exist in your tree at this point. Commit your change (we name this commit `MV`).
,--MV (move)
/
---- X -----CP----- (master)
\
`--A---B--- (local)
You can now rebase your work on top of `move`:
git rebase move local
This should work without problem, and your changes are applied to `copy.txt` in your local branch.
,--MV (move)---A'---B'--- (local)
/
---- X -----CP----- (master)
Now, you do not necessarily want or need to have commit `MV` in your main branch's history, because the move operation may lead to a conflict with the copy operation at commit `CP` in the main branch.
You only have to rebase your work again, discarding the move operation, as follows:
git rebase move local --onto CP
... where `CP` is the commit where `copy.txt` was introduced in the other branch. This rebases all the changes on `copy.txt` on top of the `CP` commit. Now, your `local` branch is exactly as if you always modified `copy.txt` and not `original.txt`, and you can continue merging with others.
,--A''---B''-- (local)
/
-----X-------CP----- (master)
It is important that the changes are applied on `CP` or otherwise `copy.txt` would not exist and the changes would be applied back on `original.txt`.
Hope this is clear. This answer comes late, but this may be useful to someone else.
Problem
I am attempting a pretty beefy git merge maneuver right now. One problem that I am coming across is that I made some changes to some code in my branch, but my colleague moved that code to a new file in his branch. So when I did `git merge my_branch his_branch`, git did not notice that the code in the new file was the same as the old, and so none of my changes are there. What's the easiest way to go about applying my changes again to the code in the new files. I won't have too many problems finding out which commits need to be reapplied (I can just use `git log --stat`). But as far as I can tell, there is no way to get git to reapply the changes into the new files. The easiest thing I am seeing right now is to manually reapply the changes, which is not looking like a good idea. I know that git recognizes blobs, not files, so surely there must be a way to tell it, "apply this exact code change from this commit, except not where it was but where it now is in this new file".