Пользоваться сценарием bulkrun очень просто. Ему нужно передать три аргумента: максимальное количество одновременно действующих процессов, каталог с файлами для обработки и запускаемую команду. Например, в листинге Б.4 показано, как изменить размеры изображений в каталоге, запустив одновременно несколько экземпляров утилиты mogrify из пакета ImageMagick.
Результаты
Листинг Б.4. Запуск команды bulkrun для параллельной обработки файлов изображений утилитой mogrify из пакета ImageMagick
$ bulkrun −p 3 −i tmp/ −x "mogrify −resize 50 %"
Running mogrify −resize 50 % tmp//1024-2006_1011_093752.jpg
Running mogrify −resize 50 % tmp//069750a6-660e-11e6-80d1-001c42daa3a7.jpg
Running mogrify −resize 50 % tmp//06970ce0-660e-11e6-8a4a-001c42daa3a7.jpg
Running mogrify −resize 50 % tmp//0696cf00-660e-11e6-8d38-001c42daa3a7.jpg
Running mogrify −resize 50 % tmp//0696cf00-660e-11e6-8d38-001c42daa3a7.jpg
-опущено-
Усовершенствование сценария
Часто бывает полезно иметь возможность указать имя файла внутри команды или использовать лексемы, подобные тем, что упоминались в описании сценария bulkrename (сценарий № 102 выше): специальные строки, динамически заменяемые во время выполнения фактическими значениями (например, %d можно было бы заменять текущей датой, или %t отметкой текущего времени). Реализация поддержки подобных специальных лексем в команде или в именах файлов стала бы ценным усовершенствованием сценария.
Другим полезным усовершенствованием было бы использование утилиты time для определения продолжительности обработки всех файлов. Вывод статистической информации о количестве обработанных файлов или файлов, ожидающих обработки, тоже мог бы пригодиться в случае выполнения массивных заданий.
№ 104. Определение фазы Луны
Если вы оборотень, ведьма или просто интересуетесь лунным календарем, вам наверняка пригодится полезная и познавательная возможность определять фазы Луны.
Вся сложность в том, что Луна совершает полный оборот вокруг Земли за 27,32 дня. И ее фаза фактически зависит от вашего местоположения на Земле. Однако эта зависимость невелика, так что фазы Луны можно определять только по заданной дате.
Но зачем разбираться со всеми этими сложностями, если в Интернете полно сайтов, которые вычисляют фазу Луны для любой даты в прошлом, в настоящем или в будущем? Для сценария в листинге Б.5 мы используем для этого тот же сайт, что использует Google: http://www.moongiant.com/.
Код
Листинг Б.5. Сценарий moonphase
··#!/bin/bash
··# moonphase — сообщает фазу Луны (в действительности процент
··#·· освещенности) на текущую или указанную дату.
··# Формат запроса к Moongiant.com:
··#·· http://www.moongiant.com/phase/MM/DD/YYYY
··# Если дата не указана, использовать текущую дату.
··if [$# −eq 0]; then
····thedate="today"
··else
····# Дата указана. Проверить правильность ее формата.
····mon="$(echo $1 | cut −d/ −f1)"
····day="$(echo $1 | cut −d/ −f2)"
····year="$(echo $1 | cut −d/ −f3)"
····if [-z "$year" −o — z "$day"]; then # Нулевая длина?
······echo "Error: valid date format is MM/DD/YYYY"
······exit 1
····fi
····thedate="$1" # Отсутствие проверки ошибок = опасность.
··fi
··url="http://www.moongiant.com/phase/$thedate"
··pattern="Illumination: "
··phase="$(curl −s "$url" | grep "$pattern" | tr ',' '\
··' | grep "$pattern" | sed 's/[^0–9]//g')"
··# Сайт возвращает ответ в формате: "Illumination: <span>NN%\n<\/span>"
··if ["$thedate" = "today"]; then
····echo "Today the moon is ${phase}% illuminated."
··else
····echo "On $thedate the moon = ${phase}% illuminated."
··fi
··exit 0
Как это работает
По аналогии с другими сценариями, извлекающими информацию из веб-запросов, основу сценария moonphase составляет код конструирования URL запроса и извлечения требуемого ответа из потока данных в формате HTML.
Анализ сайта показал, что поддерживается два вида адресов URL: один определяет текущую дату и имеет вид «phase/today», а другой — дату в прошлом или в будущем в формате MM/DD/YYYY, например: «phase/08/03/2017».
Задайте дату в правильном формате, и вы получите фазу Луны в указанный день. Но мы не можем просто добавить дату к доменному имени сайта, не выполнив некоторые проверки. С этой целью сценарий разбивает ввод пользователя на три поля — месяц, день и год — и затем проверяет строковые значения дня и года на ненулевую длину