Nachdem ich schon über Vim und Tmux längere Artikel geschrieben habe, will ich jetzt das letzte Mitglied meiner Terminal Dreifaltigkeit vorstellen. FZF.
Letztens beobachtete ich einen Kollegen der mehrere Arbeitsstände zeigen und dafür mehrfach einen Git Branch wechseln musste. Dies war recht zeitraubend zu diesem Zeitpunkt der genaue Branchname und Ticketnummer nicht bekannt war und nur mit stark frequenten Wechseln des Fensters funktionierte. Der innere Kommandozeilenliebhaber in mir schrie leise auf: "Warum nutzt du nicht FZF - damit wären wir schon viel weiter". 1
Also - was ist FZF?
Was ist FZF?
FZF ist ein "command-line" Fuzzy Finder 2 und erlaubt das schnelle Suchen innerhalb der Commandline. Und es ist schnell. Rasend schnell.
FZF funktioniert in allen gängigen Shells wie z.B. Bash, ZSH oder Fish 3. Ich benutzte FZF zu 95% innerhalb von Vim. Hierfür gibt es auch ein eigenes Plugin namens FZF.vim vom selben Entwickler, dass viele Konfigurationen bereits integriert hat.
FZF bietet eine Vielzahl von Anwendungsmöglichkeiten. Diese alle aufzuzählen würde ausufern, darum nun meine persönlichen Anwendungsfälle. Mehr Beispiele gibt es im FZF Wiki auf Github.
FZF in der Kommandozeile
Ich nutze FZF sowohl in der Kommandozeile als auch innerhalb von Vim. Die folgenden Alias
e sollten in eure Alias Datei - vermutlich ist es die bash_aliases
kopiert werden. Das Alias lässt sich natürlich noch anpassen.
Anzumerken ist auch, dass diese Beispiele teilweise für Tmux optimiert sind und zusammen mit fzf-tmux
aufgerufen werden. Solltet gerade keine Tmux Session laufen wird aber lediglich der Splitscreen wegfallen und FZF im Vollbild geöffnet. Dies ist aber afaik der einzige Drawback.
Und da man nie Code von irgendwelchen Blogs aus dem Internet kopieren sollte, all diese findet ihr auch im Wiki des FZF Github Repos. Vermutlich sogar aktueller.
Git Branches wechseln
fbr() {
local branches branch
branches=$(git branch --all | grep -v HEAD) &&
branch=$(echo "$branches" |
fzf-tmux -d $(( 2 + $(wc -l <<< "$branches") )) +m) &&
git checkout $(echo "$branch" | sed "s/.* //" | sed "s#remotes/4*/##")
}
Das Wechseln in einen Git Branch ist an sich recht trivial und mehr oder weniger nur Tipparbeit. Wer wie ich tippfaul ist, wird dieses Alias lieben. Mit diesem Alias (in meinem Fall fbr
) in der bash_aliases
werden alle Branches, auch Remote Branches, aufgelistet und mit fuzzy-search durchsuchbar. Der Vorgang dauert so insgesammt nur wenige Sekunden.
Git Commit Browser
# fshow - git commit browser (enter for show, ctrl-d for diff, ` toggles sort)
fshow() {
local out shas sha q k
while out=$(
git log --graph --color=always \
--format="%C(auto)%h%d %s %C(black)%C(bold)%cr" "$@" |
fzf --ansi --multi --no-sort --reverse --query="$q" \
--print-query --expect=ctrl-d --toggle-sort=\`); do
q=$(head -1 <<< "$out")
k=$(head -2 <<< "$out" | tail -1)
shas=$(sed '1,2d;s/^5*//;/^$/d' <<< "$out" | awk '{print $1}')
[ -z "$shas" ] && continue
if [ "$k" = ctrl-d ]; then
git diff --color=always $shas | less -R
else
for sha in $shas; do
git show --color=always $sha | less -R
done
fi
done
}
Wenn schnell ein Commit gesucht wird, hilft bei mir das fshow
Alias. Dieses zeigt alle Commits in einer durchsuchbaren Liste an.
Prozesse beenden
# fkill - kill process
fkill() {
pid=$(ps -ef | sed 1d | fzf -m | awk '{print $2}')
if [ "x$pid" != "x" ]
then
kill -${1:-9} $pid
fi
}
Reagiert ein Prozess nicht, kann dieser direkt mit einer Pid beendet werden. Aber das raussuchen dieser PID in einer langen Liste von aktiven Prozessen und das anschließende kill
en kann auch etwas umständlich sein. Mit fkill
bekomm ich nun eine mit fuzzy-search filterbare Liste und ein Prozess kann mit einem kräftigen Hieb auf "Enter" direkt beendet werden.
FZF innerhalb von Vim
In Vim scheint bei mir FZF besonders hell. An sich ist es kein Problem FZF Scripte selber zu schreiben, da aber nicht jeder ein Vimscript und Kommandozeilen Bash Künstler ist 6 gibt es noch das FZF.vim Plugin. Dies ist im Wesentlichen nur ein Wrapper für FZF, der aber die grundlegensten Funktionen bereits implementiert hat und sehr wahrscheinlich völlig ausreichend ist.
Die von mir am häufigsten genutzten Befehle:
- :Files - Projekt übergreifende Suche. In meinen Fall mit Ag.
- :Commits - Commitsuche im ganzen Projekt. Ähnlich wie mein
fshow
Alias. - :BCommits - Ähnlich wie
:Commits
, zeigt aber nur die Commits im aktuellen Buffer an. - :GitFiles - Suche in allen Gitfiles. Schneller als eine ":Files" Suche und beachtet auch die
.gitignore
Datei. - :History - Listet die zuletzt geöffneten Dateien auf.
- :Buffer - Listet alle Buffer auf.
- :BLines - Ermöglicht eine Fuzzy Search in allen Zeilen des aktuellen Buffers.
- :Colors - Schnelles Wechseln des Color Schemes :D
TL;DR
FZF ist ein mächtiges vielseitiges Tool, was selbst für nur gelegentliche Arbeiten in einer Kommandozeile sehr geeignet ist.
Achja!
Artikel wie diese sind sehr viel Arbeit und freue mich über jedes Feedback. Sollte euch der Artikel gefallen haben, schreibt per Mail oder auf Twitter und abonniert meinen YouTube Channel! Vorallem Feedback zu dem Video ist sehr willkommen.
- Ich habe inzwischen aufgehört anderen Menschen meine Arbeitsweisen und Workflows bei jeder Gelegenheit anzudrehen. Regel #32: Sei kein Smart Ass ↩
- Für diejenigen unter euch die mit dem Begriff nichts anfangen können, Mit fuzzy ist das ungefähre Suchen eines Begriffs gemeint. Will ich also eine Datei namens fuzzy-finder suchen, gebe ich einige Buchstaben ein, grob in der Reihenfolge wie sie im Dateinamen auftauchen. Zum Beispiel: fzz, fyfi oder auch - und damit erkläre ich zusätzlich noch den Namen - fzf ↩
- Sorry, liebe Hyper User ↩
- / ↩
- a-z0-9 ↩
-
Mich eingeschlossen. Ich habe sehr großen Respekt vor jedem der aus dem Stegreif einen
tar
Befehl richtig ausführen kann. Dazu ein relevantes XKCD. ↩