2

У меня есть куча файлов php в структуре каталогов скажем /mylibs
Я хочу запустить простой php -l $file каждого файла php, который проверяет синтаксические ошибки

find /mylibs -type f -iname "*.php" -exec php -l {} &>/dev/null \;

это первый шаг, &>/dev/null съедает подробный вывод php (найдены синтаксические ошибки или нет)

php -l возвращает 0, если не найдено ошибок, в зависимости от которых я хочу скопировать их в другой /mybin . Чтобы проверить, работает ли это, как ожидалось, я попытался

find /mylibs -type f -iname "*.php" -ok php -l {} &>/dev/null ; echo $? \;

но это просто печатает 1 на терминале и не запрашивает подтверждения (-ok действует так же, как -exec после интерактивного подтверждения)

Что я здесь не так делаю? разве это невозможно сделать?

2 ответа2

3

; является разделителем команд оболочки . Все, что после этого будет отдельной командой и не будет передано для find , так как синтаксический анализ команды выполняется перед выполнением. Аналогично, &>/dev/null применяется ко всей команде find , а не только к php , независимо от того, где она находится (до, в середине или после).

Чтобы использовать такие операторы в вашем -exec или -ok , вам придется явно вызвать оболочку:

find ... -exec bash -c 'php -l "{}" >&/dev/null; echo $?' \;

Обратите внимание, что специальные символы находятся внутри кавычек, что означает, что они будут переданы буквально для find а затем для bash .

Это не так просто, но может быть более надежно с "странными" именами файлов:

find ... -exec bash -c 'php -l "$1" >&/dev/null; echo $?' -- {} \;

Это отобразит результаты в более читаемой форме: (сейчас речь идет только о скриптах bash, а не о find )

find ... -exec bash -c '
    if php -l "$1" >&/dev/null; then
        echo "$1: pass"
    else
        echo "$1: fail"
    fi' -- {} \;
0

Я бы сохранил ваши найденные файлы в массиве и запустил ваш php -l для каждого элемента в цикле for или while с помощью if ["$?"= "0"] как шаг.

find /mylibs -type f -iname "*.php" -exec php -l {} &>/dev/null \;

Я бы поменял на

MYFILES=$(find /mylibs -type f -iname "*.php")
SAVEIFS=$IFS

IFS=$(echo -en "\n\b")
for FILE in ${MYFILES}
do
  php -l ${FILE} 2&>1 >>/dev/null
  if [ "$?" != "0" ]
    then
      echo "ERROR on ${FILE}
  else
      /bin/cp ${FILE} ${NEWPATH}
  fi
done
IFS=$SAVEIFS

Всё ещё ищете ответ? Посмотрите другие вопросы с метками .