22 pontos por GN⁺ 2026-05-11 | 1 comentários | Compartilhar no WhatsApp
  • O localizador difuso de linha de comando fzf oferece retorno imediato sobre o investimento e um valor único, mas muitos desenvolvedores apenas o instalam e desistem sem saber como usá-lo
  • Substituindo a busca de histórico com Ctrl+R por correspondência difusa e múltiplas prévias, é possível eliminar o incômodo do método tradicional baseado em correspondência exata de strings
  • Com Alt+C, é possível fazer cd difuso mesmo lembrando apenas vagamente do nome do diretório, e montar um fluxo de trabalho que abre arquivos imediatamente com a combinação vi $(fzf)
  • Ao conectá-lo ao ripgrep por pipe, é possível fazer um busca difusa em todas as linhas de todos os arquivos e depois abrir imediatamente no editor o arquivo correspondente
  • É uma ferramenta que melhora a produtividade de forma tão imediata que chega a quebrar até mesmo a heurística 80/20 de primeiro aprender as ferramentas Unix tradicionais (cat, grep, find etc.)

O valor que você obtém logo após instalar o fzf

  • Engenheiros de software conseguem criar facilmente ferramentas para melhorar o próprio trabalho, mas o custo aumenta com o tempo se você fica trocando entre várias ferramentas sem aprender nenhuma a fundo
  • Uma boa heurística 80/20 é aprender primeiro ferramentas Unix antigas como cat, ls, cd, grep e cut; em funções modernas de administração de sistemas, sed e awk também entram nessa lista
  • O fzf pode ser visto como uma exceção a essa heurística, porque o retorno sobre o investimento é imediato e seu valor é único
  • O ponto principal são os recursos que já podem ser usados logo após a instalação com o script de instalação do fzf em um ambiente Ubuntu padrão

Efeito imediato dos atalhos padrão

  • Ctrl+R: transforma o histórico de comandos em busca difusa

    • Na maioria dos terminais Linux e Windows, Ctrl+R oferece busca reversa no histórico de comandos
    • O Ctrl+R padrão exige correspondência exata para encontrar o comando desejado e mostra apenas uma prévia por vez, então basta errar uma letra para ficar difícil encontrar o que você quer
    • Ao instalar o fzf, vários atalhos do teclado passam a ser sobrescritos com um comportamento melhor, e o Ctrl+R também melhora bastante em relação ao modo antigo
    • Se você instalar com um gerenciador de pacotes como apt, essa integração de atalhos pode não vir incluída; por isso faz sentido usar o script de instalação do fzf
  • Alt+C: vá rapidamente para um diretório do qual você se lembra só vagamente

    • O fzf transforma Alt+C em um atalho reforçado de cd difuso
    • Você pode navegar rapidamente quando não lembra o caminho exato do diretório e só recorda parte do nome
    • É útil para encontrar repositórios ou diretórios de trabalho que você não visita há bastante tempo, a partir de um terminal vazio

O próprio comando fzf e suas combinações com o shell

  • fzf básico

    • Executar o comando fzf sozinho faz uma busca difusa por caminhos relativos de arquivos com base no diretório atual
    • Sozinho, seu uso é limitado a escolher a localização de um arquivo, então não parece tão útil
  • vi $(fzf)

    • Quando combinado com substituição de comando, como em vi $(fzf), você pode abrir no editor o arquivo escolhido pela busca difusa
    • Isso não tem nada de especial para vi; também funciona com o editor que você quiser, como emacs, nano, code etc.
  • vi $(find . '/' | fzf)

    • Ao combinar find . '/' | fzf com um editor, você pode fazer uma busca difusa entre candidatos com caminho completo e abrir um arquivo de configuração cuja localização você não conhece
    • Ao procurar um arquivo como nginx.conf, em vez de tentar adivinhar ou memorizar com base no conhecimento de FHS, basta enviar o resultado do find por pipe para o fzf
    • Se você buscar algo como conf$, pode filtrar apenas linhas que terminam em conf
    • Se o find encontrar muitos erros Permission denied, o fzf pode oscilar por um momento, mas se recupera depois de alguns segundos
    • Esse atraso de alguns segundos é o trade-off pela conveniência de encontrar arquivos de configuração de um jeito extremamente simples
  • vi **<TAB>

    • Um recurso citado em um comentário do sigmonsays no Hacker News: entre sobrescrever atalhos e executar fzf diretamente, existe uma espécie de autocompletar difuso com dois asteriscos
    • vi **<TAB> pode ser usado para escolher arquivos de um jeito parecido com vi $(fzf)
    • Depois que o comando real for completado, você ainda precisa pressionar Enter mais uma vez
    • Funciona bem em bash e zsh, mas em fish pode não funcionar
    • Se for mais fácil para você lembrar da abordagem que chama $(fzf) explicitamente, talvez esse recurso não acabe sendo usado com frequência

Usando fzf também para mover arquivos

  • mv $(fzf) $(fzf)

    • mv $(fzf) $(fzf) é útil quando você não lembra exatamente o que quer mover nem para onde, mas se recorda de pistas bem específicas para cada lado
    • A ideia é escolher com duas seleções do fzf o item a mover e o destino
    • Pode acabar sendo usado com frequência ao mover e organizar arquivos, como ao colocar GIFs em um README no GitHub
    • Como exemplo relacionado, há o README do modo interativo do finstem

