0

I used the git filter-branch --subdirectory-filter option to extract two subdirectories from one repo and merge them into another repo. However, I now need to squash the commits, because any commit touching both subdirectories is now duplicated in the new repo.

To fix this, how can I programmatically merge all such commits based on some rule? In my case I know for sure that if the commit starts with "Merge PR #PRNumber" where the number is the same, that it is a duplicate and can be squashed together.

I'm thinking about writing a script that will look at the output of "git log", then find these duplicates, and do git rebase --onto commitA commitB

However I am wondering if there's a faster/git-native way to do this. Does anyone know other ways of achieving this?

jpaugh
  • 6,634
  • 4
  • 38
  • 90
Shane
  • 369
  • 1
  • 2
  • 13
  • It's pretty confusing to try following what steps you've followed without understanding the structure of the commits before & after your changes in both repos. Could you show an abbreviated (or high level) description of your history? – jpaugh Jul 26 '19 at 21:27

2 Answers2

1

You may have to have an additional step to modify commit messages in a range, but you can use git rebase to do it. First, prepend fixup! onto each of the commit messages that you want to combine, which tells git that it can automatically squash them into the first commit in range with the matching message. Then, run git rebase --interactive --autosquash, and verify that it is doing what you expect.

0x5453
  • 12,753
  • 1
  • 32
  • 61
  • 1
    Your advice about prepending `fixup!` would behave very differently if it were performed (by a novice) *after* running `git rebase --interactive` and loading the editor. It took me a while to understand, even though I'm experienced with rebase. – jpaugh Jul 26 '19 at 21:36
0

I'm not sure how your history looks like, usually commits with message Merge PR #PRNumber come from a merge commit, and that is not a duplicate. However ...

I would do a git log to see how is the distribution of commits

$ git log --oneline
$ git cherry-pick --squash <sha1>..<sha1>

If your distribution of commits you want to squash is more disperse, a bash for loop would work (not sure if you're on windows or linux), if you can easily identify (based on the message, as you say) which one you want to squash on top.

If you would paste here your log --oneline, we can also help with the automation.

azbarcea
  • 3,323
  • 1
  • 20
  • 25