Peter
Peter

Reputation: 13485

Git: How can I split a branch by file (not by commit)?

Bottom Line:

I want to split up a pull request into two smaller pull requests with different subsets of files. I do not want to split by commit, I want to split by file.

Details:

Suppose I have a branch branch_1 (off of the master branch) in which I've modified 2 files: file_1 and file_2. Suppose these files were modified together in one or more commits (changes are not separable by commit), and suppose these files do not reference one another in any way.

After some time, I want to merge branch_1 into master, but decide that only file_1 is ready to be merged. I may merge file_2 later, so I put it on a new branch.

So I create a branch_2 off of branch_1. branch_2 now contains both the changes to file_1 and file_2. That's fine, because branch_2 will be merged after branch_1 anyway.

Now, how can I nicely revert branch_1 to remove the changes to file_2?

If I just go on branch_1 and git checkout master file_2, it works, BUT: When I merge branch_1 into master, and then master into branch_2, then it will delete file_2. This is not what I want at all!

Basically I'd like make it as if file_2 never existed at all on branch_1.

Upvotes: 20

Views: 6994

Answers (3)

DeepOne
DeepOne

Reputation: 344

A slightly more convenient way of selecting specific files:

  • create branch_2 from master
  • merge branch_1 into branch_2 with --no-commit and --squash
  • revert specific files you want excluded from the new branch (*)
  • commit remaining files in branch_2

Now you can either repeat the procedure again with inverse file selection, completely splitting the two branches right away, or just wait until branch_2 is merged into master and then merge master back into branch_1, effectively "fast-forwarding" those selected files and excluding them from the original branch_1.

(*) many UI-based git clients offer bulk revert tools, making the procedure quite comfortable

EDIT: added --squash option, as else commits from branch_1 might end up in master with only a subset of their actual content

Upvotes: 29

Peter
Peter

Reputation: 13485

So, I've come to the conclusion that git does not have a nice mechanism for this but it's easy to do using PyCharm (and probably some other tools).

To do it using pycharm, first git checkout master, then git checkout branch_3, then in Pycharm's Project toolbar right click on the root-folder of your project and go Git -> Compare with Branch, select branch_1, and then copy over file_1 from branch_1, which you want to merge, into your current code (branch_3). Now you can do a pull request from branch_3 into master.

Upvotes: 0

webbyfox
webbyfox

Reputation: 1069

Instead of making branch_2 from branch_1. I will make branch_2 from masterbranch and do the changes what you required to merge it to master and then merge branch_2 to branch_1

this is basically git workflow (nice read here)

Upvotes: -2

Related Questions