[metadata] name = "ghq-repos" description = """ ghq repositories (plus the chezmoi source tree) and Obsidian vaults, newest git activity first. Enter prints the directory; the gho shell function (ctrl-o in fish, zsh and bash) cds into it. """ requirements = ["ghq", "fd", "git", "serie", "onefetch", "mtime-sort"] # Entries are "\t": the name is what you fuzzy-match, the # path is what enter prints. ctrl-s cycles repos → vaults. [source] command = [ { name = "Repos", run = ''' root=$(ghq root) { # Checkouts living outside ghq root, listed first so they win over a ghq # clone of the same repo: chezmoi's source (github.com/prdlk/dotfiles) and # the nvim config (github.com/prdlk/nvim). c=$HOME/.local/share/chezmoi [ -d "$c/.git" ] && printf 'github.com/prdlk/dotfiles\t%s\n' "$c" n=$HOME/.config/nvim [ -d "$n/.git" ] && printf 'github.com/prdlk/nvim\t%s\n' "$n" ghq list | awk -v r="$root" '{ print $0 "\t" r "/" $0 }' } | awk -F '\t' '!seen[$1]++' | mtime-sort --repo ''' }, { name = "Vaults", run = ''' v=$HOME/Documents/Obsidian fd -H -t d -d 3 '^\.obsidian$' "$v" -x dirname | awk -v r="$v/" '{ print substr($0, length(r) + 1) "\t" $0 }' | mtime-sort ''' }, ] shell = "bash" display = "{split:\\t:0}" output = "{split:\\t:1}" # Two previews, ctrl-f cycles: commit graph (default), then onefetch. serie # itself cannot draw here -- it is a fullscreen TUI that paints the graph with # kitty images and has no print mode -- so ctrl-g (history) opens it. [preview] command = [ ''' d='{split:\t:1}' if [ -e "$d/.git" ]; then git -C "$d" log --graph --all --color=always --date=relative -n 300 \ --format='%C(yellow)%h%C(reset) %C(blue)%<(12,trunc)%ad%C(reset) %s%C(auto)%d' 2>&1 else eza --tree --level 2 --color=always "$d" 2>/dev/null || ls -la "$d" fi ''', ''' d='{split:\t:1}' if [ -e "$d/.git" ]; then onefetch --no-art "$d" 2>&1 else eza --tree --level 2 --color=always "$d" 2>/dev/null || ls -la "$d" fi ''', ] shell = "bash" # ctrl-e (edit) is bound globally in config.toml. [keybindings] ctrl-b = "actions:browse" ctrl-g = "actions:history" [actions.edit] description = "Open the repository in nvim" # /dev/tty: the gho wrapper captures tv's stdout to read the picked path. command = "cd '{split:\\t:1}' && nvim . /dev/tty" shell = "bash" mode = "execute" [actions.browse] description = "Open the repository's web page (gop)" command = "cd '{split:\\t:1}' && gop >/dev/null 2>&1" shell = "bash" mode = "fork" [actions.history] description = "Browse the commit graph in serie" # Fork: quitting serie (q) returns to the picker. /dev/tty for the same reason # as edit; serie also needs a real tty to detect kitty graphics. command = "cd '{split:\\t:1}' && [ -e .git ] && serie /dev/tty" shell = "bash" mode = "fork"