Skip to content

Instantly share code, notes, and snippets.

@jvmvik
Last active June 24, 2022 01:33
Show Gist options
  • Select an option

  • Save jvmvik/9aa318701894d2919dc98d0f1fc731d0 to your computer and use it in GitHub Desktop.

Select an option

Save jvmvik/9aa318701894d2919dc98d0f1fc731d0 to your computer and use it in GitHub Desktop.
Git tricks

Git Trick

Currated list of usefull complex command in git.

Find commmit missing on a branch in order to cherry-pick them.

Search in reverse order the hash of the commit missing on master from the dev branch.

git log origin/master..origin/dev --oneline --reverse  --pretty=format:"%h"
# copy/paste output in vscode to create a single line command like this:
git cherry-pick ef55b76d02f 1b85300d4fa a2197fe36d7 

Find where is a commit ?

git branch <branch_name> --contains <commit>
git branch -a --contains <commit>

Work tree

To parallelize the development of a single project into multiple editable branches.

# create a new project from existing clone
git worktree add <path/to/project> <branch>

Git configuration

To change git user setting

# print git output on the stdout
git config --global core.pager cat
# set editor
git config --global core.editor nano

or edit

~/.gitconfig

Find if a commit is on a branch

git branch --contains <commit_hash>

Find all the commit on a branch.

$ git checkout feature_branch 
$ git pull 
$ git merge origin/master 
$ git log --oneline --no-merges master..HEAD

Find a commit using grep

git log --grep="CAL"

Find the last commit where a file was deleted

git log -1 -- <path/to/file>

Find a file history even after being deleted

git log -- <path/to/file>

Find commit by user

git log --author $user

Apply change to the master

$ git checkout master
$ git cherry-pick <commit hash>

To automate this process with ruby

$ irb

`git checkout feature_branch`
s = `git log --oneline --no-merges master..HEAD`
list = s.split("\n").map { |s| s.scan(/^(\S+)\s+/).flatten.first }
list.reverse!
`git co porter_r2rel_dev`
`git pull`
list.each { |h| puts `git cherry-pick #{h}` }

Convert commit list to CSV

git log --pretty=format:"%h;%ad;%s%d" --date=short --author=victor . > file.csv

Revert after a branch merge

git merge -m 1 <merge_branch_commit>

Search git stash

git stash list -i -p -G<regexp>

Rebase

To combine a set of commits into one.

combine 3 last commit on the local branch

git rebase -i HEAD~3

combine all the changes from one branch into one.

git merge --squash feature/branch

Custom git command

Edit a ~/.gitconfig to add a set of custom commands, like:

$> git graph

File: ~/.gitconfig

[alias]
        ci = commit
        graph = log --oneline --graph --all --decorate --abbrev-commit
        ll = log --graph --stat --abbrev-commit --decorate=full
        lp = log --graph --patch --abbrev-commit --decorate=full
        lm = log --graph --patch --abbrev-commit --decorate=full --author victor
        ls = log -10 --pretty=format:"%h" --author victor
        cp = cherry-pick
        s  = status
        b  = branch -vv
        p  = pull
        d  = diff
        co = checkout
        stash-diff = stash show -p stash@{0}
        outstanding = log origin/dev..HEAD
        change = diff --stat --cached origin/master
        mm = merge -Xignore-space-change dev
        find = log --graph --stat --
        url = "!sh -c \"echo https://jira.arm.com/browse/`git branch | grep -e "^*" | cut -d'/' -f3`\""
        open = "!sh -c \"git checkout -b scratch/jira/$1\""
        new = "!sh -c \"git checkout -b scratch/users/vicben01/$1\""
        close = "!sh -c \"git merge --squash scratch/users/vicben01/$1 -m \"Merge $1\"\""
        ld = diff --stat HEAD..origin/dev
        root = rev-parse --show-toplevel
[color]
        diff = auto
[core]
        whitespace = trailing-space,space-before-tab
        autocrlf = input
        editor = nano
[apply]
        whitespace = fix
[branch]
        pager = cat
[pull]
	rebase = true

How can I find out which branches have been merged? How do I delete those on the remote repository? For the first question, git can answer it directly. First make sure your local copy is up to date and has master checked out

$ git checkout master 
$ git pull --prune 

Then ask git which local branches are already merged to master.

$ git branch --merged 

Unfortunately, it will always list master itself, but we can fix that with some command line magic.

$ git branch --merged | grep -v master 

Piping the output through grep and looking for lines which do not contain the word master will strip it out.

Now you can clean house locally by deleting all those branches

$ git branch -D `git branch --merged | grep -v master` 

Once you’ve done this, you want to find out which remote branches have been merged, again removing master from the list.

git branch --merged -a | grep -v master 

Now, again unfortunately, the output from the git branch command has some unwanted cruft in it .. each branch name starts with remotes/origin/ but we can fix that with sed

git branch --merged -a | grep -v master | sed 's%remotes/origin/%%' 

Finally, the trick to deleting a remote branch is simply to push an empty ref to it:

$ git push origin :unwanted_branch 

If we combine the last two commands we get the following:

$ for b in git branch --merged -a | grep -v master | sed 's%remotes/origin/%%'; do git push origin :$b; done Putting it all together, you might want to put this into a script for repeated use.

#!/bin/bash -e 
 
# Get on the master branch and up to date 
git checkout master 
git pull --prune 
 
# Delete all merged local branches 
for b in `git branch --merged | grep -v master`; do 
	echo Deleting local branch $b 
	git branch -D $b 
done 
 
# Delete all merged remote branches 
for b in `git branch --merged -a | grep -v master | sed 's%remotes/origin/%%'`; do  
	echo Deleting remote branch $b 
	git push origin :$b 
done 

All done, and you never even had to open your browser.

Git documentation

Commit naming convention. https://chris.beams.io/posts/git-commit/

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment