< Bash (Русский)

Bash (Русский)/Prompt customization (Русский)

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

Состояние перевода: На этой странице представлен перевод статьи Bash/Prompt customization. Дата последней синхронизации: 10 июля 2021. Вы можете помочь синхронизировать перевод, если в английской версии произошли изменения.

Приглашения

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

  • PS1 — основное приглашение, которое отображается перед каждой командой; по этой причине модифицируется чаще всего.
  • PS2 — второе приглашение, отображается, если команде требуются дополнительные данные для ввода (например, в случае многострочных команд).
  • PS3 — используется довольно редко. Отображается при работе встроенной команды Bash select, выводящей интерактивное меню. В отличие от остальных приглашений, не раскрывает escape-последовательности Bash. Обычно все изменения применяются непосредственно в скрипте, содержащем select, а не в файле .bashrc.
  • — также используется редко. При отладке скриптов показывает уровни вложенности — первый символ приглашения повторяется столько раз, сколько на данный момент задействовано уровней.

Настройка конкретного приглашения подразумевает присваивание (обычно в файле ) необходимой строки в переменную, например:

PS2='> '

Техники

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

Escape-последовательности Bash

При выводе строки приглашения Bash ищет экранированные символом слэша символы (escape-последовательности) и конвертирует их в специальные строки. Например, превратится в имя пользователя, а — в текущее время. Таким образом, если переменной PS1 присвоить '\A \u $ ', то приглашение будет выглядеть как 17:35 пользователь $ .

Полный список escape-последовательностей можно найти в руководстве и в справочнике Bash.

Escape-последовательности terminfo

Помимо escape-последовательностей, которые понимает Bash, большинство терминалов также распознают специальные последовательности, которые влияют на терминал сам по себе, а не на печатаемые символы. Например, так можно изменить цвет строки символов, сдвинуть курсор в произвольную позицию или очистить экран. Эти последовательности могут быть довольно неудобными и варьируются от терминала к терминалу, поэтому они задокументированы в базе данных terminfo. Чтобы увидеть, какие свойства поддерживает ваш терминал, выполните:

$ infocmp

Значение свойств можно найти в по их названиям (часть перед =). Например, свойство настраивает цвет шрифта для всего текста, который будет напечатан после него. Узнать escape-код свойства можно командой . Например,

$ tput setaf 2

выведет escape-последовательности для настройки зелёного цвета шрифта.

На практике, чтобы использовать эти возможности в приглашении командной строки, можно использовать подстановку команд Bash и интерполяцию строк. Например:

my prompt>

Escape-последовательности ANSI

К сожалению, ANSI-последовательности могут отсутствовать в базе terminfo вашего терминала. Чаще всего это касается последовательностей для новейших возможностей вроде поддержки 256 цветов. В этом случае использовать tput не получится и придётся вводить escape-последовательности вручную.

