Search code examples
gitbranchbranching-strategy

Git - transferring all commits to another branch and creating a new master


(There's a lot of similar questions on this, and I've also read through various docs, but I can't find anything answering this specific issue.)

Given a repository with no remotes and no branches, with 20 commits on master.

The intent is to end up with an empty master, and all the commits on develop, but without a messy history.

Is there a difference between:

git branch --move master develop
git checkout --orphan master

And:

git checkout -b develop 
git merge master
git checkout master
git reset --hard HEAD^20

?

The first option seems the simplest way to do this, but I've not seen it suggested anywhere - all the various things I've been reading tend to use variants of the second option (or rebasing, which I don't think applies here).

Does the first option do what I think it does, and does it have any benefits/drawbacks compared to the second option?

Is there an alternative even better way to achieve this?


Solution

  • Branches are just commit pointers. You get into some weird territory when there's nothing at which to point. Honestly if you're just looking to get a "clean" workflow history, so the first commit of any significance is a merge from develop into master, add an insignificant commit to master first:

    git branch --move master develop
    git checkout --orphan master
    git rm -rf . ;# abandon the staged, orphaned changes
    echo README > README ;# put something in this working directory
    git add README && git commit -m "Initial commit of <my_project>"
    

    Why commit something? Because once you run the --orphan checkout, you won't be able to do anything meaningful with the master branch. Try it yourself:

    $ git checkout --orphan master
    Switched to a new branch 'master'
    $ git checkout develop && git checkout master
    error: pathspec 'master' did not match any file(s) known to git.
    

    How about a merge?

    $ git checkout --orphan master
    Switched to a new branch 'master'
    $ git merge develop
    fatal: Non-fast-forward commit does not make sense into an empty head
    

    No dice. The only real way around this is to commit something, anything, to that empty branch. The moment you do, you can merge develop any way you'd like:

    $ git merge develop
    Merge made by the 'recursive' strategy.
     README | 1 +
     1 file changed, 1 insertion(+)
     create mode 100644 README
    

    And the log:

    $ git log --graph --oneline
    *   867a1f9 Merge branch 'develop'
    |\  
    | * 22df145 README
    * 15ba82a Initial commit of test project