Aquí podría ser tu PUBLICIDAD


¿Cómo puedo saber si un archivo regular no existe en Bash?

votos
2426

He utilizado la siguiente secuencia de comandos para ver si existe un archivo:

#!/bin/bash

FILE=$1     
if [ -f $FILE ]; then
   echo File $FILE exists.
else
   echo File $FILE does not exist.
fi

¿Cuál es la sintaxis correcta para usar si solo quiero verificar si el archivo no existe?

#!/bin/bash

FILE=$1     
if [ $FILE does not exist ]; then
   echo File $FILE does not exist.
fi
Publicado el 12/03/2009 a las 15:48
fuente por usuario Bill the Lizard
En otros idiomas...        العربية       

17 respuestas

votos
3409

El comando de prueba ( [aquí) tiene un operador lógico "no" que es el signo de exclamación (similar a muchos otros idiomas). Prueba esto:

if [ ! -f /tmp/foo.txt ]; then
    echo "File not found!"
fi
Respondida el 12/03/2009 a las 03:50
fuente por usuario John Feminella


Aquí podría ser tu PUBLICIDAD


votos
393

Prueba Bash Archivo

-b filename- Bloquear archivo especial
-c filename- archivo de carácter especial
-d directoryname- Comprobar la existencia del directorio
-e filename- Comprobar la existencia del archivo, independientemente del tipo (nodo, directorio, zócalo, etc.)
-f filename- Comprobar la existencia de archivos normal no es un directorio
-G filename- Comprobar si el archivo existe y es propiedad de ID de grupo efectivo
-G filename set-group-id- Cierto si fichero existe y es set-group-id
-k filename- sticky bit
-L filename- enlace simbólico
-O filename- Cierto si fichero existe y es propiedad del identificador de usuario efectivo
-r filename- Comprobar si el archivo es una legibles
-S filename- Comprobar si el archivo es socket
-s filename- Compruebe si archivo es de tamaño distinto de cero
-u filename- Compruebe si se ha establecido el bit de archivo definido por el usuario-id
-w filename- Compruebe si el archivo se puede escribir
-x filename- Comprobar si el archivo es ejecutable

Cómo utilizar:

#!/bin/bash
file=./file
if [ -e "$file" ]; then
    echo "File exists"
else 
    echo "File does not exist"
fi 

Una expresión de prueba puede ser negado utilizando el !operador

#!/bin/bash
file=./file
if [ ! -e "$file" ]; then
    echo "File does not exist"
else 
    echo "File exists"
fi 
Respondida el 16/01/2014 a las 03:25
fuente por usuario GroundZero

votos
246

Puedes negar una expresión con "!":

#!/bin/bash
FILE=$1

if [ ! -f "$FILE" ]
then
    echo "File $FILE does not exist"
fi

La página man correspondiente es man testo, de forma equivalente, man [- help testo help [para el comando bash incorporado.

Respondida el 12/03/2009 a las 03:50
fuente por usuario unbeknown

votos
107
[[ -f $FILE ]] || printf '%s does not exist!\n' "$FILE"

Además, es posible que el archivo sea un enlace simbólico roto, o un archivo no regular, como por ejemplo un socket, dispositivo o fifo. Por ejemplo, para agregar un cheque para enlaces simbólicos rotos:

if [[ ! -f $FILE ]]; then
    if [[ -L $FILE ]]; then
        printf '%s is a broken symlink!\n' "$FILE"
    else
        printf '%s does not exist!\n' "$FILE"
    fi
fi
Respondida el 12/03/2009 a las 03:52
fuente por usuario guns

votos
79

Vale la pena mencionar que si usted necesita para ejecutar un solo comando se puede abreviar

if [ ! -f "$file" ]; then
    echo "$file"
fi

a

test -f "$file" || echo "$file"

o

[ -f "$file" ] || echo "$file"
Respondida el 11/08/2011 a las 10:15
fuente por usuario Elazar Leibovich

votos
55

Yo prefiero hacer lo siguiente de una sola línea, en POSIX formato compatible shell:

$ [ -f "/$DIR/$FILE" ] || echo "$FILE NOT FOUND"

$ [ -f "/$DIR/$FILE" ] && echo "$FILE FOUND"

Durante un par de comandos, al igual que lo haría en un script:

$  [ -f "/$DIR/$FILE" ] || { echo "$FILE NOT FOUND" ; exit 1 ;}

Una vez que empecé a hacer esto, rara vez usar la sintaxis totalmente escrito más !!

Respondida el 18/10/2011 a las 05:09
fuente por usuario TechZilla

votos
35

Para probar la existencia del archivo, el parámetro puede ser cualquiera de los siguientes:

-e: Returns true if file exists (regular file, directory, or symlink)
-f: Returns true if file exists and is a regular file
-d: Returns true if file exists and is a directory
-h: Returns true if file exists and is a symlink

Todas las pruebas siguientes se aplican a los archivos regulares, directorios y enlaces simbólicos:

-r: Returns true if file exists and is readable
-w: Returns true if file exists and is writable
-x: Returns true if file exists and is executable
-s: Returns true if file exists and has a size > 0

Script de ejemplo:

#!/bin/bash
FILE=$1

if [ -f "$FILE" ]; then
   echo "File $FILE exists"
else
   echo "File $FILE does not exist"
fi
Respondida el 19/12/2013 a las 01:47
fuente por usuario SD.

votos
28

Usted debe tener cuidado acerca de la ejecución testde una variable no cotizados, ya que podría producir resultados inesperados:

$ [ -f ]
$ echo $?
0
$ [ -f "" ]
$ echo $?
1

La recomendación es por lo general para tener la variable probado rodeado por comillas dobles:

#!/bin/sh
FILE=$1

if [ ! -f "$FILE" ]
then
   echo "File $FILE does not exist."
fi
Respondida el 24/01/2012 a las 08:43
fuente por usuario artdanil

votos
17

Hay tres maneras distintas de hacerlo:

  1. Negar el estado de salida con bash (hay otra respuesta ha dicho esto):

    if ! [ -e "$file" ]; then
        echo "file does not exist"
    fi
    

    O:

    ! [ -e "$file" ] && echo "file does not exist"
    
  2. Negar la prueba dentro de la orden de prueba [(que es la forma más respuestas antes de haber presentado):

    if [ ! -e "$file" ]; then
        echo "file does not exist"
    fi
    

    O:

    [ ! -e "$file" ] && echo "file does not exist"
    
  3. Ley sobre el resultado de la prueba es negativo ( ||en lugar de &&):

    Solamente:

    [ -e "$file" ] || echo "file does not exist"
    

    Esto parece una tontería (OMI), no lo use a menos que su código tiene que ser portátil para el shell Bourne (como el /bin/shde Solaris 10 o anterior) que carecía del operador de canalización negación ( !):

    if [ -e "$file" ]; then
        :
    else
        echo "file does not exist"
    fi
    
Respondida el 05/08/2015 a las 06:10
fuente por usuario user2350426

votos
11

En

[ -f "$file" ]

el [comando hace una stat()(no lstat()) llamada al sistema en el camino almacenado en $filey devuelve verdadero si esa llamada al sistema tiene éxito y el tipo del archivo tal como lo devuelve stat()es "regular".

Así que si [ -f "$file" ]devuelve true, se puede decir que el archivo existe y es un archivo regular o un enlace simbólico con el tiempo a la resolución de un archivo normal (o al menos lo era en el momento de la stat()).

Sin embargo si devuelve falso (o si [ ! -f "$file" ]o ! [ -f "$file" ]devolver true), hay muchas posibilidades diferentes:

  • no existe el archivo
  • el archivo existe, pero no es un archivo regular
  • el archivo existe, pero que no tiene permiso de búsqueda para el directorio padre
  • el archivo existe, pero ese camino para acceder a ella es demasiado largo
  • El archivo es un enlace simbólico a un archivo normal, pero que no tiene permiso de paso a algunos de los directorios implicados en la resolución del enlace simbólico.
  • ... alguna otra razón por la stat()llamada al sistema puede fallar.

En resumen, debe ser:

if [ -f "$file" ]; then
  printf '"%s" is a path to a regular file or symlink to regular file\n' "$file"
elif [ -e "$file" ]; then
  printf '"%s" exists but is not a regular file\n' "$file"
elif [ -L "$file" ]; then
  printf '"%s" exists, is a symlink but I cannot tell if it eventually resolves to an actual file, regular or not\n' "$file"
else
  printf 'I cannot tell if "%s" exists, let alone whether it is a regular file or not\n' "$file"
fi

Para estar seguro de que el archivo no existe, necesitaríamos la stat()llamada al sistema para devolver un código de error de ENOENT( ENOTDIRnos dice uno de los componentes de la ruta no es un directorio es otro caso en el que podemos decir el archivo no existir por ese camino). Por desgracia, el [comando no nos hizo saber que. Será return false si el código de error es ENOENT, EACCESS (permiso denegado), ENAMETOOLONG o cualquier otra cosa.

El [ -e "$file" ]examen también se puede hacer con ls -Ld -- "$file" > /dev/null. En ese caso, lsle dirá por qué el stat()fracaso, aunque la información no puede ser fácilmente utilizado mediante programación:

$ file=/var/spool/cron/crontabs/root
$ if [ ! -e "$file" ]; then echo does not exist; fi
does not exist
$ if ! ls -Ld -- "$file" > /dev/null; then echo stat failed; fi
ls: cannot access '/var/spool/cron/crontabs/root': Permission denied
stat failed

Al menos lsme dice que no es debido a que el archivo no existe que falla. Es porque no puede decir si existe el archivo o no. El [comando simplemente ignorado el problema.

Con la zshcáscara, se puede consultar el código de error con la $ERRNOvariable especial después de que el defecto [del sistema, y decodificar ese número utilizando la $errnosgama especial en el zsh/systemmódulo:

zmodload zsh/system
ERRNO=0
if [ ! -f "$file" ]; then
  err=$ERRNO
  case $errnos[err] in
    ("") echo exists, not a regular file;;
    (ENOENT|ENOTDIR)
       if [ -L "$file" ]; then
         echo broken link
       else
         echo does not exist
       fi;;
    (*) echo "can't tell"; syserror "$err"
  esac
fi

(cuidado con el $errnossoporte se rompe con algunas versiones de zshcuando se construyó con las versiones recientes degcc ).

Respondida el 14/10/2016 a las 12:18
fuente por usuario Stephane Chazelas

votos
11

Puedes hacerlo:

[[ ! -f "$FILE" ]] && echo "File doesn't exist"

o

if [[ ! -f "$FILE" ]]; then
    echo "File doesn't exist"
fi

Si desea comprobar los archivos y carpetas tanto, a continuación, utilizar -ela opción en lugar de -f. -eDevuelve verdadero para los archivos regulares, directorios, zócalo, ficheros especiales de caracteres, archivos especiales de bloques etc.

Respondida el 28/04/2015 a las 07:40
fuente por usuario Jahid

votos
7

Para invertir una prueba, utilice "!". Esto es equivalente a la "no" operador lógico en otros idiomas. Prueba esto:

if [ ! -f /tmp/foo.txt ];
then
    echo "File not found!"
fi

O escrita de una manera ligeramente diferente:

if [ ! -f /tmp/foo.txt ]
    then echo "File not found!"
fi

O puede utilizar:

if ! [ -f /tmp/foo.txt ]
    then echo "File not found!"
fi

O, presing todos juntos:

if ! [ -f /tmp/foo.txt ]; then echo "File not found!"; fi

Que puede ser escrito (utilizando a continuación "y" operador: &&) como:

[ ! -f /tmp/foo.txt ] && echo "File not found!"

Que se parece más corto de esta manera:

[ -f /tmp/foo.txt ] || echo "File not found!"
Respondida el 04/05/2013 a las 11:29
fuente por usuario user2350426

votos
7

La testcosa puede contar también. Se trabajó para mí (basado en Bash: Comprobar archivo existe o no ):

test -e FILENAME && echo "File exists" || echo "File doesn't exist"
Respondida el 31/03/2013 a las 02:22
fuente por usuario android developer

votos
6

Este código también trabajar.

#!/bin/bash
FILE=$1
if [ -f $FILE ]; then
 echo "File '$FILE' Exists"
else
 echo "The File '$FILE' Does Not Exist"
fi
Respondida el 03/07/2015 a las 08:39
fuente por usuario Lemon Kazi

votos
4

La forma más sencilla

FILE=$1
[ ! -e "${FILE}" ] && echo "does not exist" || echo "exists"
Respondida el 21/05/2014 a las 07:11
fuente por usuario lancerex

votos
2

Este script también trabaja para encontrar un archivo en un directorio:

echo "enter file"

read -r a

if [ -s /home/trainee02/"$a" ]
then
    echo "yes. file is there."
else
    echo "sorry. file is not there."
fi
Respondida el 29/08/2013 a las 07:59
fuente por usuario Simmant

votos
1

a veces puede ser útil para usar && y || operadores.

Al igual que en (si tiene una "prueba" de comandos):

test -b $FILE && echo File not there!

o

test -b $FILE || echo File there!
Respondida el 11/04/2017 a las 05:25
fuente por usuario André


Aquí podría ser tu PUBLICIDAD