Estou usando grep
para pesquisar 1 TB de arquivos. Eu quero grep nomes de arquivos e colocar os nomes em um arquivo de texto E eu quero cp
todos os arquivos com uma correspondência para o dir /home/user/matches
. Eu quero ambas as tarefas sem pesquisar todos os meus arquivos com grep duas vezes.
Tive a ideia de colocar a saída dos nomes dos arquivos em um arquivo de texto com grep
grep -ril "xxx" . >> /home/user/matches/output-filename.txt
E agora use output-filename.txt
como entrada para cp e faça cp executar linha por linha. Como faço isso? awk? Ou vocês têm outras ideias para evitar pesquisar todos os arquivos duas vezes
Caminhos de arquivos são sequências de bytes diferentes de 0; eles não são necessariamente texto, muito menos linhas de texto. Em particular, um caminho de arquivo
A implementação GNU de
grep
(aquela que adicionou a-r
opção), pode imprimir os caminhos em um formato não textual com-Z
pós-processamento seguro. Por exemplo, o GNUxargs
pode processar esse formato com sua-0
opção:(aqui também assumindo o GNU
cp
como-t
opção)Se você deseja imprimir essa lista em um formato de texto¹ que seja compreensível por um ser humano, com GNU
printf
:¹ Bem, ele deve garantir que os bytes que não podem ser decodificados enquanto os caracteres são renderizados como
$'\234'
representações. O mesmo para caracteres de controle, incluindo nova linha, que é renderizada como$'\n'
. Isso aborda os dois primeiros pontos acima, mas não garante que a saída terá linhas mais curtas do queLINE_MAX
(mas, novamente, as implementações GNU de utilitários de texto padrão geralmente não têm um limite de comprimento de linhas que suportam).Você pode usar
find
com um par encadeado deexec
comandos. Talvez não seja a solução mais eficiente, pois invocagrep
para cada arquivo (ecp
para cada arquivo correspondente), mas funcionará independentemente dos caracteres no nome do arquivo:Assim
tee
, usandoxargs
os comandos , (usandoNULL byte \0
como separador de final de nome de arquivo) eGNU grep
:Lidar com nomes de arquivos com espaços, novas linhas, etc...