вторник, 27 декабря 2011 г.

липкий смит

Часто спрашивают есть ли какой-то список fastpath'ов для SMIT'а. Приходится пожимать плечами и отсылать к гуглу.
Вот загуглил сам в кои то веки.

Список, ясное дело, неполный. Но у вас всегда остается кнопка F8 как средство узнать fastpath диалога, в котором вы находитесь.

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

Огромное количество людей пользуется интерпретатором bash. Чуть меньше людей знают про существование bash_completion (спасибо, Дмитрий). Собственно вот и задача: заставить bash дополнять команду smit необходимым fastpath'ом. Например так:

bash#: smit ls[TAB]

lsattr    lsfs      lslv      lsmntdsk  lsrole    lsvg      lsvg2
lsbackvg  lsgroup   lsmksysb  lspv      lsuser    lsvg1     
bash#: smit ls

или

bash#:  smit ins[TAB]
bash#:  smit install[TAB][TAB]
install            install_bundle     install_update     
install_all        install_latest     installed_license 

Итак, нам понадобится bash (я беру его здесь) и bash_completion (дают тут).

Предположим, мы скачали bash-4.2-5.aix5.1.ppc.rpm и положили в /tmp нашего AIX.
Поставим его:

ksh#:  rpm -ihv /tmp/bash-4*
bash                        ##################################################
ksh#:

Здесь же, в /tmp, у нас лежит bash-completion-1.3.tar.bz2.
Из всего архива нам понадобится только скрипт bash_completion

ksh#: cd /tmp
ksh#: bunzip2 bash-completion-1.3.tar.bz2
ksh#: tar -xvf bash-completion-1.3.tar
ksh#: cp /tmp/bash-completion-1.3/bash_completion /etc

Вот и вся установка. Или почти вся - еще надо заставить скрипт bash_completion запускаться при старте bash. README в нашем /tmp/bash-completion-1.3 говорит:


INSTALLATION

------------

The easiest way to install this software is to use a package; it is available

in many operating system distributions.  The package's name is usually

bash-completion.  Depending on the package, you may still need to source it

from either /etc/bashrc or ~/.bashrc (or any other file sourcing those). You

can do this by simply using:

# Use bash-completion, if available
if [ -f /etc/bash_completion ]; then
  . /etc/bash_completion
fi

Звучит логично - ведь при старте bash выполняется .bashrc. То есть наша задача положить строки 

if [ -f /etc/bash_completion ]; then
  . /etc/bash_completion
fi

в файл .bashrc в домашнем каталоге нужного пользователя (у нас это как обычно root =).
Обратите внимание на пробел между "." и "/etc/bash_completion" - он есть!

Вы можете проверить исполнение скрипта при старте bash просто запустив команду set до и после старта bash. Во втором случае set будет выдавать много функций типа:

quote_readline () 
    local quoted;
    _quote_readline_by_ref "$1" ret;
    printf %s "$ret"
}

Если bash при старте не выдал ошибок и set показывает новые переменные и функции, то bash_completion успешно проинициализировался. Ура!  Если нет - не ура - пишите, разберемся.

Официальный мануал по bash в разделе

8.6 Programmable Completion


рассказывает что при запуске bash_completion выполняется все что лежит в каталоге /etc/bash_completion.d/

Это так называемые COMPSPEC'и - или функции, создающие completion-списки для разных программ. Ксати, когда мы расTARили bash-completion-1.3.tar в /tmp/bash-completion-1.3 появился каталог completions с COMPSPEC'ами для разных утилит - нужные вам можно задействовать скопировав их в /etc/bash_completion.d/



Нам же нужно написать свой COMPSPEC для smit. Но перед этим выполним некоторые подготовительные шаги:



bash#: mkdir /etc/bash_completion.d

bash#: mkdir /etc/bash_completion.d/smit

Качаем файл smit_fastpaths (в нем список fastpath'ов в одну строку, разделенных пробелами), и помещаем его в /etc/bash_completion.d/smit. Напомню, что все в каталоге /etc/bash_completion.d будет исполняться, и, поместив файл с fastpath'ами в подкаталог,  мы защитили его от этого. Вы можете дополнять этот файл своими fastpath'ами.

Далее пишем собственно COMPSPEC и кладем его в /etc/bash_completion.d:
(название любое, право на исполнение не требуется)

bash#: cat /etc/bash_completion.d/smit.sh
_smit()
{
        local args
        args=$(cat /etc/bash_completion.d/smit/smit_fastpaths)
        COMPREPLY=( $(compgen -W "${args}" "${COMP_WORDS[COMP_CWORD]}") )
}
complete -F _smit smit 
bash#:

Думаю нужны некоторые пояснения.
Согласно Bash-Variables:

COMPREPLY
An array variable from which Bash reads the possible completions generated by a shell function invoked by the programmable completion facility
То есть сюда генерируется список дополнений. Массив.

COMP_WORDS
An array variable consisting of the individual words in the current command line. The line is split into words as Readline would split it, using COMP_WORDBREAKS as described above. This variable is available only in shell functions invoked by the programmable completion facilities
А тут уже введенная пользователем строка из массива слов.



COMP_CWORD
An index into ${COMP_WORDS} of the word containing the current cursor position. This variable is available only in shell functions invoked by the programmable completion facilities
Номер слова в COMP_WORDS, на котором стоит курсор в командной строке.


complete

          complete [-abcdefgjksuv] [-o comp-option] [-DE] [-A action] [-G globpat] [-W wordlist]
          [-F function] [-C command] [-X filterpat]
          [-P prefix] [-S suffix] name [name ...]
          complete -pr [-DE] [name ...]

Specify how arguments to each name should be completed. Собственно дополняет введенную команду одним из способов. У нас name - это smit, а способ дополнения - функция _smit().



compgen

          compgen [option] [word]
Generate possible completion matches for word according to the options, which may be any option accepted by the complete builtin with the exception of -p and -r, and write the matches to the standard output. Генерирует список дополнений. Ключи те же. Мы используем -W с указанием всего списка вариантов дополнения из файла smit_fastpaths.

Кажется все! Осталось перезапустить shell.


Примерно таким же макаром вы теперь можете дополнять любые команды.
Искушенный читатель может сказать, что нам вовсе не нужен скрипт bash_completion из TAR архива. И будет прав! По сути, все, что приносит нам этот скрипт - это функции для более качественного разбора командной строки, ну и еще несколько мелочей (не поленитесь, загляните в него). Кроме того, это уже написанные COMPSPEC'и для целой кучи команд. То есть мы с вами рассмотрели как добавить функционал дополнения smit в общем случае (кстати, файл smit_fastpaths читатся каждый раз при нажатии [TAB], а значит его можно менять не перезапуская bash).
Если вы решили не пользоваться благами цивилизации в виде bash_completion, то можете просто написать в $HOME/.bashrc что-то вроде:


list=$(cat /home/smit_fastpaths)
complete -W "$list" smit


Это, безусловно, очень статичный метод, но вполне рабочий (не проверял =)


P.S. Напрашиваются дополнения к командам в VIOS'е. Если вам интересно - пишите, попробуем реализовать.


Комментариев нет:

Отправить комментарий