←back to thread

Oh Shit, Git?

(ohshitgit.com)
464 points Anon84 | 1 comments | | HN request time: 0s | source
Show context
pitaj ◴[] No.42729155[source]
Some changes I would make:

1. Always use `git switch` instead of `git checkout`

2. Avoid `reset --hard` at all costs. So for the "accidentally committed something to master that should have been on a brand new branch" issue, I would do this instead:

    # create a new branch from the current state of master
    git branch some-new-branch-name
    # switch to the previous commit
    git switch -d HEAD~
    # overwrite master branch to that commit instead
    git switch -C master
    # switch to the work branch you created
    git switch some-new-branch-name
    # your commit lives in this branch now :)
3. I'd apply the same to the `cherry-pick` version of "accidentally committed to the wrong branch":

    git switch name-of-the-correct-branch
    # grab the last commit to master
    git cherry-pick master
    # delete it from master
    git switch -d master~
    git switch -C master
4. And also to the "git-approved" way for "Fuck this noise, I give up.":

    # get the lastest state of origin
    git fetch origin
    # reset tracked files
    git restore -WS .
    # delete untracked files and directories
    git clean -d --force
    # reset master to remote version
    git switch -d origin/master
    git switch -C master
    # repeat for each borked branch
replies(11): >>42729838 #>>42729902 #>>42730974 #>>42731510 #>>42731713 #>>42731798 #>>42731885 #>>42732130 #>>42734933 #>>42737820 #>>42740404 #
lalaithion ◴[] No.42729838[source]
The disconnect between git's beautiful internal model of blobs, a tree of commits, and pointers to commits, and the command line interface is so wild. All of these recipes are unintuitive even if you have a firm grasp of git's model; you also need to know the quirks of the commands! To just look at the first one... wouldn't it be more intuitive for the command line interface to be:

    # this command exists already;
    $ git switch -c some-new-branch-name
    # is there a command that simply moves a branch from one commit to another without changing anything else? It feels like it should be possible given how git works.
    $ git move-branch master HEAD~
replies(8): >>42729951 #>>42729992 #>>42730629 #>>42730721 #>>42730733 #>>42730978 #>>42731467 #>>42740395 #
Certhas ◴[] No.42730721[source]
The real "internal model" of git contains much more data/moving parts.

There isn't one tree of commits, there are typically at least two: local and remote

Branches are not just pointers to commits, but also possibly related to pointers in the other tree via tracking.

Stash and index and the actual contents of the working directory are additional data that live outside the tree of commits. When op says "avoid git reset hard" it's because of how all these interact.

Files can be tracked, untracked and ignored not ignored. All four combinations are possible.

replies(1): >>42731353 #
lalaithion ◴[] No.42731353[source]
None of these seem to preclude a command to make an arbitrary branch point to an arbitrary commit without changing anything else.
replies(2): >>42731671 #>>42732411 #
karatinversion ◴[] No.42732411[source]
You are looking for

  git update-ref <branch-name> <commit-sha>
replies(1): >>42740833 #
DiggyJohnson ◴[] No.42740833[source]
Wouldn't the fail or break under any circumstance where they don't immediately share a history?
replies(1): >>42770192 #
1. karatinversion ◴[] No.42770192[source]
I just tested it by creating a repo with two branches without a common ancestor, and I was able to move a branch pointer to either history with update-ref, so no, I don't think so