Esta é mais uma prática mental com a sintaxe bash. Gostaria de convidá-lo a considerar isso como um quebra-cabeça, para que possamos resolver isso juntos. Ou como um desafio para entender o bash.
O problema
Por exemplo, eu tenho 3 arquivos em uma pasta ./etc
:
-
%código%
-
./etc
-
foo.txt.example
-
bar.txt.example
(sim, há espaço neste arquivo)
Eu construí o alvo para fazer este alvo, baseado nos arquivos acima, funciona:
make "etc/foo.txt"
make "etc/bar.txt"
make "etc/hello world.txt"
Portanto, em teoria, posso construir um comando como este para executar todos os alvos:
make "etc/foo.txt" "etc/bar.txt" "etc/hello world.txt"
Aí vem minha pergunta: Você pode criar um script bash que pesquise todos os hello world.txt.example
nomes de arquivos e construir o comando acima?
Requisito
- A resposta precisa estar no formato de um comando bash ou de uma definição de destino preferível do Makefile;
- Ele precisa ser executado na maioria dos ambientes Linux por padrão. Não deve exigir a instalação de pacotes incomuns.
O que eu tentei
Eu já descobri uma maneira no Makefile para obter todos os nomes de arquivos acima:
txt:
for fn in "etc/*.txt.example"; do \
echo "etc/$$(basename -s ".example" "$$fn")"; \
done
O que basicamente significa rodar isso no bash:
for fn in "etc/*.txt.example"; do \
echo "etc/$(basename -s ".example" "$fn")"; \
done
que fornece a seguinte saída:
etc/foo.txt
etc/bar.txt
etc/hello world.txt
Se você usar a saída deste loop como entrada de outro comando, o comando parece tratar todo o espaço ./etc/*.txt.example
como separador de argumentos. Então isso:
make $(for fn in "etc/*.txt.example"; do \
echo "etc/$(basename -s ".example" "$fn")"; \
done)
é praticamente isso:
make "etc/foo.txt" "etc/bar.txt" "etc/hello" "world.txt"
Existe uma maneira de transformar a saída do loop em um argumento que preserve adequadamente os espaços?