- Подписка на печатную версию:
- Подписка на электронную версию:
- Подшивки старых номеров журнала (печатные версии)
LXF78:Мощные инструменты командной строки
Материал из Linuxformat.
(→Шаг 2 — Могучие команды Unix) |
|||
Строка 136: | Строка 136: | ||
grep -ilr paul * | grep -cv «\.txt$» | grep -ilr paul * | grep -cv «\.txt$» | ||
- | Здесь мы используем пять из шести важнейших параметров, превращая сложную задачу в простой конечный результат: число соответствующих условию файлов. В этом примере -ilr означает, что выполняется поиск по файлам слов Paul, PAUL, PaUl и т.д., поиск проходит рекурсивно по вашей файловой системе (начните с корневого каталога, чтобы выполнить поиск по всему диску) и возвращает имена подходящих файлов. Всё это поступает на вход другого экземпляра grep, который использует флаги -cv, включающие режим подсчёта и поиск файлов, которые не соответствуют регулярному выражению «\.txt$». Обратный слеш здесь экранирует точку: без него мы получили бы специальный символ. Знак доллара в конце означает, что .txt должно находиться в конце имени файла, то есть foo.txt.bar не будет соответствовать выражению. | + | Здесь мы используем пять из шести важнейших параметров, превращая сложную задачу в простой конечный результат: число соответствующих условию файлов. В этом примере '''-ilr''' означает, что выполняется поиск по файлам слов Paul, PAUL, PaUl и т.д., поиск проходит рекурсивно по вашей файловой системе (начните с корневого каталога, чтобы выполнить поиск по всему диску) и возвращает имена подходящих файлов. Всё это поступает на вход другого экземпляра grep, который использует флаги '''-cv''', включающие режим подсчёта и поиск файлов, которые не соответствуют регулярному выражению «\.txt$». Обратный слеш здесь экранирует точку: без него мы получили бы специальный символ. Знак доллара в конце означает, что .txt должно находиться в конце имени файла, то есть foo.txt.bar не будет соответствовать выражению. |
- | Если вам предстоит прошлепать по огромному тексту, настоятельно рекомендую использовать дополнительный ключ --color, чтобы grep подсвечивал в выводе соответствующие выражения. | + | Если вам предстоит прошлепать по огромному тексту, настоятельно рекомендую использовать дополнительный ключ '''--color''', чтобы grep подсвечивал в выводе соответствующие выражения. |
*Ищите и обрящете | *Ищите и обрящете | ||
- | Команда find печально знаменита своим коварством: никто не может правильно её использовать, не прочитав предварительно руководство. Впервые принимаясь за find, многие думают, что нужно попробовать нечто вроде find <иголка> <стог_сена>. Например, find myfile.txt /etc должна бы просматривать каталог /etc и его подкаталоги в поисках файла myfile.txt. Ха-ха! Когда я вижу новичков, набирающих подобное, я обычно хлопаю их по спине, говорю, что всё у них получится, и расхаживаю, невинно посвистывая. | + | Команда find печально знаменита своим коварством: никто не может правильно её использовать, не прочитав предварительно руководство. Впервые принимаясь за find, многие думают, что нужно попробовать нечто вроде '''find <иголка> <стог_сена>'''. Например, find '''myfile.txt /etc''' должна бы просматривать каталог '''/etc''' и его подкаталоги в поисках файла '''myfile.txt'''. Ха-ха! Когда я вижу новичков, набирающих подобное, я обычно хлопаю их по спине, говорю, что всё у них получится, и расхаживаю, невинно посвистывая. |
Вместо того чтобы работать в соответствии со здравым смыслом, find работает как фильтр. Наиболее общая команда выглядит так: | Вместо того чтобы работать в соответствии со здравым смыслом, find работает как фильтр. Наиболее общая команда выглядит так: | ||
Строка 147: | Строка 147: | ||
find . | find . | ||
- | Первый параметр (путь, по которому выполняется поиск) – это «.», так что будет возвращён список всех файлов в текущем каталоге. Теперь сузим вывод при помощи параметров. Например, -name указывает, что find должна возвратить только файлы с указанным именем, скажем, myfile.txt или «*bar*», соответствующий файлам с «bar» где-нибудь в имени. Например: | + | Первый параметр (путь, по которому выполняется поиск) – это «.», так что будет возвращён список всех файлов в текущем каталоге. Теперь сузим вывод при помощи параметров. Например, '''-name''' указывает, что find должна возвратить только файлы с указанным именем, скажем, myfile.txt или «*bar*», соответствующий файлам с «bar» где-нибудь в имени. Например: |
find . -name «*bar*» | find . -name «*bar*» | ||
- | Мы могли бы добавить параметр -size, который ограничивает результаты поиска файлами, размер которых больше, меньше или равен заданному. Например: | + | Мы могли бы добавить параметр '''-size''', который ограничивает результаты поиска файлами, размер которых больше, меньше или равен заданному. Например: |
find . -name «*bar*» -size +1M | find . -name «*bar*» -size +1M | ||
Строка 158: | Строка 158: | ||
Первая команда найдёт все файлы с нужными именами, которые больше 1 МБ, а вторая – те, которые меньше 10 КБ. Файлы, размер которых точно равен заданному (например, 1 МБ), не будут возвращены, если поиск выполняется со строгим условием «больше» или «меньше». | Первая команда найдёт все файлы с нужными именами, которые больше 1 МБ, а вторая – те, которые меньше 10 КБ. Файлы, размер которых точно равен заданному (например, 1 МБ), не будут возвращены, если поиск выполняется со строгим условием «больше» или «меньше». | ||
- | Параметр -user возвращает только файлы, принадлежащие указанному пользователю. Например, -user paul вернёт файлы, принадлежащие пользователю paul. В частности, это полезно с параметром -not, который может предшествовать любому параметру и выполняет инвертирование значения. Вот несколько примеров: | + | Параметр '''-user''' возвращает только файлы, принадлежащие указанному пользователю. Например, '''-user paul''' вернёт файлы, принадлежащие пользователю paul. В частности, это полезно с параметром -not, который может предшествовать любому параметру и выполняет инвертирование значения. Вот несколько примеров: |
# все файлы, не принадлежащие пользователю paul | # все файлы, не принадлежащие пользователю paul | ||
Строка 167: | Строка 167: | ||
find . -not -not -name «*bar*» -not -user paul | find . -not -not -name «*bar*» -not -user paul | ||
- | Ещё один небезынтересный фильтр – -newer, он возвращает все файлы, которые новее, чем указанный файл. Это очень удобно для скриптов резервного копирования: когда делаете копию, просто укажите произвольный файл, и он будет служить временной меткой, которую можно использовать в команде find -newer. Вы получите список всех файлов, которые изменились с момента создания этого файла. Вот нужная вам команда: | + | Ещё один небезынтересный фильтр – '''-newer''', он возвращает все файлы, которые новее, чем указанный файл. Это очень удобно для скриптов резервного копирования: когда делаете копию, просто укажите произвольный файл, и он будет служить временной меткой, которую можно использовать в команде '''find -newer'''. Вы получите список всех файлов, которые изменились с момента создания этого файла. Вот нужная вам команда: |
find . -newer /path/to/myfile | find . -newer /path/to/myfile | ||
*Последние штрихи | *Последние штрихи | ||
- | Есть целая группа параметров find, которые мы не затронули: действия. Каждый раз, когда find наталкивается на файл, соответствующий вашим критериям, она может что-то с этим файлом проделать. Например, -ls выведет на экран информацию об этом файле в стиле ls -l, а параметром -exec заставит find запустить для этого файла определённую команду. Скажем, вы хотите найти все текстовые файлы в своём домашнем каталоге и вывести их на экран. Это можно сделать так: | + | Есть целая группа параметров find, которые мы не затронули: действия. Каждый раз, когда find наталкивается на файл, соответствующий вашим критериям, она может что-то с этим файлом проделать. Например, '''-ls''' выведет на экран информацию об этом файле в стиле '''ls -l''', а параметром '''-exec''' заставит find запустить для этого файла определённую команду. Скажем, вы хотите найти все текстовые файлы в своём домашнем каталоге и вывести их на экран. Это можно сделать так: |
find /home/someuser -name «*.txt» -exec cat {} \; | find /home/someuser -name «*.txt» -exec cat {} \; | ||
- | Фигурные скобки {} заменятся именем соответствующего файла, и при каждом совпадении будет выполняться cat. Конструкция \; в конце необходима, потому что find считает всё, что после -exec, выполняемой программой, пока не наткнется на точку с запятой. Но если вы просто наберете -exec cat {};, то Bash в процессе обработки строки эту точку с запятой удалит, и find пожалуется на ошибку. | + | Фигурные скобки '''{}''' заменятся именем соответствующего файла, и при каждом совпадении будет выполняться cat. Конструкция \; в конце необходима, потому что find считает всё, что после '''-exec''', выполняемой программой, пока не наткнется на точку с запятой. Но если вы просто наберете '''-exec cat {};''', то Bash в процессе обработки строки эту точку с запятой удалит, и find пожалуется на ошибку. |
- | Альтернативой -exec является -ok, который работает точно таким же образом, но запрашивает ввод пользователя перед выполнением каждой команды. Нажмите <y> для выполнения команды (опять-таки, для каждого соответствующего файла), или <n>, чтобы пропустить её. | + | Альтернативой '''-exec''' является '''-ok''', который работает точно таким же образом, но запрашивает ввод пользователя перед выполнением каждой команды. Нажмите '''<y>''' для выполнения команды (опять-таки, для каждого соответствующего файла), или '''<n>''', чтобы пропустить её. |
К сожалению, на этот месяц больше места нам не досталось, и я сумел лишь обсудить Bash и четыре самых популярных команды Unix. Мы надеемся, что наступит день, когда вы полюбите командную строку с той же страстью, что и мы – или, по крайней мере, не так будете пугаться пролетающего во время загрузки текста. | К сожалению, на этот месяц больше места нам не досталось, и я сумел лишь обсудить Bash и четыре самых популярных команды Unix. Мы надеемся, что наступит день, когда вы полюбите командную строку с той же страстью, что и мы – или, по крайней мере, не так будете пугаться пролетающего во время загрузки текста. |
Версия 11:46, 22 марта 2008
Срубите GUI, вышвырните мышь из дома и дайте вашей графической супер-карте отдохнуть – «реальные пацаны» используют командную строку, утверждает Пол Хадсон.
Содержание |
Это четвёртый из наших уроков серии Hardcore Linux, и если вы досюда добрались, то вам почти пора наниматься в Linux Format. Заметьте, только почти, потому что ваши испытания на самом деле только начинаются. Вот как побываете под брюхом овцы, ослепите циклопа горящим бревном, перехитрите Цирцею и напишете собственный драйвер, тогда и будете готовы присоединиться к суперэлитной команде LXF.
А пока – сидите на коленях мастеров и учитесь, и в этом месяце вам откроются тайны командной строки. Причина, по которой храбрецы вроде нас овладевают командной строкой, та же самая, из-за которой Эдмунд Хиллари [новозеландец, впервые покоривший Эверест, в паре с проводником-шерпом Тенсингом Норгеем, – прим. перев.], по его словам, совершил восхождение на Эверест. Нет, не ради свежего горного воздуха, а просто потому, что Эверест есть.
Я хотел бы стать вашим Тенсингом Норгеем и помочь вам в восхождении к знаниям. Но, к сожалению, возможность слияния разумов исключается, ибо профанам Башни LXF недоступны, а Древнейшее Таинство Приобщения осложнено тем, что Mountain Dew в ближайшем универсаме на всех не хватит. Придется обойтись прозаическими бумагой и чернилами.
Шаг 1 – Секреты Bash
Стивен Борн (Stephen Bourne) написал первоначальный вариант командной оболочки Bourne для 7-й версии Unix в далёких семидесятых, и увидел Бог, что это хорошо. Но в 1987 году ее заменили улучшенной версией, названной Bourne-again Shell и большинству известной как Bash. Этот терминал уже много лет используется по умолчанию чуть ли не в каждом дистрибутиве Linux, так что новички даже не догадываются, что бывают и другие оболочки. Команда ls -l /bin/sh докажет вам, что самая основная оболочка на вашей системе – на самом деле просто ссылка на Bash, поскольку Bash – расширение sh, добавляющее новые функции, не нарушая работоспособность скриптов.
Bash еще функциональнее, чем можно вообразить. Всем нам доводилось пользоваться встроенными командами типа cd и export, а как насчёт time, alias, for и волшебного обратного апострофа? Даже управление заданиями, считавшееся абсолютно необходимым во времена больших компьютеров, – это вымирающее искусство. Ладно, я несколько отклонился от темы, дальше отклоняться не буду: настало время воскресить старые методы и поведать молодёжи, почему псевдонимы столь важны, сохраняя традиции наших Unix-предков. И первый шаг в этой революции – освоить Bash.
- Меняем псевдонимы
Используемый по умолчанию набор команд в Unix довольно ограничен, но его можно обогатить с помощью различных параметров, передаваемых командам для модификации их работы. Кому нравится набирать команды, загибающиеся на три строки, поднимите руку! Конечно, это подвох – немногие люди, которые и вправду любят подобные вещи, вероятно, из-за артроза кистей рук поднять их не смогут.
Псевдонимы (aliases) – это простой способ создавать укороченные команды в Linux. Например, можно определить псевдоним la, который запускал бы ls -a. На самом деле многие дистрибутивы поставляются именно с таким псевдонимом, установленным по умолчанию – если вы введёте alias в командной строке, то увидите список всех готовых псевдонимов. Чтобы создать собственный, введите
alias la=’ls -a’
По идее, нужно вводить этот (и другие ваши псевдонимы) каждый раз после перезагрузки, но чтобы не увеличивать ваши ежедневные заботы, Bash позволит вам раз навсегда занести ваши псевдонимы в файл ~/.Bash_aliases, да сам их и загрузит.
- Условный ответ
Bash – мощная система разработки скриптов, способная проверять условия в операторах if и циклах не хуже других языков программирования. Скриптов я касаться не буду, но условные операторы могут очень пригодиться при использовании в псевдонимах.
Вот общий пример условного оператора:
if uname -a | grep «GNU/Linux» > /dev/null; then echo «Вы работаете в Linux»; fi
Работает он следующим образом: сперва исполняет uname -a, для получения информации о системе, а затем просеивает эту информацию через grep, пытаясь обнаружить строку «GNU/Linux». Заметьте, что вывод команды перенаправлен в /dev/null, чтобы результат grep не выводился на экран. Если grep найдёт строку, значит, наше условие истинно (true), и Bash выведет: «Вы работаете в Linux». Обратите внимание на использование точки с запятой: после условия и действия, но не после fi (if наоборот; по сути, то же, что и endif).
Мы можем усложнить оператор, добавив блок else – действие, которое будет выполнено, если условие вернёт значение «ложь» (false).
Расширим предыдущий пример:
if uname -a | grep «GNU/Hurd» > /dev/null; then echo «Вы работаете в Hurd»; else echo «Вы работаете не в Hurd»; fi
Само условие может быть любой сложности. Попробуем, например, проверить, запущен ли Firefox, выполнив ps aux и перенаправив вывод на grep для поиска процесса firefox.
Однако, grep сам является программой, а значит, появится в выводе ps. И поскольку строка «firefox» содержится в «grep firefox», то окажется, что Firefox якобы запущен, хотя на самом деле мы всего лишь запустили поиск такой строки. Чтобы обойти эту проблему, применим grep дважды: сперва для проверки наличия Firefox, а затем, с ключом -v, для инвертирования условия, чтобы исключить из результата строку с grep. Итак:
if ps aux | grep firefox | grep -v grep > /dev/null; then echo «Firefox запущен»; fi
Совершенно неудобоваримо, так что заготовим псевдоним...
alias isff=’if ps aux | grep firefox | grep -v grep > /dev/null; then echo «Firefox запущен»; fi’
Теперь, чтобы узнать, запущен ли ваш любимый браузер, достаточно выполнить команду isff.
- Зацикливаем циклы
Условные операторы превосходны для основных задач, но истинная мощь Bash заключается в циклах – в них оператор неоднократно повторяется, обрабатывая новые данные. Иногда это просто выполнение команды несколько раз, например:
while (true); do sleep 1; date; done
Эта команда ежесекундно выводит на экран дату и время, пока не нажмут Ctrl+C. Но вам, скорее всего, захочется пройтись циклом по строкам файла или файлам в каталоге и что-нибудь с ними сделать.
Как, например, распаковать несколько файлов tar.bz2 одной командой? Новички вообразят, что можно скомандовать
tar xjf *.tar.bz2
Но при попытке это сделать возникает сообщение об ошибке: «tar: foo.tar.bz2: Not found in archive (не найден в архиве)». Дело в том, что Bash разворачивает регулярное выражение *.tar.bz2 в список файлов каталога, фактически превращая введённую команду в такую:
tar xjf bar.tar.bz2 baz.tar.bz2 foo.tar.bz2
Когда вы передаёте утилите tar несколько файлов, первый из них рассматривается как имя архива, и tar попытается извлечь оттуда перечисленные далее файлы. Приведённая выше команда читается так: «извлечь baz.tar.bz2 и foo.tar.bz2 из bar.tar.bz2».
Значительно лучшее решение – использовать циклы: воспользуй тесь командой ls, чтобы получить список bz2-файлов в каталоге, и пройдитесь по ним в цикле, распаковывая каждый по отдельности. Итак:
for i in `ls *.tar.bz2`; do tar xjf «$i»; done
Здесь используется оператор «`» (обратный апостроф, который обычно расположен на клавиатуре слева от цифры 1), он выполняет ls *.tar.bz2 и вставляет её результат в команду на соответствующее место. Вы можете заставить Bash читать данные из файла, используя cat, например, так:
ls *.tar.bz2 > bzip_files for i in `cat bzip_files`; do tar xjf «$i»; done
Шаг 2 — Могучие команды Unix
Вторая часть нашего урока посвящена тому, как выжать всё из команд, которыми вы пользуетесь ежедневно – или, по крайней мере, должны бы пользоваться. Все команды Unix очень хорошо выполняют какую-то одну простую задачу, но чтобы предоставить опытным пользователям (вроде вас – по крайней мере, такими вы должны стать после наших уроков) максимальную гибкость, эти команды имеют множество параметров, чтобы изменять их поведение.
- «Меньше» значит «больше»
Рассмотрим команду less. Вероятно, вы используете её так:
cat /etc/somefile | less
Она выводит на экран файл и позволяет вам перемещаться по нему с помощью стрелок курсора. Пользователи поумнее (это мы) вместо этого употребляют команду
less /etc/somefile
Эффект будет тот же. А если я скажу вам, что у less множество параметров, изменяющих ее работу? На них прямо-таки нехватает букв алфавита, а некоторые даже чувствительны к регистру символов! И это только параметры, которые вы передаёте в программу – а ведь после запуска less ею можно управлять с помощью различных комбинаций клавиш.
Сильно ли вас бесит сообщение об ошибке, говорящее, что в файле somefile.txt есть проблема в строке 780? Не все так плохо: вспомните, что команда less с параметром -N (заметьте: не -n) распечатает номера строк, и вы узнаете, в чем дело. А чтобы получить больше информации, можете попробовать ключ -M – в строке статуса будут выведены имя файла, диапазон строк и текущая позиция в процентах.
Можно передать less несколько имён файлов, и они будут открыты все за одну сессию. Например:
less /etc/passwd /mnt/backup/etc/passwd
Когда less запустится, в её буфер будет загружен /etc/passwd, и в строке статуса появится сообщение «Файл 1 из 2». Для перемещения к следующему файлу (/mnt/backup/etc/passwd) используйте :n, а чтобы вернуться назад к первому – :p. Открыть следующий файл, сохраняя уже открытые два, можно взять :e и ввести имя файла, используя Tab для автодополнения, если потребуется. Чтобы закрыть текущий файл и убрать его из буфера less, пригодится :d.
Наконец, мощная клавиша «!». Если вы наберёте ! с последующей командой, которую нужно выполнить, less запустит эту команду, покажет вам её вывод и вернётся к просмотру файлов. Бесполезное вроде занятие; но вспомните, что текущий файл обозначается «%». Допустим, вы просматриваете в less файл /home/paul/somefile.txt и сообразили, что хотели включить в него список файлов из каталоге /etc. Сделать это можно прямо из less:
!ls /etc >> %
Перенаправление >> припишет вывод команды ls к концу файла. Когда вы вернётесь в less, её буфер будет обновлён, чтобы показать результат программы, и вы можете продолжить чтение.
- top-парад
Команда top – одна из тех, которые новички осваивают в первую очередь, поскольку это простейший способ узнать, какая программа сжирает все процессорное время в вашей системе. Но поначалу top может напугать: уйма данных вверху, далее 12 или больше столбцов информации, напичканной акронимами...
Столбцы, которые нам интересны – PID (идентификатор запущенного процесса), User (пользователь, запустивший процесс), NI (значение niceness, показывающее, с какой лёгкостью процесс отдаёт свои ресурсы) и сама команда. Остальные значения можно либо игнорировать, либо просто удалить из списка отображаемых полей. Для этого нажмите клавишу F, и вы увидите список всех отображаемых полей, вместе с клавишей, которую следует нажать для отключения поля. Например, «* N: %MEM =Memory usage (RES)» означает, что %MEM сейчас отображается (помечено звёздочкой), а нажатие n исключит это поле из списка. Выбрав нужные поля, нажмите Enter – и вернетесь к основному экрану.
Если вы нажмёте F (заметьте, что буква на сей раз заглавная), вы увидите примерно такой же список, но теперь сможете выбрать, какое поле будет использоваться для сортировки. Для пробы нажмите F (чтобы попасть на экран сортировки), a (выбор сортировки по PID), Enter (возврат в основной экран) и затем R (сортировка в обратном порядке – первыми отображаются PID с наименьшим значением).
top умеет не только показывать цифры: это мощнейший инструмент администрирования. Например, нажмите k и введите PID процесса, который нужно завершить (по умолчанию используется сигнал 15, который вежливо просит программу прекратить работу; в случае неудачи сигнал 9, так сказать, «вырубить питание»). Можно также нажать <r>, указать PID процесса и изменить его значение nice, и вашей системе гарантирован более высокий приоритет. Здесь есть одна хитрость – чем ниже значение nice, тем выше приоритет, самое низшее значение – 20, наивысшее – минус 19. Будьте внимательны при установке значений nice: повышать приоритеты разрешено только от имени суперпользователя, и любое значение ниже нуля требует особой осторожности.
- Грызем grep
Держу пари, что я смогу по пальцам сосчитать людей, которые регулярно используют grep в ситуациях, отличных от этих двух:
somecommand | grep «foo»
или
grep «foo» *
Увы, при своей-то чудовищной мощности, grep обычно прикован к дебильным задачам, едва отвлекающим процессор от спячки. Grep тоже имеет столько параметров, что и не упомнишь, но некоторые всё же следует выучить:
• -c Подсчитывает число вхождений искомой строки.
• -i Поиск, не зависящий от регистра символов.
• -l Выводит на экран имена совпавших файлов (это строчная L).
• -n Отображает номер соответствующей запросу строки.
• -r Выполняет рекурсивный поиск по каталогам.
• -v Инвертирует условие поиска (строки, не содержащие цель поиска).
Их можно объединять, перенаправив grep на самого себя. Например, если нужно подсчитать число файлов, которые содержат слово «paul» (или «PAUL», «PaUl» и т.д.), кроме тех, которые имеют расширение .txt, вам следует сделать что-то подобное:
grep -ilr paul * | grep -cv «\.txt$»
Здесь мы используем пять из шести важнейших параметров, превращая сложную задачу в простой конечный результат: число соответствующих условию файлов. В этом примере -ilr означает, что выполняется поиск по файлам слов Paul, PAUL, PaUl и т.д., поиск проходит рекурсивно по вашей файловой системе (начните с корневого каталога, чтобы выполнить поиск по всему диску) и возвращает имена подходящих файлов. Всё это поступает на вход другого экземпляра grep, который использует флаги -cv, включающие режим подсчёта и поиск файлов, которые не соответствуют регулярному выражению «\.txt$». Обратный слеш здесь экранирует точку: без него мы получили бы специальный символ. Знак доллара в конце означает, что .txt должно находиться в конце имени файла, то есть foo.txt.bar не будет соответствовать выражению.
Если вам предстоит прошлепать по огромному тексту, настоятельно рекомендую использовать дополнительный ключ --color, чтобы grep подсвечивал в выводе соответствующие выражения.
- Ищите и обрящете
Команда find печально знаменита своим коварством: никто не может правильно её использовать, не прочитав предварительно руководство. Впервые принимаясь за find, многие думают, что нужно попробовать нечто вроде find <иголка> <стог_сена>. Например, find myfile.txt /etc должна бы просматривать каталог /etc и его подкаталоги в поисках файла myfile.txt. Ха-ха! Когда я вижу новичков, набирающих подобное, я обычно хлопаю их по спине, говорю, что всё у них получится, и расхаживаю, невинно посвистывая.
Вместо того чтобы работать в соответствии со здравым смыслом, find работает как фильтр. Наиболее общая команда выглядит так:
find .
Первый параметр (путь, по которому выполняется поиск) – это «.», так что будет возвращён список всех файлов в текущем каталоге. Теперь сузим вывод при помощи параметров. Например, -name указывает, что find должна возвратить только файлы с указанным именем, скажем, myfile.txt или «*bar*», соответствующий файлам с «bar» где-нибудь в имени. Например:
find . -name «*bar*»
Мы могли бы добавить параметр -size, который ограничивает результаты поиска файлами, размер которых больше, меньше или равен заданному. Например:
find . -name «*bar*» -size +1M find . -name «*bar*» -size -10k
Первая команда найдёт все файлы с нужными именами, которые больше 1 МБ, а вторая – те, которые меньше 10 КБ. Файлы, размер которых точно равен заданному (например, 1 МБ), не будут возвращены, если поиск выполняется со строгим условием «больше» или «меньше».
Параметр -user возвращает только файлы, принадлежащие указанному пользователю. Например, -user paul вернёт файлы, принадлежащие пользователю paul. В частности, это полезно с параметром -not, который может предшествовать любому параметру и выполняет инвертирование значения. Вот несколько примеров:
# все файлы, не принадлежащие пользователю paul find . -name «*bar*» -not -user paul # все файлы, кроме myfile.txt и тех, которыми владеет paul find . -not -name «myfile.txt» -not -user paul # аналогично первому примеру, но с двойным отрицанием для прикола! find . -not -not -name «*bar*» -not -user paul
Ещё один небезынтересный фильтр – -newer, он возвращает все файлы, которые новее, чем указанный файл. Это очень удобно для скриптов резервного копирования: когда делаете копию, просто укажите произвольный файл, и он будет служить временной меткой, которую можно использовать в команде find -newer. Вы получите список всех файлов, которые изменились с момента создания этого файла. Вот нужная вам команда:
find . -newer /path/to/myfile
- Последние штрихи
Есть целая группа параметров find, которые мы не затронули: действия. Каждый раз, когда find наталкивается на файл, соответствующий вашим критериям, она может что-то с этим файлом проделать. Например, -ls выведет на экран информацию об этом файле в стиле ls -l, а параметром -exec заставит find запустить для этого файла определённую команду. Скажем, вы хотите найти все текстовые файлы в своём домашнем каталоге и вывести их на экран. Это можно сделать так:
find /home/someuser -name «*.txt» -exec cat {} \;
Фигурные скобки {} заменятся именем соответствующего файла, и при каждом совпадении будет выполняться cat. Конструкция \; в конце необходима, потому что find считает всё, что после -exec, выполняемой программой, пока не наткнется на точку с запятой. Но если вы просто наберете -exec cat {};, то Bash в процессе обработки строки эту точку с запятой удалит, и find пожалуется на ошибку.
Альтернативой -exec является -ok, который работает точно таким же образом, но запрашивает ввод пользователя перед выполнением каждой команды. Нажмите <y> для выполнения команды (опять-таки, для каждого соответствующего файла), или <n>, чтобы пропустить её.
К сожалению, на этот месяц больше места нам не досталось, и я сумел лишь обсудить Bash и четыре самых популярных команды Unix. Мы надеемся, что наступит день, когда вы полюбите командную строку с той же страстью, что и мы – или, по крайней мере, не так будете пугаться пролетающего во время загрузки текста.