Сегодня будет сказка о утилите fzf (command line fuzzy finder). В основе лежит простая идея: fzf читает строки из STDIN, отображает в виде меню с нечётким поиском в консоли и пишет выбранную строку в STDOUT. Несмотря на, скажем даже, примитивность, такой подход позволяет удобно интегрировать со стандартными утилитами командной строки и делать интересные вещи. Ниже приведу несколько примеров того, что на её основе можно сделать.
Поиск файла
Начнём с самого простого примера - найти файл в текущей директории и открыть в nano.
Список файлов без git директории:
Передаём список в fzf и добавляем привью для файлов, в котором отображаем первые 30 строк:
И последним шагом - выбранный путь передаём в nano:
Теперь можно однострочник заворачивать в скрипт и добавлять в PATH. И пользоваться:
Энтузиасты сделали на этом механизме целый файловый менеджер.
Список файлов без git директории:
find * -type f -not -path '*/.git/*'
find * -type f -not -path '*/.git/*' | fzf --preview="head -30 {}"
nano $(find * -type f -not -path '*/.git/*' | fzf --preview="head -$LINES {}")
История команд
Предыдущий пример хоть и самый очевидный способ применения, но у меня не прижился. Можно использовать утилиту гораздо интереснее. Например сделать поиск по истории команд консоли. Встроенный - сделан чужими для хищников и пользоваться им лишний раз не хочется.
Для реализации внешним скриптом обойтись не получилось, не вышло добавить результат в строку редактирования, пришлось писать widget для zsh. Для bash он в чистом виде не подойдёт, но переделать не составит труда. Представленный ниже скрипт впишите в ".zshrc":
Тут:
Для реализации внешним скриптом обойтись не получилось, не вышло добавить результат в строку редактирования, пришлось писать widget для zsh. Для bash он в чистом виде не подойдёт, но переделать не составит труда. Представленный ниже скрипт впишите в ".zshrc":
fzf-history-widget() { LBUFFER=$(fc -lnr 1 | fzf --tiebreak=begin) zle redisplay } zle -N fzf-history-widget bindkey '^R' fzf-history-widget
-
"fc -lnr 1" - возвращает инвертированный список всех ранее введённых команд
-
опция "–tiebreak=begin" для fzf - при сортировке результатов, предпочитать строки с совпадениями ближе к началу
-
всё остальное это специфичный для zsh способ записать результат в строку редактирования и навесить на это горячую клавишу ctrl+R
Закладки
Ещё один пример удобного использования - закладки для перехода в часто используемые директории. Он так же, как и предыдущий написан для zsh и добавляется в ".zshrc":
Файл настроек - "bookmarks.cfg" имеет вот такой вид:
Т.е. имя закладки без пробелов и через пробел - путь к директории.
Общая идея скрипта: читаем построчно "bookmarks.cfg", отображаем через fzf, из результата достаём второй столбец с путём к директории, переходим в него. Буквально 1 строка (не считая обвязки для zsh) и менеджер закладок готов. Навешиваем горячую клавишу ctrl+D и пользуемся.
Сюда не сложно добавить операции добавления и удаления новых элементов прямо из zsh. Но по опыту - список изменяется настолько редко, что алиасы для команд забываются, их приходиться искать в исходниках. В итоге быстрее вручную удалить\добавить строчку в конфиге.
function fzf-bookmarks-widget() { cd $(cat "$HOME/.config/bookmarks.cfg" | fzf --tiebreak=begin --tac | awk '{print $2}') zle reset-prompt } zle -N fzf-bookmarks-widget bindkey '^D' fzf-bookmarks-widget
menu_item_1: /home/rean/test1 menu_item_2: /home/rean/test2 menu_item_3: /home/rean/test3
Общая идея скрипта: читаем построчно "bookmarks.cfg", отображаем через fzf, из результата достаём второй столбец с путём к директории, переходим в него. Буквально 1 строка (не считая обвязки для zsh) и менеджер закладок готов. Навешиваем горячую клавишу ctrl+D и пользуемся.
Сюда не сложно добавить операции добавления и удаления новых элементов прямо из zsh. Но по опыту - список изменяется настолько редко, что алиасы для команд забываются, их приходиться искать в исходниках. В итоге быстрее вручную удалить\добавить строчку в конфиге.
Что ещё…
Что ещё можно сделать, зависит от вашей фантазии, вот навскидку составленный список:
-
Поиск процесса + "kill -9".
-
Выбор файлов для "git add".
-
Интеграция с менеджерами паролей.
-
Сделать TODO лист.
-
Поиск по истории браузера.