Usando o comando “Find” em conjunto com instruções “if” “and”

1

Eu preciso pesquisar e encontrar subdiretórios que contenham um determinado arquivo, no entanto, se eles contiverem esse determinado arquivo + esse outro arquivo, não quero que eles sejam listados.

A declaração é algo como isto:

  1. Localize os diretórios que contêm o arquivo "password.old"
  2. Se o diretório contiver "password.old" e "webvirtual", não os liste
  3. Se o diretório contiver "password.old" e não contiver "webvirtual", o caminho do diretório de saída será > Arquivo OLD.TXT

Isto é o que eu tenho até agora, isso é totalmente errado? Parece estar funcionando corretamente, mas eu sou relativamente novo no bash scripting e só queria ter certeza de que não estou perdendo algo ... ou talvez exista uma maneira melhor de lidar com isso?

#!/bin/sh
if FILE=$(find ./ -path OLD/ -prune -o -name "password.old") && FILE=$(find ./ -path OLD/ -prune -o -name "webvirtual*")
then
printf %"s\n" $FILE > Not_Old_Ones.txt
fi
if FILE=$(find ./ -path OLD/ -prune -o -name "password.old") && FILE=$(find ./ -path OLD/ -prune -o ! -name "webvirtual*")
then
printf %"s\n" $FILE > Old_Ones.txt
fi
    
por Pietro Aretino 25.01.2017 / 19:26

2 respostas

1

Solução ligeiramente demorada, mas funcional, que deve funcionar nos casos em que -execdir não está disponível:

$ tree
.
├── dir_one
│   ├── password.old
│   └── webvirtual
└── dir_two
    └── password.old
$ find . -iname "*password.old" -exec dirname "{}" \; 2>/dev/null | while IFS= read -r directory; do
> [ -e "$directory"/webvirtual ] && continue || echo "$directory"
> done
./dir_two

Assim, tudo o que você precisa fazer agora é adicionar > OLD.txt no final da instrução done para redirecionar a saída para o arquivo

Caso o comando dirname não esteja disponível, você pode usar o seguinte script com o diretório como argumento.

#!/bin/sh

find "$1" -type f -iname "*password.old"  -printf "%h\n" |
while IFS= read -r directory;
do
    [ -e "$directory"/webvirtual ] && continue || echo "$directory"
done

Por exemplo:

$ ./find_missing_webvirtual.sh ./TESTDIR/                                                                                
./TESTDIR/dir_two
    
por 25.01.2017 / 19:53
4

Eu faria:

find . -path ./OLD -prune -o -name password.old \
  ! -execdir [ -e webvirtual ] \; -printf '%h\n'

-execdir é encontrado no GNU find (desde 4.2.12 (2005)), sfind e na maioria dos BSDs (de onde vem). -printf é específico do GNU. Você pode substituí-lo por -execdir pwd \; para outras implementações find .

Se -execdir não estiver disponível:

find . -path ./OLD -prune -o -name password.old -exec sh -c '
  for file do
    dir=${file%/*}
    [ -e "$dir/webvirtual" ] || printf "%s\n" "$dir"
  done' sh {} +

O acima seria POSIX. No Solaris 10 e anterior, certifique-se de usar o padrão sh em /usr/xpg4/bin , não o em /bin .

    
por 25.01.2017 / 19:48

Tags