diff --git a/README.md b/README.md index 78f073c..c93a51e 100644 --- a/README.md +++ b/README.md @@ -1,34 +1,69 @@ -# dotGit - 🐚 shell aliases + 🪄 dotfiles + 🧸 bare git repo +# dotGit ::: 🪄 dotfiles + 🧸 bare git repo + 🐚 shell aliases -There are a lot of ways to manage your dotfiles. dotGit implements an idea that has been floating around on the internet for a while: a bare git repo for storing your dotfiles. A quick search finds [this post](https://news.ycombinator.com/item?id=11070797), but there may be older sources. +There are a lot of ways to manage your dotfiles. dotGit implements an idea that has been floating around on the internet for a while: a bare git repo for storing your dotfiles. A quick search finds [this post](https://news.ycombinator.com/item?id=11070797), but there may be older sources. dotGit combines this with some convenient shell aliases, a couple of functions, and FZF's matching magic to track your dotfiles files with ease. dotGit has modest aims: -- 🏡 keep config files where tools expect them in `$HOME` +- 🏡 keep configuration files where tools expect them in `$HOME` - 🐚 stay as light and close to git and the shell as possible -- 🚀 reduce friction and make config changes quick and convenient +- 🚀 reduce friction and make configuration changes quick and convenient -dotGit gives you a handful of shell aliases (tested with `zsh`🐚 and `bash`) to make dotfile management quick and easy. The shortcuts mimic a subset of those found in the [oh-my-zsh](https://github.com/ohmyzsh/ohmyzsh) [git](https://github.com/ohmyzsh/ohmyzsh/tree/master/plugins/git) plugin. -- `.g` is the alias for running `git` with correct `--git-dir` and `--work-tree` -- `.ga` runs `git add` -- `.gc` runs `git commmit` -- `.gco` runs `git checkout` -- `.gd` runs `git diff` -- `.gss` shows the `git status --short` -- `.gp` will `git push` the changes to the origin -- `.gl` will `git pull` changes from the origin -- `.glo` runs `git log --oneline --decorate ` -- `.glg` runs `git log --stat` -- `.glgp` runs `git log --stat --patch` -- `.gg` runs `git grep` on your dotfiles. If [FZF](https://github.com/junegunn/fzf) is installed it will be used to present the matches, and make it easy open your `$EDITOR` on the right line (works with vi, emacs, nano, micro, and any editor that accepts the `+` syntax to indicate the line number). -- `.ge` (requires [FZF](https://github.com/junegunn/fzf)) lists all files using FZF and opens the selected file in your `$EDITOR` -- `.lazygit` (requires [lazygit](https://github.com/jesseduffield/lazygit)) will run `lazygit` with the correct `-g` and `-w` -- `.gitui` (requires [gitui](https://github.com/extrawurst/gitui)) will run `gitui` with the correct `-d` and `-w` +## usage -There are two additional aliases used to (re)set up the bare git setup. -- `.ginit` creates the bare git repository in `$DOT_FILES` directory. -- `.gclone` will clone the repository set in `$DOT_ORIGIN` into the `$DOT_FILES` directory -Both of these aliases also set git's `status.showUntrackedFiles` to `no`. This prevents every file in `$DOT_HOME` from showing as "untracked" by git. +Most of dotGit is just some aliases that point to the `--git-dir` and `--work-tree`. + +The real daily winners for me are the "edit" (`.ge`) and "grep" (`.gg`) aliases. They get me to where I need to be fast. + +### a normal workflow for making configuration changes + +1. `.gl` - pull changes from origin +2. make some changes. Try: + - `.ge zshrc` - presents all files with `zshrc` in the name + - `.gg PATH` - runs `git grep` across your dotfiles and presents the results +4. `.gc -m 'commit comment' .zshrc` - will commit the changes +5. `.gp` - pushes the changes to the origin + +### a list of all aliases defined + + +| alias | action | note | +| --- | --- | --- | +| .git | `git --git-dir=${DOT_REPO} --work-tree=${DOT_HOME}` | | +| .g | `.git` | | +| .ga | `.git add` | | +| .gc | `.git commit` | | +| .gco | `.git checkout` | | +| .gd | `.git diff` | | +| .ge | calls the `_dotgit_ge` helper function | the dotGit edit feature [^fzf] | +| .gg | calls the `_dotgit_gg` helper function | grep your dotfiles, and jump to correct line [^line] | +| .gss | `.git status --short` | | +| .glo | `.git log --oneline --decorate` | | +| .glg | `.git log --stat` | | +| .glgp | `.git log --stat --patch` | | +| .gbl | `.git blame -w` | | +| .gb | `.git branch` | | +| .gba | `.git branch --all` | | +| .gbd | `.git branch --delete` | | +| .gbD | `.git branch --delete --force` | | +| .gm | `.git merge` | | +| .gma | `.git merge --abort` | | +| .gmc | `.git merge --continue` | | +| .gc! | `.git commit --verbose --amend` | +| .gcm | `.git commit --message` | | +| .gcp | `.git cherry-pick` | | +| .gcpa | `.git cherry-pick --abort` | | +| .gcpc | `.git cherry-pick --continue` | | +| .gclean | `.git clean --interactive -d` | | +| .ginit | `git init --bare "${DOT_REPO}"; .git config --local status.showUntrackedFiles no` | [^untracked] | +| .gp | `.git push` | requires `DOT_ORIGIN` be set | +| .gl | `.git pull` | requires `DOT_ORIGIN` be set +| .gclone | `git clone --bare "${DOT_ORIGIN}" "${DOT_REPO}"; .git config --local status.showUntrackedFiles no` | | +| .lazygit | `lazygit -g ${DOT_REPO}/ -w ${DOT_HOME}` | requires `lazygit` be installed | +| .gitui | `gitui -d ${DOT_REPO}/ -w ${DOT_HOME}` | requires gitui to be installed | + +[^line]: This works with vi, emacs, nano, micro, and any editor that accepts the line number to open the file to. +[^untracked]: Also set git's `status.showUntrackedFiles` to `no`. This prevents every file in `$DOT_HOME` from showing as "untracked" by git. +[^fzf]: requires [FZF](https://github.com/junegunn/fzf) ## requirements @@ -41,12 +76,12 @@ Both of these aliases also set git's `status.showUntrackedFiles` to `no`. This p ## installation -1. clone this repository or simply copy the [dotGit.sh](./dotGit.sh) -2. add some config sauce to your shell initialization (.i.e. `.zshrc` or `.bashrc`). The `DOT_FILES` and `DOT_HOME` variables **must be set** for the dotGit.sh to load! +1. clone this repository or simply copy the [dotgit.sh](./dotgit.sh) +2. add some configuration sauce to your shell initialization (.i.e. `.zshrc` or `.bashrc`). The `DOT_REPO` and `DOT_HOME` variables **must be set** for the dotgit.sh to load! ```bash - export DOT_FILES="${HOME}/.dotfiles" - export DOT_HOME="${HOME}" - export DOT_ORIGIN="git@github.com:user/your-dotfiles-repo.git" # optional + export DOT_REPO="${HOME}/.dotfiles" # this is where the repo will live + export DOT_HOME="${HOME}" # this is generally the same as `$HOME` + export DOT_ORIGIN="git@github.com:user/your-dotfiles-repo.git" # optional source ` ``` 3. restart your shell or `source ~/.zshrc` or `source ~/.bashrc` @@ -56,7 +91,7 @@ Both of these aliases also set git's `status.showUntrackedFiles` to `no`. This p ## initial clone cleanup -Existing config files will prevent checking out the files. To list the files causing the checkout to fail, run the following. +Existing configuration files will prevent checking out the files. To list the files causing the checkout to fail, run the following. ```bash .g checkout 2>&1|grep -E '^\s'|cut -f2-|xargs -I {} echo "{}" @@ -64,6 +99,10 @@ Existing config files will prevent checking out the files. To list the files cau To remove all the conflicting files, simply change the `echo` in the above command to `rm`. **This will delete files, so be sure you want to remove them.** Once the files are removed the checkout will succeed. +## future features + +- command line completion +- manage system configuration files ## alternatives diff --git a/dotgit.sh b/dotgit.sh index e409b52..8fe3d11 100644 --- a/dotgit.sh +++ b/dotgit.sh @@ -1,48 +1,108 @@ #!/usr/bin/env bash -[[ ! "${DOT_FILES}" ]] && echo "NOT setting dotGit aliases, since DOT_FILES not set." && return -[[ ! "${DOT_HOME}" ]] && echo "NOT setting dotGit aliases, since DOT_HOME not set." && return +[[ ! "$DOT_REPO" ]] && echo "NOT setting dotgit aliases, since DOT_REPO not set." && return +[[ ! "$DOT_HOME" ]] && echo "NOT setting dotgit aliases, since DOT_HOME not set." && return -alias .g='git --git-dir=${DOT_FILES} --work-tree=${DOT_HOME}' -alias .ga='.g add' -alias .gc='.g commit' -alias .gco='.g checkout' -alias .gd='.g diff' -alias .gss='.g status --short' -alias .gp='.g push' -alias .gl='.g pull' -alias .glo='.g log --oneline --decorate' -alias .glg='.g log --stat' -alias .glgp='.g log --stat --patch' +[[ -n "$DEBUG" ]] && echo loading dotgit aliases -# shellcheck disable=SC2142,SC215 -alias .ge='_dotgit_ge(){ - cd ${DOT_HOME} - FILE=$( Q="$@"; .g ls-files --full-name | - fzf --preview "bat -n --color=always {}" -q "${Q}") - [[ "$FILE" ]] && $EDITOR "${FILE}" - cd ${OLDPWD} -}; _dotgit_ge' +[[ -z "$DOTGIT_MULTI_LIMIT" ]] && DOTGIT_MULTI_LIMIT=2 +[[ -z "$DOTGIT_MULTI_ACCEPT" ]] && DOTGIT_MULTI_ACCEPT='{1}' +[[ -z "$DOTGIT_PREVIEW" ]] && DOTGIT_PREVIEW='bat -p --color=always' + +# the master alias +alias .git='git --git-dir=${DOT_REPO} --work-tree=${DOT_HOME}' +# the short one +alias .g='.git' + +# and all the shortcuts +alias .ga='.git add' +alias .gc='.git commit' +alias .gco='.git checkout' +alias .gd='.git diff' +alias .gss='.git status --short' +alias .glo='.git log --oneline --decorate' +alias .glg='.git log --stat' +alias .glgp='.git log --stat --patch' +alias .gbl='.git blame -w' +alias .gb='.git branch' +alias .gba='.git branch --all' +alias .gbd='.git branch --delete' +alias .gbD='.git branch --delete --force' +alias .gm='.git merge' +alias .gma='.git merge --abort' +alias .gmc='.git merge --continue' +alias .gc!='.git commit --verbose --amend' +alias .gcm='.git commit --message' +alias .gcp='.git cherry-pick' +alias .gcpa='.git cherry-pick --abort' +alias .gcpc='.git cherry-pick --continue' +alias .gclean='.git clean --interactive -d' +alias .ginit='git init --bare "${DOT_REPO}"; .git config --local status.showUntrackedFiles no' +# only set up push and pull if DOT_ORIGIN is set +if [[ -n "$DOT_ORIGIN" ]]; then + alias .gp='.git push' + alias .gl='.git pull' + alias .gclone='git clone --bare "${DOT_ORIGIN}" "${DOT_REPO}"; .git config --local status.showUntrackedFiles no' +else + alias .gp='echo "error: must first configure DOT_ORIGIN"' + alias .gl='echo "error: must first configure DOT_ORIGIN"' + alias .gclone='echo "error: must first configure DOT_ORIGIN"' +fi +# if lazygit or gitui are available, we set up a .lazygit and .gitui +[[ $(command -v lazygit) ]] && + alias .lazygit='lazygit -g ${DOT_REPO}/ -w ${DOT_HOME}' +[[ $(command -v gitui) ]] && + alias .gitui='gitui -d ${DOT_REPO}/ -w ${DOT_HOME}' + +# if fzf is installed we can have nice things +# https://github.com/junegunn/fzf +read -r -d '' FZF_HEADER<