Skip to article

Committed to the Wrong Git Branch? Move Your Commits

Move commits from main to another Git branch. Practice unpushed recovery and a shared-history revert in real repositories inside a browser VM.

You finish two commits, glance at the prompt, and discover that you were on main. The changes are useful; the branch is wrong. You do not need to copy files into a new folder or recreate the commits by hand.

If the commits are local, create a branch pointing at them before moving main back. If the commits are already shared, preserve them on the intended branch and undo their effect with a new commit on the shared branch. The decision depends on who may already rely on that history.

A branch is a name for a commit, not a separate container of files. Creating a branch at the current tip preserves access to that commit and its ancestors. Resetting a different branch afterward does not remove commits that the new branch still reaches.

The VM contains two real Git repositories and two local bare remotes. move-lab has two unpushed commits on main; shared-lab has one accidental commit already pushed to its local remote. No command contacts GitHub or changes a repository on your computer. Run the cards in order; Reset recreates both accidents.

01

Check the branch, working tree and unpushed commits

Start in move-lab. git status --short should print nothing: there are no uncommitted changes to protect. git branch --show-current confirms main. The log range origin/main..HEAD lists commits reachable from your current tip but not from the local origin/main tracking reference.

Here you should see Add tax rule and Add checkout note. The setup pushed the initial commit before creating those two, so the tracking reference gives us the intended baseline. In a real project, fetch first and confirm which branch is the correct base. A tracking reference can be stale; a local log comparison does not prove that nobody else has received the commits by another route.

If status shows work in progress, preserve it before any hard reset. A temporary commit on a separate branch or a deliberate stash can help, but understand what is included: ordinary stash behavior does not automatically cover every untracked or ignored file. The clean VM example avoids that additional recovery problem.

Also inspect the selected commits. You may need only the last commit, rather than everything after origin/main. The next card deliberately moves both commits; choose a different baseline in a real repository only after identifying the intended range.

↳ TRY IT / CURRENT IMAGELive Git
cd /home/student/move-lab
git status --short
git branch --show-current
git log --oneline origin/main..HEAD

Expected: The current branch is main; the log lists Add tax rule and Add checkout note.

 

02

Move local commits by saving a branch first

Create feature/checkout while main still points at the two new commits. git branch creates the name without switching branches, so the following reset still applies to main. Only after main returns to origin/main do we switch to the feature branch and inspect its log.

The order matters. Saving the branch first gives the commits an explicit home. The hard reset resets main's tip, index and tracked working-tree contents to the selected baseline. It can discard uncommitted work, which is why the clean-status check came before it. It can also remove untracked paths that obstruct checkout of tracked paths.

Once you switch to feature/checkout, checkout.txt and tax.txt are present again because that branch points to the commit containing them. Nothing was copied between branches. The branch names now reach different snapshots of the same repository.

Use a new branch name for this recipe. If the intended destination already exists, switch to it and use cherry-pick to apply the selected commits, then inspect the result before cleaning up the mistaken branch. Do not replace an existing branch tip simply to make it match a tutorial. Conflicts during cherry-pick require inspection; you can abort that operation if it is not the move you intended.

↳ TRY IT / CURRENT IMAGELive Git
cd /home/student/move-lab
git branch feature/checkout
git reset --hard origin/main
git switch feature/checkout
git log --oneline origin/main..HEAD
cat checkout.txt tax.txt

Expected: feature/checkout contains both commits and both files. main matches origin/main.

 

03

Undo the effect of an already-pushed commit without rewriting history

The independent shared-lab repository represents the other case. Its accidental Add shared checkout note commit already exists on the bare remote's main branch. Save a feature branch at that commit, then use revert on main to create a new commit reversing its change. Push that new commit normally.

The log now contains both the accidental commit and the revert. That is intentional: existing consumers can advance through ordinary history instead of reconciling a rewritten main. The feature branch still points to the snapshot with checkout.txt, while main no longer contains that file.

Our local remote has no branch-protection rules. On a protected main branch, perform the revert on a cleanup branch and submit it through the project's normal review process. Reverting multiple commits or a merge needs additional care; this card reverses one simple, independent commit only.

Saving the original commit on a feature branch preserves the work, but does not make a later pull request automatically reapply it: main already contains that original commit in its ancestry. To reintroduce the change later, make fresh commits on a branch from the corrected main, or deliberately revert the revert through review. Do not force-push shared main just to make its graph look tidier.

↳ TRY IT / CURRENT IMAGELive Git
cd /home/student/shared-lab
git branch feature/shared-checkout
git revert --no-edit HEAD
git push origin main
git log --oneline -3

Expected: A new Revert commit is pushed. The original accidental commit remains in history and on feature/shared-checkout.

 

Pick the recovery from the history you have

For local commits, save a branch at the work before resetting the mistaken branch to a verified baseline. For shared commits, preserve the work and reverse unwanted changes with new, reviewable history.

Continue with the committed-to-main recovery lesson and reverting safely. Git's manuals document reset, revert and cherry-pick. Before leaving the VM, inspect both repositories with git log --graph --oneline --all: the two recovery strategies should now look different for a reason.