What are your git aliases?
source link: https://dev.to/imjoseangel/what-are-your-git-aliases-43om
Go to the source link to view the article. You can view the picture content, updated content and better typesetting reading experience. If the link is broken, please click the button below to view the snapshot at that time.
Introduction
I've been requested multiple times about sharing my .gitconfig
to copy my aliases.
I use git aliases for two reasons:
- To improve productivity.
- To remember interesting
git
commands and learn from them.
My Gitconfig
These are my aliases included in my ~/.gitconfig
file for your reference:
[alias]
a = add .
aliases = config --get-regexp alias
alias = ! git config --get-regexp ^alias\. | sed -e s/^alias.// -e s/\ /\ $(printf "\043")--\>\ / | column -t -s $(printf "\043") | sort -k 1
ap = add . -p
addups = remote add upstream
bd = branch -d
bi = bisect
bl = branch -l
blr = branch -a
br = branch -r
ca = commit -a
cam = commit -a -m
ci = commit -m
cia = commit --author='imjoseangel <[email protected]>' -m
cm = commit
co = checkout
colast = checkout -
comments = commit -m 📒Comments
count = rev-list --count devel
db = branch -D
forgetAbout = rm --cached
formatting = commit -m 💅Formatting
fp = fetch -p
grep = grep -F
laf = fsck --lost-found
last = log -1 HEAD
latest = log -5 --pretty --oneline
ls = ls-files --others --exclude-standard -z
mend = commit --amend
nb = checkout -b
op = gc --prune=now --aggressive
pdo = push -d origin
pf = push --force-with-lease
po = push origin
pou = push --set-upstream origin
pr = pull --rebase
pror = remote prune origin
prud = pull --rebase upstream devel
prum = pull --rebase upstream main
prune = remote update --prune
ptag = push origin --tags
ra = rebase --abort
rc = rebase --continue
refactor = commit -m 👷Refactor
remotes = remote -v
renb = branch -m
rh = reset --hard
rhh = reset --hard HEAD
ri = rebase -i upstream/devel
rim = rebase -i upstream/main
rl = reflog
rp = repack -ad
s = status -s
search = rev-list --all
sh = show
short = shortlog -sn
sign = commit --amend --no-edit --signoff
st = status
stashes = stash list
tests = commit --allow empty -m ✅Tests
tuto = help tutorial
tuto2 = help tutorial-2
unstash = stash pop
vc = clean -dfx
wow = log --all --graph --decorate --oneline --simplify-by-decoration
Running git alias
after adding to the .gitconfig
shows the list of all the aliases as a reference list.
To get more info, just run git help <command or alias>
. For instance:
git help st
'st' is aliased to 'status'
git help status
There are two aliases I find interesting for beginners:
git tuto
git tuto2
Comments and suggestions with different approaches are always welcomed.
Top comments (32)
My aliases are either things I use regularly or things that I find useful on occasion and would otherwise have to look up every time. I've added explanatory comments to some of the less-obvious aliases.
[alias]
# File changes
## gen-ignore <lang>: Outputs a .gitignore file for `lang` from gitignore.io to stdout.
gen-ignore = "!_gi() { curl -L -s https://www.gitignore.io/api/$@ ;}; _gi"
## ignore/hard-ignore: See https://stackoverflow.com/a/13631525
ignore = update-index --assume-unchanged
unignore = update-index --no-assume-unchanged
hard-ignore = update-index --skip-worktree
hard-unignore = update-index --no-skip-worktree
## ls-ignored: Lists files marked with assume-unchanged.
ls-ignored = !git ls-files -v | grep '^[[:lower:]]' | cut -c 3-
## ls-hard-ignored: Lists files marked with skip-worktree.
ls-hard-ignored = !git ls-files -v | grep -i '^S' | cut -c 3-
word-diff = diff --word-diff
char-diff = diff --word-diff --word-diff-regex='([^[:alnum:]]|[^[:space:]])'
## drop [stash_args...]: Like `reset HEAD`, but changes are recoverable from the stash reflog. Forwards arguments to `stash push`.
drop = "!_drop() { git stash push \"$@\" && git stash drop; }; _drop"
stat = status --short --branch
# Commits
## init-commit: Initializes the repo and creates an empty initial commit.
init-commit = !git init && git commit --allow-empty -m \"Initial commit\" -m \"This commit intentionally left blank.\"
amend = commit --amend --no-edit
fixup = commit --fixup
squash = commit --squash
# Log
graph = log --graph --oneline
log-yesterday = log --since=yesterday.midnight --oneline
# Branches
pulre = pull --rebase
## push-new: Pushes the current branch to `origin` with the same name and sets up tracking.
push-new = push -u origin HEAD
push-lease = push --force-with-lease
## sq [base_branch]: Starts an interactive rebase from the base of the branch relative to `base_branch`
## (defaults to `master`; can be any ref) without applying changes on top of `base_branch`.
sq = "!_sq() { git rebase --interactive --autosquash $(git merge-base HEAD ${1:-master}); }; _sq"
push-new
can easily be rewritten to accept other remote names as arguments, and sq
's default can be changed to use main
or pull init.defaultBranch
from the Git config instead of master
.
I tend not to use too many short forms or have too many aliases because tab completion exists and I don't want to develop non-portable muscle memory.
Wow! I will take some from you and adding to my list of learning commands. Thanks!
CollapseExpand
Good timing this post!
I recreated my WSL space on my Windows 10, and I created some aliases for git and others commands.
aliases ga="git add"
aliases gc="git commit -m $1"
aliases gp="git push"
aliases gpu="git pull"
CollapseExpand
Great list! Will definitely add a few of these.
A few more that I like:
# oops, missed a file in prior commit
ca = commit --amend --no-edit
fa = fetch --all --prune
# IMO this option should be the default for force pushing
pf = push --force-with-lease
# thing you do for first push of a branch
pu = push -u origin HEAD
# create a WIP commit without running precommit
wip = commit -m\"WIP\" --no-verify
# "uncommit"
pop = reset HEAD^
# list branches by most recent commit
recent = for-each-ref --sort=-committerdate --count=30 --format='%(refname:short)' refs/heads/
Thanks for sharing @ehaynes99 ! I will take note of yours too.
CollapseExpand
wow… @tpenguinltg ’s stuff - that’s on a different level entirely (: can’t wait to try some of those!
i use many of the aliases shared by others regularly. one alias in particular saves me a ton of time daily:
#!/bin/bash
alias gmd=“git checkout development && git pull && git checkout - && git merge development”
alias push=“gmd && git push”
- stashes any wd changes
- checks out
development
/master
/etc - pulls the latest
- checks out the previous branch
- merges the latest from the main (e.g.
development
), then lastly
It’s not strictly a git alias, i know, though you could prob make that work 🤷♂️ never tried 😉 useful nonetheless IMH
I use it anytime i’m done with a feature and need push and open a PR on main.
great post. inspiring stuff!
CollapseExpand
Here's some of mine that I've found useful over the years:
# Laziness typing out `git branch`
bb = branch --all
b = branch --show-current
# Less or more verbose `git status`
ss = status -b --short
sl = status --long --ignored
# Show a nicely formatted tree-like git graph
h = log --graph --date-order --date=short --pretty=format:'%C(auto)%h%d %C(reset)%s %C(bold blue)%cn %C(reset)%C(green)%cr (%cd)'
# List all release tags and their commit hashes
tl = tag -l --sort=-creatordate --format='%(creatordate:short) | %(refname)'
# Delete all local changes
pristine = !git reset --hard && git clean -f
# When I need to answer the question of "who and when added this file?"
whenadded = log --diff-filter=A
# Delete all local branches where the remote branch already deleted (ex. after PRs are merged)
gone = "!git fetch -p && for b in $(git for-each-ref --format='%(if:equals=[gone])%(upstream:track)%(then)%(refname:short)%(end)' refs/heads); do git branch -D $b; done"
# Opposite of `git pristine`
wip = "git stash push -u -m "WIP"
Nice ones also @ginomempin . Thanks for sharing!
CollapseExpand
I mostly just stick with these:
alias gdiff="git difftool"
alias gap="git add -p"
Everything else is longform because I prefer to be familiar with the most common commands in case i'm ever not on a computer that's mine.
CollapseExpand
The only one I sometimes configure is git s
for status, but even that I usually just type out. One thing I did alias was merging current branch to our integration branch, which lets me easily chain either the push or the push and checkout $currb after it, or waiting for the CI pipeline to start before pushing.
Though I do sometimes think about aliasing m
to merge --no-edit
and ca
to merge --amend --no-edit
, because I often forget to add the no-edit param and get annoyed by the need to quit nano.
CollapseExpand
Great aliases you've got!
I have just one git alias at the moment and that is:
[alias]
## sign your commit message
csm = commit -s -m
This comes very handy especially if you contribute to open source projects frequently.
CollapseExpand
Nice, thanks for sharing.
I would add some of my aliases
no-edit = commit --amend --no-edit
back = reset --soft HEAD~1
back2 = reset --soft HEAD~2
back3 = reset --soft HEAD~3
Thanks for sharing you too!!
CollapseExpand
Well, my git alias list is not that long. It's like 8 lines which are for the most used git commands. And I don't have aliases for commands with different flags.
But that's the good thing about it, personalization rules.
CollapseExpand
I have only two aliases:
[alias]
changes=!git fetch && git log --name-status HEAD..
fire=git add . && git commit -m "OMG, FIRE" && git push
CollapseExpand
I don't believe using aliases is a good idea. I seldom use it even in my shell, but I prefer to leave it out entirely with applications that I might not be the only one using. And Git is definitely not something of which I'm the sole user, so avoiding aliases makes it much easier to remember the full commands as they would be available for my friends and colleagues if I need to help them out, or if I'll be writing documentation on how we're doing certain processes.
In those cases I think using an alias will cause more harm than good, and so I avoid them. The extra keystrokes are not an issue for me, as I'm a slow thinker anyways, haha.
I understand @necrophcodr , You can always have them to learn new commands and git options. Thanks for sharing!
CollapseExpandCollapseExpandCollapseExpand
CollapseExpand
Hi @motuncoded , just create a .gitalias
file in your home:
cat ~/.gitconfig
, and add your list in the [alias]
section as shown in the post.
Let me know if it help.
Thank you!
CollapseExpand
[alias]
line = log --oneline
st = status -sb
last = log -1 HEAD --stat
fap = fetch --all --prune
cb = checkout -b
gc-full = gc --prune=now --aggressive
search = "!f() { s=\"$1\"; shift; if (( $# > 0 )); then set -- @; fi; git rev-list \"$@\" | xargs git grep \"$s\" ; }; f"
changed-files = "!f() { git log --name-only --pretty=oneline --full-index \"$1\" | grep -vE '^[0-9a-f]{40}'|sort|uniq;}; f"
push-new = !git push -u upstream $(git rev-parse --abbrev-ref @)
Also, for work specifically, my company works on GitHub, and I have a bash script to easily create a new PR from the current branch.
#!/bin/bash
set -eu
declare -r UPSTREAM_NAME=upstream
declare MERGE_BRANCH=main
declare -r BRANCH=$(git rev-parse --abbrev-ref HEAD)
declare UPSTREAM_URL=$(git remote get-url upstream)
UPSTREAM_URL=$(echo "$UPSTREAM_URL" | sed -E -e 's|^git@|https://|' -e 's|.com:|.com/|' -e 's/.git$//')
MERGE_BRANCH=${1:-$MERGE_BRANCH}
declare -r PR_URL="${UPSTREAM_URL}/compare/${MERGE_BRANCH}...${BRANCH}?expand=1"
echo $PR_URL
open $PR_URL
I name it git-new-pr
, and add it to my $PATH
. Then, I can call git new-pr
, and it'll automatically open up a page for a new PR in my browser.
This script is for macOS. So, the last line opens the URL in the default browser. If using Linux, this could be xdg-open $PR_URL
. Also, a specific browser could be specified.
Most people would just use the GitHub cli for this, but I've never bothered installing it, and this works really well.
CollapseExpand
The thing that confuses is that alias set is very uneven in sense of pressings. If you press something on keyboard, you anyway press some sequences, and all git commands start with "git " - already 4 presses... After it, difference, for example, between "git br" = "git branch -r" and "git b -r" where "b" is already aliased as "branch" is nearly void, compared with any other difference. This suggests the alias set is accrued historically without substantial reconcerning.
Alias "db" is dangerous. I prefer to write such actions only explicitly. Same for "op": it's normal to refer to something done a few days ago, and for "vc". (BTW do you use IDE? Something like "git clean -dfx -e .vscode" would be better.)
What is use case for "search"?
"last" could be extended with "--stat" to show changes, because anyway only a single commit is printed.
OTOH, it clearly exposes some manners and developing approaches - as presence of "main" and "devel" branches. For me, it showed some features I was unaware or forgot them due to standing out of usual habits... thanks for this.
Formatting was broken - e.g. what is "git alias" is unparseable (seems the website markdown was active). If it allows editing the post, please reconsider.
To compare, my typical set (with comments):
Maybe more specific to my manner, but it is typical to cache only some changes among ones in file (others could be for later commits, not committed as debug, etc.) - just interactive mode is not enough. Git's recalculating of chunk line count works well enough.
In rebase, sometimes it is needed to see full patch to apply now.
Just shortening for all branch related commands.
"current branch" in an easy solitary way.
To adjust the last commit with catch-up changes.
Habitual from previous VCSes. To edit commit message is more useful because it never should be one-liner in a final version.
Obviously needed before commit is created from parts.
Maybe "cp -n", etc. is enough but often used in some flows.
lggo = log --graph --oneline
lg = log --graph
lgf = log --graph --pretty=fuller --topo-order
lgs = log --graph --stat
logf = log --pretty=fuller --topo-order
lpf = log -M -p --pretty=fuller
lp = log -M -p
lss = log -M --shortstat
lstf = log -M --stat --pretty=fuller --topo-order
lst = log -M --stat
lggo = log --graph --oneline
lg = log --graph
lgf = log --graph --pretty=fuller --topo-order
lgs = log --graph --stat
logf = log --pretty=fuller --topo-order
lpf = log -M -p --pretty=fuller
lp = log -M -p
lss = log -M --shortstat
lstf = log -M --stat --pretty=fuller --topo-order
lst = log -M --stat
Convenience for log view styles.
pura = pull --rebase --autostash
For some flows, merge is impossible - it's required to actualize the working state regularly.
rba = rebase --abort
rbas = rebase --autostash
rbc = rebase --continue
rbi = rebase -i
rbias = rebase -i --autostash
rbs = rebase --skip
Interactive rebase helpers in different styles to keep propositions clear.
startempty = commit --allow-empty -m 'Initial empty'
Rare but... for a new work, having basic empty commit is crucial to keep the first commit clear. Otherwise, complex dances with filtering are needed. (I'm wondering why it is not in Git base logic.)
I'd also note some crucial settings out of aliases:
merge.conflictstyle=diff3
To show base version for a conflict - crucial both for a human and automatic merging tools.
pager.status=true
Otherwise some tools avoid paging.
push.default=simple
Never push many-to-many without an explicit specification in a command.
pull.ff=only
Useful default to minimize underwater pull effects.
CollapseExpand
Sorry to be a Party Pooper!!
But why not use ZSH with the Oh ZSH add-on and it's various plugins. ohmyz.sh/
Even posted on Dev.to
dev.to/0xkoji/do-you-know-oh-my-zs...
Using .gitconfig is more portable, especially when setting-up aliases on remote terminals and servers. Nothing needs to be setup other than copying the .gitconfig (since most environments already have Git installed).
Recommend
About Joyk
Aggregate valuable and interesting links.
Joyk means Joy of geeK