Bash: как проверить, существует ли файл или папка
Чтобы проверить, существует ли файл, в Bash используют условие [ -f путь ]. Для папки [ -d путь ], для любого объекта файловой системы [ -e путь ]. Внутри скобок обязательны пробелы, а путь лучше брать в двойные кавычки.
Основные проверки
Условие | Истинно, если |
|---|---|
| Путь существует (файл, папка, ссылка) |
| Это обычный файл |
| Это папка |
| Файл существует и не пустой |
| Это символическая ссылка |
| Есть право на чтение, запись, выполнение |
| Строка пустая |
| Строка не пустая |
Условие if
file="/tmp/check/config.ini"
if [ -f "$file" ]; then
echo "Файл есть"
else
echo "Файла нет"
fiВ одну строку
[ -f "$file" ] && echo "есть" || echo "нет"
[ -d /tmp/check ] && echo "папка есть"Отрицание: файла нет
if [ ! -f "$file" ]; then
echo "Файл не найден: $file" >&2
exit 1
fiСообщения об ошибках принято отправлять в поток ошибок: >&2.
Создать, если нет
[ -d /tmp/check/logs ] || mkdir -p /tmp/check/logs # или просто mkdir -p, он не ругается на существующую папку
[ -f "$file" ] || touch "$file"Файл есть, но пустой
if [ -s "$file" ]; then
echo "Файл не пустой"
else
echo "Файл пустой или отсутствует"
fiДвойные скобки и несколько условий
if [[ -f "$file" && -r "$file" ]]; then
echo "Файл существует и доступен для чтения"
fiДвойные скобки [[ ]] есть в Bash, но отсутствуют в строгом POSIX sh. Внутри них кавычки вокруг переменных не обязательны, но привычка ставить их безопасна.
Проверить маску файлов
Условие -f не понимает шаблоны вроде *.log. Для масок подойдёт ls или compgen:
if compgen -G "/tmp/check/*.log" > /dev/null; then
echo "Логи найдены"
fiЧастые вопросы
Почему выдаёт «too many arguments» или «unary operator expected»?
Путь содержит пробел или переменная пустая, а кавычек нет. Всегда пишите [ -f "$file" ].
Чем -e отличается от -f?
-e истинно для любого существующего пути, включая папки. -f только для обычных файлов.
Как проверить существование команды, а не файла?
Используйте command -v имя: command -v git >/dev/null || echo "git не установлен".