+---------------------------+
|.-------------------------.|
|| kee_reel@blog:~/ru $ cd ||
|| ссылки контакты         ||
|| c c++ linux opengl sql  ||
|| python сети             ||
||                         ||
|.-------------------------.|
+-::---------------------::-+
.---------------------------.
 // /oooooooooooooooooooooo\\ \\ 
 // /oooooooooooooooooooooooo\\ \\ 
//-------------------------------\\
\\-------------------------------//


Linux. Продвинутое использование терминала

Время чтения: 12 минут

В этой статье я постарался показать различные приёмы, которые помогут поднять твой навык владения терминалом на новый уровень.

Что будет в этой статье:

Не бойся объёма – запомни только то, что захочешь. Главная цель этой статьи – дать тебе возможность взглянуть на продвинутые возможности терминала.

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

При работе с терминалом часто приходится редактировать уже написанные команды.

Чтобы изменить какое-то слово в команде, все новички зажимают стрелку вправо/влево, и ждут пока курсор до туда доползёт, чтобы потом зажать Delete или Backspace для удаления слова:

Так вот, забудь про зажимание стрелок на клавиатуре – каждый раз, когда ты это делаешь, у тебя отнимается 10 очков стиля.

Вместо стрелок, Delete и Backspace, используй следующие горячие клавиши:

  • Alt+F – сдвинуться на слово вперёд (F - forward)
  • Alt+B – сдвинуться на слово назад (B - backward)
  • Ctrl+A – переместиться в начало строки (я запомнил как “AАААА…)
  • Ctrl+E – переместиться в конец строки (”…ЕЕЕЕЕ РОККК!")
  • Ctrl+W – удалить предыдущее слово

Вот тебе, для сравнения, то же самое редактирование команды, что и выше, но с помощью Alt+B, Alt+B, Ctrl+W, Ctrl+W:

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

echo 'this is example of some command'

Эти горячие клавиши впитаются в подкорку только при условии постоянной практики, так что просто старайся с этого дня использовать их как можно чаще.

Перемещение по истории команд

Иногда тебе надо ещё раз исполнить команду, которую ты исполнял до этого – для этого в терминале существует история команд.

Для работы с историей команд тебе надо знать 3 основных комбинации:

  • Ctrl+P – предыдущая команда
  • Ctrl+N – следующая команда
  • Ctrl+R – поиск в истории команд (поиск идёт в направлении от новых команд к старым)

Вот тебе пример, как можно перемещаться взад/вперёд по истории с помощью Ctrl+P/Ctrl+N:

Обрати внимание что я перемещаюсь по словам через Alt+B и удаляю их через Ctrl+W

Вот пример поиска в истории команд – нажимаешь Ctrl+R, пишешь слово и оно появляется в строке. Ты можешь нажать Enter чтобы исполнить команду, а стрелочку чтобы начать редактировать выбранную команду:

Ещё можно искать определённое слово во всех подходящих командах – нажимаешь Ctrl+R, пишешь слово, нажимаешь Ctrl+R чтобы перейти на следующую подходящую команду (Enter чтобы исполнить команду):

Вся история команд хранится в файле ~/.bash_history – терминал берёт её оттуда.

Попробуй воспользоваться этими горячими клавишами прямо сейчас:

  • Пройдись туда-сюда с помощью Ctrl+P и Ctrl+N
  • Поищи какую-нибудь команду с помощью Ctrl+R
  • Понажимай Ctrl+R несколько раз, чтобы найти несколько подходящих команд

Да, для навигации по истории можно использовать стрелочки клавиатуры (вверх/вниз), но я не рекомендую привыкать к этому методу – чтобы нажать на стрелочку, тебе надо убрать руки с основной части клавиатуры, а это заметно снижает скорость работы. Стрелочки привычнее и легче для запоминания, но комбинации Ctrl+N и Ctl+P правда удобнее, если к ней привыкнуть.

Что такое Bash

Сейчас будет небольшое откровение – терминал в Linux это тоже программа, которая называется bash.

Bash расшифровывается как “Bourn Again Shell”, типо “Перерожденный Shell”. “Shell” (англ. “Оболочка”) – это одновременно и синоним слова “терминал”, и отслылка к более древнему терминалу “sh”.

Кроме Bash есть еще терминалы zsh, fish, sh.

Как ты мог уже понять, терминал передает твои команды операционной системе, однако он не передает их напрямую – он интерпретирует твою команду, и делает соответствующий запрос в операционную систему (системный вызов).

Однако Bash это не просто программа, которая исполняет твои команды – это интерпретатор языка программирования Bash, который предоставляет следующие, вполне базовые для любого языка, возможности:

  • Переменные
  • Условия
  • Циклы
  • Массивы
  • Функции

Если ты не знаком с этими базовыми понятиями, то рекомендую сначала освоить какой-либо язык программирования (например Python)

Кроме этого, он еще предоставляет в некоторой степени уникальные возможности:

  • Сокращения (alias)
  • Конвейеры (pipe)
  • Перенаправление вывода

Если ты освоишь хотя бы базовые возможности Bash, то ты сможешь писать программы, способные автоматизировать любую задачу, которую ты мог бы решить вручную!

Полноценный разбор Bash я вынесу в отдельную статью, а здесь я опишу только самое основное.

Конфигурация .bashrc

Каждый раз, когда ты запускаешь Bash, он сначала исполняет файл ~/.bashrc, который как раз написан на языке Bash.

Все что ты пропишешь в этом файле, будет применено к новосозданной сессии терминала.

Скорее всего в твоём файле ~/.bashrc уже что-то есть – почти во всех дистрибутивах Linux .bashrc содержит набор полезных переменных/функций/команд.

Давай прикинем что такого можно там прописать.

Переменные

Переменная – это переменная с определённым значением, используемая в рамках текущей сессии.

Переменная задаётся так:

ИМЯ_ПЕРЕМЕННОЙ=ЗНАЧЕНИЕ_ПЕРЕМЕННОЙ

Например, в своём ~/.bashrc ты можешь задать переменную HISTSIZE, которая определяет максимальное количество команд, которое терминал будет помнить (при перемещении по истории команд):

HISTSIZE=10000

Если ты добавишь в свой ~/.bashrc эту строчку, то сессия терминала будет “помнить” 10000 последних команд.

Существует множество переменных, которыми ты можешь настроить поведение сессии терминала – я опишу несколько полезных.

  • PATH

Переменная PATH содержит пути (разделённые “:”), которые используются для поиска исполняемых программ.

Например, вот так в PATH можно добавить директорию ~/bin:

PATH="~/bin:$PATH"

Перед $PATH написан $, чтобы вставить значение самой переменной PATH – таким образом мы склеиваем “~/bin:” и текущее значение PATH. Ещё с помощью $ ты можешь вывести текущее значение переменной:

echo $PATH

Так вот, мы добавили директорию “~/bin” в PATH. Предположим, что в этой директории лежит программа “hack-the-planet”:

kee-reel@blog:~/bin$ ls
hack-the-planet

Обычно, если нужно исполнить программу из текущей директории, тебе надо написать “./”:

kee-reel@blog:~/bin$ ./hack-the-planet
HACKING FOLDER ~/bin
COMPLETE!

Но, если директория с этой программой находится в PATH, то ты можешь исполнить эту программу откуда угодно (писать “./” не надо):

kee-reel@blog:~/some/other/folder$ hack-the-planet
HACKING FOLDER ~/some/other/folder
COMPLETE!

Про PATH рассказал больше, чем про остальные, потому что это самая главная переменная окружения

  • HISTCONTROL

Не сохранять в истории дублирующиеся команды (если одна и та же команда исполняется несколько раз)

HISTCONTROL='ignoredups'
  • PS1

Можно изменить формат приглашения командной строки на более компактный:

PS1='\[\033[01;32m\]\W\[\033[01;32m\] \$\[\033[00m\] '

Тогда он будет не таким:

kee-reel@blog:~/some/folder$

А таким:

folder $

Можешь поискать в интернете другие примеры изменения переменной PS1 – в нее можно много всего засунуть.

Сокращения (alias)

Иногда пользователь терминала выполняет некоторые команды намного чаще других. Чтобы не прописывать их полностью или не искать их каждый раз в истории через Ctrl+R, можно создать alias.

Например, вот команда, которую я часто исполняю:

cd ~/some/other/folder/with/the-project

Чтобы не мучить клавиатуру, я могу прописать в ~/.bashrc alias:

alias cdpr='cd ~/some/other/folder/with/the-project'

После добавления чего-либо в ~/.bashrc необходимо перезагрузить терминал (~/.bashrc считывается на старте). Однако, можно схитрить, и заново считать все содержимое ~/.bashrc в текущей сессии терминала через такую команду: source ~/.bashrc

Теперь, чтобы перейти в нужную мне директорию, достаточно лишь исполнить команду:

cdpr

Мануал (man)

В начале знакомства с терминалом Linux возникают трудности с запоминанием всего этого множества команд и параметров, которые нужно в них передавать.

Однако, чтобы в этом разобраться, не обязательно каждый раз гуглить – нужно запомнить только одну команду man.

man (от слова manual, англ. иструкция к применению) – программа, отображающая документацию для указанной программы.

Например, ты хочешь узнать что еще такого может сделать rm – вызови man, и передай в параметрах rm:

folder $ man rm

Откроется файл документации, который ты можешь скроллить стрелочками (на одну строчку) и через PageDown/PageUp (на страницу). Закрыть этот файл можно нажатием буквы “q”.

Почитав документацию для “rm” я узнал, что если указать параметр “-i”, то я должен буду подтверждать удаление каждого файла.

Так как “rm” удаляет файл сразу, не помещая его в корзину, это довольно полезный параметр, если ты боишься удалить что-то лишнее. В “~/.bashrc” можно добавить такой alias:

alias rm='rm -i'

Таким образом, обычное поведение “rm” будет переопределено.

Дальше я покажу много новых команд – чтобы ознакомиться как с ними работать, ты можешь использовать man

Конвейер (pipe)

Многие люди считают терминал намного более удобным иструментом именно из-за возможности использовать ковейер – pipe.

Pipe (англ. труба) – это механизм ОС Linux, позволяющий передавать вывод одной программы во ввод другой.

Лучше объяснить это на примере.

Ты помнишь команду ls – она просто выводит содержимое текущей папки:

folder $ ls
file_10.jpg   file_13.jpg   file_14.jpg   file_15.html	file_15.jpg
file_16.html  file_17.html  file_19.html  file_1.txt	file_20.html
file_2.txt    file_3.txt    file_4.txt	  file_5.txt	file_6.cpp
file_7.c      file_8.h	    file_9.py	  folder_1	folder_10
folder_2      folder_3	    folder_4	  folder_5	folder_6
folder_7      folder_8	    folder_9

Предположим, что ты хочешь получить список файлов с расширением “.jpg” – можно, конечно искать их в этой мешанине файлов, а можно использовать программу grep.

grep

grep – программа, которая ищет определенный текст во входном потоке или в файле.

Эта программа очень часто используется чтобы отфильтровать вывод другой программы – давай отфильтруем вывод ls:

folder $ ls | grep jpg
file_10.jpg   file_13.jpg   file_14.jpg file_15.jpg

Как ты видишь, вывелись только имена файлов, содержащие расширение “.jpg”.

sed

sed – программа, которая производит замену одного текста на другой по заданному правилу.

Эта программа часто используется чтобы массово изменить какие-то наименования – давай изменим названия всех входных файлов:

folder $ ls | grep jpg | sed 's/file/new_file_name/'
new_file_name_10.jpg   new_file_name_13.jpg   new_file_name_14.jpg	new_file_name_15.jpg

tr

tr – программа, которая производит замену заданного символа на другой.

Используется чтобы изменить формат наименований или избавиться от лишних символов – давай будем использовать “-” вместо “_”:

folder $ ls | grep jpg | sed 's/file/new_file_name/' | tr '_' '-'
new-file-name-10.jpg   new-file-name-13.jpg   new-file-name-14.jpg	new-file-name-15.jpg

cat

cat – программа, выводящая содержимое файла.

Очень часто используется для передачи содержимого файла в другие программы через pipe (конвейер).

Давай соберем новый конвейер, чтобы он работал с содержимым файла. Для начала, я создам файл с “контактами” каких-то людей через редактор nano (описывал как с ним работать в первой статье):

folder $ nano contacts.txt

С помощью cat я могу вывести содержимое этого файла:

folder $ cat contacts.txt
Ivan +123456 Omsk
Mary +234561 Moscow
Lena +345612 Saint-Petersburg
Gera +456123 Kazan
Nick +561234 Saint-Petersburg
Alex +612345 Moscow

Ну, а теперь давай выведем все московские контакты:

folder $ cat contacts.txt | grep Moscow
Alex +234561 Moscow
Mary +612345 Moscow

cut

cut – программа, вычленяющая из текстового потока определенные слова.

Давай с ее помощью вытащим имена и телефоны людей из Москвы:

folder $ cat contacts.txt | grep Moscow | cut -d' ' -f 1,2
Mary +234561
Alex +612345

sort

sort – сортирует строки из входного потока.

Давай отсортируем их в алфавитном порядке:

folder $ cat contacts.txt | grep Moscow | cut -d' ' -f 1,2 | sort
Alex +612345
Mary +234561

Перенаправление потока

Ну и последняя фишка для настоящего X4K3R4 – перенаправление потоков вывода.

В Linux ты можешь перенаправить вывод любой программы в файл – например, давай выведем контакты москвичей из предыдущего примера в файл:

folder $ cat contacts.txt | grep Moscow | cut -d' ' -f 1,2 | sort > moscow_contacts.txt

Заметь, что в терминал ничего не вывелось – весь вывод ушел в файл “moscow_contacts.txt”.

Можно проверить что записалось в файл:

folder $ cat moscow_contacts.txt
Alex +612345
Mary +234561

В общем это реально просто, нужно только добавить > в конец команды.

Иногда, вместо > можно еще увидеть >> – в чем разница?

  • > – заполняет файл текстом из потока (если был – перезапишет, если не было – создаст)
  • >> – дописывает в конец файла текст из потока (если был – допишет, если не было – создаст)

Внимательно следи за > и >> – у меня бывали случаи, когда я хотел дописать что-то в конец файла, но перезаписывал его. По умолчанию лучше используй >> – так, ты избежишь подобных ситуаций.

Вот отличный пример использования >>:

echo "alias rm='rm -i'" >> ~/.bashrc

Дописываем в конец “~/.bashrc” новый alias, вместо того чтобы лезть в файл через текстовый редактор.

Итоги

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

Давай закрепим:

Я не ожидаю, что после прочтения этой статьи ты вдруг начнёшь всё это использовать, а скорее надеюсь, что ты увидишь горизонт знаний, который можно освоить, и примешь для себя решение – хочешь ли ты следовать за белым кроликом?

~ $ wget https://s3.amazonaws.com/vspodtools-images-display/12676318/12682544-5841-b-display.jpg -O rabbit.png
~ $ sudo apt install -y jp2a
~ $ jp2a rabbit.png
.......;,,,,,,,,,;'  .',;,,,,,,..  ,;.           ,,.           .',,,,,,,,'.  .;'      .;;.     .
.......:;'......... .;,'......;;,  ;;'          .;,'           ,;,......',,. ,,'      .;;.     .
.......:;....       .;;.      ,,,  ;;'          .,,'           ;;,      .;;. ,;,      .::.     .
.......:;'.......   .;,.      ,,,  ,;'          .;,'           ;;,      .,;. ,;,  .'. .;:.   ...
.......:,,,'',,,.   .;;.      ,,,  ,,.          .;,'           ,;,      .,;. ,,, .;;, .;:.  ....
.......:;.          .;;.      ,,,  ,;'          .;,'           ,;,      .;;. ,,, .;;, .;:.   ...
.......::.          .;,.......;,,  ,;'........  .;,'........   ,,,......',;. ,;,..;,,..,:.   ...
.......cc.           .,;;;;;;;;,.  ;,;;;;;;;;:, .;,,;;;,;,;;,  .,;;;;;;;;;.  .,;;;;,;;;;.   .
...... ..      .'.    .........    ............  ............    .........     .... ....
..           .::dOl.        '''''''''''.  ',.      .,'  ''''''''''''
.. ..         .lkXxk,       .'''',,'.''. .;;'      ',:. ;,'...'.'''.
..  .           .,:kko'         .;:.     .;;'      ',;. ;,,
..               .'xO00.        .;:.     .;,'......',;. ;,,.......
               .lkkK0K'         .;;.     .;',;;;;;;'';. ;',;;;;;:'
              ,OKXk00k.         .;;.     .;;'......',;. ;,'......
              c0KKO0do.         .;;.     .;;'      ',;. ;,'
              :OKXkd.           .;:.     .:;'      ';;. ;,,''''''','
               .,::o,           ...       .'.      ...  ............
              ..       ...  ..       ...    ........    ............  ............
             .:;.      ;;,  ;:.      ,;;    .,',,',.    ';,,,,,,,,;,  ,,,',,',,,,,
             .:;.      ;,,  ;;.      ,;,      .;;.          .;;.      ,,,
             .;;.      ;,, .;;.      ,;,      .;;.          .;;.      ,,,
             .:;. .;,. ,,,  ;,,,;;,,,,,,      .;;.          .:;.      ,,',,,,;;'
             .;;. ',;. ;,'  ;;'......,;;      .;;.          .:;.      ,,,.......
             .:;. ',;. ;,'  ;;.      ,;,      .;;.          .:;.      ,,,
     .       .;,'.,,,..;;.  ;;.      ,;,    ..',,'..        .:;.      ,;,.........
     .        ..'''..'''.   ',.      .,'    .,,''',.        .,,.      .,'''''''',,
    .. .........       .......     ..........    ..........       ......      ..........
    ...c;:;;;:;;,'.  .,;;:;;;;;,.  ;;;;;;;;;;,.  ;;;::;:;;;,.    .c;,,;:,    ':;;;,,,;;;:.
   .. .:;.......,,' .;;'......,,,  ,;'......,,;  ;,'......',,     ..;;..      ....;,'...
   .. .:;.      ,,, .;;.      ,,,  ,;.      ',;  ;,'      .;,      .;;.           ;;'
   .  .:,,''''''',. .;,''''''',,,  ,,,'''''',,'  ;''''.'''','      .;;.           ;;'
  ..  .:;,'''..',;. .;,''.....,,,  ,,'.....',,'  ;''.'.'..,;'      .;;.           ;;'
  ..  .;:.      ,,, .;;.      ,,,  ,;.      ',;  ;,'      .;,      .:;.           ;,.
 ...  .;;.      ,,, .;;.      ,,'  ,;'......',,  ;''......';,     ..;,..          ;;.
 ...  .;;.      ';'  ,;.      ';'  ,,,;,,;;;,'.  ,,,;;,;,,,;.    .:,,,,;,         ,;.

Если что – пиши, я помогу и постараюсь объяснить лучше.