Вопрос или проблема
В моем сценарии bash я пытаюсь вывести строку, если определенная строка не существует в файле.
if grep -q "$user2" /etc/passwd; then
echo "Пользователь существует!!"
Вот как я это написал, если хотел, чтобы строка существовала в файле. Но как я могу изменить это, чтобы он печатал “пользователь не существует”, если пользователь не найден в файле /etc/passwd
?
grep
вернет успех, если найдет хотя бы одно вхождение шаблона, и неудачу, если не найдет. Таким образом, вы можете добавить условие else
, если хотите получить оба вывода “существует” и “не существует”, или просто отрицать условие if
, чтобы получить только неудачи. Пример каждого:
if grep -q "$user2" /etc/passwd; then
echo "Пользователь существует!!"
else
echo "Пользователь не существует!!"
fi
if ! grep -q "$user2" /etc/passwd; then
echo "Пользователь не существует!!"
fi
Вы можете использовать опцию grep “-L / –files-without-match”, чтобы проверить, содержит ли файл строку:
if [[ $(grep -L "$user2" /etc/passwd) ]]; then
echo "Пользователь не существует!!";
fi
Альтернатива – проверить статус выхода grep
. Например:
grep -q "$user2" /etc/passwd
if [[ $? != 0 ]]; then
echo "Пользователь не существует!!"
Если grep
не находит совпадение, он завершится с кодом 1
, поэтому $?
будет 1
. grep
всегда возвращает 0
, если успешно. Так что безопаснее использовать $? != 0
вместо $? == 1
.
grep -q query_text ./file.txt && echo true || echo false
Я решаю это с помощью простого однострочного решения:
for f in *.txt; do grep "tasks:" $f || echo $f; done
Команда проверит все файлы в каталоге с расширением txt и либо запишет поисковую строку (т.е. “tasks:”), если она найдена, либо имя файла.
Чтобы выяснить, является ли имя пользователя в $user2
допустимым пользователем в этой системе, используйте getent passwd "$user2"
. Это либо даст вам запись базы данных паролей для пользователя, либо завершится с ненулевым кодом выхода, если пользователь не существует:
if ! getent passwd "$user2" >/dev/null
then
printf 'Пользователь "%s" не существует\n' "$user2"
fi
Не используйте grep
. Предположим, у вас есть два пользователя, mattias
и smatteo
, и вы хотите проверить, существует ли matt
. Если вы используете grep 'matt'
в файле passwd
, вы обязательно увидите обоих пользователей и любого другого пользователя с подстрокой matt
где-либо в их записи базы данных паролей. Ваш код тогда сделает вывод, что “пользователь matt
существует”, даже если это не так.
Кроме того, если вы используете какую-либо службу каталогов, ваши пользователи могут не храниться вовсе в /etc/passwd
. Тем не менее, команда getent
должна работать.
Ответ или решение
Конечно! Давайте подробно рассмотрим, как использовать команду grep
для проверки наличия пользователя в файле /etc/passwd
, а также альтернативные подходы и лучшие практики для этой задачи.
Проверка существования пользователя в файле /etc/passwd
с помощью grep
Команда grep
позволяет искать строки, содержащие определённый текст, в файле. Для проверки, существует ли пользователь в файле /etc/passwd
, можно использовать grep
следующим образом:
if grep -q "$user2" /etc/passwd; then
echo "Пользователь существует!!"
else
echo "Пользователь не существует!!"
fi
В данном случае флаг -q
указывает на то, что grep
должен работать в тихом режиме, не выводя соответствующие строки, а лишь возвращая статус завершения. Если пользователь найден (статус 0), то выведется сообщение о том, что пользователь существует, в противном случае – о том, что он не существует.
Негативная проверка с использованием !
Можно изменить условие if
, чтобы проверять, если grep
не нашёл пользователя:
if ! grep -q "$user2" /etc/passwd; then
echo "Пользователь не существует!!"
fi
Этот подход делает код более компактным, так как вы не используете оператор else
.
Использование grep -L
для поиска файлов без совпадений
Вы также можете воспользоваться опцией -L
, которая позволяет выводить имена файлов, не содержащих матчей, но для вашего случая это не совсем подходящее решение, так как нам только нужно проверить один файл:
if grep -L "$user2" /etc/passwd; then
echo "Пользователь не существует!!"
fi
Проверка статуса выхода с помощью $?
Вы можете проверить код завершения grep
с помощью переменной $?
, которая содержит код выхода последней выполненной команды:
grep -q "$user2" /etc/passwd
if [[ $? -ne 0 ]]; then
echo "Пользователь не существует!!"
fi
Однако, использование ! grep
является более читаемым и предпочтительным подходом.
Лучший способ: Использование getent
Хотя grep
подходит для этой задачи, рекомендуется использовать команду getent
для более надежной проверки существования пользователя:
if ! getent passwd "$user2" >/dev/null; then
printf 'Пользователь "%s" не существует\n' "$user2"
fi
Преимущества использования getent
:
- Она учитывает не только локальных пользователей, но и пользователей из сетевых служб, таких как LDAP.
- Это позволяет избежать возможных ложных срабатываний, когда пользователь имеет схожее имя.
Заключение
Для проверки существования пользователя рекомендуется использовать getent
, что делает ваш скрипт более универсальным. В случае необходимости работы только с локальным файлом /etc/passwd
, методы с использованием grep
также подходят. Однако важно помнить, что для предотвращения ложных срабатываний лучше использовать более сильные методы, такие как getent
.
Следуя этим рекомендациям, вы можете оптимизировать свой скрипт и обеспечить его корректную работу в различных средах.