Combinando com rg para fazer busca difusa até no conteúdo dos arquivos

  • rg: um grep rápido com busca recursiva por padrão

    • A combinação abaixo também poderia ser feita com grep, mas rg ou ripgrep tem como vantagem, para esse caso, fazer busca recursiva por padrão
    • Para seguir os exemplos, recomenda-se instalar e usar rg
  • rg . | fzf

    • rg . produz como saída cada linha dos arquivos nos resultados de busca; ao enviar isso para o fzf, você pode fazer busca difusa em todas as linhas de todos os arquivos
    • Em vez do nome do arquivo, a pista de busca passa a ser o conteúdo das linhas dentro dos arquivos
  • rg . | fzf | cut -d ":" -f 1

    • Ao adicionar cut -d ":" -f 1 ao resultado escolhido em rg . | fzf, você pode retornar o primeiro campo separado por dois-pontos, ou seja, a localização do arquivo
    • É uma combinação que faz busca difusa pelo conteúdo de uma linha e depois obtém apenas o caminho do arquivo que contém essa linha
  • vim $(rg . | fzf | cut -d ":" -f 1)

    • vim $(rg . | fzf | cut -d ":" -f 1) faz uma busca difusa em todas as linhas de todos os arquivos e depois abre no vim o arquivo que contém a linha selecionada
    • Quando você não lembra o nome do arquivo e só recorda parte do conteúdo, isso permite seguir direto para o editor

1 comentários

 
GN⁺ 2026-05-11
Opiniões no Lobste.rs
  • Parece que o público-alvo deste texto sou exatamente eu. Instalei o fzf, achei “genial”, mas acabava sempre esquecendo de usar; agora talvez eu passe a usar

    • O ponto principal é integrá-lo à configuração do shell existente, scripts pessoais e aliases. Eu uso fzf o tempo todo, mas quase nunca o executo diretamente
  • Pode até ser um bom texto, mas se o objetivo é responder “o que fazer agora?”, começar pela integração com o shell do fzf dá a sensação de falar com um público mais restrito
    Estou acostumado a usar ctrl-r no bash, então pedir para trocar isso parece exigir demais. Eu preferiria que mostrasse primeiro como praticar o mesmo comportamento sem substituir o padrão

    • Na prática, é mais um padrão aprimorado. Faz sentido deixá-lo substituir o ctrl-r, e metade do apelo principal está em manter uma ação já familiar, com um fluxo quase igual ao de antes, mas com uma experiência mais rica
      ctrl-r provavelmente é o comando que mais uso, e o fzf foi uma melhoria que se encaixou de imediato, sem curva de aprendizado. Como ele é acionado com ctrl-r, eu também não esqueço de usar o fzf. Depois acabei migrando para o Fish shell, onde esse mesmo comportamento já vem por padrão
  • Fui convencido. Vou adicionar integração com o shell ao fzf em breve, e hoje aprendi uma coisa nova

  • Ao procurar arquivos para colocar em um comando, também dá para usar o atalho ctrl-t. Eu uso bastante com git para escolher arquivos incluídos em uma alteração específica, e também já usei para filtrar a saída do grep e reduzir o escopo da busca

  • Além de melhorar a busca no histórico do shell, também venho usando fzf com estes dois aliases
    alias gbd='git -c color.ui=never branch | fzf | xargs -I {} git branch -D {}'
    Uso principalmente para escolher quais branches locais apagar depois de mesclar pull requests. Talvez exista uma forma melhor, mas até hoje nunca falhou
    alias awp='export AWS_PROFILE="$(grep -e "\[\(.*\)\]" ~/.aws/config | sed -e "s/\[//g" | sed -e "s/\]//g" | cut -d " " -f 2 | sort -u | fzf)"'
    Isso me permite trocar rapidamente o AWS_PROFILE com base nos valores em ~/.aws/config. Agora estou pensando em criar um alias parecido para trocar de namespace no Kubernetes

  • Se você usar o plugin fzf.vim, poderá usar o fzf dentro do vim. Não só para abrir arquivos, mas também para fazer busca difusa em buffers, histórico de comandos, conteúdo de arquivos etc.

  • O principal uso do fzf para mim é percorrer e pesquisar um histórico linear de commits do Git para entender o que mudou recentemente
    Na minha configuração padrão do Git, defini git fzf assim

    [alias]  
      # Browse commit history with fzf  
      # Inspired by: https://chrismanbrown.gitlab.io/67.html  
      fzf = "!git log --oneline --color=always --decorate=short $@ | \  
          fzf --ansi --reverse --no-sort \  
            --preview 'git show --color=always {1}' \  
            --preview-window '<50(down)' \  
            --bind 'enter:become(git show {1})' #"  
    
  • Acho que estou deixando passar alguma coisa. Fico me perguntando por que alguém instalaria o fzf sem saber o que fazer com ele

  • Também houve um texto relacionado recentemente. Um usuário está usando o fzf como seletor de arquivos para o jj
    https://lobste.rs/s/exlogg/jjj