Скобки, в если условие: почему я получаю синтаксические ошибки без пробела?

Я иду на некоторые примеры pdbedit вывод я нашел онлайн. Ваш мог бы отличаться; если можно обеспечить некоторые примеры того, что это печатает, этот код может быть более адаптирован в соответствии с тем, в чем Вы нуждаетесь.

Во-первых, необходимо найти имена пользователей, которые соответствуют префиксу. Это кажется этим pdbedit вывод находится в username: foo формат, таким образом, Вы могли использовать awk сделать это:

pdbedit -L -v | awk '/username:/ {print $2}'

Затем мы должны найти имена, которые запускаются с Вашего префикса, поэтому давайте использовать grep:

pdbedit -L -v | awk '/username:/ {print $2}' | grep ^eg

Чтобы видеть, должен ли пароль конкретного пользователя измениться, мы можем просто видеть ли grep найденный, что строка, путем проверки ее кода возврата:

if pdbedit -v -u $name | grep -q "Password must change" ; then
    echo $name
fi

Помещение всего этого вместе с циклом, который проверяет каждое имя:

for name in $(pdbedit -L -v | awk '/username:/ {print $2}' | grep ^eg); do
    if pdbedit -v -u $name | grep -q "Password must change" ; then
        echo $name
    fi
done

Обновление после регистрации демонстрационного вывода

Тот формат ясно не разработан кем-то, кто поклонник нормальных инструментов обработки текста командной строки Unix! В то время как можно, конечно, сделать что-либо на любом языке, я, вероятно, переместился бы во что-то как Python или Perl для парсинга этого. Я выбрал Perl здесь, потому что обработка Python дат и времени плачевна.

#!/usr/bin/perl

use Date::Parse;

$now = time();
while (<>) {
    if (/Unix username:\s*(.*)/) {
        $username = $1;
    }
    if (/Password must change:\s*(.*)/) {
        $change = str2time($1);
        if ($change <= $now) {
            print "$username\n";
        }
    }
}

Это распечатает имя пользователя Unix любого пользователя, пароль которого истекает. Используйте его как:

pdbedit -L -v | perl parse.pl

Редактирование автором Вопроса

Заключительный код, который я использовал, был:

#!/usr/bin/perl
use Date::Parse;
$now = time();
while (<>) {
    if (/Unix username:\s*(.*)/) {
        $username = $1;
    }
    if (/Password must change:\s*(.*)/) {
        $expiry = $1;
        $change = str2time($expiry);
        if ($expiry !~ /^never/ && $change <= $now && $username =~ /^eg[a-z]{3}\d+/) {
            print "$username expiry: $expiry\n";
        }
    }
}

Который производит вывод как это:

egdfd001 expiry: Mon, 30 Jul 2012 08:12:02 NZST
egjpf001 expiry: Mon, 13 Aug 2012 07:50:03 NZST
17
17.10.2014, 01:33
3 ответа

Другой способ записать это:

case $month:$day in
  (01:0[12])
    date="$last_month/$yes_day/$last_year"
    fulldate="$last_month/$yes_day/$last_year"
    ;;
  (*:0[12])
    date="$last_month/$yes_day/$year"
    fulldate="$year$last_month$yes_day"
    ;;
  (*)
    date="$month/$yes_day/$year"
    fulldate="$year$month$yes_day"
esac
4
27.01.2020, 19:46

Итак, вот ваш ответ:

if [ $var1 == $var2 ];
 then
    echo "bla bla"
fi

Итак, вы должны поставить "пробел" между квадратной скобкой и переменной/значением.

-1
27.01.2020, 19:46

[ не является ни метасимволом, ни управляющим оператором (даже не зарезервированным словом; то же самое для ]), поэтому ему нужен пробел вокруг него. Иначе оболочка "увидит" команду [01=01] вместо команды [ с отдельными параметрами 01, =, 01 и ]. Каждый оператор и операнд должен быть отдельным аргументом команды [, поэтому вокруг операторов также необходимы пробелы.

if [ "$month" = "01" ]

[$month="01"] - это шаблон подстановки, который соответствует любому из символов в $month или "01. Если он ничему не соответствует, его оставляют в покое.

Если после закрывающей скобки стоит точка с запятой, пробел перед ней не нужен, потому что точка с запятой всегда является частью отдельной лексемы.

if [ "$month" = "01" ]; then

То же самое относится к синтаксису двойных скобок в bash (а также в ksh и zsh).

Более одного условия

Существует два способа объединения условий:

  1. внутри [

  2. отдельными командами [ в сочетании с && или ||

Группировка с помощью скобок, вероятно, проще внутри [.

if [ "$month" = "01" -a "$day" = "01" ] # -a for and, -o for or

if [ "$month" = "01" ] && [ "$day" = "01" ]

Первого варианта следует избегать, так как он ненадежен (попробуйте, например, month='!'). Проблем со странным содержимым переменных можно избежать, используя сначала безопасную строку (если она есть); или используя [[/]] вместо [/]:

if [ "01" = "$month" -a "01" = "$day" ]
27
27.01.2020, 19:46

Теги

Похожие вопросы