Примеры escape-последовательностей можно найти в статье Управляющие последовательности ANSI. Каждая последовательность начинается с литерала escape-последовательности, которую вы можете ввести с помощью escape-последовательности Bash . Например, задаст персиковый цвет фона (если есть поддержка 256 цветов), а \e[2;2H сдвинет курсор в левый верхний угол экрана.

В случаях, когда escape-последовательности Bash не поддерживаются (как в приглашении PS3), их можно добавить командой printf:

ESC=$(printf "\e")
PEACH="$ESC[48;5;209m"

Встроенные команды

Если вы хотите добавить вывод какой-нибудь команды в приглашение, то используйте подстановку команд (command substitution). Например, чтобы добавить величину свободной памяти к приглашению попробуйте что-то вроде:

Как видно, это работает не совсем корректно — значение памяти всегда одно и то же! Причина — команда выполняется только один раз при первой настройке PS1. Необходимо предотвратить подстановку либо экранированием символа , либо определением строки в одиночных кавычках — в обоих случаях подстановка будет производиться каждый раз при настоящем отображении приглашения:

PS1="\$(awk '/MemFree/{print \$2}' /proc/meminfo) prompt > "
# или
PS1='$(awk "/MemFree/{print \$2}" /proc/meminfo) prompt > '

Если команды сделали приглашение слишком длинным, для лучшей читабельности можно вынести их в функцию:

PROMPT_COMMAND

Переменной PROMPT_COMMAND можно присвоить произвольную команду, которая будет выполняться непосредственно перед выводом PS1. Это позволяет создавать довольно мощные эффекты. Например, можно переназначить PS1 на основе некоторых условий, или выполнить какие-то действия с историей Bash при выполнении любой команды.

Escape-последовательности между вводом и выводом

Свойства вводимого текста можно изменить, "забыв" отключить свойства в конце PS1. Например, если вставить в конец PS1, то вводимые команды будут мерцать. Тем не менее, этот эффект также перейдёт и на вывод команды, поскольку свойства не отключаются при нажатии .

Чтобы вставить escape-последовательность после ввода, но перед началом вывода, можно перехватить (trap) Bash-сигнал DEBUG, который посылается перед выполнением каждой команды:

$ trap 'tput sgr0' DEBUG

Настройка приглашения root

Для удобства можно сделать приглашение командной строки root-пользователя визуально отличным от обычного (возможно, мерцающий красный цвет?). Настройка приглашения производится как обычно, но в домашнем каталоге суперпользователя, . Начните с копирования шаблонов /etc/skel/.bash_profile и в каталог , после чего внесите в файл необходимые изменения.

Примеры

Цвета

Увидеть все цвета вашего терминала можно с помощью простого цикла (замените на , если нужен цвет текста, а не фона):

Если это не работает (причём установлено правильное значение TERM), протестируйте вручную разные последовательности:

Аналогичные значения для текста (не фона): стандартные — 30..37, высокая интенсивность — , а для 256 цветов замените 48 на 38.

Основные свойства

Следующие свойства terminfo будут полезны при настройке приглашения и поддерживаются во многих терминалах. #1 и #2 необходимо заменить на числовые аргументы.

СвойствоEscape-последовательностьОписание
Свойства текста
blink\E[5mмерцающий тект вкл
bold\E[1mполужирный текст вкл
dim\E[2mтусклый текст вкл
rev\E[7mобратное отображение вкл (текст/фон меняются цветами)
sitm\E[3mкурсив вкл
ritm\E[23mкурсив выкл
smso\E[7mвыделение текста вкл
rmso\E[27mвыделение текста выкл
smul\E[4mподчёркивание вкл
rmul\E[24mподчёркивание выкл
setab #1\E[4#1mзадать цвет фона #1 (0-7)
setaf #1\E[3#1mзадать цвет текста #1 (0-7)
sgr0\E(B\E[mотключить все атрибуты текста
Перемещение курсора
sc\E7сохранить позицию курсора
rc\E8вернуть курсор в сохранённую позицию
clear\E[H\E[2Jочистить экран и переместить курсор в левый верхний угол
cuu #1\E[#1Aпереместить курсор вверх на #1 строк
cud #1\E[#1Bпереместить курсор вниз #1 строк
cuf #1\E[#1Cпереместить курсор вправо #1 столбцов
cub #1\E[#1Dпереместить курсор влево #1 столбцов
home\E[Hпереместить курсор в левый верхний угол окна
hpa #1\E[#1Gпереместить курсор в столбец #1
vpa #1\E[#1dпереместить курсор в строку #1, первый столбец
cup #1 #2\E[#1;#2Hпереместить курсор в строку #1, столбец #2
Удаление символов
dch #1\E#1Pудалить #1 символов (аналогично нажатию клавиши backspace)
dl #1\E#1Mудалить #1 строк
ech #1\E#1Xстереть #1 символов (без перемещения курсора)
ed\E[Jочистить до нижнего края экрана
el\E[Kочистить до конца строки
el1\E[1Kочистить до начала строки

Отображение кода выхода

Тем же приёмом, как в случае встроенных команд, можно отложить интерполяцию специальной переменной Bash вроде . Следующие приглашения будут содержать код выхода предыдущей команды:

PS1="\$? > "
# или
PS1='$? > '
0 > true
0 > false
1 >

Это можно сделать с помощью условных выражений и функций:

exitstatus()
{
    if [[ $? == 0 ]]; then
        echo ':)'
    else
        echo 'D:'
    fi
}
PS1='$(exitstatus) > '
:) > true
:) > false
D: >

Позиционирование курсора

Курсор можно перемещать по экрану во время нахождения "внутри" приглашения PS1, чтобы разные части приглашения появлялись в разных местах. Важный момент — после всех перемещений и вывода символов в любых местах экрана курсор необходимо вернуть в исходную позицию. Это можно сделать с помощью свойств и , которые сохраняют и восстанавливают позицию курсора соответственно. Общая схема приглашения, содержащего перемещения курсора:

PS1="\[$(tput sc; перемещение курсора) работа с курсором $(tput rc)\] работа с курсором после возврата"

Весь блок с перемещениями курсора обёрнут в , чтобы Bash не учитывал непечатаемые символы как часть приглашения.

Выравнивание по правому краю

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

left prompt > right prompt

Здесь задано поле переменной длины с выравниванием по правому краю. Размер поля равен текущему количеству столбцов в терминале ().

Произвольное позиционирование

Свойство cup перемещает курсор в конкретную позицию экрана, например, переместит курсор на строку 20, столбец 5 (координаты 0 0 обозначают верхний левый угол). , cud, и (вверх, вниз, вперёд, назад) перемещают курсор относительно текущей позиции. Например, переместит курсор на 10 символов вправо. В аргументах можно использовать переменные и , если требуется переместить курсор относительно нижнего и правого краёв окна. Например, перемещение на 10 строк и 5 столбцов от правого нижнего угла:

$ tput cup $((LINES - 11)) $((COLUMNS - 6))

Настройка названия окна терминала

Название окна терминала можно настроить так же, как и приглашение: выводом escape-последовательностей в оболочке. Часто пользователи встраивают настройки названия окна в своё приглашение. Технически это возможность xterm, но и другие современные терминалы её поддерживают. В этом случае используют последовательности , где ESC и — символы escape (выход) и bell (сигнал). С последовательностями Bash приглашение с встроенным названием окна будет иметь вид:

PS1='\[\e]2;новое название\a\]prompt > '

Само собой, строка названия окна может включать вывод встроенных команд или переменные вроде , так что она может перенастраиваться после каждой команды.

Смотрите также

gollark: Hmm, it says it's a normal disconnection. I'll have to reconnect it and monitor the log in real time.
gollark: Hold on while I check the logs.
gollark: ++radio connect
gollark: Oh dear, did it implode?
gollark: It actually streams at 128kbps into our 64kbps voice chat via [BEES SIMULTANEOUSLY DELETED AND EXPUNGED, BUT THEN REDACTED, BUT THEN EXPUNGED, AND THEN UNEXPUNGED, UNDELETED AND UNREDACTED, ONLY TO BE REDACTED AGAIN].
This article is issued from Archlinux. The text is licensed under Creative Commons - Attribution - Sharealike. Additional terms may apply for the media files.