Redhat Shell Symantics de teste de condição de script

1

Estou usando o Redhat Enterprise 5.3, e tenho um pequeno script que lê o nome do diretório e o compara com uma variável. Algo parece estar fazendo com que pense que estou tentando fazer com que ele execute o nome do diretório como um comando e também não avalie corretamente o nome do diretório com relação à cadeia ... (o nome do diretório é "ll_bkup"):

SCRIPT:

#!/bin/bash
# Changes backup folder to standard name after LogLogic System Stores a session number in t$
#TCJ 6/1/09

declare RESULT
cd /home/storegrid/scripts/test/backup
RESULT=$('ls')
TEST="ll_bkup"

if ["${RESULT}" = "${TEST}"]; then
        echo "it's ll_bkup"
else
        echo $RESULT
fi

exit 0

RESULTADO:

[root@NB-BACKUP-01 backup]# sh /home/storegrid/scripts/test/nb-script-changellbackup.sh
/home/storegrid/scripts/test/nb-script-changellbackup.sh: line 10: [ll_bkup: command not found
ll_bkup
    
por TrevJen 18.06.2009 / 18:48

5 respostas

1

Comparações de strings com shell são complicadas. Todos querem usar "if" e "test", mas há outra estrutura que funciona muito bem para correspondência de strings.

A estrutura if realmente apenas verifica o status de saída da última coisa que é executada após o if. O "[" é realmente o programa "test", que pode fazer comparações de strings, mas também pode fazer outras coisas, como verificar se uma entrada de diretório é um link ou um diretório ou um arquivo.

Além disso, a estrutura variável = $ (ls) potencialmente fará coisas ruins se você tiver mais de uma entrada de diretório nesse diretório ou se tiver um nome com espaço em branco nela. Você está mais seguro em deixar o shell fazer o globbing para você com algo como um loop for.

Coloque tudo junto com:

#!/bin/sh
default_name=ll_bkup

if
  cd /home/storegrid/scripts/test/backup
then
  for result in *
  do
    case "$result"
    in
      "$default_name")
          if 
            test -d "$result"
          then
            echo "the default directory exists"
          else
            echo "the default directory exists but is not a directory!!"
            exit 33
          fi
         ;;
       *)
         if
           test -d "$result"
         then
           echo "non-standard directory $result exists"
         else
           echo "file named $result exists in directory $(pwd)"
         fi
        ;;
    esac
  done
else
  echo "directory doesn't exist or permission problem!"
  exit 40
fi
    
por 18.06.2009 / 20:55
3

$ {foo} é uma sintaxe para elementos de matriz de referência no bash . Outras respostas apontam seu uso geral na avaliação de variáveis, mas você não precisa disso aqui. Você provavelmente quer apenas comparar

[ $RESULT = $TEST ]

Você está procurando um diretório chamado ll_bkup? Você poderia fazer

[ -d ll_bkup ]

para "ll_bkup existe e é um diretório". Use -f se for um arquivo.

Se você está procurando o conteúdo que está sendo somente ll_bkup, você também pode fazer um teste em

[ $(ls | wc -l) == 1 ]

Veja 'man test' para a sintaxe que você pode usar.

Pode haver uma maneira mais sucinta de fazer isso, mas o aprendizado das partes, uma de cada vez, dá a você uma boa compreensão das partes, e você pode trabalhar até testes mais interessantes com utilitários como find .

    
por 18.06.2009 / 18:53
2

No segundo exemplo, você precisa de um espaço após o ' [ ' e antes dos caracteres ' ] '.

Ou seja:

if [$RESULT = $TEST]; then

Deve ser:

if [ $RESULT = $TEST ]; then

Isso ocorre porque [ é realmente um comando e não apenas alguma sintaxe no bash (embora eu acredite que haja um bash embutido [ também !!).

Por exemplo se você executar o seguinte no seu shell:

# ls -l /usr/bin/[

ele deve mostrar um arquivo executável, por exemplo:

-rwxr-xr-x 1 root root 43648 2008-10-13 19:20 /usr/bin/[

Assim, o seu script não está tentando executar o ll_bkup , em vez disso, ele está tentando executar um comando chamado [ll_bkup - que obviamente não existe. / p>

O que você realmente deseja executar [ com os argumentos " $RESULT = $TEST ] "

(sem as aspas, mas com o espaço antes de $ RESULT)

Isso faz sentido?

    
por 18.06.2009 / 19:32
0
Still get the same results with that syntax:

if [$RESULT = $TEST]; then
        echo "it's ll_bkup"
else
        echo $RESULT
fi

exit 0

RESULTADO:

[root@NB-BACKUP-01 backup]# sh /home/storegrid/scripts/test/nb-script-changellbackup.sh
/home/storegrid/scripts/test/nb-script-changellbackup.sh: line 10: [ll_bkup: command not found
ll_bkup
    
por 18.06.2009 / 18:56
0

Os espaços são o que você precisa, como diz Jason.

if [ $RESULT = $TEST ]; then
    ^ space here    ^ and here

O {} não deve fazer diferença no seu caso. $ {foo} é não apenas uma sintaxe para dereferenciamento de elementos de matriz no bash.

É a melhor maneira de acessar variáveis. Verifique isto

    
por 18.06.2009 / 20:21