Abra um arquivo fornecido pelo resultado de um comando no vim

34

Encontro-me fazendo o seguinte quase todos os dias

  1. Executar uma busca ( find -name somefile.txt)
  2. Abra o resultado em vim

O problema é que eu tenho que copiar e colar o resultado da findno vimcomando. Existe alguma maneira de evitar ter que fazer isso? Eu experimentei um pouco ( find -name somefile.txt | vim), mas não encontrei nada que funcione.

desde já, obrigado

smauel
fonte

Respostas:

31

Você pode usar a substituição de comando:

vim $(find -name somefile.txt)

ou

find -name somefile.txt -exec vim {} \;
dogbane
fonte
1
Está bem. Se é isso que é necessário, localize -name somefile.txt | xargs vim
balki
3
Não, isso não funciona corretamente e pode até atrapalhar o seu terminal! Você não pode canalizar para o xargs vim, porque o vim espera que a entrada seja proveniente de um terminal interativo.
dogbane
1
Um usuário anônimo observa que isso falhará se o nome do arquivo tiver espaços
Michael Mrozek
4
Outra alternativa seria vim `find -name somefile.txt`. @StuartPowers Alternativamente, você pode usar vim `!-1`se você já usou esta descoberta foi que você comando anterior
Bernhard
1
@balki para usar xargs neste cenário, você deve usar a flag -o, está no man: -o Reabra stdin como / dev / tty no processo filho antes de executar o comando. Isso é útil se você deseja que o xargs execute um aplicativo interativo.
Davidmh
7

Tente o seguinte:

  1. start vim
  2. no vim, use o seguinte:

:r!find /<path> -name 'expression'

Os resultados devem aparecer no vim quando a pesquisa estiver concluída.

Ou

Experimentar:

find /<path> -name > results.txt
vim results.txt 
Karl
fonte
Minha solução faz exatamente o mesmo, mas por que é votada negativamente?
balki
5

Se você não se importa de executar o comando novamente: pressione Upe acrescente um xargscomando. Ou use a substituição do histórico e execute

!! | xargs vim          # won't work with file names containing \'" or whitespace
!! | xargs -d \\n vim   # GNU only (Linux, Cygwin)

Existe uma maneira leve de salvar a saída de um comando que funciona no ksh e zsh, mas não no bash (requer que o lado de saída de um pipeline seja executado no shell pai). O tubo de comando para a função K(definição zsh abaixo), que k PEE sua saída na variável $K.

function K {
    K=("${(@f)$(tee /dev/fd/3)}") 3>&1;
}
find  |K
vim $K

Salvar automaticamente a saída de cada comando não é realmente possível apenas com o shell; é necessário executar o comando em um terminal emulado. Você pode fazer isso executando dentro script(um utilitário BSD, mas disponível na maioria dos departamentos, incluindo Linux e Solaris), que salva toda a saída da sua sessão através de um arquivo (ainda é necessário um pouco de esforço para detectar com segurança o último prompt no texto datilografado )

Gilles 'SO- parar de ser mau'
fonte
2

Eu gosto de usar os ticks de volta `(está na mesma tecla que o ~)

> vim `find . -name somefile.txt`

O back ticks executa o comando dentro dos ticks e a saída pode ser usada pelo comando. O acima irá encontrar todos os arquivos somefile.txt, permitindo que você use :nextpara percorrer todos os arquivos.

É muito útil se você gastar algumas tentativas para refinar o comando, porque poderá usar a substituição do histórico para repetir o comando para o editor.

> find . -name somefile.txt
./debug/somefile.txt
./somefile.txt
> vi `!!`
Martin York
fonte
2

Eu devo ter esquecido o ponto aqui, porque eu usaria:

:find **/somefile.txt

(se eu soubesse que havia apenas um no meu :echo &path ) ou se quisesse todos eles:

:args **/somefile.txt

Edit: Uau! Ok, então eu fiz perder o ponto - você deseja que a lista de procura, não os arquivos reais de abrir? Tente (novamente, de dentro do Vim):

!!find . -name somefile.txt

-- minha culpa :)

Barry Arthur
fonte
1

Como @davidmh apontou nos comentários, você pode usar xargscom o sinalizador -ose desejar usar um aplicativo interativo.

find . -name somefile.txt | xargs -o vim

Se você não usar -o, provavelmente irá atrapalhar o estado do terminal depois de sair do vim. Se você tiver feito isso, poderá redefinir seu terminal com o seguinte comando:

reset
durum
fonte
0

Eu escrevi uma função pvimque faz o que você quer. Se várias linhas forem canalizadas para pvimele, ignorando todas, exceto a primeira, ela poderá ser estendida para abrir vários arquivos no vim.

stu@sente ~ $ function pvim() { read -r somefile; exec < /dev/fd/1; vim "$somefile"; }
stu@sente ~ $ type pvim
pvim is a function
pvim ()
{
    read -r somefile;
    exec < /dev/fd/1;
    vi "$somefile"
}

Use-o como:

stu@sente ~ $ find . -name "foo.txt" | pvim

que carregará o primeiro "foo.txt" no vim como se você tivesse digitado:

vim $(find . -name "foo.txt | head -n1")

sente
fonte
0

Aqui está uma xargssolução mais simples que as já mencionadas:

find -name somefile.txt | xargs vim -p

A -popção diz vimpara abrir cada arquivo em uma guia separada. Acho isso mais conveniente do que usar buffers.

Cory Klein
fonte
0

Descobri que abrir um arquivo com a ajuda do locatein vim é extremamente conveniente e muito mais rápido que find.

O comando a seguir pesquisa um arquivo chamado app.pyno caminho que contém o diretório MyPythonProject.

:args `locate '*MyPythonProject*app.py'`
Searene
fonte