С помощью ls можно быстро узнать размер получившейся базы данных, как показано ниже:
$ ls −l /var/locate.db
-rw-r-r-··1 root··wheel··174088165 Mar 26 10:02 /var/locate.db
Теперь все готово к поиску файлов с помощью locate:
$ locate −i solitaire
/Users/taylor/Documents/AskDaveTaylor image folders/0-blog-pics/vista-search-solitaire.png
/Users/taylor/Documents/AskDaveTaylor image folders/8-blog-pics/windows-play-solitaire-1.png
/usr/share/emacs/22.1/lisp/play/solitaire.el.gz
/usr/share/emacs/22.1/lisp/play/solitaire.elc
/Volumes/MobileBackups/Backups.backupdb/Dave’s MBP/2014-04-03-163622/BigHD/Users/taylor/Documents/AskDaveTaylor image folders/0-blog-pics/vista-search-solitaire.png
/Volumes/MobileBackups/Backups.backupdb/Dave’s MBP/2014-04-03-163622/BigHD/Users/taylor/Documents/AskDaveTaylor image folders/8-blog-pics/windows-play-solitaire-3.png
С помощью этого сценария можно извлекать другую интересную информацию о системе, например, количество файлов с исходным кодом на языке C:
$ locate '\.c$' | wc −l
1479
ПРИМЕЧАНИЕ
Обратите внимание на использованное здесь регулярное выражение. Команда grep требует экранировать символ точки (.), иначе она будет соответствовать любому одному символу. Кроме того, символ $ обозначает конец строки или, в данном случае, конец имени файла.
Приложив чуть больше усилий, мы могли бы передать каждый из найденных файлов команде wc и подсчитать общее количество строк исходного кода на языке C в системе, но это будет, пожалуй, перебор.
Усовершенствование сценария
Чтобы обеспечить своевременное обновление базы данных, можно создать задание для cron, вызывающее mklocatedb в ночные часы раз в неделю, как это организовано в большинстве систем со встроенной командой locate или даже чаще, в зависимости от особенностей использования системы. Как и в случае с другими сценариями, действующими с привилегиями root, позаботьтесь о том, чтобы сделать сценарий недоступным для редактирования рядовым пользователям.
Еще одно усовершенствование, которое можно добавить в сценарий locate, — проверка и завершение с сообщением об ошибке при попытке запустить его без шаблона для поиска или в отсутствие файла базы данных locate.db. В текущей реализации сценарий просто выведет стандартное сообщение об ошибке от команды grep, которое может оказаться неинформативным для обычного пользователя. Еще более важной, как обсуждалось выше, является проблема безопасности: доступность рядовым пользователям имен всех файлов в системе, включая те, что должны быть скрыты от их глаз. Усовершенствования, касающиеся безопасности, мы добавим в сценарии № 39, в главе 5.
№ 20. Имитация других окружений: MS-DOS
Хотя в повседневной практике это едва ли понадобится, но с точки зрения освоения некоторых понятий командной оболочки будет интересно и показательно попробовать создать версии классических команд MS-DOS, таких как DIR, в виде сценариев, совместимых с Unix. Конечно, можно просто определить псевдоним и отобразить команду DIR в Unix-команду ls:
alias DIR=ls
Но такое отображение не имитирует фактического поведения команды; оно просто помогает забывчивым пользователям заучить новые названия команд. Если вам доводилось использовать древние способы взаимодействий с компьютером, вы наверняка вспомните, что флаг /W требует использовать широкий формат вывода. Но если передать флаг /W команде ls, она сообщит, что каталог /W не найден. Следующий сценарий DIR, представленный в листинге 2.17, напротив, написан так, что принимает и обрабатывает флаги, начинающиеся с символа слеша.
Код
Листинг 2.17. Сценарий DIR, имитирующий DOS-команду DIR в Unix
#!/bin/bash
# DIR — имитирует поведение команды DIR в DOS, принимает некоторые
#·· стандартные флаги команды DIR и выводит содержимое указанного каталога
function usage
{
cat << EOF >&2
··Usage: $0 [DOS flags] directory or directories
··Where:
····/D sort by columns
····/H show help for this shell script
····/N show long listing format with filenames on right
····/OD sort by oldest to newest
····/O-D sort by newest to oldest
····/P pause after each screenful of information
····/Q show owner of the file
····/S recursive listing
····/W use wide listing format
EOF
··exit 1
}
#####################
### ОСНОВНОЙ СЦЕНАРИЙ
postcmd=""
flags=""
while [$# −gt 0]
do
··case $1 in
····/D······) flags="$flags −x"··;;
····/H······) usage··············;;
····/[NQW]··) flags="$fl −l— l"··;;